From c4e24cd2cd94720bf95be7144c117940b6618159 Mon Sep 17 00:00:00 2001 From: Rohit Singh <27754873+razein97@users.noreply.github.com> Date: Tue, 10 Feb 2026 10:43:06 +0530 Subject: [PATCH 01/95] detect arm systems in windows - Arm system were not detected when running signtool causing bundle failures when signing windows binaries --- .changes/windows_arm_signtool_detect.md | 15 +++++++++++++++ crates/tauri-bundler/src/bundle/windows/util.rs | 3 +++ 2 files changed, 18 insertions(+) create mode 100644 .changes/windows_arm_signtool_detect.md diff --git a/.changes/windows_arm_signtool_detect.md b/.changes/windows_arm_signtool_detect.md new file mode 100644 index 000000000000..889255763a88 --- /dev/null +++ b/.changes/windows_arm_signtool_detect.md @@ -0,0 +1,15 @@ +--- +"tauri-bundler": patch:enhance +--- + +Signtool path for windows arm systems was not being properly returned which caused failure in signing of windows binaries. + +This patch addresses it. + +Previously only the following were supported: +- PROCESSOR_ARCHITECTURE_INTEL +- PROCESSOR_ARCHITECTURE_AMD64 + +The following were added: +- PROCESSOR_ARCHITECTURE_ARM +- PROCESSOR_ARCHITECTURE_ARM64 \ No newline at end of file diff --git a/crates/tauri-bundler/src/bundle/windows/util.rs b/crates/tauri-bundler/src/bundle/windows/util.rs index 55cfea3a968f..60706976d0d5 100644 --- a/crates/tauri-bundler/src/bundle/windows/util.rs +++ b/crates/tauri-bundler/src/bundle/windows/util.rs @@ -67,6 +67,7 @@ pub fn download_webview2_offline_installer(base_path: &Path, arch: &str) -> crat pub fn os_bitness<'a>() -> Option<&'a str> { use windows_sys::Win32::System::SystemInformation::{ GetNativeSystemInfo, PROCESSOR_ARCHITECTURE_AMD64, PROCESSOR_ARCHITECTURE_INTEL, SYSTEM_INFO, + PROCESSOR_ARCHITECTURE_ARM, PROCESSOR_ARCHITECTURE_ARM64, }; let mut system_info: SYSTEM_INFO = unsafe { std::mem::zeroed() }; @@ -74,6 +75,8 @@ pub fn os_bitness<'a>() -> Option<&'a str> { match unsafe { system_info.Anonymous.Anonymous.wProcessorArchitecture } { PROCESSOR_ARCHITECTURE_INTEL => Some("x86"), PROCESSOR_ARCHITECTURE_AMD64 => Some("x64"), + PROCESSOR_ARCHITECTURE_ARM => Some("arm"), + PROCESSOR_ARCHITECTURE_ARM64 => Some("arm64"), _ => None, } } From 2a42b7327de00a3d325657260c2563ec03806ac9 Mon Sep 17 00:00:00 2001 From: Rohit Singh <27754873+razein97@users.noreply.github.com> Date: Fri, 6 Mar 2026 22:08:23 +0530 Subject: [PATCH 02/95] Add changelog for PR 14923 Add changelog for PR 14923 with patch updates and a fix for arm system detection in tauri-bundler. --- .changes/change-pr-14923.md | 18 ++++++++++++++++++ 1 file changed, 18 insertions(+) create mode 100644 .changes/change-pr-14923.md diff --git a/.changes/change-pr-14923.md b/.changes/change-pr-14923.md new file mode 100644 index 000000000000..d4ab557a9f78 --- /dev/null +++ b/.changes/change-pr-14923.md @@ -0,0 +1,18 @@ +--- +"@tauri-apps/api": patch +"tauri-utils": patch +"tauri-macos-sign": patch +"tauri-bundler": patch +"tauri-runtime": patch +"tauri-runtime-wry": patch +"tauri-codegen": patch +"tauri-macros": patch +"tauri-plugin": patch +"tauri-build": patch +"tauri": patch +"@tauri-apps/cli": patch +"tauri-cli": patch +"tauri-driver": patch +--- + +fix(windows): tauri-bundler detect arm system From a2fa49cacdccbce47d524799a16112d10a0efd7d Mon Sep 17 00:00:00 2001 From: Rohit Singh <27754873+razein97@users.noreply.github.com> Date: Thu, 30 Apr 2026 11:57:18 +0530 Subject: [PATCH 03/95] rename os_bitness to processor_architecture --- .changes/change-pr-14923.md | 18 ------------------ .../tauri-bundler/src/bundle/windows/sign.rs | 2 +- .../tauri-bundler/src/bundle/windows/util.rs | 6 +++--- 3 files changed, 4 insertions(+), 22 deletions(-) delete mode 100644 .changes/change-pr-14923.md diff --git a/.changes/change-pr-14923.md b/.changes/change-pr-14923.md deleted file mode 100644 index d4ab557a9f78..000000000000 --- a/.changes/change-pr-14923.md +++ /dev/null @@ -1,18 +0,0 @@ ---- -"@tauri-apps/api": patch -"tauri-utils": patch -"tauri-macos-sign": patch -"tauri-bundler": patch -"tauri-runtime": patch -"tauri-runtime-wry": patch -"tauri-codegen": patch -"tauri-macros": patch -"tauri-plugin": patch -"tauri-build": patch -"tauri": patch -"@tauri-apps/cli": patch -"tauri-cli": patch -"tauri-driver": patch ---- - -fix(windows): tauri-bundler detect arm system diff --git a/crates/tauri-bundler/src/bundle/windows/sign.rs b/crates/tauri-bundler/src/bundle/windows/sign.rs index f7c7ad1e2122..d9922f58ff69 100644 --- a/crates/tauri-bundler/src/bundle/windows/sign.rs +++ b/crates/tauri-bundler/src/bundle/windows/sign.rs @@ -97,7 +97,7 @@ fn signtool() -> Option { kit_bin_paths.push(kits_root_10_bin_path); // Choose which version of SignTool to use based on OS bitness - let arch_dir = util::os_bitness().ok_or(crate::Error::UnsupportedBitness)?; + let arch_dir = util::processor_architecture().ok_or(crate::Error::UnsupportedBitness)?; /* Iterate through all bin paths, checking for existence of a SignTool executable. */ for kit_bin_path in &kit_bin_paths { diff --git a/crates/tauri-bundler/src/bundle/windows/util.rs b/crates/tauri-bundler/src/bundle/windows/util.rs index 60706976d0d5..e716ad7bbef5 100644 --- a/crates/tauri-bundler/src/bundle/windows/util.rs +++ b/crates/tauri-bundler/src/bundle/windows/util.rs @@ -64,10 +64,10 @@ pub fn download_webview2_offline_installer(base_path: &Path, arch: &str) -> crat } #[cfg(target_os = "windows")] -pub fn os_bitness<'a>() -> Option<&'a str> { +pub fn processor_architecture<'a>() -> Option<&'a str> { use windows_sys::Win32::System::SystemInformation::{ - GetNativeSystemInfo, PROCESSOR_ARCHITECTURE_AMD64, PROCESSOR_ARCHITECTURE_INTEL, SYSTEM_INFO, - PROCESSOR_ARCHITECTURE_ARM, PROCESSOR_ARCHITECTURE_ARM64, + GetNativeSystemInfo, PROCESSOR_ARCHITECTURE_AMD64, PROCESSOR_ARCHITECTURE_ARM, + PROCESSOR_ARCHITECTURE_ARM64, PROCESSOR_ARCHITECTURE_INTEL, SYSTEM_INFO, }; let mut system_info: SYSTEM_INFO = unsafe { std::mem::zeroed() }; From 968107442b52d97b180c23c9ce339cc9e869adb8 Mon Sep 17 00:00:00 2001 From: Rohit Singh <27754873+razein97@users.noreply.github.com> Date: Thu, 30 Apr 2026 12:00:03 +0530 Subject: [PATCH 04/95] Update windows_arm_signtool_detect.md remove arm32 changes --- .changes/windows_arm_signtool_detect.md | 7 ++++--- 1 file changed, 4 insertions(+), 3 deletions(-) diff --git a/.changes/windows_arm_signtool_detect.md b/.changes/windows_arm_signtool_detect.md index 889255763a88..7d951e7f3dcb 100644 --- a/.changes/windows_arm_signtool_detect.md +++ b/.changes/windows_arm_signtool_detect.md @@ -7,9 +7,10 @@ Signtool path for windows arm systems was not being properly returned which caus This patch addresses it. Previously only the following were supported: + - PROCESSOR_ARCHITECTURE_INTEL - PROCESSOR_ARCHITECTURE_AMD64 -The following were added: -- PROCESSOR_ARCHITECTURE_ARM -- PROCESSOR_ARCHITECTURE_ARM64 \ No newline at end of file +The following were added: + +- PROCESSOR_ARCHITECTURE_ARM64 From b299866b49398042508f5a55bd7f95b39c9f37f9 Mon Sep 17 00:00:00 2001 From: Rohit Singh <27754873+razein97@users.noreply.github.com> Date: Thu, 30 Apr 2026 12:00:03 +0530 Subject: [PATCH 05/95] Update windows_arm_signtool_detect.md remove arm32 changes --- .changes/windows_arm_signtool_detect.md | 7 ++++--- 1 file changed, 4 insertions(+), 3 deletions(-) diff --git a/.changes/windows_arm_signtool_detect.md b/.changes/windows_arm_signtool_detect.md index 889255763a88..7d951e7f3dcb 100644 --- a/.changes/windows_arm_signtool_detect.md +++ b/.changes/windows_arm_signtool_detect.md @@ -7,9 +7,10 @@ Signtool path for windows arm systems was not being properly returned which caus This patch addresses it. Previously only the following were supported: + - PROCESSOR_ARCHITECTURE_INTEL - PROCESSOR_ARCHITECTURE_AMD64 -The following were added: -- PROCESSOR_ARCHITECTURE_ARM -- PROCESSOR_ARCHITECTURE_ARM64 \ No newline at end of file +The following were added: + +- PROCESSOR_ARCHITECTURE_ARM64 From db8dc15270e4657a7c1bc7f0e8de1879f618603f Mon Sep 17 00:00:00 2001 From: Lucas Fernandes Nogueira Date: Thu, 30 Apr 2026 07:13:11 -0300 Subject: [PATCH 06/95] update change file --- .changes/windows_arm_signtool_detect.md | 1 + 1 file changed, 1 insertion(+) diff --git a/.changes/windows_arm_signtool_detect.md b/.changes/windows_arm_signtool_detect.md index 7d951e7f3dcb..afff5dc2b395 100644 --- a/.changes/windows_arm_signtool_detect.md +++ b/.changes/windows_arm_signtool_detect.md @@ -13,4 +13,5 @@ Previously only the following were supported: The following were added: +- PROCESSOR_ARCHITECTURE_ARM - PROCESSOR_ARCHITECTURE_ARM64 From 364bb63e919d7f72de7d3f3d8bd612e8e5b13230 Mon Sep 17 00:00:00 2001 From: Rohit Singh <27754873+razein97@users.noreply.github.com> Date: Tue, 10 Feb 2026 10:43:06 +0530 Subject: [PATCH 07/95] detect arm systems in windows - Arm system were not detected when running signtool causing bundle failures when signing windows binaries --- .changes/windows_arm_signtool_detect.md | 15 +++++++++++++++ crates/tauri-bundler/src/bundle/windows/util.rs | 3 +++ 2 files changed, 18 insertions(+) create mode 100644 .changes/windows_arm_signtool_detect.md diff --git a/.changes/windows_arm_signtool_detect.md b/.changes/windows_arm_signtool_detect.md new file mode 100644 index 000000000000..889255763a88 --- /dev/null +++ b/.changes/windows_arm_signtool_detect.md @@ -0,0 +1,15 @@ +--- +"tauri-bundler": patch:enhance +--- + +Signtool path for windows arm systems was not being properly returned which caused failure in signing of windows binaries. + +This patch addresses it. + +Previously only the following were supported: +- PROCESSOR_ARCHITECTURE_INTEL +- PROCESSOR_ARCHITECTURE_AMD64 + +The following were added: +- PROCESSOR_ARCHITECTURE_ARM +- PROCESSOR_ARCHITECTURE_ARM64 \ No newline at end of file diff --git a/crates/tauri-bundler/src/bundle/windows/util.rs b/crates/tauri-bundler/src/bundle/windows/util.rs index 55cfea3a968f..60706976d0d5 100644 --- a/crates/tauri-bundler/src/bundle/windows/util.rs +++ b/crates/tauri-bundler/src/bundle/windows/util.rs @@ -67,6 +67,7 @@ pub fn download_webview2_offline_installer(base_path: &Path, arch: &str) -> crat pub fn os_bitness<'a>() -> Option<&'a str> { use windows_sys::Win32::System::SystemInformation::{ GetNativeSystemInfo, PROCESSOR_ARCHITECTURE_AMD64, PROCESSOR_ARCHITECTURE_INTEL, SYSTEM_INFO, + PROCESSOR_ARCHITECTURE_ARM, PROCESSOR_ARCHITECTURE_ARM64, }; let mut system_info: SYSTEM_INFO = unsafe { std::mem::zeroed() }; @@ -74,6 +75,8 @@ pub fn os_bitness<'a>() -> Option<&'a str> { match unsafe { system_info.Anonymous.Anonymous.wProcessorArchitecture } { PROCESSOR_ARCHITECTURE_INTEL => Some("x86"), PROCESSOR_ARCHITECTURE_AMD64 => Some("x64"), + PROCESSOR_ARCHITECTURE_ARM => Some("arm"), + PROCESSOR_ARCHITECTURE_ARM64 => Some("arm64"), _ => None, } } From 38d807186cd1db751f13d0a88c6eb591414d9978 Mon Sep 17 00:00:00 2001 From: Lucas Fernandes Nogueira Date: Thu, 12 Feb 2026 12:24:40 -0300 Subject: [PATCH 08/95] fix(cli): features should support a comma separated list (#14931) --- .changes/features-separator.md | 6 + crates/tauri-cli/src/acl/permission/new.rs | 4 +- crates/tauri-cli/src/build.rs | 4 +- crates/tauri-cli/src/bundle.rs | 2 +- crates/tauri-cli/src/dev.rs | 2 +- crates/tauri-cli/src/icon.rs | 2 +- crates/tauri-cli/src/mobile/android/build.rs | 2 +- crates/tauri-cli/src/mobile/android/dev.rs | 2 +- crates/tauri-cli/src/mobile/android/run.rs | 2 +- crates/tauri-cli/src/mobile/ios/build.rs | 2 +- crates/tauri-cli/src/mobile/ios/dev.rs | 2 +- crates/tauri-cli/src/mobile/ios/run.rs | 2 +- .../templates/mobile/android/app/.gitignore | 2 +- packages/cli/index.js | 247 +++++++++++++++--- 14 files changed, 233 insertions(+), 48 deletions(-) create mode 100644 .changes/features-separator.md diff --git a/.changes/features-separator.md b/.changes/features-separator.md new file mode 100644 index 000000000000..02277d87e07d --- /dev/null +++ b/.changes/features-separator.md @@ -0,0 +1,6 @@ +--- +"tauri-cli": patch:bug +"@tauri-apps/cli": patch:bug +--- + +Support comma-separated list of Cargo features on all commands. diff --git a/crates/tauri-cli/src/acl/permission/new.rs b/crates/tauri-cli/src/acl/permission/new.rs index cb17fa35714a..f4c52b079c13 100644 --- a/crates/tauri-cli/src/acl/permission/new.rs +++ b/crates/tauri-cli/src/acl/permission/new.rs @@ -24,10 +24,10 @@ pub struct Options { #[clap(long)] description: Option, /// List of commands to allow - #[clap(short, long, use_value_delimiter = true)] + #[clap(short, long, value_delimiter = ',')] allow: Option>, /// List of commands to deny - #[clap(short, long, use_value_delimiter = true)] + #[clap(short, long, value_delimiter = ',')] deny: Option>, /// Output file format. #[clap(long, default_value_t = FileFormat::Json)] diff --git a/crates/tauri-cli/src/build.rs b/crates/tauri-cli/src/build.rs index 627fd763ac90..2819bc3fcd6d 100644 --- a/crates/tauri-cli/src/build.rs +++ b/crates/tauri-cli/src/build.rs @@ -39,7 +39,7 @@ pub struct Options { #[clap(short, long)] pub target: Option, /// Space or comma separated list of features to activate - #[clap(short, long, action = ArgAction::Append, num_args(0..))] + #[clap(short, long, action = ArgAction::Append, num_args(0..), value_delimiter = ',')] pub features: Vec, /// Space or comma separated list of bundles to package. #[clap(short, long, action = ArgAction::Append, num_args(0..), value_delimiter = ',')] @@ -117,7 +117,7 @@ pub fn command(mut options: Options, verbosity: u8) -> Result<()> { let bin_path = interface.build(interface_options, &dirs)?; - log::info!(action ="Built"; "application at: {}", tauri_utils::display_path(bin_path)); + log::info!(action = "Built"; "application at: {}", tauri_utils::display_path(bin_path)); let app_settings = interface.app_settings(); diff --git a/crates/tauri-cli/src/bundle.rs b/crates/tauri-cli/src/bundle.rs index 4d3637ab58ba..3db831c1849a 100644 --- a/crates/tauri-cli/src/bundle.rs +++ b/crates/tauri-cli/src/bundle.rs @@ -70,7 +70,7 @@ pub struct Options { #[clap(short, long)] pub config: Vec, /// Space or comma separated list of features, should be the same features passed to `tauri build` if any. - #[clap(short, long, action = ArgAction::Append, num_args(0..))] + #[clap(short, long, action = ArgAction::Append, num_args(0..), value_delimiter = ',')] pub features: Vec, /// Target triple to build against. /// diff --git a/crates/tauri-cli/src/dev.rs b/crates/tauri-cli/src/dev.rs index d175c4c18774..3a6d58140547 100644 --- a/crates/tauri-cli/src/dev.rs +++ b/crates/tauri-cli/src/dev.rs @@ -54,7 +54,7 @@ pub struct Options { #[clap(short, long)] pub target: Option, /// List of cargo features to activate - #[clap(short, long, action = ArgAction::Append, num_args(0..))] + #[clap(short, long, action = ArgAction::Append, num_args(0..), value_delimiter = ',')] pub features: Vec, /// Exit on panic #[clap(short, long)] diff --git a/crates/tauri-cli/src/icon.rs b/crates/tauri-cli/src/icon.rs index 4945fb8266aa..e5863b1a31ec 100644 --- a/crates/tauri-cli/src/icon.rs +++ b/crates/tauri-cli/src/icon.rs @@ -94,7 +94,7 @@ pub struct Options { output: Option, /// Custom PNG icon sizes to generate. When set, the default icons are not generated. - #[clap(short, long, use_value_delimiter = true)] + #[clap(short, long, value_delimiter = ',')] png: Option>, /// The background color of the iOS icon - string as defined in the W3C's CSS Color Module Level 4 . diff --git a/crates/tauri-cli/src/mobile/android/build.rs b/crates/tauri-cli/src/mobile/android/build.rs index 8113ace54e32..e19a7c3769d9 100644 --- a/crates/tauri-cli/src/mobile/android/build.rs +++ b/crates/tauri-cli/src/mobile/android/build.rs @@ -48,7 +48,7 @@ pub struct Options { )] pub targets: Option>, /// List of cargo features to activate - #[clap(short, long, action = ArgAction::Append, num_args(0..))] + #[clap(short, long, action = ArgAction::Append, num_args(0..), value_delimiter = ',')] pub features: Vec, /// JSON strings or paths to JSON, JSON5 or TOML files to merge with the default configuration file /// diff --git a/crates/tauri-cli/src/mobile/android/dev.rs b/crates/tauri-cli/src/mobile/android/dev.rs index 7387eb831a1c..3e143b7b5728 100644 --- a/crates/tauri-cli/src/mobile/android/dev.rs +++ b/crates/tauri-cli/src/mobile/android/dev.rs @@ -44,7 +44,7 @@ use std::{env::set_current_dir, net::Ipv4Addr, path::PathBuf}; )] pub struct Options { /// List of cargo features to activate - #[clap(short, long, action = ArgAction::Append, num_args(0..))] + #[clap(short, long, action = ArgAction::Append, num_args(0..), value_delimiter = ',')] pub features: Vec, /// Exit on panic #[clap(short, long)] diff --git a/crates/tauri-cli/src/mobile/android/run.rs b/crates/tauri-cli/src/mobile/android/run.rs index c77596b03877..2e6c7ba012fe 100644 --- a/crates/tauri-cli/src/mobile/android/run.rs +++ b/crates/tauri-cli/src/mobile/android/run.rs @@ -29,7 +29,7 @@ pub struct Options { #[clap(short, long)] pub release: bool, /// List of cargo features to activate - #[clap(short, long, action = ArgAction::Append, num_args(0..))] + #[clap(short, long, action = ArgAction::Append, num_args(0..), value_delimiter = ',')] pub features: Vec, /// JSON strings or paths to JSON, JSON5 or TOML files to merge with the default configuration file /// diff --git a/crates/tauri-cli/src/mobile/ios/build.rs b/crates/tauri-cli/src/mobile/ios/build.rs index 7e75ca462af7..1489417c0836 100644 --- a/crates/tauri-cli/src/mobile/ios/build.rs +++ b/crates/tauri-cli/src/mobile/ios/build.rs @@ -59,7 +59,7 @@ pub struct Options { )] pub targets: Option>, /// List of cargo features to activate - #[clap(short, long, action = ArgAction::Append, num_args(0..))] + #[clap(short, long, action = ArgAction::Append, num_args(0..), value_delimiter = ',')] pub features: Vec, /// JSON strings or paths to JSON, JSON5 or TOML files to merge with the default configuration file /// diff --git a/crates/tauri-cli/src/mobile/ios/dev.rs b/crates/tauri-cli/src/mobile/ios/dev.rs index 0ef7fc083e37..4fe2c4dbecae 100644 --- a/crates/tauri-cli/src/mobile/ios/dev.rs +++ b/crates/tauri-cli/src/mobile/ios/dev.rs @@ -53,7 +53,7 @@ environment variable to determine whether the public network should be used or n )] pub struct Options { /// List of cargo features to activate - #[clap(short, long, action = ArgAction::Append, num_args(0..))] + #[clap(short, long, action = ArgAction::Append, num_args(0..), value_delimiter = ',')] pub features: Vec, /// Exit on panic #[clap(short, long)] diff --git a/crates/tauri-cli/src/mobile/ios/run.rs b/crates/tauri-cli/src/mobile/ios/run.rs index 61e696ef94a1..d80828d1c660 100644 --- a/crates/tauri-cli/src/mobile/ios/run.rs +++ b/crates/tauri-cli/src/mobile/ios/run.rs @@ -26,7 +26,7 @@ pub struct Options { #[clap(short, long)] pub release: bool, /// List of cargo features to activate - #[clap(short, long, action = ArgAction::Append, num_args(0..))] + #[clap(short, long, action = ArgAction::Append, num_args(0..), value_delimiter = ',')] pub features: Vec, /// JSON strings or paths to JSON, JSON5 or TOML files to merge with the default configuration file /// diff --git a/crates/tauri-cli/templates/mobile/android/app/.gitignore b/crates/tauri-cli/templates/mobile/android/app/.gitignore index 439b71f0e392..6c4d56b4a287 100644 --- a/crates/tauri-cli/templates/mobile/android/app/.gitignore +++ b/crates/tauri-cli/templates/mobile/android/app/.gitignore @@ -1,4 +1,4 @@ -/src/main/{{package-path}}/generated +/src/main/**/generated /src/main/jniLibs/**/*.so /src/main/assets/tauri.conf.json /tauri.build.gradle.kts diff --git a/packages/cli/index.js b/packages/cli/index.js index ab5cfc87f97a..c9e399696117 100644 --- a/packages/cli/index.js +++ b/packages/cli/index.js @@ -7,9 +7,6 @@ // @ts-nocheck /* auto-generated by NAPI-RS */ -const { createRequire } = require('node:module') -require = createRequire(__filename) - const { readFileSync } = require('node:fs') let nativeBinding = null const loadErrors = [] @@ -70,7 +67,7 @@ const isMuslFromChildProcess = () => { function requireNative() { if (process.env.NAPI_RS_NATIVE_LIBRARY_PATH) { try { - nativeBinding = require(process.env.NAPI_RS_NATIVE_LIBRARY_PATH); + return require(process.env.NAPI_RS_NATIVE_LIBRARY_PATH); } catch (err) { loadErrors.push(err) } @@ -82,7 +79,12 @@ function requireNative() { loadErrors.push(e) } try { - return require('@tauri-apps/cli-android-arm64') + const binding = require('@tauri-apps/cli-android-arm64') + const bindingPackageVersion = require('@tauri-apps/cli-android-arm64/package.json').version + if (bindingPackageVersion !== '2.10.0' && process.env.NAPI_RS_ENFORCE_VERSION_CHECK && process.env.NAPI_RS_ENFORCE_VERSION_CHECK !== '0') { + throw new Error(`Native binding package version mismatch, expected 2.10.0 but got ${bindingPackageVersion}. You can reinstall dependencies to fix this issue.`) + } + return binding } catch (e) { loadErrors.push(e) } @@ -93,7 +95,12 @@ function requireNative() { loadErrors.push(e) } try { - return require('@tauri-apps/cli-android-arm-eabi') + const binding = require('@tauri-apps/cli-android-arm-eabi') + const bindingPackageVersion = require('@tauri-apps/cli-android-arm-eabi/package.json').version + if (bindingPackageVersion !== '2.10.0' && process.env.NAPI_RS_ENFORCE_VERSION_CHECK && process.env.NAPI_RS_ENFORCE_VERSION_CHECK !== '0') { + throw new Error(`Native binding package version mismatch, expected 2.10.0 but got ${bindingPackageVersion}. You can reinstall dependencies to fix this issue.`) + } + return binding } catch (e) { loadErrors.push(e) } @@ -102,16 +109,39 @@ function requireNative() { } } else if (process.platform === 'win32') { if (process.arch === 'x64') { + if (process.config?.variables?.shlib_suffix === 'dll.a' || process.config?.variables?.node_target_type === 'shared_library') { + try { + return require('./cli.win32-x64-gnu.node') + } catch (e) { + loadErrors.push(e) + } try { + const binding = require('@tauri-apps/cli-win32-x64-gnu') + const bindingPackageVersion = require('@tauri-apps/cli-win32-x64-gnu/package.json').version + if (bindingPackageVersion !== '2.10.0' && process.env.NAPI_RS_ENFORCE_VERSION_CHECK && process.env.NAPI_RS_ENFORCE_VERSION_CHECK !== '0') { + throw new Error(`Native binding package version mismatch, expected 2.10.0 but got ${bindingPackageVersion}. You can reinstall dependencies to fix this issue.`) + } + return binding + } catch (e) { + loadErrors.push(e) + } + } else { + try { return require('./cli.win32-x64-msvc.node') } catch (e) { loadErrors.push(e) } try { - return require('@tauri-apps/cli-win32-x64-msvc') + const binding = require('@tauri-apps/cli-win32-x64-msvc') + const bindingPackageVersion = require('@tauri-apps/cli-win32-x64-msvc/package.json').version + if (bindingPackageVersion !== '2.10.0' && process.env.NAPI_RS_ENFORCE_VERSION_CHECK && process.env.NAPI_RS_ENFORCE_VERSION_CHECK !== '0') { + throw new Error(`Native binding package version mismatch, expected 2.10.0 but got ${bindingPackageVersion}. You can reinstall dependencies to fix this issue.`) + } + return binding } catch (e) { loadErrors.push(e) } + } } else if (process.arch === 'ia32') { try { return require('./cli.win32-ia32-msvc.node') @@ -119,7 +149,12 @@ function requireNative() { loadErrors.push(e) } try { - return require('@tauri-apps/cli-win32-ia32-msvc') + const binding = require('@tauri-apps/cli-win32-ia32-msvc') + const bindingPackageVersion = require('@tauri-apps/cli-win32-ia32-msvc/package.json').version + if (bindingPackageVersion !== '2.10.0' && process.env.NAPI_RS_ENFORCE_VERSION_CHECK && process.env.NAPI_RS_ENFORCE_VERSION_CHECK !== '0') { + throw new Error(`Native binding package version mismatch, expected 2.10.0 but got ${bindingPackageVersion}. You can reinstall dependencies to fix this issue.`) + } + return binding } catch (e) { loadErrors.push(e) } @@ -130,7 +165,12 @@ function requireNative() { loadErrors.push(e) } try { - return require('@tauri-apps/cli-win32-arm64-msvc') + const binding = require('@tauri-apps/cli-win32-arm64-msvc') + const bindingPackageVersion = require('@tauri-apps/cli-win32-arm64-msvc/package.json').version + if (bindingPackageVersion !== '2.10.0' && process.env.NAPI_RS_ENFORCE_VERSION_CHECK && process.env.NAPI_RS_ENFORCE_VERSION_CHECK !== '0') { + throw new Error(`Native binding package version mismatch, expected 2.10.0 but got ${bindingPackageVersion}. You can reinstall dependencies to fix this issue.`) + } + return binding } catch (e) { loadErrors.push(e) } @@ -144,7 +184,12 @@ function requireNative() { loadErrors.push(e) } try { - return require('@tauri-apps/cli-darwin-universal') + const binding = require('@tauri-apps/cli-darwin-universal') + const bindingPackageVersion = require('@tauri-apps/cli-darwin-universal/package.json').version + if (bindingPackageVersion !== '2.10.0' && process.env.NAPI_RS_ENFORCE_VERSION_CHECK && process.env.NAPI_RS_ENFORCE_VERSION_CHECK !== '0') { + throw new Error(`Native binding package version mismatch, expected 2.10.0 but got ${bindingPackageVersion}. You can reinstall dependencies to fix this issue.`) + } + return binding } catch (e) { loadErrors.push(e) } @@ -155,7 +200,12 @@ function requireNative() { loadErrors.push(e) } try { - return require('@tauri-apps/cli-darwin-x64') + const binding = require('@tauri-apps/cli-darwin-x64') + const bindingPackageVersion = require('@tauri-apps/cli-darwin-x64/package.json').version + if (bindingPackageVersion !== '2.10.0' && process.env.NAPI_RS_ENFORCE_VERSION_CHECK && process.env.NAPI_RS_ENFORCE_VERSION_CHECK !== '0') { + throw new Error(`Native binding package version mismatch, expected 2.10.0 but got ${bindingPackageVersion}. You can reinstall dependencies to fix this issue.`) + } + return binding } catch (e) { loadErrors.push(e) } @@ -166,7 +216,12 @@ function requireNative() { loadErrors.push(e) } try { - return require('@tauri-apps/cli-darwin-arm64') + const binding = require('@tauri-apps/cli-darwin-arm64') + const bindingPackageVersion = require('@tauri-apps/cli-darwin-arm64/package.json').version + if (bindingPackageVersion !== '2.10.0' && process.env.NAPI_RS_ENFORCE_VERSION_CHECK && process.env.NAPI_RS_ENFORCE_VERSION_CHECK !== '0') { + throw new Error(`Native binding package version mismatch, expected 2.10.0 but got ${bindingPackageVersion}. You can reinstall dependencies to fix this issue.`) + } + return binding } catch (e) { loadErrors.push(e) } @@ -181,7 +236,12 @@ function requireNative() { loadErrors.push(e) } try { - return require('@tauri-apps/cli-freebsd-x64') + const binding = require('@tauri-apps/cli-freebsd-x64') + const bindingPackageVersion = require('@tauri-apps/cli-freebsd-x64/package.json').version + if (bindingPackageVersion !== '2.10.0' && process.env.NAPI_RS_ENFORCE_VERSION_CHECK && process.env.NAPI_RS_ENFORCE_VERSION_CHECK !== '0') { + throw new Error(`Native binding package version mismatch, expected 2.10.0 but got ${bindingPackageVersion}. You can reinstall dependencies to fix this issue.`) + } + return binding } catch (e) { loadErrors.push(e) } @@ -192,7 +252,12 @@ function requireNative() { loadErrors.push(e) } try { - return require('@tauri-apps/cli-freebsd-arm64') + const binding = require('@tauri-apps/cli-freebsd-arm64') + const bindingPackageVersion = require('@tauri-apps/cli-freebsd-arm64/package.json').version + if (bindingPackageVersion !== '2.10.0' && process.env.NAPI_RS_ENFORCE_VERSION_CHECK && process.env.NAPI_RS_ENFORCE_VERSION_CHECK !== '0') { + throw new Error(`Native binding package version mismatch, expected 2.10.0 but got ${bindingPackageVersion}. You can reinstall dependencies to fix this issue.`) + } + return binding } catch (e) { loadErrors.push(e) } @@ -208,7 +273,12 @@ function requireNative() { loadErrors.push(e) } try { - return require('@tauri-apps/cli-linux-x64-musl') + const binding = require('@tauri-apps/cli-linux-x64-musl') + const bindingPackageVersion = require('@tauri-apps/cli-linux-x64-musl/package.json').version + if (bindingPackageVersion !== '2.10.0' && process.env.NAPI_RS_ENFORCE_VERSION_CHECK && process.env.NAPI_RS_ENFORCE_VERSION_CHECK !== '0') { + throw new Error(`Native binding package version mismatch, expected 2.10.0 but got ${bindingPackageVersion}. You can reinstall dependencies to fix this issue.`) + } + return binding } catch (e) { loadErrors.push(e) } @@ -219,7 +289,12 @@ function requireNative() { loadErrors.push(e) } try { - return require('@tauri-apps/cli-linux-x64-gnu') + const binding = require('@tauri-apps/cli-linux-x64-gnu') + const bindingPackageVersion = require('@tauri-apps/cli-linux-x64-gnu/package.json').version + if (bindingPackageVersion !== '2.10.0' && process.env.NAPI_RS_ENFORCE_VERSION_CHECK && process.env.NAPI_RS_ENFORCE_VERSION_CHECK !== '0') { + throw new Error(`Native binding package version mismatch, expected 2.10.0 but got ${bindingPackageVersion}. You can reinstall dependencies to fix this issue.`) + } + return binding } catch (e) { loadErrors.push(e) } @@ -232,7 +307,12 @@ function requireNative() { loadErrors.push(e) } try { - return require('@tauri-apps/cli-linux-arm64-musl') + const binding = require('@tauri-apps/cli-linux-arm64-musl') + const bindingPackageVersion = require('@tauri-apps/cli-linux-arm64-musl/package.json').version + if (bindingPackageVersion !== '2.10.0' && process.env.NAPI_RS_ENFORCE_VERSION_CHECK && process.env.NAPI_RS_ENFORCE_VERSION_CHECK !== '0') { + throw new Error(`Native binding package version mismatch, expected 2.10.0 but got ${bindingPackageVersion}. You can reinstall dependencies to fix this issue.`) + } + return binding } catch (e) { loadErrors.push(e) } @@ -243,7 +323,12 @@ function requireNative() { loadErrors.push(e) } try { - return require('@tauri-apps/cli-linux-arm64-gnu') + const binding = require('@tauri-apps/cli-linux-arm64-gnu') + const bindingPackageVersion = require('@tauri-apps/cli-linux-arm64-gnu/package.json').version + if (bindingPackageVersion !== '2.10.0' && process.env.NAPI_RS_ENFORCE_VERSION_CHECK && process.env.NAPI_RS_ENFORCE_VERSION_CHECK !== '0') { + throw new Error(`Native binding package version mismatch, expected 2.10.0 but got ${bindingPackageVersion}. You can reinstall dependencies to fix this issue.`) + } + return binding } catch (e) { loadErrors.push(e) } @@ -256,7 +341,12 @@ function requireNative() { loadErrors.push(e) } try { - return require('@tauri-apps/cli-linux-arm-musleabihf') + const binding = require('@tauri-apps/cli-linux-arm-musleabihf') + const bindingPackageVersion = require('@tauri-apps/cli-linux-arm-musleabihf/package.json').version + if (bindingPackageVersion !== '2.10.0' && process.env.NAPI_RS_ENFORCE_VERSION_CHECK && process.env.NAPI_RS_ENFORCE_VERSION_CHECK !== '0') { + throw new Error(`Native binding package version mismatch, expected 2.10.0 but got ${bindingPackageVersion}. You can reinstall dependencies to fix this issue.`) + } + return binding } catch (e) { loadErrors.push(e) } @@ -267,7 +357,46 @@ function requireNative() { loadErrors.push(e) } try { - return require('@tauri-apps/cli-linux-arm-gnueabihf') + const binding = require('@tauri-apps/cli-linux-arm-gnueabihf') + const bindingPackageVersion = require('@tauri-apps/cli-linux-arm-gnueabihf/package.json').version + if (bindingPackageVersion !== '2.10.0' && process.env.NAPI_RS_ENFORCE_VERSION_CHECK && process.env.NAPI_RS_ENFORCE_VERSION_CHECK !== '0') { + throw new Error(`Native binding package version mismatch, expected 2.10.0 but got ${bindingPackageVersion}. You can reinstall dependencies to fix this issue.`) + } + return binding + } catch (e) { + loadErrors.push(e) + } + } + } else if (process.arch === 'loong64') { + if (isMusl()) { + try { + return require('./cli.linux-loong64-musl.node') + } catch (e) { + loadErrors.push(e) + } + try { + const binding = require('@tauri-apps/cli-linux-loong64-musl') + const bindingPackageVersion = require('@tauri-apps/cli-linux-loong64-musl/package.json').version + if (bindingPackageVersion !== '2.10.0' && process.env.NAPI_RS_ENFORCE_VERSION_CHECK && process.env.NAPI_RS_ENFORCE_VERSION_CHECK !== '0') { + throw new Error(`Native binding package version mismatch, expected 2.10.0 but got ${bindingPackageVersion}. You can reinstall dependencies to fix this issue.`) + } + return binding + } catch (e) { + loadErrors.push(e) + } + } else { + try { + return require('./cli.linux-loong64-gnu.node') + } catch (e) { + loadErrors.push(e) + } + try { + const binding = require('@tauri-apps/cli-linux-loong64-gnu') + const bindingPackageVersion = require('@tauri-apps/cli-linux-loong64-gnu/package.json').version + if (bindingPackageVersion !== '2.10.0' && process.env.NAPI_RS_ENFORCE_VERSION_CHECK && process.env.NAPI_RS_ENFORCE_VERSION_CHECK !== '0') { + throw new Error(`Native binding package version mismatch, expected 2.10.0 but got ${bindingPackageVersion}. You can reinstall dependencies to fix this issue.`) + } + return binding } catch (e) { loadErrors.push(e) } @@ -280,7 +409,12 @@ function requireNative() { loadErrors.push(e) } try { - return require('@tauri-apps/cli-linux-riscv64-musl') + const binding = require('@tauri-apps/cli-linux-riscv64-musl') + const bindingPackageVersion = require('@tauri-apps/cli-linux-riscv64-musl/package.json').version + if (bindingPackageVersion !== '2.10.0' && process.env.NAPI_RS_ENFORCE_VERSION_CHECK && process.env.NAPI_RS_ENFORCE_VERSION_CHECK !== '0') { + throw new Error(`Native binding package version mismatch, expected 2.10.0 but got ${bindingPackageVersion}. You can reinstall dependencies to fix this issue.`) + } + return binding } catch (e) { loadErrors.push(e) } @@ -291,7 +425,12 @@ function requireNative() { loadErrors.push(e) } try { - return require('@tauri-apps/cli-linux-riscv64-gnu') + const binding = require('@tauri-apps/cli-linux-riscv64-gnu') + const bindingPackageVersion = require('@tauri-apps/cli-linux-riscv64-gnu/package.json').version + if (bindingPackageVersion !== '2.10.0' && process.env.NAPI_RS_ENFORCE_VERSION_CHECK && process.env.NAPI_RS_ENFORCE_VERSION_CHECK !== '0') { + throw new Error(`Native binding package version mismatch, expected 2.10.0 but got ${bindingPackageVersion}. You can reinstall dependencies to fix this issue.`) + } + return binding } catch (e) { loadErrors.push(e) } @@ -303,7 +442,12 @@ function requireNative() { loadErrors.push(e) } try { - return require('@tauri-apps/cli-linux-ppc64-gnu') + const binding = require('@tauri-apps/cli-linux-ppc64-gnu') + const bindingPackageVersion = require('@tauri-apps/cli-linux-ppc64-gnu/package.json').version + if (bindingPackageVersion !== '2.10.0' && process.env.NAPI_RS_ENFORCE_VERSION_CHECK && process.env.NAPI_RS_ENFORCE_VERSION_CHECK !== '0') { + throw new Error(`Native binding package version mismatch, expected 2.10.0 but got ${bindingPackageVersion}. You can reinstall dependencies to fix this issue.`) + } + return binding } catch (e) { loadErrors.push(e) } @@ -314,7 +458,12 @@ function requireNative() { loadErrors.push(e) } try { - return require('@tauri-apps/cli-linux-s390x-gnu') + const binding = require('@tauri-apps/cli-linux-s390x-gnu') + const bindingPackageVersion = require('@tauri-apps/cli-linux-s390x-gnu/package.json').version + if (bindingPackageVersion !== '2.10.0' && process.env.NAPI_RS_ENFORCE_VERSION_CHECK && process.env.NAPI_RS_ENFORCE_VERSION_CHECK !== '0') { + throw new Error(`Native binding package version mismatch, expected 2.10.0 but got ${bindingPackageVersion}. You can reinstall dependencies to fix this issue.`) + } + return binding } catch (e) { loadErrors.push(e) } @@ -324,34 +473,49 @@ function requireNative() { } else if (process.platform === 'openharmony') { if (process.arch === 'arm64') { try { - return require('./cli.linux-arm64-ohos.node') + return require('./cli.openharmony-arm64.node') } catch (e) { loadErrors.push(e) } try { - return require('@tauri-apps/cli-linux-arm64-ohos') + const binding = require('@tauri-apps/cli-openharmony-arm64') + const bindingPackageVersion = require('@tauri-apps/cli-openharmony-arm64/package.json').version + if (bindingPackageVersion !== '2.10.0' && process.env.NAPI_RS_ENFORCE_VERSION_CHECK && process.env.NAPI_RS_ENFORCE_VERSION_CHECK !== '0') { + throw new Error(`Native binding package version mismatch, expected 2.10.0 but got ${bindingPackageVersion}. You can reinstall dependencies to fix this issue.`) + } + return binding } catch (e) { loadErrors.push(e) } } else if (process.arch === 'x64') { try { - return require('./cli.linux-x64-ohos.node') + return require('./cli.openharmony-x64.node') } catch (e) { loadErrors.push(e) } try { - return require('@tauri-apps/cli-linux-x64-ohos') + const binding = require('@tauri-apps/cli-openharmony-x64') + const bindingPackageVersion = require('@tauri-apps/cli-openharmony-x64/package.json').version + if (bindingPackageVersion !== '2.10.0' && process.env.NAPI_RS_ENFORCE_VERSION_CHECK && process.env.NAPI_RS_ENFORCE_VERSION_CHECK !== '0') { + throw new Error(`Native binding package version mismatch, expected 2.10.0 but got ${bindingPackageVersion}. You can reinstall dependencies to fix this issue.`) + } + return binding } catch (e) { loadErrors.push(e) } } else if (process.arch === 'arm') { try { - return require('./cli.linux-arm-ohos.node') + return require('./cli.openharmony-arm.node') } catch (e) { loadErrors.push(e) } try { - return require('@tauri-apps/cli-linux-arm-ohos') + const binding = require('@tauri-apps/cli-openharmony-arm') + const bindingPackageVersion = require('@tauri-apps/cli-openharmony-arm/package.json').version + if (bindingPackageVersion !== '2.10.0' && process.env.NAPI_RS_ENFORCE_VERSION_CHECK && process.env.NAPI_RS_ENFORCE_VERSION_CHECK !== '0') { + throw new Error(`Native binding package version mismatch, expected 2.10.0 but got ${bindingPackageVersion}. You can reinstall dependencies to fix this issue.`) + } + return binding } catch (e) { loadErrors.push(e) } @@ -366,22 +530,32 @@ function requireNative() { nativeBinding = requireNative() if (!nativeBinding || process.env.NAPI_RS_FORCE_WASI) { + let wasiBinding = null + let wasiBindingError = null try { - nativeBinding = require('./cli.wasi.cjs') + wasiBinding = require('./cli.wasi.cjs') + nativeBinding = wasiBinding } catch (err) { if (process.env.NAPI_RS_FORCE_WASI) { - loadErrors.push(err) + wasiBindingError = err } } if (!nativeBinding) { try { - nativeBinding = require('@tauri-apps/cli-wasm32-wasi') + wasiBinding = require('@tauri-apps/cli-wasm32-wasi') + nativeBinding = wasiBinding } catch (err) { if (process.env.NAPI_RS_FORCE_WASI) { + wasiBindingError.cause = err loadErrors.push(err) } } } + if (process.env.NAPI_RS_FORCE_WASI === 'error' && !wasiBinding) { + const error = new Error('WASI binding not found and NAPI_RS_FORCE_WASI is set to error') + error.cause = wasiBindingError + throw error + } } if (!nativeBinding) { @@ -390,7 +564,12 @@ if (!nativeBinding) { `Cannot find native binding. ` + `npm has a bug related to optional dependencies (https://github.com/npm/cli/issues/4828). ` + 'Please try `npm i` again after removing both package-lock.json and node_modules directory.', - { cause: loadErrors } + { + cause: loadErrors.reduce((err, cur) => { + cur.cause = err + return cur + }), + }, ) } throw new Error(`Failed to load native binding`) From d72faec72b01ed9b9ece1844e5f20fa6f0b216a5 Mon Sep 17 00:00:00 2001 From: Lucas Fernandes Nogueira Date: Thu, 12 Feb 2026 21:12:00 -0300 Subject: [PATCH 09/95] fix(cli): missing options on mobile dev/build commands (#14932) * fix(cli): missing options on mobile dev/build commands * avoid duplicated flags * clippy --- .changes/fix-missing-options.md | 6 ++++++ crates/tauri-cli/src/interface/rust.rs | 6 ++++-- crates/tauri-cli/src/mobile/android/build.rs | 12 ++++++++++-- crates/tauri-cli/src/mobile/android/dev.rs | 11 ++++++++++- crates/tauri-cli/src/mobile/ios/build.rs | 14 +++++++++++--- crates/tauri-cli/src/mobile/ios/dev.rs | 15 ++++++++++++--- crates/tauri-cli/src/mobile/mod.rs | 16 +--------------- 7 files changed, 54 insertions(+), 26 deletions(-) create mode 100644 .changes/fix-missing-options.md diff --git a/.changes/fix-missing-options.md b/.changes/fix-missing-options.md new file mode 100644 index 000000000000..957f07a64f59 --- /dev/null +++ b/.changes/fix-missing-options.md @@ -0,0 +1,6 @@ +--- +"tauri-cli": patch:bug +"@tauri-apps/cli": patch:bug +--- + +Fix missing Cargo args when running mobile dev and build commands. diff --git a/crates/tauri-cli/src/interface/rust.rs b/crates/tauri-cli/src/interface/rust.rs index c4c339e697d6..d6026b3b24dd 100644 --- a/crates/tauri-cli/src/interface/rust.rs +++ b/crates/tauri-cli/src/interface/rust.rs @@ -425,7 +425,7 @@ fn dev_options( } *args = dev_args; - if mobile { + if mobile && !args.contains(&"--lib".into()) { args.push("--lib".into()); } @@ -483,7 +483,9 @@ impl Rust { pub fn build_options(&self, args: &mut Vec, features: &mut Vec, mobile: bool) { features.push("tauri/custom-protocol".into()); if mobile { - args.push("--lib".into()); + if !args.contains(&"--lib".into()) { + args.push("--lib".into()); + } } else { args.push("--bins".into()); } diff --git a/crates/tauri-cli/src/mobile/android/build.rs b/crates/tauri-cli/src/mobile/android/build.rs index e19a7c3769d9..3a4369402a8a 100644 --- a/crates/tauri-cli/src/mobile/android/build.rs +++ b/crates/tauri-cli/src/mobile/android/build.rs @@ -154,14 +154,22 @@ pub fn run( build_options.target = Some(first_target.triple.into()); let interface = AppInterface::new(tauri_config, build_options.target.clone(), dirs.tauri)?; - interface.build_options(&mut Vec::new(), &mut build_options.features, true); + interface.build_options(&mut build_options.args, &mut build_options.features, true); let app = get_app(MobileTarget::Android, tauri_config, &interface, dirs.tauri); let (config, metadata) = get_config( &app, tauri_config, &build_options.features, - &Default::default(), + &CliOptions { + dev: false, + features: build_options.features.clone(), + args: build_options.args.clone(), + noise_level, + vars: Default::default(), + config: build_options.config.clone(), + target_device: None, + }, ); let profile = if options.debug { diff --git a/crates/tauri-cli/src/mobile/android/dev.rs b/crates/tauri-cli/src/mobile/android/dev.rs index 3e143b7b5728..93692f6d0454 100644 --- a/crates/tauri-cli/src/mobile/android/dev.rs +++ b/crates/tauri-cli/src/mobile/android/dev.rs @@ -182,6 +182,7 @@ fn run_command(options: Options, noise_level: NoiseLevel, dirs: Dirs) -> Result< .map(|d| d.target().triple.to_string()) .unwrap_or_else(|| Target::all().values().next().unwrap().triple.into()); dev_options.target = Some(target_triple); + dev_options.args.push("--lib".into()); let interface = AppInterface::new(&tauri_config, dev_options.target.clone(), dirs.tauri)?; @@ -190,7 +191,15 @@ fn run_command(options: Options, noise_level: NoiseLevel, dirs: Dirs) -> Result< &app, &tauri_config, dev_options.features.as_ref(), - &Default::default(), + &CliOptions { + dev: true, + features: dev_options.features.clone(), + args: dev_options.args.clone(), + noise_level, + vars: Default::default(), + config: dev_options.config.clone(), + target_device: None, + }, ); set_current_dir(dirs.tauri).context("failed to set current directory to Tauri directory")?; diff --git a/crates/tauri-cli/src/mobile/ios/build.rs b/crates/tauri-cli/src/mobile/ios/build.rs index 1489417c0836..a016ccca3263 100644 --- a/crates/tauri-cli/src/mobile/ios/build.rs +++ b/crates/tauri-cli/src/mobile/ios/build.rs @@ -195,14 +195,22 @@ pub fn run(options: Options, noise_level: NoiseLevel, dirs: &Dirs) -> Result Result Result< .map(|d| d.target().triple.to_string()) .unwrap_or_else(|| "aarch64-apple-ios".into()); dev_options.target = Some(target_triple.clone()); + dev_options.args.push("--lib".into()); let tauri_config = get_tauri_config( tauri_utils::platform::Target::Ios, @@ -195,7 +196,15 @@ fn run_command(options: Options, noise_level: NoiseLevel, dirs: Dirs) -> Result< &app, &tauri_config, &dev_options.features, - &Default::default(), + &CliOptions { + dev: true, + features: dev_options.features.clone(), + args: dev_options.args.clone(), + noise_level, + vars: Default::default(), + config: dev_options.config.clone(), + target_device: None, + }, dirs.tauri, )?; @@ -297,7 +306,7 @@ fn run_dev( )?; } - crate::dev::setup(&interface, &mut dev_options, &mut tauri_config, &dirs)?; + crate::dev::setup(&interface, &mut dev_options, &mut tauri_config, dirs)?; let app_settings = interface.app_settings(); let out_dir = app_settings.out_dir( @@ -360,7 +369,7 @@ fn run_dev( open_xcode() } }, - &dirs, + dirs, ) } diff --git a/crates/tauri-cli/src/mobile/mod.rs b/crates/tauri-cli/src/mobile/mod.rs index f7ab30357f62..2e85355f32aa 100644 --- a/crates/tauri-cli/src/mobile/mod.rs +++ b/crates/tauri-cli/src/mobile/mod.rs @@ -166,7 +166,7 @@ impl Default for DevHost { } } -#[derive(Debug, Clone, Serialize, Deserialize)] +#[derive(Debug, Default, Clone, Serialize, Deserialize)] pub struct CliOptions { pub dev: bool, pub features: Vec, @@ -177,20 +177,6 @@ pub struct CliOptions { pub target_device: Option, } -impl Default for CliOptions { - fn default() -> Self { - Self { - dev: false, - features: Vec::new(), - args: vec!["--lib".into()], - noise_level: Default::default(), - vars: Default::default(), - config: Vec::new(), - target_device: None, - } - } -} - fn local_ip_address(force: bool) -> &'static IpAddr { static LOCAL_IP: OnceLock = OnceLock::new(); LOCAL_IP.get_or_init(|| { From 04bf31452bf0da320c6ce8a2db7e0d43f5c500ab Mon Sep 17 00:00:00 2001 From: cui Date: Sun, 15 Feb 2026 20:53:01 +0800 Subject: [PATCH 10/95] fix(core): fix content-boundaries start/end order in asset protocol (#14938) --- crates/tauri/src/protocol/asset.rs | 2 +- examples/streaming/main.rs | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/crates/tauri/src/protocol/asset.rs b/crates/tauri/src/protocol/asset.rs index e7c7133248b1..78ff0e38a44a 100644 --- a/crates/tauri/src/protocol/asset.rs +++ b/crates/tauri/src/protocol/asset.rs @@ -190,7 +190,7 @@ fn get_response( // multi-part range header let mut buf = Vec::new(); - for (end, start) in ranges { + for (start, end) in ranges { // a new range is being written, write the range boundary buf.write_all(boundary_sep.as_bytes()).await?; diff --git a/examples/streaming/main.rs b/examples/streaming/main.rs index b2f7f1ef15ae..608df9270640 100644 --- a/examples/streaming/main.rs +++ b/examples/streaming/main.rs @@ -116,7 +116,7 @@ fn get_stream_response( format!("multipart/byteranges; boundary={boundary}"), ); - for (end, start) in ranges { + for (start, end) in ranges { // a new range is being written, write the range boundary buf.write_all(boundary_sep.as_bytes())?; From 035227c331db68a4f07a22c81bbdefd54ac16f3f Mon Sep 17 00:00:00 2001 From: "renovate[bot]" <29139614+renovate[bot]@users.noreply.github.com> Date: Sun, 15 Feb 2026 14:02:39 +0100 Subject: [PATCH 11/95] chore(deps): update rust crate time to v0.3.47 [security] (#14902) Co-authored-by: renovate[bot] <29139614+renovate[bot]@users.noreply.github.com> --- Cargo.lock | 24 ++++++++++++------------ 1 file changed, 12 insertions(+), 12 deletions(-) diff --git a/Cargo.lock b/Cargo.lock index 8b199ae40008..3e48acfb357b 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -1804,12 +1804,12 @@ dependencies = [ [[package]] name = "deranged" -version = "0.3.11" +version = "0.5.6" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "b42b6fa04a440b495c8b04d0e71b707c585f83cb9cb28cf8cd0d976c315e31b4" +checksum = "cc3dc5ad92c2e2d1c193bbbbdf2ea477cb81331de4f3103f267ca18368b988c4" dependencies = [ "powerfmt", - "serde", + "serde_core", ] [[package]] @@ -4937,9 +4937,9 @@ dependencies = [ [[package]] name = "num-conv" -version = "0.1.0" +version = "0.2.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "51d515d32fb182ee37cda2ccdcb92950d6a3c2893aa280e540671c2cd0f3b1d9" +checksum = "cf97ec579c3c42f953ef76dbf8d55ac91fb219dde70e49aa4a6b7d74e9919050" [[package]] name = "num-derive" @@ -9119,9 +9119,9 @@ dependencies = [ [[package]] name = "time" -version = "0.3.37" +version = "0.3.47" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "35e7868883861bd0e56d9ac6efcaaca0d6d5d82a2a7ec8209ff492c07cf37b21" +checksum = "743bd48c283afc0388f9b8827b976905fb217ad9e647fae3a379a9283c4def2c" dependencies = [ "deranged", "itoa", @@ -9129,22 +9129,22 @@ dependencies = [ "num-conv", "num_threads", "powerfmt", - "serde", + "serde_core", "time-core", "time-macros", ] [[package]] name = "time-core" -version = "0.1.2" +version = "0.1.8" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "ef927ca75afb808a4d64dd374f00a2adf8d0fcff8e7b184af886c3c87ec4a3f3" +checksum = "7694e1cfe791f8d31026952abf09c69ca6f6fa4e1a1229e18988f06a04a12dca" [[package]] name = "time-macros" -version = "0.2.19" +version = "0.2.27" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "2834e6017e3e5e4b9834939793b282bc03b37a3336245fa820e35e233e2a85de" +checksum = "2e70e4c5a0e0a8a4823ad65dfe1a6930e4f4d756dcd9dd7939022b5e8c501215" dependencies = [ "num-conv", "time-core", From c154b87cdbd6fed810af76ca37b06d6bac0fec1f Mon Sep 17 00:00:00 2001 From: FabianLars <30730186+FabianLars@users.noreply.github.com> Date: Sun, 15 Feb 2026 14:19:06 +0100 Subject: [PATCH 12/95] Revert "chore(deps): update rust crate time to v0.3.47 [security] (#14902)" This reverts commit 86c8c870c8bfa7259952af94ad70548e3d85653b. --- Cargo.lock | 24 ++++++++++++------------ 1 file changed, 12 insertions(+), 12 deletions(-) diff --git a/Cargo.lock b/Cargo.lock index 3e48acfb357b..8b199ae40008 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -1804,12 +1804,12 @@ dependencies = [ [[package]] name = "deranged" -version = "0.5.6" +version = "0.3.11" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "cc3dc5ad92c2e2d1c193bbbbdf2ea477cb81331de4f3103f267ca18368b988c4" +checksum = "b42b6fa04a440b495c8b04d0e71b707c585f83cb9cb28cf8cd0d976c315e31b4" dependencies = [ "powerfmt", - "serde_core", + "serde", ] [[package]] @@ -4937,9 +4937,9 @@ dependencies = [ [[package]] name = "num-conv" -version = "0.2.0" +version = "0.1.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "cf97ec579c3c42f953ef76dbf8d55ac91fb219dde70e49aa4a6b7d74e9919050" +checksum = "51d515d32fb182ee37cda2ccdcb92950d6a3c2893aa280e540671c2cd0f3b1d9" [[package]] name = "num-derive" @@ -9119,9 +9119,9 @@ dependencies = [ [[package]] name = "time" -version = "0.3.47" +version = "0.3.37" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "743bd48c283afc0388f9b8827b976905fb217ad9e647fae3a379a9283c4def2c" +checksum = "35e7868883861bd0e56d9ac6efcaaca0d6d5d82a2a7ec8209ff492c07cf37b21" dependencies = [ "deranged", "itoa", @@ -9129,22 +9129,22 @@ dependencies = [ "num-conv", "num_threads", "powerfmt", - "serde_core", + "serde", "time-core", "time-macros", ] [[package]] name = "time-core" -version = "0.1.8" +version = "0.1.2" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "7694e1cfe791f8d31026952abf09c69ca6f6fa4e1a1229e18988f06a04a12dca" +checksum = "ef927ca75afb808a4d64dd374f00a2adf8d0fcff8e7b184af886c3c87ec4a3f3" [[package]] name = "time-macros" -version = "0.2.27" +version = "0.2.19" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "2e70e4c5a0e0a8a4823ad65dfe1a6930e4f4d756dcd9dd7939022b5e8c501215" +checksum = "2834e6017e3e5e4b9834939793b282bc03b37a3336245fa820e35e233e2a85de" dependencies = [ "num-conv", "time-core", From b55bfbd04cae5727108774ae8b611797255b2b17 Mon Sep 17 00:00:00 2001 From: Varun Chawla <34209028+veeceey@users.noreply.github.com> Date: Mon, 16 Feb 2026 08:34:58 -0800 Subject: [PATCH 13/95] fix(bundler): swap WIX registry search order to prioritize InstallDir (#14945) --- .changes/fix-wix-registry-search-order.md | 5 +++++ crates/tauri-bundler/src/bundle/windows/msi/main.wxs | 12 ++++++++---- 2 files changed, 13 insertions(+), 4 deletions(-) create mode 100644 .changes/fix-wix-registry-search-order.md diff --git a/.changes/fix-wix-registry-search-order.md b/.changes/fix-wix-registry-search-order.md new file mode 100644 index 000000000000..10e11326ced6 --- /dev/null +++ b/.changes/fix-wix-registry-search-order.md @@ -0,0 +1,5 @@ +--- +"tauri-bundler": patch:bug +--- + +Fix WIX installer registry search order so that the named `InstallDir` key takes priority over the NSIS default key, preventing install location from changing on updates. diff --git a/crates/tauri-bundler/src/bundle/windows/msi/main.wxs b/crates/tauri-bundler/src/bundle/windows/msi/main.wxs index a11b2ec4381c..a08c3b2cc5dc 100644 --- a/crates/tauri-bundler/src/bundle/windows/msi/main.wxs +++ b/crates/tauri-bundler/src/bundle/windows/msi/main.wxs @@ -70,12 +70,16 @@ {{/if}} + - - - - + + + + From a99f6be04cf121b316c9f8edaab1ffafb64cc895 Mon Sep 17 00:00:00 2001 From: montyc1999 <211852937+montyc1999@users.noreply.github.com> Date: Wed, 18 Feb 2026 15:31:23 -0500 Subject: [PATCH 14/95] fix(deps): disable default-features in objc2 crates (#14967) --- Cargo.lock | 78 +------------------- crates/tauri-runtime-wry/Cargo.toml | 3 +- crates/tauri-runtime-wry/src/window/macos.rs | 2 +- crates/tauri-runtime/Cargo.toml | 6 +- crates/tauri/Cargo.toml | 3 +- crates/tauri/src/app.rs | 4 +- crates/tauri/src/webview/webview_window.rs | 2 +- 7 files changed, 13 insertions(+), 85 deletions(-) diff --git a/Cargo.lock b/Cargo.lock index 8b199ae40008..9b92b2d867b4 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -5072,36 +5072,8 @@ checksum = "5906f93257178e2f7ae069efb89fbd6ee94f0592740b5f8a1512ca498814d0fb" dependencies = [ "bitflags 2.7.0", "block2 0.6.0", - "libc", "objc2 0.6.0", - "objc2-cloud-kit", - "objc2-core-data", "objc2-core-foundation", - "objc2-core-graphics", - "objc2-core-image", - "objc2-foundation 0.3.0", - "objc2-quartz-core 0.3.0", -] - -[[package]] -name = "objc2-cloud-kit" -version = "0.3.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "6c1948a9be5f469deadbd6bcb86ad7ff9e47b4f632380139722f7d9840c0d42c" -dependencies = [ - "bitflags 2.7.0", - "objc2 0.6.0", - "objc2-foundation 0.3.0", -] - -[[package]] -name = "objc2-core-data" -version = "0.3.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "1f860f8e841f6d32f754836f51e6bc7777cd7e7053cf18528233f6811d3eceb4" -dependencies = [ - "bitflags 2.7.0", - "objc2 0.6.0", "objc2-foundation 0.3.0", ] @@ -5122,19 +5094,7 @@ source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "f8dca602628b65356b6513290a21a6405b4d4027b8b250f0b98dddbb28b7de02" dependencies = [ "bitflags 2.7.0", - "objc2 0.6.0", "objc2-core-foundation", - "objc2-io-surface", -] - -[[package]] -name = "objc2-core-image" -version = "0.3.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "6ffa6bea72bf42c78b0b34e89c0bafac877d5f80bf91e159a5d96ea7f693ca56" -dependencies = [ - "objc2 0.6.0", - "objc2-foundation 0.3.0", ] [[package]] @@ -5172,18 +5132,6 @@ checksum = "3a21c6c9014b82c39515db5b396f91645182611c97d24637cf56ac01e5f8d998" dependencies = [ "bitflags 2.7.0", "block2 0.6.0", - "libc", - "objc2 0.6.0", - "objc2-core-foundation", -] - -[[package]] -name = "objc2-io-surface" -version = "0.3.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "161a8b87e32610086e1a7a9e9ec39f84459db7b3a0881c1f16ca5a2605581c19" -dependencies = [ - "bitflags 2.7.0", "objc2 0.6.0", "objc2-core-foundation", ] @@ -5213,28 +5161,6 @@ dependencies = [ "objc2-metal", ] -[[package]] -name = "objc2-quartz-core" -version = "0.3.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "6fb3794501bb1bee12f08dcad8c61f2a5875791ad1c6f47faa71a0f033f20071" -dependencies = [ - "bitflags 2.7.0", - "objc2 0.6.0", - "objc2-foundation 0.3.0", -] - -[[package]] -name = "objc2-security" -version = "0.3.0" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "3126341c65c5d5728423ae95d788e1b660756486ad0592307ab87ba02d9a7268" -dependencies = [ - "bitflags 2.7.0", - "objc2 0.6.0", - "objc2-core-foundation", -] - [[package]] name = "objc2-ui-kit" version = "0.3.0" @@ -5259,7 +5185,6 @@ dependencies = [ "objc2-app-kit", "objc2-core-foundation", "objc2-foundation 0.3.0", - "objc2-security", ] [[package]] @@ -8044,7 +7969,7 @@ dependencies = [ "log", "objc2 0.5.2", "objc2-foundation 0.2.2", - "objc2-quartz-core 0.2.2", + "objc2-quartz-core", "raw-window-handle", "redox_syscall", "wasm-bindgen", @@ -8905,7 +8830,6 @@ dependencies = [ "log", "objc2 0.6.0", "objc2-app-kit", - "objc2-foundation 0.3.0", "once_cell", "percent-encoding", "raw-window-handle", diff --git a/crates/tauri-runtime-wry/Cargo.toml b/crates/tauri-runtime-wry/Cargo.toml index c0e73af1e5bc..091d57b4fc25 100644 --- a/crates/tauri-runtime-wry/Cargo.toml +++ b/crates/tauri-runtime-wry/Cargo.toml @@ -46,8 +46,7 @@ percent-encoding = "2" objc2 = "0.6" [target.'cfg(target_os = "macos")'.dependencies] -objc2-foundation = { version = "0.3", features = [] } -objc2-app-kit = { version = "0.3", features = [ +objc2-app-kit = { version = "0.3", default-features = false, features = [ "block2", "NSApplication", "NSResponder", diff --git a/crates/tauri-runtime-wry/src/window/macos.rs b/crates/tauri-runtime-wry/src/window/macos.rs index e0bd82ef9490..6bb16ce3e5f1 100644 --- a/crates/tauri-runtime-wry/src/window/macos.rs +++ b/crates/tauri-runtime-wry/src/window/macos.rs @@ -2,8 +2,8 @@ // SPDX-License-Identifier: Apache-2.0 // SPDX-License-Identifier: MIT +use objc2::MainThreadMarker; use objc2_app_kit::{NSBackingStoreType, NSWindow, NSWindowStyleMask}; -use objc2_foundation::MainThreadMarker; use tao::platform::macos::WindowExtMacOS; impl super::WindowExt for tao::window::Window { diff --git a/crates/tauri-runtime/Cargo.toml b/crates/tauri-runtime/Cargo.toml index bab5dc7533cd..014d59b2fa2e 100644 --- a/crates/tauri-runtime/Cargo.toml +++ b/crates/tauri-runtime/Cargo.toml @@ -59,7 +59,11 @@ objc2-ui-kit = { version = "0.3.0", default-features = false, features = [ [target."cfg(target_os = \"macos\")".dependencies] url = "2" objc2 = "0.6" -objc2-web-kit = { version = "0.3", features = ["objc2-app-kit", "WKWebView"] } +objc2-web-kit = { version = "0.3", default-features = false, features = [ + "objc2-app-kit", + "WKWebView", + "WKWebViewConfiguration", +] } [features] devtools = [] diff --git a/crates/tauri/Cargo.toml b/crates/tauri/Cargo.toml index 7f0ed98cdc27..0e71e5c35900 100644 --- a/crates/tauri/Cargo.toml +++ b/crates/tauri/Cargo.toml @@ -121,9 +121,10 @@ objc2-app-kit = { version = "0.3", default-features = false, features = [ "NSWindow", "NSImage", ] } -objc2-web-kit = { version = "0.3", features = [ +objc2-web-kit = { version = "0.3", default-features = false, features = [ "objc2-app-kit", "WKWebView", + "WKWebViewConfiguration", "WKUserContentController", ] } window-vibrancy = "0.6" diff --git a/crates/tauri/src/app.rs b/crates/tauri/src/app.rs index e53f22675245..e8e5343d9abf 100644 --- a/crates/tauri/src/app.rs +++ b/crates/tauri/src/app.rs @@ -2414,9 +2414,9 @@ fn on_event_loop_event( // set the app icon in development #[cfg(all(dev, target_os = "macos"))] { - use objc2::AllocAnyThread; + use objc2::{AllocAnyThread, MainThreadMarker}; use objc2_app_kit::{NSApplication, NSImage}; - use objc2_foundation::{MainThreadMarker, NSData}; + use objc2_foundation::NSData; if let Some(icon) = app_handle.manager.app_icon.clone() { // TODO: Enable this check. diff --git a/crates/tauri/src/webview/webview_window.rs b/crates/tauri/src/webview/webview_window.rs index 290730067f5d..ca84e83b2426 100644 --- a/crates/tauri/src/webview/webview_window.rs +++ b/crates/tauri/src/webview/webview_window.rs @@ -1248,7 +1248,7 @@ impl> WebviewWindowBuilder<'_, R, M> { /// #[cfg(target_os = "ios")] /// { /// window_builder = window_builder.with_input_accessory_view_builder(|_webview| unsafe { - /// let mtm = objc2_foundation::MainThreadMarker::new_unchecked(); + /// let mtm = objc2::MainThreadMarker::new_unchecked(); /// let button = objc2_ui_kit::UIButton::buttonWithType(objc2_ui_kit::UIButtonType(1), mtm); /// button.setTitle_forState( /// Some(&objc2_foundation::NSString::from_str("Tauri")), From a2af293ecba50057b6873467f0236474507566ec Mon Sep 17 00:00:00 2001 From: "dependabot[bot]" <49699333+dependabot[bot]@users.noreply.github.com> Date: Fri, 20 Feb 2026 19:39:52 +0800 Subject: [PATCH 15/95] chore(deps): bump keccak from 0.1.5 to 0.1.6 (#14972) Bumps [keccak](https://github.com/RustCrypto/sponges) from 0.1.5 to 0.1.6. - [Commits](https://github.com/RustCrypto/sponges/compare/keccak-v0.1.5...keccak-v0.1.6) --- updated-dependencies: - dependency-name: keccak dependency-version: 0.1.6 dependency-type: indirect ... Signed-off-by: dependabot[bot] Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com> --- Cargo.lock | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/Cargo.lock b/Cargo.lock index 9b92b2d867b4..0166651d0884 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -4175,9 +4175,9 @@ dependencies = [ [[package]] name = "keccak" -version = "0.1.5" +version = "0.1.6" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "ecc2af9a1119c51f12a14607e783cb977bde58bc069ff0c3da1095e635d70654" +checksum = "cb26cec98cce3a3d96cbb7bced3c4b16e3d13f27ec56dbd62cbc8f39cfb9d653" dependencies = [ "cpufeatures", ] From 1e26226aecdf4988b8e351c7c58c7ea8854e3b20 Mon Sep 17 00:00:00 2001 From: "renovate[bot]" <29139614+renovate[bot]@users.noreply.github.com> Date: Fri, 20 Feb 2026 20:58:41 +0800 Subject: [PATCH 16/95] chore(deps): update eslint monorepo to v10 (major) (#14922) * chore(deps): update eslint monorepo to v10 * Update typescript-eslint and plugin security --- packages/api/package.json | 8 +- pnpm-lock.yaml | 486 ++++++++++++++++---------------------- 2 files changed, 203 insertions(+), 291 deletions(-) diff --git a/packages/api/package.json b/packages/api/package.json index dc45c4bafa18..17ab8fe525ac 100644 --- a/packages/api/package.json +++ b/packages/api/package.json @@ -45,19 +45,19 @@ "eslint:fix": "eslint src/**/*.ts --fix" }, "devDependencies": { - "@eslint/js": "^9.29.0", + "@eslint/js": "^10.0.0", "@rollup/plugin-terser": "0.4.4", "@rollup/plugin-typescript": "12.3.0", "@types/eslint": "^9.6.1", "@types/node": "^24.0.0", - "eslint": "^9.29.0", + "eslint": "^10.0.0", "eslint-config-prettier": "10.1.8", - "eslint-plugin-security": "3.0.1", + "eslint-plugin-security": "4.0.0", "fast-glob": "3.3.3", "globals": "^17.0.0", "rollup": "4.57.1", "tslib": "^2.8.1", "typescript": "^5.8.3", - "typescript-eslint": "^8.34.1" + "typescript-eslint": "^8.56.0" } } diff --git a/pnpm-lock.yaml b/pnpm-lock.yaml index 603eb41f6646..c97ae8574358 100644 --- a/pnpm-lock.yaml +++ b/pnpm-lock.yaml @@ -59,8 +59,8 @@ importers: packages/api: devDependencies: '@eslint/js': - specifier: ^9.29.0 - version: 9.29.0 + specifier: ^10.0.0 + version: 10.0.1(eslint@10.0.0(jiti@2.4.2)) '@rollup/plugin-terser': specifier: 0.4.4 version: 0.4.4(rollup@4.57.1) @@ -74,14 +74,14 @@ importers: specifier: ^24.0.0 version: 24.10.0 eslint: - specifier: ^9.29.0 - version: 9.29.0(jiti@2.4.2) + specifier: ^10.0.0 + version: 10.0.0(jiti@2.4.2) eslint-config-prettier: specifier: 10.1.8 - version: 10.1.8(eslint@9.29.0(jiti@2.4.2)) + version: 10.1.8(eslint@10.0.0(jiti@2.4.2)) eslint-plugin-security: - specifier: 3.0.1 - version: 3.0.1 + specifier: 4.0.0 + version: 4.0.0 fast-glob: specifier: 3.3.3 version: 3.3.3 @@ -98,8 +98,8 @@ importers: specifier: ^5.8.3 version: 5.8.3 typescript-eslint: - specifier: ^8.34.1 - version: 8.34.1(eslint@9.29.0(jiti@2.4.2))(typescript@5.8.3) + specifier: ^8.56.0 + version: 8.56.0(eslint@10.0.0(jiti@2.4.2))(typescript@5.8.3) packages/cli: devDependencies: @@ -510,47 +510,44 @@ packages: cpu: [x64] os: [win32] - '@eslint-community/eslint-utils@4.7.0': - resolution: {integrity: sha512-dyybb3AcajC7uha6CvhdVRJqaKyn7w2YKqKyAN37NKYgZT36w+iRb0Dymmc5qEJ549c/S31cMMSFd75bteCpCw==} + '@eslint-community/eslint-utils@4.9.1': + resolution: {integrity: sha512-phrYmNiYppR7znFEdqgfWHXR6NCkZEK7hwWDHZUjit/2/U0r6XvkDl0SYnoM51Hq7FhCGdLDT6zxCCOY1hexsQ==} engines: {node: ^12.22.0 || ^14.17.0 || >=16.0.0} peerDependencies: eslint: ^6.0.0 || ^7.0.0 || >=8.0.0 - '@eslint-community/regexpp@4.12.1': - resolution: {integrity: sha512-CCZCDJuduB9OUkFkY2IgppNZMi2lBQgD2qzwXkEia16cge2pijY/aXi96CJMquDMn3nJdlPV1A5KrJEXwfLNzQ==} + '@eslint-community/regexpp@4.12.2': + resolution: {integrity: sha512-EriSTlt5OC9/7SXkRSCAhfSxxoSUgBm33OH+IkwbdpgoqsSsUg7y3uh+IICI/Qg4BBWr3U2i39RpmycbxMq4ew==} engines: {node: ^12.0.0 || ^14.0.0 || >=16.0.0} - '@eslint/config-array@0.20.1': - resolution: {integrity: sha512-OL0RJzC/CBzli0DrrR31qzj6d6i6Mm3HByuhflhl4LOBiWxN+3i6/t/ZQQNii4tjksXi8r2CRW1wMpWA2ULUEw==} - engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0} + '@eslint/config-array@0.23.1': + resolution: {integrity: sha512-uVSdg/V4dfQmTjJzR0szNczjOH/J+FyUMMjYtr07xFRXR7EDf9i1qdxrD0VusZH9knj1/ecxzCQQxyic5NzAiA==} + engines: {node: ^20.19.0 || ^22.13.0 || >=24} - '@eslint/config-helpers@0.2.3': - resolution: {integrity: sha512-u180qk2Um1le4yf0ruXH3PYFeEZeYC3p/4wCTKrr2U1CmGdzGi3KtY0nuPDH48UJxlKCC5RDzbcbh4X0XlqgHg==} - engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0} + '@eslint/config-helpers@0.5.2': + resolution: {integrity: sha512-a5MxrdDXEvqnIq+LisyCX6tQMPF/dSJpCfBgBauY+pNZ28yCtSsTvyTYrMhaI+LK26bVyCJfJkT0u8KIj2i1dQ==} + engines: {node: ^20.19.0 || ^22.13.0 || >=24} - '@eslint/core@0.14.0': - resolution: {integrity: sha512-qIbV0/JZr7iSDjqAc60IqbLdsj9GDt16xQtWD+B78d/HAlvysGdZZ6rpJHGAc2T0FQx1X6thsSPdnoiGKdNtdg==} - engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0} - - '@eslint/core@0.15.1': - resolution: {integrity: sha512-bkOp+iumZCCbt1K1CmWf0R9pM5yKpDv+ZXtvSyQpudrI9kuFLp+bM2WOPXImuD/ceQuaa8f5pj93Y7zyECIGNA==} - engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0} + '@eslint/core@1.1.0': + resolution: {integrity: sha512-/nr9K9wkr3P1EzFTdFdMoLuo1PmIxjmwvPozwoSodjNBdefGujXQUF93u1DDZpEaTuDvMsIQddsd35BwtrW9Xw==} + engines: {node: ^20.19.0 || ^22.13.0 || >=24} - '@eslint/eslintrc@3.3.1': - resolution: {integrity: sha512-gtF186CXhIl1p4pJNGZw8Yc6RlshoePRvE0X91oPGb3vZ8pM3qOS9W9NGPat9LziaBV7XrJWGylNQXkGcnM3IQ==} - engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0} - - '@eslint/js@9.29.0': - resolution: {integrity: sha512-3PIF4cBw/y+1u2EazflInpV+lYsSG0aByVIQzAgb1m1MhHFSbqTyNqtBKHgWf/9Ykud+DhILS9EGkmekVhbKoQ==} - engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0} + '@eslint/js@10.0.1': + resolution: {integrity: sha512-zeR9k5pd4gxjZ0abRoIaxdc7I3nDktoXZk2qOv9gCNWx3mVwEn32VRhyLaRsDiJjTs0xq/T8mfPtyuXu7GWBcA==} + engines: {node: ^20.19.0 || ^22.13.0 || >=24} + peerDependencies: + eslint: ^10.0.0 + peerDependenciesMeta: + eslint: + optional: true - '@eslint/object-schema@2.1.6': - resolution: {integrity: sha512-RBMg5FRL0I0gs51M/guSAj5/e14VQ4tpZnQNWwuDT66P14I43ItmPfIZRhO9fUVIPOAQXU47atlywZ/czoqFPA==} - engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0} + '@eslint/object-schema@3.0.1': + resolution: {integrity: sha512-P9cq2dpr+LU8j3qbLygLcSZrl2/ds/pUpfnHNNuk5HW7mnngHs+6WSq5C9mO3rqRX8A1poxqLTC9cu0KOyJlBg==} + engines: {node: ^20.19.0 || ^22.13.0 || >=24} - '@eslint/plugin-kit@0.3.4': - resolution: {integrity: sha512-Ul5l+lHEcw3L5+k8POx6r74mxEYKG5kOb6Xpy2gCRW6zweT6TEhAf8vhxGgjhqrd/VO/Dirhsb+1hNpD1ue9hw==} - engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0} + '@eslint/plugin-kit@0.6.0': + resolution: {integrity: sha512-bIZEUzOI1jkhviX2cp5vNyXQc6olzb2ohewQubuYlMXZ2Q/XjBO0x0XhGPvc9fjSIiUN0vw+0hq53BJ4eQSJKQ==} + engines: {node: ^20.19.0 || ^22.13.0 || >=24} '@humanfs/core@0.19.1': resolution: {integrity: sha512-5DyQ4+1JEUzejeK1JGICcideyfUbGixgS9jNgex5nqkW+cY7WZhxBigmieN5Qnw9ZosSNVC9KQKyb+GUaGyKUA==} @@ -1485,6 +1482,9 @@ packages: '@types/eslint@9.6.1': resolution: {integrity: sha512-FXx2pKgId/WyYo2jXw63kk7/+TY7u7AziEJxJAnSFzHlqTAS3Ync6SvgYAN/k4/PQpnnVuzoMuVnByKK2qp0ag==} + '@types/esrecurse@4.3.1': + resolution: {integrity: sha512-xJBAbDifo5hpffDBuHl0Y8ywswbiAp/Wi7Y/GtAgSlZyIABppyurxVueOPE8LUQOxdlgi6Zqce7uoEpqNTeiUw==} + '@types/estree@1.0.8': resolution: {integrity: sha512-dWHzHa2WqEXI/O1E9OjrocMTKJl2mSrEolh1Iomrv6U+JuNwaHXsXx9bLu5gG7BUWFIN0skIQJQ/L1rIex4X6w==} @@ -1494,63 +1494,63 @@ packages: '@types/node@24.10.0': resolution: {integrity: sha512-qzQZRBqkFsYyaSWXuEHc2WR9c0a0CXwiE5FWUvn7ZM+vdy1uZLfCunD38UzhuB7YN/J11ndbDBcTmOdxJo9Q7A==} - '@typescript-eslint/eslint-plugin@8.34.1': - resolution: {integrity: sha512-STXcN6ebF6li4PxwNeFnqF8/2BNDvBupf2OPx2yWNzr6mKNGF7q49VM00Pz5FaomJyqvbXpY6PhO+T9w139YEQ==} + '@typescript-eslint/eslint-plugin@8.56.0': + resolution: {integrity: sha512-lRyPDLzNCuae71A3t9NEINBiTn7swyOhvUj3MyUOxb8x6g6vPEFoOU+ZRmGMusNC3X3YMhqMIX7i8ShqhT74Pw==} engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0} peerDependencies: - '@typescript-eslint/parser': ^8.34.1 - eslint: ^8.57.0 || ^9.0.0 - typescript: '>=4.8.4 <5.9.0' + '@typescript-eslint/parser': ^8.56.0 + eslint: ^8.57.0 || ^9.0.0 || ^10.0.0 + typescript: '>=4.8.4 <6.0.0' - '@typescript-eslint/parser@8.34.1': - resolution: {integrity: sha512-4O3idHxhyzjClSMJ0a29AcoK0+YwnEqzI6oz3vlRf3xw0zbzt15MzXwItOlnr5nIth6zlY2RENLsOPvhyrKAQA==} + '@typescript-eslint/parser@8.56.0': + resolution: {integrity: sha512-IgSWvLobTDOjnaxAfDTIHaECbkNlAlKv2j5SjpB2v7QHKv1FIfjwMy8FsDbVfDX/KjmCmYICcw7uGaXLhtsLNg==} engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0} peerDependencies: - eslint: ^8.57.0 || ^9.0.0 - typescript: '>=4.8.4 <5.9.0' + eslint: ^8.57.0 || ^9.0.0 || ^10.0.0 + typescript: '>=4.8.4 <6.0.0' - '@typescript-eslint/project-service@8.34.1': - resolution: {integrity: sha512-nuHlOmFZfuRwLJKDGQOVc0xnQrAmuq1Mj/ISou5044y1ajGNp2BNliIqp7F2LPQ5sForz8lempMFCovfeS1XoA==} + '@typescript-eslint/project-service@8.56.0': + resolution: {integrity: sha512-M3rnyL1vIQOMeWxTWIW096/TtVP+8W3p/XnaFflhmcFp+U4zlxUxWj4XwNs6HbDeTtN4yun0GNTTDBw/SvufKg==} engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0} peerDependencies: - typescript: '>=4.8.4 <5.9.0' + typescript: '>=4.8.4 <6.0.0' - '@typescript-eslint/scope-manager@8.34.1': - resolution: {integrity: sha512-beu6o6QY4hJAgL1E8RaXNC071G4Kso2MGmJskCFQhRhg8VOH/FDbC8soP8NHN7e/Hdphwp8G8cE6OBzC8o41ZA==} + '@typescript-eslint/scope-manager@8.56.0': + resolution: {integrity: sha512-7UiO/XwMHquH+ZzfVCfUNkIXlp/yQjjnlYUyYz7pfvlK3/EyyN6BK+emDmGNyQLBtLGaYrTAI6KOw8tFucWL2w==} engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0} - '@typescript-eslint/tsconfig-utils@8.34.1': - resolution: {integrity: sha512-K4Sjdo4/xF9NEeA2khOb7Y5nY6NSXBnod87uniVYW9kHP+hNlDV8trUSFeynA2uxWam4gIWgWoygPrv9VMWrYg==} + '@typescript-eslint/tsconfig-utils@8.56.0': + resolution: {integrity: sha512-bSJoIIt4o3lKXD3xmDh9chZcjCz5Lk8xS7Rxn+6l5/pKrDpkCwtQNQQwZ2qRPk7TkUYhrq3WPIHXOXlbXP0itg==} engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0} peerDependencies: - typescript: '>=4.8.4 <5.9.0' + typescript: '>=4.8.4 <6.0.0' - '@typescript-eslint/type-utils@8.34.1': - resolution: {integrity: sha512-Tv7tCCr6e5m8hP4+xFugcrwTOucB8lshffJ6zf1mF1TbU67R+ntCc6DzLNKM+s/uzDyv8gLq7tufaAhIBYeV8g==} + '@typescript-eslint/type-utils@8.56.0': + resolution: {integrity: sha512-qX2L3HWOU2nuDs6GzglBeuFXviDODreS58tLY/BALPC7iu3Fa+J7EOTwnX9PdNBxUI7Uh0ntP0YWGnxCkXzmfA==} engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0} peerDependencies: - eslint: ^8.57.0 || ^9.0.0 - typescript: '>=4.8.4 <5.9.0' + eslint: ^8.57.0 || ^9.0.0 || ^10.0.0 + typescript: '>=4.8.4 <6.0.0' - '@typescript-eslint/types@8.34.1': - resolution: {integrity: sha512-rjLVbmE7HR18kDsjNIZQHxmv9RZwlgzavryL5Lnj2ujIRTeXlKtILHgRNmQ3j4daw7zd+mQgy+uyt6Zo6I0IGA==} + '@typescript-eslint/types@8.56.0': + resolution: {integrity: sha512-DBsLPs3GsWhX5HylbP9HNG15U0bnwut55Lx12bHB9MpXxQ+R5GC8MwQe+N1UFXxAeQDvEsEDY6ZYwX03K7Z6HQ==} engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0} - '@typescript-eslint/typescript-estree@8.34.1': - resolution: {integrity: sha512-rjCNqqYPuMUF5ODD+hWBNmOitjBWghkGKJg6hiCHzUvXRy6rK22Jd3rwbP2Xi+R7oYVvIKhokHVhH41BxPV5mA==} + '@typescript-eslint/typescript-estree@8.56.0': + resolution: {integrity: sha512-ex1nTUMWrseMltXUHmR2GAQ4d+WjkZCT4f+4bVsps8QEdh0vlBsaCokKTPlnqBFqqGaxilDNJG7b8dolW2m43Q==} engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0} peerDependencies: - typescript: '>=4.8.4 <5.9.0' + typescript: '>=4.8.4 <6.0.0' - '@typescript-eslint/utils@8.34.1': - resolution: {integrity: sha512-mqOwUdZ3KjtGk7xJJnLbHxTuWVn3GO2WZZuM+Slhkun4+qthLdXx32C8xIXbO1kfCECb3jIs3eoxK3eryk7aoQ==} + '@typescript-eslint/utils@8.56.0': + resolution: {integrity: sha512-RZ3Qsmi2nFGsS+n+kjLAYDPVlrzf7UhTffrDIKr+h2yzAlYP/y5ZulU0yeDEPItos2Ph46JAL5P/On3pe7kDIQ==} engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0} peerDependencies: - eslint: ^8.57.0 || ^9.0.0 - typescript: '>=4.8.4 <5.9.0' + eslint: ^8.57.0 || ^9.0.0 || ^10.0.0 + typescript: '>=4.8.4 <6.0.0' - '@typescript-eslint/visitor-keys@8.34.1': - resolution: {integrity: sha512-xoh5rJ+tgsRKoXnkBPFRLZ7rjKM0AfVbC68UZ/ECXoDbfggb9RbEySN359acY1vS3qZ0jVTVWzbtfapwm5ztxw==} + '@typescript-eslint/visitor-keys@8.56.0': + resolution: {integrity: sha512-q+SL+b+05Ud6LbEE35qe4A99P+htKTKVbyiNEe45eCbJFyh/HVK9QXwlrbz+Q4L8SOW4roxSVwXYj4DMBT7Ieg==} engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0} '@unocss/astro@66.3.3': @@ -1736,9 +1736,9 @@ packages: resolution: {integrity: sha512-qIj0G9wZbMGNLjLmg1PT6v2mE9AH2zlnADJD/2tC6E00hgmhUOfEB6greHPAfLRSufHqROIUTkw6E+M3lH0PTQ==} engines: {node: '>= 0.4'} - balanced-match@3.0.1: - resolution: {integrity: sha512-vjtV3hiLqYDNRoiAv0zC4QaGAMPomEoq83PRmYIofPswwZurCeWR5LByXm7SyoL0Zh5+2z0+HC7jG8gSZJUh0w==} - engines: {node: '>= 16'} + balanced-match@4.0.3: + resolution: {integrity: sha512-1pHv8LX9CpKut1Zp4EXey7Z8OfH11ONNH6Dhi2WDUt31VVZFXZzKwXcysBgqSumFCmR+0dqjMK5v5JiFHzi0+g==} + engines: {node: 20 || >=22} before-after-hook@4.0.0: resolution: {integrity: sha512-q6tR3RPqIB1pMiTRMFcZwuG5T8vwp+vUvEG0vuI6B+Rikh5BfPp2fQ82c925FOs+b0lcFQ8CFrL+KbilfZFhOQ==} @@ -1750,9 +1750,9 @@ packages: blake3-wasm@2.1.5: resolution: {integrity: sha512-F1+K8EbfOZE49dtoPtmxUQrpXaBIl3ICvasLh+nJta0xkz+9kF/7uet9fLnwKqhDrmj6g+6K3Tw9yQPUg2ka5g==} - brace-expansion@4.0.1: - resolution: {integrity: sha512-YClrbvTCXGe70pU2JiEiPLYXO9gQkyxYeKpJIQHVS/gOs6EWMQP2RYBwjFLNT322Ji8TOC3IMPfsYCedNpzKfA==} - engines: {node: '>= 18'} + brace-expansion@5.0.2: + resolution: {integrity: sha512-Pdk8c9poy+YhOgVWw1JNN22/HcivgKWwpxKq04M/jTmHyCZn12WPJebZxdjSa5TmBqISrUSgNYU3eRORljfCCw==} + engines: {node: 20 || >=22} braces@3.0.3: resolution: {integrity: sha512-yQbXgO/OSZVD2IsiLlro+7Hf6Q18EJrKSEsdoMzKePKXct3gvD8oLcOQdIzGupr5Fj+EDe8gO/lxc1BzfMpxvA==} @@ -1765,18 +1765,10 @@ packages: resolution: {integrity: sha512-b6Ilus+c3RrdDk+JhLKUAQfzzgLEPy6wcXqS7f/xe1EETvsDP6GORG7SFuOs6cID5YkqchW/LXZbX5bc8j7ZcQ==} engines: {node: '>=8'} - callsites@3.1.0: - resolution: {integrity: sha512-P8BjAsXvZS+VIDUI11hHCQEv74YT67YUi5JJFNWIqL235sBmjX4+qx9Muvls5ivyNENctx46xQLQ3aTuE7ssaQ==} - engines: {node: '>=6'} - chai@6.2.0: resolution: {integrity: sha512-aUTnJc/JipRzJrNADXVvpVqi6CO0dn3nx4EVPxijri+fj3LUUDyZQOgVeW54Ob3Y1Xh9Iz8f+CgaCl8v0mn9bA==} engines: {node: '>=18'} - chalk@4.1.2: - resolution: {integrity: sha512-oKnbhFyRIXpUuez8iBMmyEa4nbj4IOQyuhc/wy9kY7/WVPcwIO9VA668Pu8RkO7+0G76SLROeyw9CpQ061i4mA==} - engines: {node: '>=10'} - chardet@2.1.1: resolution: {integrity: sha512-PsezH1rqdV9VvyNhxxOW32/d75r01NY7TQCmOqomRo15ZSOKbpTFVsfjghxo6JloQUCGnH4k1LGu0R4yCLlWQQ==} @@ -1913,25 +1905,25 @@ packages: peerDependencies: eslint: '>=7.0.0' - eslint-plugin-security@3.0.1: - resolution: {integrity: sha512-XjVGBhtDZJfyuhIxnQ/WMm385RbX3DBu7H1J7HNNhmB2tnGxMeqVSnYv79oAj992ayvIBZghsymwkYFS6cGH4Q==} + eslint-plugin-security@4.0.0: + resolution: {integrity: sha512-tfuQT8K/Li1ZxhFzyD8wPIKtlzZxqBcPr9q0jFMQ77wWAbKBVEhaMPVQRTMTvCMUDhwBe5vPVqQPwAGk/ASfxQ==} engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0} - eslint-scope@8.4.0: - resolution: {integrity: sha512-sNXOfKCn74rt8RICKMvJS7XKV/Xk9kA7DyJr8mJik3S7Cwgy3qlkkmyS2uQB3jiJg6VNdZd/pDBJu0nvG2NlTg==} - engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0} + eslint-scope@9.1.0: + resolution: {integrity: sha512-CkWE42hOJsNj9FJRaoMX9waUFYhqY4jmyLFdAdzZr6VaCg3ynLYx4WnOdkaIifGfH4gsUcBTn4OZbHXkpLD0FQ==} + engines: {node: ^20.19.0 || ^22.13.0 || >=24} eslint-visitor-keys@3.4.3: resolution: {integrity: sha512-wpc+LXeiyiisxPlEkUzU6svyS1frIO3Mgxj1fdy7Pm8Ygzguax2N3Fa/D/ag1WqbOprdI+uY6wMUl8/a2G+iag==} engines: {node: ^12.22.0 || ^14.17.0 || >=16.0.0} - eslint-visitor-keys@4.2.1: - resolution: {integrity: sha512-Uhdk5sfqcee/9H/rCOJikYz67o0a2Tw2hGRPOG2Y1R2dg7brRe1uG0yaNQDHu+TO/uQPF/5eCapvYSmHUjt7JQ==} - engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0} + eslint-visitor-keys@5.0.0: + resolution: {integrity: sha512-A0XeIi7CXU7nPlfHS9loMYEKxUaONu/hTEzHTGba9Huu94Cq1hPivf+DE5erJozZOky0LfvXAyrV/tcswpLI0Q==} + engines: {node: ^20.19.0 || ^22.13.0 || >=24} - eslint@9.29.0: - resolution: {integrity: sha512-GsGizj2Y1rCWDu6XoEekL3RLilp0voSePurjZIkxL3wlm5o5EC9VpgaP7lrCvjnkuLvzFBQWB3vWB3K5KQTveQ==} - engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0} + eslint@10.0.0: + resolution: {integrity: sha512-O0piBKY36YSJhlFSG8p9VUdPV/SxxS4FYDWVpr/9GJuMaepzwlf4J8I4ov1b+ySQfDTPhc3DtLaxcT1fN0yqCg==} + engines: {node: ^20.19.0 || ^22.13.0 || >=24} hasBin: true peerDependencies: jiti: '*' @@ -1942,12 +1934,12 @@ packages: esm-env@1.2.2: resolution: {integrity: sha512-Epxrv+Nr/CaL4ZcFGPJIYLWFom+YeV1DqMLHJoEd9SYRxNbaFruBwfEX/kkHUJf55j2+TUbmDcmuilbP1TmXHA==} - espree@10.4.0: - resolution: {integrity: sha512-j6PAQ2uUr79PZhBjP5C5fhl8e39FmRnOjsD5lGnWrFU8i2G776tBK7+nP8KuQUTTyAZUwfQqXAgrVH5MbH9CYQ==} - engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0} + espree@11.1.0: + resolution: {integrity: sha512-WFWYhO1fV4iYkqOOvq8FbqIhr2pYfoDY0kCotMkDeNtGpiGGkZ1iov2u8ydjtgM8yF8rzK7oaTbw2NAzbAbehw==} + engines: {node: ^20.19.0 || ^22.13.0 || >=24} - esquery@1.6.0: - resolution: {integrity: sha512-ca9pw9fomFcKPvFLXhBKUK90ZvGibiGOvRJNbjljY7s7uq/5YO4BOzcYtJqExdx99rF6aAcnRxHmcUHcz6sQsg==} + esquery@1.7.0: + resolution: {integrity: sha512-Ap6G0WQwcU/LHsvLwON1fAQX9Zp0A2Y6Y/cJBl9r/JbW90Zyg4/zbG6zzKa2OTALELarYHmKu0GhpM5EO+7T0g==} engines: {node: '>=0.10'} esrap@2.1.0: @@ -2041,10 +2033,6 @@ packages: resolution: {integrity: sha512-XxwI8EOhVQgWp6iDL+3b0r86f4d6AX6zSU55HfB4ydCEuXLXc5FcYeOu+nnGftS4TEju/11rt4KJPTMgbfmv4A==} engines: {node: '>=10.13.0'} - globals@14.0.0: - resolution: {integrity: sha512-oahGvuMGQlPw/ivIYBjVSrWAfWLBeku5tpPE2fOPLi+WHffIWbuh2tCjhyQhTBPMf5E9jDEH4FOmTYgYwbKwtQ==} - engines: {node: '>=18'} - globals@15.15.0: resolution: {integrity: sha512-7ACyT3wmyp3I61S4fG682L0VA2RGD9otkqGJIwNUMF1SWUombIIk+af1unuDYgMm082aHYwD+mzJvv9Iu8dsgg==} engines: {node: '>=18'} @@ -2053,17 +2041,10 @@ packages: resolution: {integrity: sha512-gv5BeD2EssA793rlFWVPMMCqefTlpusw6/2TbAVMy0FzcG8wKJn4O+NqJ4+XWmmwrayJgw5TzrmWjFgmz1XPqw==} engines: {node: '>=18'} - graphemer@1.4.0: - resolution: {integrity: sha512-EtKwoO6kxCL9WO5xipiHTZlSzBm7WLT627TqC/uVRd0HKmq8NXyebnNYxDoBi7wt8eTWrUrKXCOVaFq9x1kgag==} - gzip-size@6.0.0: resolution: {integrity: sha512-ax7ZYomf6jqPTQ4+XCpUGyXKHk5WweS+e05MBO4/y3WJ5RkmPXNKvX+bx1behVILVwr6JSQvZAku021CHPXG3Q==} engines: {node: '>=10'} - has-flag@4.0.0: - resolution: {integrity: sha512-EykJT/Q1KjTWctppgIAgfSO0tKVuZUjhgMr17kqTumMl6Afv3EISleU7qZUzoXDFTAHTDC4NOoG/ZxU3EvlMPQ==} - engines: {node: '>=8'} - hasown@2.0.2: resolution: {integrity: sha512-0hJU9SCPvmMzIBdZFqNPXWa6dqh7WdH0cII9y+CyS8rG3nL48Bclra9HmKhVVUHyPWNH5Y7xDwAB7bfgSjkUMQ==} engines: {node: '>= 0.4'} @@ -2080,10 +2061,6 @@ packages: resolution: {integrity: sha512-Hs59xBNfUIunMFgWAbGX5cq6893IbWg4KnrjbYwX3tx0ztorVgTDA6B2sxf8ejHJ4wz8BqGUMYlnzNBer5NvGg==} engines: {node: '>= 4'} - import-fresh@3.3.1: - resolution: {integrity: sha512-TR3KfrTZTYLPB6jUjfx6MF9WcWrHL9su5TObK4ZkYgBdWKPOFoSoQIdEuTuR82pmtxH2spWG9h6etwfr1pLBqQ==} - engines: {node: '>=6'} - imurmurhash@0.1.4: resolution: {integrity: sha512-JmXMZ6wuvDmLiHEml9ykzqO6lwFbof0GG4IkcGaENdCRDDmMVnny7s5HsIgHCbaq0w2MyPhDqkhTUgS2LU2PHA==} engines: {node: '>=0.8.19'} @@ -2160,9 +2137,6 @@ packages: resolution: {integrity: sha512-iPZK6eYjbxRu3uB4/WZ3EsEIMJFMqAoopl3R+zuq0UjcAm/MO6KCweDgPfP3elTztoKP3KtnVHxTn2NHBSDVUw==} engines: {node: '>=10'} - lodash.merge@4.6.2: - resolution: {integrity: sha512-0KpjqXRVvrYyCsX1swR/XTK0va6VQkQM6MNo7PqW77ByjAhoARA8EfrP1N4+KlKj8YS0ZUCtRT/YUuhyYDujIQ==} - magic-string@0.30.21: resolution: {integrity: sha512-vd2F4YUyEXKGcLHoq+TEyCjxueSeHnFxyyjNp80yg0XV4vUhnDer/lvvlqM/arB5bXQN5K2/3oinyCRyx8T2CQ==} @@ -2182,8 +2156,9 @@ packages: engines: {node: '>=18.0.0'} hasBin: true - minimatch@3.1.2: - resolution: {integrity: sha512-J7p63hRiAjw1NDEww1W7i37+ByIrOWO5XQQAzZ3VOcL0PNybwpfmV/N05zFAzwQ9USyEcX6t3UO+K5aqBQOIHw==} + minimatch@10.2.2: + resolution: {integrity: sha512-+G4CpNBxa5MprY+04MbgOw1v7So6n5JY166pFi9KfYwT78fxScCeSNQSNzp6dpPSW2rONOps6Ocam1wFhCgoVw==} + engines: {node: 18 || 20 || >=22} minimatch@9.0.5: resolution: {integrity: sha512-G6T0ZX48xgozx7587koeX9Ys2NYy6Gmv//P89sEte9V9whIapMNF4idKxnW2QtCcLiTWlb/wfCabAtAFWhhBow==} @@ -2236,10 +2211,6 @@ packages: package-manager-detector@1.3.0: resolution: {integrity: sha512-ZsEbbZORsyHuO00lY1kV3/t72yp6Ysay6Pd17ZAlNGuGwmWDLCJxFpRs0IzfXfj1o4icJOkUEioexFHzyPurSQ==} - parent-module@1.0.1: - resolution: {integrity: sha512-GQ2EWRpQV8/o+Aw8YqtfZZPfNRWZYkbidE9k5rpl/hC3vtHHBfGm2Ifi6qWV+coDGkrUKZAxE3Lot5kcsRlh+g==} - engines: {node: '>=6'} - path-exists@4.0.0: resolution: {integrity: sha512-ak9Qy5Q7jYb2Wwcey5Fpvg2KoAc/ZIhLSLOSBmRmygPsGwkVVt0fZa0qrtMz+m6tJTAHfZQ8FnmB4MG4LWy7/w==} engines: {node: '>=8'} @@ -2311,10 +2282,6 @@ packages: resolution: {integrity: sha512-iETxpjK6YoRWJG5o6hXLwvjYAoW+FEZn9os0PD/b6AP6xQwsa/Y7lCVgIixBbUPMfhu+i2LtdeAqVTgGlQarfA==} hasBin: true - resolve-from@4.0.0: - resolution: {integrity: sha512-pb/MYmXstAkysRFx8piNI1tGFNQIFA3vkE3Gq4EuA1dF6gHp/+vgZqsCGJapvy8N3Q+4o7FwvquPJcnZ7RYy4g==} - engines: {node: '>=4'} - resolve@1.22.10: resolution: {integrity: sha512-NPRy+/ncIMeDlTAsuqwKIiferiawhefFJtkNSW0qZJEqMEb+qBt/77B/jGeeek+F0uOeN05CDa6HXbbIgtVX4w==} engines: {node: '>= 0.4'} @@ -2400,18 +2367,10 @@ packages: resolution: {integrity: sha512-Y38VPSHcqkFrCpFnQ9vuSXmquuv5oXOKpGeT6aGrr3o3Gc9AlVa6JBfUSOCnbxGGZF+/0ooI7KrPuUSztUdU5A==} engines: {node: '>=8'} - strip-json-comments@3.1.1: - resolution: {integrity: sha512-6fPc+R4ihwqP6N/aIv2f1gMH8lOVtWQHoqC4yK6oSDVVocumAsfCqjkXnqiYMhmMwS/mEHLp7Vehlt3ql6lEig==} - engines: {node: '>=8'} - supports-color@10.2.2: resolution: {integrity: sha512-SS+jx45GF1QjgEXQx4NJZV9ImqmO2NPz5FNsIHrsDjh2YsHnawpan7SNQ1o8NuhrbHZy9AZhIoCUiCeaW/C80g==} engines: {node: '>=18'} - supports-color@7.2.0: - resolution: {integrity: sha512-qpCAvRl9stuOHveKsn7HncJRvv501qIacKzQlO/+Lwxc9+0q2wLyv4Dfvt80/DPn2pqOBsJdDiogXGR9+OvwRw==} - engines: {node: '>=8'} - supports-preserve-symlinks-flag@1.0.0: resolution: {integrity: sha512-ot0WnXS9fgdkgIcePe6RHNk1WA8+muPa6cSjeR3V8K27q9BB1rTE3R1p7Hv0z1ZyAc8s6Vvv8DIyWf681MAt0w==} engines: {node: '>= 0.4'} @@ -2450,8 +2409,8 @@ packages: resolution: {integrity: sha512-sf4i37nQ2LBx4m3wB74y+ubopq6W/dIzXg0FDGjsYnZHVa1Da8FH853wlL2gtUhg+xJXjfk3kUZS3BRoQeoQBQ==} engines: {node: '>=6'} - ts-api-utils@2.1.0: - resolution: {integrity: sha512-CUgTZL1irw8u29bzrOD/nH85jqyc74D6SshFgujOIA7osm2Rz7dYH77agkx7H4FBNxDq7Cjf+IjaX/8zwFW+ZQ==} + ts-api-utils@2.4.0: + resolution: {integrity: sha512-3TaVTaAv2gTiMB35i3FiGJaRfwb3Pyn/j3m/bfAvGe8FB7CF6u+LMYqYlDh7reQf7UNvoTvdfAqHGmPGOSsPmA==} engines: {node: '>=18.12'} peerDependencies: typescript: '>=4.8.4' @@ -2466,12 +2425,12 @@ packages: resolution: {integrity: sha512-XleUoc9uwGXqjWwXaUTZAmzMcFZ5858QA2vvx1Ur5xIcixXIP+8LnFDgRplU30us6teqdlskFfu+ae4K79Ooew==} engines: {node: '>= 0.8.0'} - typescript-eslint@8.34.1: - resolution: {integrity: sha512-XjS+b6Vg9oT1BaIUfkW3M3LvqZE++rbzAMEHuccCfO/YkP43ha6w3jTEMilQxMF92nVOYCcdjv1ZUhAa1D/0ow==} + typescript-eslint@8.56.0: + resolution: {integrity: sha512-c7toRLrotJ9oixgdW7liukZpsnq5CZ7PuKztubGYlNppuTqhIoWfhgHo/7EU0v06gS2l/x0i2NEFK1qMIf0rIg==} engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0} peerDependencies: - eslint: ^8.57.0 || ^9.0.0 - typescript: '>=4.8.4 <5.9.0' + eslint: ^8.57.0 || ^9.0.0 || ^10.0.0 + typescript: '>=4.8.4 <6.0.0' typescript@5.8.3: resolution: {integrity: sha512-p1diW6TqL9L07nNxvRMM7hMMw4c5XOo/1ibL4aAIGmSAt9slTE1Xgw5KWuof2uTOvCg9BY7ZRi+GaF+7sfgPeQ==} @@ -2898,52 +2857,38 @@ snapshots: '@esbuild/win32-x64@0.27.0': optional: true - '@eslint-community/eslint-utils@4.7.0(eslint@9.29.0(jiti@2.4.2))': + '@eslint-community/eslint-utils@4.9.1(eslint@10.0.0(jiti@2.4.2))': dependencies: - eslint: 9.29.0(jiti@2.4.2) + eslint: 10.0.0(jiti@2.4.2) eslint-visitor-keys: 3.4.3 - '@eslint-community/regexpp@4.12.1': {} + '@eslint-community/regexpp@4.12.2': {} - '@eslint/config-array@0.20.1': + '@eslint/config-array@0.23.1': dependencies: - '@eslint/object-schema': 2.1.6 + '@eslint/object-schema': 3.0.1 debug: 4.4.3 - minimatch: 3.1.2 + minimatch: 10.2.2 transitivePeerDependencies: - supports-color - '@eslint/config-helpers@0.2.3': {} - - '@eslint/core@0.14.0': + '@eslint/config-helpers@0.5.2': dependencies: - '@types/json-schema': 7.0.15 + '@eslint/core': 1.1.0 - '@eslint/core@0.15.1': + '@eslint/core@1.1.0': dependencies: '@types/json-schema': 7.0.15 - '@eslint/eslintrc@3.3.1': - dependencies: - ajv: 6.12.6 - debug: 4.4.3 - espree: 10.4.0 - globals: 14.0.0 - ignore: 5.3.2 - import-fresh: 3.3.1 - js-yaml: 4.1.1 - minimatch: 3.1.2 - strip-json-comments: 3.1.1 - transitivePeerDependencies: - - supports-color - - '@eslint/js@9.29.0': {} + '@eslint/js@10.0.1(eslint@10.0.0(jiti@2.4.2))': + optionalDependencies: + eslint: 10.0.0(jiti@2.4.2) - '@eslint/object-schema@2.1.6': {} + '@eslint/object-schema@3.0.1': {} - '@eslint/plugin-kit@0.3.4': + '@eslint/plugin-kit@0.6.0': dependencies: - '@eslint/core': 0.15.1 + '@eslint/core': 1.1.0 levn: 0.4.1 '@humanfs/core@0.19.1': {} @@ -3712,6 +3657,8 @@ snapshots: '@types/estree': 1.0.8 '@types/json-schema': 7.0.15 + '@types/esrecurse@4.3.1': {} + '@types/estree@1.0.8': {} '@types/json-schema@7.0.15': {} @@ -3720,97 +3667,96 @@ snapshots: dependencies: undici-types: 7.16.0 - '@typescript-eslint/eslint-plugin@8.34.1(@typescript-eslint/parser@8.34.1(eslint@9.29.0(jiti@2.4.2))(typescript@5.8.3))(eslint@9.29.0(jiti@2.4.2))(typescript@5.8.3)': + '@typescript-eslint/eslint-plugin@8.56.0(@typescript-eslint/parser@8.56.0(eslint@10.0.0(jiti@2.4.2))(typescript@5.8.3))(eslint@10.0.0(jiti@2.4.2))(typescript@5.8.3)': dependencies: - '@eslint-community/regexpp': 4.12.1 - '@typescript-eslint/parser': 8.34.1(eslint@9.29.0(jiti@2.4.2))(typescript@5.8.3) - '@typescript-eslint/scope-manager': 8.34.1 - '@typescript-eslint/type-utils': 8.34.1(eslint@9.29.0(jiti@2.4.2))(typescript@5.8.3) - '@typescript-eslint/utils': 8.34.1(eslint@9.29.0(jiti@2.4.2))(typescript@5.8.3) - '@typescript-eslint/visitor-keys': 8.34.1 - eslint: 9.29.0(jiti@2.4.2) - graphemer: 1.4.0 + '@eslint-community/regexpp': 4.12.2 + '@typescript-eslint/parser': 8.56.0(eslint@10.0.0(jiti@2.4.2))(typescript@5.8.3) + '@typescript-eslint/scope-manager': 8.56.0 + '@typescript-eslint/type-utils': 8.56.0(eslint@10.0.0(jiti@2.4.2))(typescript@5.8.3) + '@typescript-eslint/utils': 8.56.0(eslint@10.0.0(jiti@2.4.2))(typescript@5.8.3) + '@typescript-eslint/visitor-keys': 8.56.0 + eslint: 10.0.0(jiti@2.4.2) ignore: 7.0.5 natural-compare: 1.4.0 - ts-api-utils: 2.1.0(typescript@5.8.3) + ts-api-utils: 2.4.0(typescript@5.8.3) typescript: 5.8.3 transitivePeerDependencies: - supports-color - '@typescript-eslint/parser@8.34.1(eslint@9.29.0(jiti@2.4.2))(typescript@5.8.3)': + '@typescript-eslint/parser@8.56.0(eslint@10.0.0(jiti@2.4.2))(typescript@5.8.3)': dependencies: - '@typescript-eslint/scope-manager': 8.34.1 - '@typescript-eslint/types': 8.34.1 - '@typescript-eslint/typescript-estree': 8.34.1(typescript@5.8.3) - '@typescript-eslint/visitor-keys': 8.34.1 + '@typescript-eslint/scope-manager': 8.56.0 + '@typescript-eslint/types': 8.56.0 + '@typescript-eslint/typescript-estree': 8.56.0(typescript@5.8.3) + '@typescript-eslint/visitor-keys': 8.56.0 debug: 4.4.3 - eslint: 9.29.0(jiti@2.4.2) + eslint: 10.0.0(jiti@2.4.2) typescript: 5.8.3 transitivePeerDependencies: - supports-color - '@typescript-eslint/project-service@8.34.1(typescript@5.8.3)': + '@typescript-eslint/project-service@8.56.0(typescript@5.8.3)': dependencies: - '@typescript-eslint/tsconfig-utils': 8.34.1(typescript@5.8.3) - '@typescript-eslint/types': 8.34.1 + '@typescript-eslint/tsconfig-utils': 8.56.0(typescript@5.8.3) + '@typescript-eslint/types': 8.56.0 debug: 4.4.3 typescript: 5.8.3 transitivePeerDependencies: - supports-color - '@typescript-eslint/scope-manager@8.34.1': + '@typescript-eslint/scope-manager@8.56.0': dependencies: - '@typescript-eslint/types': 8.34.1 - '@typescript-eslint/visitor-keys': 8.34.1 + '@typescript-eslint/types': 8.56.0 + '@typescript-eslint/visitor-keys': 8.56.0 - '@typescript-eslint/tsconfig-utils@8.34.1(typescript@5.8.3)': + '@typescript-eslint/tsconfig-utils@8.56.0(typescript@5.8.3)': dependencies: typescript: 5.8.3 - '@typescript-eslint/type-utils@8.34.1(eslint@9.29.0(jiti@2.4.2))(typescript@5.8.3)': + '@typescript-eslint/type-utils@8.56.0(eslint@10.0.0(jiti@2.4.2))(typescript@5.8.3)': dependencies: - '@typescript-eslint/typescript-estree': 8.34.1(typescript@5.8.3) - '@typescript-eslint/utils': 8.34.1(eslint@9.29.0(jiti@2.4.2))(typescript@5.8.3) + '@typescript-eslint/types': 8.56.0 + '@typescript-eslint/typescript-estree': 8.56.0(typescript@5.8.3) + '@typescript-eslint/utils': 8.56.0(eslint@10.0.0(jiti@2.4.2))(typescript@5.8.3) debug: 4.4.3 - eslint: 9.29.0(jiti@2.4.2) - ts-api-utils: 2.1.0(typescript@5.8.3) + eslint: 10.0.0(jiti@2.4.2) + ts-api-utils: 2.4.0(typescript@5.8.3) typescript: 5.8.3 transitivePeerDependencies: - supports-color - '@typescript-eslint/types@8.34.1': {} + '@typescript-eslint/types@8.56.0': {} - '@typescript-eslint/typescript-estree@8.34.1(typescript@5.8.3)': + '@typescript-eslint/typescript-estree@8.56.0(typescript@5.8.3)': dependencies: - '@typescript-eslint/project-service': 8.34.1(typescript@5.8.3) - '@typescript-eslint/tsconfig-utils': 8.34.1(typescript@5.8.3) - '@typescript-eslint/types': 8.34.1 - '@typescript-eslint/visitor-keys': 8.34.1 + '@typescript-eslint/project-service': 8.56.0(typescript@5.8.3) + '@typescript-eslint/tsconfig-utils': 8.56.0(typescript@5.8.3) + '@typescript-eslint/types': 8.56.0 + '@typescript-eslint/visitor-keys': 8.56.0 debug: 4.4.3 - fast-glob: 3.3.3 - is-glob: 4.0.3 minimatch: 9.0.5 semver: 7.7.3 - ts-api-utils: 2.1.0(typescript@5.8.3) + tinyglobby: 0.2.15 + ts-api-utils: 2.4.0(typescript@5.8.3) typescript: 5.8.3 transitivePeerDependencies: - supports-color - '@typescript-eslint/utils@8.34.1(eslint@9.29.0(jiti@2.4.2))(typescript@5.8.3)': + '@typescript-eslint/utils@8.56.0(eslint@10.0.0(jiti@2.4.2))(typescript@5.8.3)': dependencies: - '@eslint-community/eslint-utils': 4.7.0(eslint@9.29.0(jiti@2.4.2)) - '@typescript-eslint/scope-manager': 8.34.1 - '@typescript-eslint/types': 8.34.1 - '@typescript-eslint/typescript-estree': 8.34.1(typescript@5.8.3) - eslint: 9.29.0(jiti@2.4.2) + '@eslint-community/eslint-utils': 4.9.1(eslint@10.0.0(jiti@2.4.2)) + '@typescript-eslint/scope-manager': 8.56.0 + '@typescript-eslint/types': 8.56.0 + '@typescript-eslint/typescript-estree': 8.56.0(typescript@5.8.3) + eslint: 10.0.0(jiti@2.4.2) typescript: 5.8.3 transitivePeerDependencies: - supports-color - '@typescript-eslint/visitor-keys@8.34.1': + '@typescript-eslint/visitor-keys@8.56.0': dependencies: - '@typescript-eslint/types': 8.34.1 - eslint-visitor-keys: 4.2.1 + '@typescript-eslint/types': 8.56.0 + eslint-visitor-keys: 5.0.0 '@unocss/astro@66.3.3(vite@7.1.11(@types/node@24.10.0)(jiti@2.4.2)(terser@5.43.1))(vue@3.5.17(typescript@5.8.3))': dependencies: @@ -4089,7 +4035,7 @@ snapshots: axobject-query@4.1.0: {} - balanced-match@3.0.1: {} + balanced-match@4.0.3: {} before-after-hook@4.0.0: {} @@ -4097,9 +4043,9 @@ snapshots: blake3-wasm@2.1.5: {} - brace-expansion@4.0.1: + brace-expansion@5.0.2: dependencies: - balanced-match: 3.0.1 + balanced-match: 4.0.3 braces@3.0.3: dependencies: @@ -4109,15 +4055,8 @@ snapshots: cac@6.7.14: {} - callsites@3.1.0: {} - chai@6.2.0: {} - chalk@4.1.2: - dependencies: - ansi-styles: 4.3.0 - supports-color: 7.2.0 - chardet@2.1.1: {} chokidar@3.6.0: @@ -4263,47 +4202,45 @@ snapshots: escape-string-regexp@4.0.0: {} - eslint-config-prettier@10.1.8(eslint@9.29.0(jiti@2.4.2)): + eslint-config-prettier@10.1.8(eslint@10.0.0(jiti@2.4.2)): dependencies: - eslint: 9.29.0(jiti@2.4.2) + eslint: 10.0.0(jiti@2.4.2) - eslint-plugin-security@3.0.1: + eslint-plugin-security@4.0.0: dependencies: safe-regex: 2.1.1 - eslint-scope@8.4.0: + eslint-scope@9.1.0: dependencies: + '@types/esrecurse': 4.3.1 + '@types/estree': 1.0.8 esrecurse: 4.3.0 estraverse: 5.3.0 eslint-visitor-keys@3.4.3: {} - eslint-visitor-keys@4.2.1: {} + eslint-visitor-keys@5.0.0: {} - eslint@9.29.0(jiti@2.4.2): + eslint@10.0.0(jiti@2.4.2): dependencies: - '@eslint-community/eslint-utils': 4.7.0(eslint@9.29.0(jiti@2.4.2)) - '@eslint-community/regexpp': 4.12.1 - '@eslint/config-array': 0.20.1 - '@eslint/config-helpers': 0.2.3 - '@eslint/core': 0.14.0 - '@eslint/eslintrc': 3.3.1 - '@eslint/js': 9.29.0 - '@eslint/plugin-kit': 0.3.4 + '@eslint-community/eslint-utils': 4.9.1(eslint@10.0.0(jiti@2.4.2)) + '@eslint-community/regexpp': 4.12.2 + '@eslint/config-array': 0.23.1 + '@eslint/config-helpers': 0.5.2 + '@eslint/core': 1.1.0 + '@eslint/plugin-kit': 0.6.0 '@humanfs/node': 0.16.6 '@humanwhocodes/module-importer': 1.0.1 '@humanwhocodes/retry': 0.4.3 '@types/estree': 1.0.8 - '@types/json-schema': 7.0.15 ajv: 6.12.6 - chalk: 4.1.2 cross-spawn: 7.0.6 debug: 4.4.3 escape-string-regexp: 4.0.0 - eslint-scope: 8.4.0 - eslint-visitor-keys: 4.2.1 - espree: 10.4.0 - esquery: 1.6.0 + eslint-scope: 9.1.0 + eslint-visitor-keys: 5.0.0 + espree: 11.1.0 + esquery: 1.7.0 esutils: 2.0.3 fast-deep-equal: 3.1.3 file-entry-cache: 8.0.0 @@ -4313,8 +4250,7 @@ snapshots: imurmurhash: 0.1.4 is-glob: 4.0.3 json-stable-stringify-without-jsonify: 1.0.1 - lodash.merge: 4.6.2 - minimatch: 3.1.2 + minimatch: 10.2.2 natural-compare: 1.4.0 optionator: 0.9.4 optionalDependencies: @@ -4324,13 +4260,13 @@ snapshots: esm-env@1.2.2: {} - espree@10.4.0: + espree@11.1.0: dependencies: acorn: 8.15.0 acorn-jsx: 5.3.2(acorn@8.15.0) - eslint-visitor-keys: 4.2.1 + eslint-visitor-keys: 5.0.0 - esquery@1.6.0: + esquery@1.7.0: dependencies: estraverse: 5.3.0 @@ -4413,20 +4349,14 @@ snapshots: dependencies: is-glob: 4.0.3 - globals@14.0.0: {} - globals@15.15.0: {} globals@17.0.0: {} - graphemer@1.4.0: {} - gzip-size@6.0.0: dependencies: duplexer: 0.1.2 - has-flag@4.0.0: {} - hasown@2.0.2: dependencies: function-bind: 1.1.2 @@ -4439,11 +4369,6 @@ snapshots: ignore@7.0.5: {} - import-fresh@3.3.1: - dependencies: - parent-module: 1.0.1 - resolve-from: 4.0.0 - imurmurhash@0.1.4: {} is-binary-path@2.1.0: @@ -4507,8 +4432,6 @@ snapshots: dependencies: p-locate: 5.0.0 - lodash.merge@4.6.2: {} - magic-string@0.30.21: dependencies: '@jridgewell/sourcemap-codec': 1.5.5 @@ -4534,13 +4457,13 @@ snapshots: - bufferutil - utf-8-validate - minimatch@3.1.2: + minimatch@10.2.2: dependencies: - brace-expansion: 4.0.1 + brace-expansion: 5.0.2 minimatch@9.0.5: dependencies: - brace-expansion: 4.0.1 + brace-expansion: 5.0.2 mlly@1.7.4: dependencies: @@ -4588,10 +4511,6 @@ snapshots: package-manager-detector@1.3.0: {} - parent-module@1.0.1: - dependencies: - callsites: 3.1.0 - path-exists@4.0.0: {} path-key@3.1.1: {} @@ -4648,8 +4567,6 @@ snapshots: regexp-tree@0.1.27: {} - resolve-from@4.0.0: {} - resolve@1.22.10: dependencies: is-core-module: 2.16.1 @@ -4779,14 +4696,8 @@ snapshots: dependencies: ansi-regex: 5.0.1 - strip-json-comments@3.1.1: {} - supports-color@10.2.2: {} - supports-color@7.2.0: - dependencies: - has-flag: 4.0.0 - supports-preserve-symlinks-flag@1.0.0: {} svelte@5.35.6: @@ -4832,7 +4743,7 @@ snapshots: totalist@3.0.1: {} - ts-api-utils@2.1.0(typescript@5.8.3): + ts-api-utils@2.4.0(typescript@5.8.3): dependencies: typescript: 5.8.3 @@ -4844,12 +4755,13 @@ snapshots: dependencies: prelude-ls: 1.2.1 - typescript-eslint@8.34.1(eslint@9.29.0(jiti@2.4.2))(typescript@5.8.3): + typescript-eslint@8.56.0(eslint@10.0.0(jiti@2.4.2))(typescript@5.8.3): dependencies: - '@typescript-eslint/eslint-plugin': 8.34.1(@typescript-eslint/parser@8.34.1(eslint@9.29.0(jiti@2.4.2))(typescript@5.8.3))(eslint@9.29.0(jiti@2.4.2))(typescript@5.8.3) - '@typescript-eslint/parser': 8.34.1(eslint@9.29.0(jiti@2.4.2))(typescript@5.8.3) - '@typescript-eslint/utils': 8.34.1(eslint@9.29.0(jiti@2.4.2))(typescript@5.8.3) - eslint: 9.29.0(jiti@2.4.2) + '@typescript-eslint/eslint-plugin': 8.56.0(@typescript-eslint/parser@8.56.0(eslint@10.0.0(jiti@2.4.2))(typescript@5.8.3))(eslint@10.0.0(jiti@2.4.2))(typescript@5.8.3) + '@typescript-eslint/parser': 8.56.0(eslint@10.0.0(jiti@2.4.2))(typescript@5.8.3) + '@typescript-eslint/typescript-estree': 8.56.0(typescript@5.8.3) + '@typescript-eslint/utils': 8.56.0(eslint@10.0.0(jiti@2.4.2))(typescript@5.8.3) + eslint: 10.0.0(jiti@2.4.2) typescript: 5.8.3 transitivePeerDependencies: - supports-color From 5ac3d63e43ca5185e343dec8360de7d9ef94df2f Mon Sep 17 00:00:00 2001 From: "dependabot[bot]" <49699333+dependabot[bot]@users.noreply.github.com> Date: Fri, 20 Feb 2026 21:14:55 +0800 Subject: [PATCH 17/95] chore(deps-dev): bump svelte from 5.35.6 to 5.51.5 (#14973) Bumps [svelte](https://github.com/sveltejs/svelte/tree/HEAD/packages/svelte) from 5.35.6 to 5.51.5. - [Release notes](https://github.com/sveltejs/svelte/releases) - [Changelog](https://github.com/sveltejs/svelte/blob/main/packages/svelte/CHANGELOG.md) - [Commits](https://github.com/sveltejs/svelte/commits/svelte@5.51.5/packages/svelte) --- updated-dependencies: - dependency-name: svelte dependency-version: 5.51.5 dependency-type: direct:development ... Signed-off-by: dependabot[bot] --- examples/api/package.json | 2 +- pnpm-lock.yaml | 132 ++++++++++++++++++++++---------------- 2 files changed, 77 insertions(+), 57 deletions(-) diff --git a/examples/api/package.json b/examples/api/package.json index 65ede4686080..0c8fbd693058 100644 --- a/examples/api/package.json +++ b/examples/api/package.json @@ -17,7 +17,7 @@ "@iconify-json/ph": "^1.2.2", "@sveltejs/vite-plugin-svelte": "^6.0.0", "@unocss/extractor-svelte": "^66.3.3", - "svelte": "^5.35.6", + "svelte": "^5.51.5", "unocss": "^66.3.3", "vite": "^7.1.11" } diff --git a/pnpm-lock.yaml b/pnpm-lock.yaml index c97ae8574358..be3ac9b72da6 100644 --- a/pnpm-lock.yaml +++ b/pnpm-lock.yaml @@ -38,13 +38,13 @@ importers: version: 1.2.2 '@sveltejs/vite-plugin-svelte': specifier: ^6.0.0 - version: 6.0.0(svelte@5.35.6)(vite@7.1.11(@types/node@24.10.0)(jiti@2.4.2)(terser@5.43.1)) + version: 6.0.0(svelte@5.51.5)(vite@7.1.11(@types/node@24.10.0)(jiti@2.4.2)(terser@5.43.1)) '@unocss/extractor-svelte': specifier: ^66.3.3 version: 66.3.3 svelte: - specifier: ^5.35.6 - version: 5.35.6 + specifier: ^5.51.5 + version: 5.51.5 unocss: specifier: ^66.3.3 version: 66.3.3(postcss@8.5.6)(vite@7.1.11(@types/node@24.10.0)(jiti@2.4.2)(terser@5.43.1))(vue@3.5.17(typescript@5.8.3)) @@ -136,13 +136,13 @@ packages: resolution: {integrity: sha512-qSs4ifwzKJSV39ucNjsvc6WVHs6b7S03sOh2OcHF9UHfVPqWWALUsNUVzhSBiItjRZoLHx7nIarVjqKVusUZ1Q==} engines: {node: '>=6.9.0'} - '@babel/parser@7.28.6': - resolution: {integrity: sha512-TeR9zWR18BvbfPmGbLampPMW+uW1NZnJlRuuHso8i87QZNq2JRF9i6RgxRqtEq+wQGsS19NNTWr2duhnE49mfQ==} + '@babel/parser@7.29.0': + resolution: {integrity: sha512-IyDgFV5GeDUVX4YdF/3CPULtVGSXXMLh1xVIgdCgxApktqnQV0r7/8Nqthg+8YLGaAtdyIlo2qIdZrbCv4+7ww==} engines: {node: '>=6.0.0'} hasBin: true - '@babel/types@7.28.6': - resolution: {integrity: sha512-0ZrskXVEHSWIqZM/sQZ4EV3jZJXRkio/WCxaqKZP1g//CEWEPSfeZFcms4XeKBCHU0ZKnIkdJeU/kF+eRp5lBg==} + '@babel/types@7.29.0': + resolution: {integrity: sha512-LwdZHpScM4Qz8Xw2iKSzS+cfglZzJGvofQICy7W7v4caru4EaAmyUuO6BGrbyQ2mYV11W0U8j5mBhd14dd3B0A==} engines: {node: '>=6.9.0'} '@cloudflare/kv-asset-handler@0.4.2': @@ -852,8 +852,11 @@ packages: '@types/node': optional: true - '@jridgewell/gen-mapping@0.3.12': - resolution: {integrity: sha512-OuLGC46TjB5BbN1dH8JULVVZY4WTdkF7tV9Ys6wLL1rubZnCMstOhNHueU5bLCrnRuDhKPDM4g6sw4Bel5Gzqg==} + '@jridgewell/gen-mapping@0.3.13': + resolution: {integrity: sha512-2kkt/7niJ6MgEPxF0bYdQ6etZaA+fQvDcLKckhy1yIQOzaoKjBBjSj63/aLVjYE3qhRt5dvM+uUyfCg6UKCBbA==} + + '@jridgewell/remapping@2.3.5': + resolution: {integrity: sha512-LI9u/+laYG4Ds1TDKSJW2YPrIlcVYOwi2fUC6xB43lueCjgxV4lffOCZCtYFiH6TNOX+tQKXx97T4IKHbhyHEQ==} '@jridgewell/resolve-uri@3.1.2': resolution: {integrity: sha512-bRISgCIjP20/tbWSPWMEi54QVPRZExkuD9lJL+UIxUKtwVJA8wW1Trb1jMs1RFXo1CBTNZ/5hpC9QvmKWdopKw==} @@ -865,8 +868,8 @@ packages: '@jridgewell/sourcemap-codec@1.5.5': resolution: {integrity: sha512-cYQ9310grqxueWbl+WuIUIaiUaDcj7WOq5fVhEljNVgRfOUhY9fy2zTvfoqWsnebh8Sl70VScFbICvJnLKB0Og==} - '@jridgewell/trace-mapping@0.3.29': - resolution: {integrity: sha512-uw6guiW/gcAGPDhLmd77/6lW8QLeiV5RUTsAX46Db6oLhGaVj4lhnPwb184s1bkc8kdVg/+h988dro8GRDpmYQ==} + '@jridgewell/trace-mapping@0.3.31': + resolution: {integrity: sha512-zzNR+SdQSDJzc8joaeP8QQoCQr8NuYx2dIIytl1QeBEZHJ9uW6hebsrYgbz8hJwUQao3TWCMtmfV8Nu1twOLAw==} '@jridgewell/trace-mapping@0.3.9': resolution: {integrity: sha512-3Belt6tdc8bPgAtbcmdtNJlirVoTmEb5e2gC94PnkwEW9jI6CAHUeoG85tjWP5WquqfavoMtMwiG4P926ZKKuQ==} @@ -1450,8 +1453,8 @@ packages: '@standard-schema/spec@1.0.0': resolution: {integrity: sha512-m2bOd0f2RT9k8QJx1JN85cZYyH1RqFBdlwtkSlf4tBDYLCiiZnv1fIIwacK6cqwXavOydf0NPToMQgpKq+dVlA==} - '@sveltejs/acorn-typescript@1.0.5': - resolution: {integrity: sha512-IwQk4yfwLdibDlrXVE04jTZYlLnwsTT2PIOQQGNLWfjavGifnk1JD1LcZjZaBTRcxZu2FfPfNLOE04DSu9lqtQ==} + '@sveltejs/acorn-typescript@1.0.9': + resolution: {integrity: sha512-lVJX6qEgs/4DOcRTpo56tmKzVPtoWAaVbL4hfO7t7NVwl9AAXzQR6cihesW1BmNMPl+bK6dreu2sOKBP2Q9CIA==} peerDependencies: acorn: ^8.9.0 @@ -1494,6 +1497,9 @@ packages: '@types/node@24.10.0': resolution: {integrity: sha512-qzQZRBqkFsYyaSWXuEHc2WR9c0a0CXwiE5FWUvn7ZM+vdy1uZLfCunD38UzhuB7YN/J11ndbDBcTmOdxJo9Q7A==} + '@types/trusted-types@2.0.7': + resolution: {integrity: sha512-ScaPdn1dQczgbl0QFTeTOmVHFULt394XJgOQNoyVhZ6r2vLnMLJfBPd53SB52T/3G36VI1/g2MZaX0cwDuXsfw==} + '@typescript-eslint/eslint-plugin@8.56.0': resolution: {integrity: sha512-lRyPDLzNCuae71A3t9NEINBiTn7swyOhvUj3MyUOxb8x6g6vPEFoOU+ZRmGMusNC3X3YMhqMIX7i8ShqhT74Pw==} engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0} @@ -1705,8 +1711,8 @@ packages: peerDependencies: acorn: ^6.0.0 || ^7.0.0 || ^8.0.0 - acorn@8.15.0: - resolution: {integrity: sha512-NZyJarBfL7nWwIq+FDL6Zp/yHEhePMNnnJ0y3qfieCrmNvYct8uvtiV41UvlSe6apAfk0fY1FbWx+NwfmpvtTg==} + acorn@8.16.0: + resolution: {integrity: sha512-UVJyE9MttOsBQIDKw1skb9nAwQuR5wuGD3+82K6JgJlm/Y+KI92oNsMNGZCYdDsVtRHSak0pcV5Dno5+4jh9sw==} engines: {node: '>=0.4.0'} hasBin: true @@ -1858,6 +1864,9 @@ packages: resolution: {integrity: sha512-Btj2BOOO83o3WyH59e8MgXsxEQVcarkUOpEYrubB0urwnN10yQ364rsiByU11nZlqWYZm05i/of7io4mzihBtQ==} engines: {node: '>=8'} + devalue@5.6.3: + resolution: {integrity: sha512-nc7XjUU/2Lb+SvEFVGcWLiKkzfw8+qHI7zn8WYXKkLMgfGSHbgCEaR6bJpev8Cm6Rmrb19Gfd/tZvGqx9is3wg==} + duplexer@0.1.2: resolution: {integrity: sha512-jtD6YG370ZCIi/9GTaJKQxWTZD045+4R4hTk/x1UyoqadyJ9x9CgSi1RlVDQF8U2sxLLSnFkCaMihqljHIWgMg==} @@ -1942,8 +1951,8 @@ packages: resolution: {integrity: sha512-Ap6G0WQwcU/LHsvLwON1fAQX9Zp0A2Y6Y/cJBl9r/JbW90Zyg4/zbG6zzKa2OTALELarYHmKu0GhpM5EO+7T0g==} engines: {node: '>=0.10'} - esrap@2.1.0: - resolution: {integrity: sha512-yzmPNpl7TBbMRC5Lj2JlJZNPml0tzqoqP5B1JXycNUwtqma9AKCO0M2wHrdgsHcy1WRW7S9rJknAMtByg3usgA==} + esrap@2.2.3: + resolution: {integrity: sha512-8fOS+GIGCQZl/ZIlhl59htOlms6U8NvX6ZYgYHpRU/b6tVSh3uHkOHZikl3D4cMbYM0JlpBe+p/BkZEi8J9XIQ==} esrecurse@4.3.0: resolution: {integrity: sha512-KmfKL3b6G+RXvP8N1vr3Tq1kL/oCFgn2NYXEtqP8/L3pKapUA4G8cFVaoF3SU323CD4XypR/ffioHmkti6/Tag==} @@ -2375,8 +2384,8 @@ packages: resolution: {integrity: sha512-ot0WnXS9fgdkgIcePe6RHNk1WA8+muPa6cSjeR3V8K27q9BB1rTE3R1p7Hv0z1ZyAc8s6Vvv8DIyWf681MAt0w==} engines: {node: '>= 0.4'} - svelte@5.35.6: - resolution: {integrity: sha512-p7PVLQYrvCxJuxzGfOv/l71hVuHC6EZk5UDjbt/bndMYaBcUV5sFjDsj+PSIYvz1vcfbG6inX83/xIUeik1xGA==} + svelte@5.51.5: + resolution: {integrity: sha512-/4tR5cLsWOgH3wnNRXnFoWaJlwPGbJanZPSKSD6nHM2y01dvXeEF4Nx7jevoZ+UpJpkIHh6mY2tqDncuI4GHng==} engines: {node: '>=18'} terser@5.43.1: @@ -2629,15 +2638,15 @@ packages: youch@4.1.0-beta.10: resolution: {integrity: sha512-rLfVLB4FgQneDr0dv1oddCVZmKjcJ6yX6mS4pU82Mq/Dt9a3cLZQ62pDBL4AUO+uVrCvtWz3ZFUL2HFAFJ/BXQ==} - zimmerframe@1.1.2: - resolution: {integrity: sha512-rAbqEGa8ovJy4pyBxZM70hg4pE6gDgaQ0Sl9M3enG3I0d6H4XSAM3GeNGLKnsBpuijUow064sf7ww1nutC5/3w==} + zimmerframe@1.1.4: + resolution: {integrity: sha512-B58NGBEoc8Y9MWWCQGl/gq9xBCe4IiKM0a2x7GZdQKOW5Exr8S1W24J6OgM1njK8xCRGvAJIL/MxXHf6SkmQKQ==} snapshots: '@ampproject/remapping@2.3.0': dependencies: - '@jridgewell/gen-mapping': 0.3.12 - '@jridgewell/trace-mapping': 0.3.29 + '@jridgewell/gen-mapping': 0.3.13 + '@jridgewell/trace-mapping': 0.3.31 '@antfu/install-pkg@1.1.0': dependencies: @@ -2650,11 +2659,11 @@ snapshots: '@babel/helper-validator-identifier@7.28.5': {} - '@babel/parser@7.28.6': + '@babel/parser@7.29.0': dependencies: - '@babel/types': 7.28.6 + '@babel/types': 7.29.0 - '@babel/types@7.28.6': + '@babel/types@7.29.0': dependencies: '@babel/helper-string-parser': 7.27.1 '@babel/helper-validator-identifier': 7.28.5 @@ -3148,21 +3157,26 @@ snapshots: optionalDependencies: '@types/node': 24.10.0 - '@jridgewell/gen-mapping@0.3.12': + '@jridgewell/gen-mapping@0.3.13': dependencies: '@jridgewell/sourcemap-codec': 1.5.5 - '@jridgewell/trace-mapping': 0.3.29 + '@jridgewell/trace-mapping': 0.3.31 + + '@jridgewell/remapping@2.3.5': + dependencies: + '@jridgewell/gen-mapping': 0.3.13 + '@jridgewell/trace-mapping': 0.3.31 '@jridgewell/resolve-uri@3.1.2': {} '@jridgewell/source-map@0.3.6': dependencies: - '@jridgewell/gen-mapping': 0.3.12 - '@jridgewell/trace-mapping': 0.3.29 + '@jridgewell/gen-mapping': 0.3.13 + '@jridgewell/trace-mapping': 0.3.31 '@jridgewell/sourcemap-codec@1.5.5': {} - '@jridgewell/trace-mapping@0.3.29': + '@jridgewell/trace-mapping@0.3.31': dependencies: '@jridgewell/resolve-uri': 3.1.2 '@jridgewell/sourcemap-codec': 1.5.5 @@ -3615,27 +3629,27 @@ snapshots: '@standard-schema/spec@1.0.0': {} - '@sveltejs/acorn-typescript@1.0.5(acorn@8.15.0)': + '@sveltejs/acorn-typescript@1.0.9(acorn@8.16.0)': dependencies: - acorn: 8.15.0 + acorn: 8.16.0 - '@sveltejs/vite-plugin-svelte-inspector@5.0.0(@sveltejs/vite-plugin-svelte@6.0.0(svelte@5.35.6)(vite@7.1.11(@types/node@24.10.0)(jiti@2.4.2)(terser@5.43.1)))(svelte@5.35.6)(vite@7.1.11(@types/node@24.10.0)(jiti@2.4.2)(terser@5.43.1))': + '@sveltejs/vite-plugin-svelte-inspector@5.0.0(@sveltejs/vite-plugin-svelte@6.0.0(svelte@5.51.5)(vite@7.1.11(@types/node@24.10.0)(jiti@2.4.2)(terser@5.43.1)))(svelte@5.51.5)(vite@7.1.11(@types/node@24.10.0)(jiti@2.4.2)(terser@5.43.1))': dependencies: - '@sveltejs/vite-plugin-svelte': 6.0.0(svelte@5.35.6)(vite@7.1.11(@types/node@24.10.0)(jiti@2.4.2)(terser@5.43.1)) + '@sveltejs/vite-plugin-svelte': 6.0.0(svelte@5.51.5)(vite@7.1.11(@types/node@24.10.0)(jiti@2.4.2)(terser@5.43.1)) debug: 4.4.3 - svelte: 5.35.6 + svelte: 5.51.5 vite: 7.1.11(@types/node@24.10.0)(jiti@2.4.2)(terser@5.43.1) transitivePeerDependencies: - supports-color - '@sveltejs/vite-plugin-svelte@6.0.0(svelte@5.35.6)(vite@7.1.11(@types/node@24.10.0)(jiti@2.4.2)(terser@5.43.1))': + '@sveltejs/vite-plugin-svelte@6.0.0(svelte@5.51.5)(vite@7.1.11(@types/node@24.10.0)(jiti@2.4.2)(terser@5.43.1))': dependencies: - '@sveltejs/vite-plugin-svelte-inspector': 5.0.0(@sveltejs/vite-plugin-svelte@6.0.0(svelte@5.35.6)(vite@7.1.11(@types/node@24.10.0)(jiti@2.4.2)(terser@5.43.1)))(svelte@5.35.6)(vite@7.1.11(@types/node@24.10.0)(jiti@2.4.2)(terser@5.43.1)) + '@sveltejs/vite-plugin-svelte-inspector': 5.0.0(@sveltejs/vite-plugin-svelte@6.0.0(svelte@5.51.5)(vite@7.1.11(@types/node@24.10.0)(jiti@2.4.2)(terser@5.43.1)))(svelte@5.51.5)(vite@7.1.11(@types/node@24.10.0)(jiti@2.4.2)(terser@5.43.1)) debug: 4.4.3 deepmerge: 4.3.1 kleur: 4.1.5 magic-string: 0.30.21 - svelte: 5.35.6 + svelte: 5.51.5 vite: 7.1.11(@types/node@24.10.0)(jiti@2.4.2)(terser@5.43.1) vitefu: 1.1.1(vite@7.1.11(@types/node@24.10.0)(jiti@2.4.2)(terser@5.43.1)) transitivePeerDependencies: @@ -3667,6 +3681,8 @@ snapshots: dependencies: undici-types: 7.16.0 + '@types/trusted-types@2.0.7': {} + '@typescript-eslint/eslint-plugin@8.56.0(@typescript-eslint/parser@8.56.0(eslint@10.0.0(jiti@2.4.2))(typescript@5.8.3))(eslint@10.0.0(jiti@2.4.2))(typescript@5.8.3)': dependencies: '@eslint-community/regexpp': 4.12.2 @@ -3953,7 +3969,7 @@ snapshots: '@vue/compiler-core@3.5.17': dependencies: - '@babel/parser': 7.28.6 + '@babel/parser': 7.29.0 '@vue/shared': 3.5.17 entities: 4.5.0 estree-walker: 2.0.2 @@ -3966,7 +3982,7 @@ snapshots: '@vue/compiler-sfc@3.5.17': dependencies: - '@babel/parser': 7.28.6 + '@babel/parser': 7.29.0 '@vue/compiler-core': 3.5.17 '@vue/compiler-dom': 3.5.17 '@vue/compiler-ssr': 3.5.17 @@ -4005,11 +4021,11 @@ snapshots: '@vue/shared@3.5.17': {} - acorn-jsx@5.3.2(acorn@8.15.0): + acorn-jsx@5.3.2(acorn@8.16.0): dependencies: - acorn: 8.15.0 + acorn: 8.16.0 - acorn@8.15.0: {} + acorn@8.16.0: {} ajv@6.12.6: dependencies: @@ -4129,6 +4145,8 @@ snapshots: detect-libc@2.1.2: {} + devalue@5.6.3: {} + duplexer@0.1.2: {} emnapi@1.7.1: {} @@ -4262,15 +4280,15 @@ snapshots: espree@11.1.0: dependencies: - acorn: 8.15.0 - acorn-jsx: 5.3.2(acorn@8.15.0) + acorn: 8.16.0 + acorn-jsx: 5.3.2(acorn@8.16.0) eslint-visitor-keys: 5.0.0 esquery@1.7.0: dependencies: estraverse: 5.3.0 - esrap@2.1.0: + esrap@2.2.3: dependencies: '@jridgewell/sourcemap-codec': 1.5.5 @@ -4467,7 +4485,7 @@ snapshots: mlly@1.7.4: dependencies: - acorn: 8.15.0 + acorn: 8.16.0 pathe: 2.0.3 pkg-types: 1.3.1 ufo: 1.6.1 @@ -4700,27 +4718,29 @@ snapshots: supports-preserve-symlinks-flag@1.0.0: {} - svelte@5.35.6: + svelte@5.51.5: dependencies: - '@ampproject/remapping': 2.3.0 + '@jridgewell/remapping': 2.3.5 '@jridgewell/sourcemap-codec': 1.5.5 - '@sveltejs/acorn-typescript': 1.0.5(acorn@8.15.0) + '@sveltejs/acorn-typescript': 1.0.9(acorn@8.16.0) '@types/estree': 1.0.8 - acorn: 8.15.0 + '@types/trusted-types': 2.0.7 + acorn: 8.16.0 aria-query: 5.3.2 axobject-query: 4.1.0 clsx: 2.1.1 + devalue: 5.6.3 esm-env: 1.2.2 - esrap: 2.1.0 + esrap: 2.2.3 is-reference: 3.0.3 locate-character: 3.0.0 magic-string: 0.30.21 - zimmerframe: 1.1.2 + zimmerframe: 1.1.4 terser@5.43.1: dependencies: '@jridgewell/source-map': 0.3.6 - acorn: 8.15.0 + acorn: 8.16.0 commander: 2.20.3 source-map-support: 0.5.21 @@ -4954,4 +4974,4 @@ snapshots: cookie: 1.1.1 youch-core: 0.3.3 - zimmerframe@1.1.2: {} + zimmerframe@1.1.4: {} From ea2477d8d0680e1eedb706d1fde5edee57cef328 Mon Sep 17 00:00:00 2001 From: montyc1999 <211852937+montyc1999@users.noreply.github.com> Date: Mon, 23 Feb 2026 10:14:56 -0500 Subject: [PATCH 18/95] fix(tauri-utils): sort csp/plugin/header config maps during codegen so `generate_context!` is deterministic (#14986) * fix(tauri-utils): sort csp/plugin/header config maps during codegen so generate_context! is deterministic * add comments explaining rationale, and todo for removing the hack in v3 --- .../fix-nondeterministic-context-codegen.md | 7 +++++ crates/tauri-utils/src/config.rs | 26 ++++++++++++++++--- 2 files changed, 30 insertions(+), 3 deletions(-) create mode 100644 .changes/fix-nondeterministic-context-codegen.md diff --git a/.changes/fix-nondeterministic-context-codegen.md b/.changes/fix-nondeterministic-context-codegen.md new file mode 100644 index 000000000000..5b4d8237a072 --- /dev/null +++ b/.changes/fix-nondeterministic-context-codegen.md @@ -0,0 +1,7 @@ +--- +'tauri-utils': 'patch:bug' +--- + +Sort csp/plugin/header configs when generating HashMap constructors so that `generate_context!` is deterministic. + +See: https://github.com/tauri-apps/tauri/issues/14978 for more information \ No newline at end of file diff --git a/crates/tauri-utils/src/config.rs b/crates/tauri-utils/src/config.rs index 8826e3f51b43..78f0ed3eceda 100644 --- a/crates/tauri-utils/src/config.rs +++ b/crates/tauri-utils/src/config.rs @@ -3842,9 +3842,14 @@ mod build { quote!(#prefix::Policy(#policy.into())) } Self::DirectiveMap(list) => { + // Pass a sorted vec so the HashMap constructor is deterministic + // see: https://github.com/tauri-apps/tauri/issues/14978 + // TODO: Remove this in v3, use a BTreeMap instead of a HashMap + let mut sorted: Vec<_> = list.iter().collect(); + sorted.sort_by_key(|(k, _)| *k); let map = map_lit( quote! { ::std::collections::HashMap }, - list, + sorted, str_lit, identity, ); @@ -3900,7 +3905,17 @@ mod build { quote!(#prefix::List(#list)) } Self::Map(m) => { - let map = map_lit(quote! { ::std::collections::HashMap }, m, str_lit, str_lit); + // Pass a sorted vec so the HashMap constructor is deterministic + // see: https://github.com/tauri-apps/tauri/issues/14978 + // TODO: Remove this in v3, use a BTreeMap instead of a HashMap + let mut sorted: Vec<_> = m.iter().collect(); + sorted.sort_by_key(|(k, _)| *k); + let map = map_lit( + quote! { ::std::collections::HashMap }, + sorted, + str_lit, + str_lit, + ); quote!(#prefix::Map(#map)) } }) @@ -4047,9 +4062,14 @@ mod build { impl ToTokens for PluginConfig { fn to_tokens(&self, tokens: &mut TokenStream) { + // Pass a sorted vec so the HashMap constructor is deterministic + // see: https://github.com/tauri-apps/tauri/issues/14978 + // TODO: Remove this in v3, use a BTreeMap instead of a HashMap + let mut sorted: Vec<_> = self.0.iter().collect(); + sorted.sort_by_key(|(k, _)| *k); let config = map_lit( quote! { ::std::collections::HashMap }, - &self.0, + sorted, str_lit, json_value_lit, ); From c23bdb58c4d14c16384f428cceaaf7cb6123f615 Mon Sep 17 00:00:00 2001 From: "renovate[bot]" <29139614+renovate[bot]@users.noreply.github.com> Date: Wed, 25 Feb 2026 11:13:03 +0800 Subject: [PATCH 19/95] chore(deps): update dependency rollup to v4.58.0 (#14991) Co-authored-by: renovate[bot] <29139614+renovate[bot]@users.noreply.github.com> --- packages/api/package.json | 2 +- pnpm-lock.yaml | 230 +++++++++++++++++++------------------- 2 files changed, 116 insertions(+), 116 deletions(-) diff --git a/packages/api/package.json b/packages/api/package.json index 17ab8fe525ac..ae4a4871a25d 100644 --- a/packages/api/package.json +++ b/packages/api/package.json @@ -55,7 +55,7 @@ "eslint-plugin-security": "4.0.0", "fast-glob": "3.3.3", "globals": "^17.0.0", - "rollup": "4.57.1", + "rollup": "4.58.0", "tslib": "^2.8.1", "typescript": "^5.8.3", "typescript-eslint": "^8.56.0" diff --git a/pnpm-lock.yaml b/pnpm-lock.yaml index be3ac9b72da6..9610511a2295 100644 --- a/pnpm-lock.yaml +++ b/pnpm-lock.yaml @@ -63,10 +63,10 @@ importers: version: 10.0.1(eslint@10.0.0(jiti@2.4.2)) '@rollup/plugin-terser': specifier: 0.4.4 - version: 0.4.4(rollup@4.57.1) + version: 0.4.4(rollup@4.58.0) '@rollup/plugin-typescript': specifier: 12.3.0 - version: 12.3.0(rollup@4.57.1)(tslib@2.8.1)(typescript@5.8.3) + version: 12.3.0(rollup@4.58.0)(tslib@2.8.1)(typescript@5.8.3) '@types/eslint': specifier: ^9.6.1 version: 9.6.1 @@ -89,8 +89,8 @@ importers: specifier: ^17.0.0 version: 17.0.0 rollup: - specifier: 4.57.1 - version: 4.57.1 + specifier: 4.58.0 + version: 4.58.0 tslib: specifier: ^2.8.1 version: 2.8.1 @@ -1318,128 +1318,128 @@ packages: rollup: optional: true - '@rollup/rollup-android-arm-eabi@4.57.1': - resolution: {integrity: sha512-A6ehUVSiSaaliTxai040ZpZ2zTevHYbvu/lDoeAteHI8QnaosIzm4qwtezfRg1jOYaUmnzLX1AOD6Z+UJjtifg==} + '@rollup/rollup-android-arm-eabi@4.58.0': + resolution: {integrity: sha512-mr0tmS/4FoVk1cnaeN244A/wjvGDNItZKR8hRhnmCzygyRXYtKF5jVDSIILR1U97CTzAYmbgIj/Dukg62ggG5w==} cpu: [arm] os: [android] - '@rollup/rollup-android-arm64@4.57.1': - resolution: {integrity: sha512-dQaAddCY9YgkFHZcFNS/606Exo8vcLHwArFZ7vxXq4rigo2bb494/xKMMwRRQW6ug7Js6yXmBZhSBRuBvCCQ3w==} + '@rollup/rollup-android-arm64@4.58.0': + resolution: {integrity: sha512-+s++dbp+/RTte62mQD9wLSbiMTV+xr/PeRJEc/sFZFSBRlHPNPVaf5FXlzAL77Mr8FtSfQqCN+I598M8U41ccQ==} cpu: [arm64] os: [android] - '@rollup/rollup-darwin-arm64@4.57.1': - resolution: {integrity: sha512-crNPrwJOrRxagUYeMn/DZwqN88SDmwaJ8Cvi/TN1HnWBU7GwknckyosC2gd0IqYRsHDEnXf328o9/HC6OkPgOg==} + '@rollup/rollup-darwin-arm64@4.58.0': + resolution: {integrity: sha512-MFWBwTcYs0jZbINQBXHfSrpSQJq3IUOakcKPzfeSznONop14Pxuqa0Kg19GD0rNBMPQI2tFtu3UzapZpH0Uc1Q==} cpu: [arm64] os: [darwin] - '@rollup/rollup-darwin-x64@4.57.1': - resolution: {integrity: sha512-Ji8g8ChVbKrhFtig5QBV7iMaJrGtpHelkB3lsaKzadFBe58gmjfGXAOfI5FV0lYMH8wiqsxKQ1C9B0YTRXVy4w==} + '@rollup/rollup-darwin-x64@4.58.0': + resolution: {integrity: sha512-yiKJY7pj9c9JwzuKYLFaDZw5gma3fI9bkPEIyofvVfsPqjCWPglSHdpdwXpKGvDeYDms3Qal8qGMEHZ1M/4Udg==} cpu: [x64] os: [darwin] - '@rollup/rollup-freebsd-arm64@4.57.1': - resolution: {integrity: sha512-R+/WwhsjmwodAcz65guCGFRkMb4gKWTcIeLy60JJQbXrJ97BOXHxnkPFrP+YwFlaS0m+uWJTstrUA9o+UchFug==} + '@rollup/rollup-freebsd-arm64@4.58.0': + resolution: {integrity: sha512-x97kCoBh5MOevpn/CNK9W1x8BEzO238541BGWBc315uOlN0AD/ifZ1msg+ZQB05Ux+VF6EcYqpiagfLJ8U3LvQ==} cpu: [arm64] os: [freebsd] - '@rollup/rollup-freebsd-x64@4.57.1': - resolution: {integrity: sha512-IEQTCHeiTOnAUC3IDQdzRAGj3jOAYNr9kBguI7MQAAZK3caezRrg0GxAb6Hchg4lxdZEI5Oq3iov/w/hnFWY9Q==} + '@rollup/rollup-freebsd-x64@4.58.0': + resolution: {integrity: sha512-Aa8jPoZ6IQAG2eIrcXPpjRcMjROMFxCt1UYPZZtCxRV68WkuSigYtQ/7Zwrcr2IvtNJo7T2JfDXyMLxq5L4Jlg==} cpu: [x64] os: [freebsd] - '@rollup/rollup-linux-arm-gnueabihf@4.57.1': - resolution: {integrity: sha512-F8sWbhZ7tyuEfsmOxwc2giKDQzN3+kuBLPwwZGyVkLlKGdV1nvnNwYD0fKQ8+XS6hp9nY7B+ZeK01EBUE7aHaw==} + '@rollup/rollup-linux-arm-gnueabihf@4.58.0': + resolution: {integrity: sha512-Ob8YgT5kD/lSIYW2Rcngs5kNB/44Q2RzBSPz9brf2WEtcGR7/f/E9HeHn1wYaAwKBni+bdXEwgHvUd0x12lQSA==} cpu: [arm] os: [linux] - '@rollup/rollup-linux-arm-musleabihf@4.57.1': - resolution: {integrity: sha512-rGfNUfn0GIeXtBP1wL5MnzSj98+PZe/AXaGBCRmT0ts80lU5CATYGxXukeTX39XBKsxzFpEeK+Mrp9faXOlmrw==} + '@rollup/rollup-linux-arm-musleabihf@4.58.0': + resolution: {integrity: sha512-K+RI5oP1ceqoadvNt1FecL17Qtw/n9BgRSzxif3rTL2QlIu88ccvY+Y9nnHe/cmT5zbH9+bpiJuG1mGHRVwF4Q==} cpu: [arm] os: [linux] - '@rollup/rollup-linux-arm64-gnu@4.57.1': - resolution: {integrity: sha512-MMtej3YHWeg/0klK2Qodf3yrNzz6CGjo2UntLvk2RSPlhzgLvYEB3frRvbEF2wRKh1Z2fDIg9KRPe1fawv7C+g==} + '@rollup/rollup-linux-arm64-gnu@4.58.0': + resolution: {integrity: sha512-T+17JAsCKUjmbopcKepJjHWHXSjeW7O5PL7lEFaeQmiVyw4kkc5/lyYKzrv6ElWRX/MrEWfPiJWqbTvfIvjM1Q==} cpu: [arm64] os: [linux] - '@rollup/rollup-linux-arm64-musl@4.57.1': - resolution: {integrity: sha512-1a/qhaaOXhqXGpMFMET9VqwZakkljWHLmZOX48R0I/YLbhdxr1m4gtG1Hq7++VhVUmf+L3sTAf9op4JlhQ5u1Q==} + '@rollup/rollup-linux-arm64-musl@4.58.0': + resolution: {integrity: sha512-cCePktb9+6R9itIJdeCFF9txPU7pQeEHB5AbHu/MKsfH/k70ZtOeq1k4YAtBv9Z7mmKI5/wOLYjQ+B9QdxR6LA==} cpu: [arm64] os: [linux] - '@rollup/rollup-linux-loong64-gnu@4.57.1': - resolution: {integrity: sha512-QWO6RQTZ/cqYtJMtxhkRkidoNGXc7ERPbZN7dVW5SdURuLeVU7lwKMpo18XdcmpWYd0qsP1bwKPf7DNSUinhvA==} + '@rollup/rollup-linux-loong64-gnu@4.58.0': + resolution: {integrity: sha512-iekUaLkfliAsDl4/xSdoCJ1gnnIXvoNz85C8U8+ZxknM5pBStfZjeXgB8lXobDQvvPRCN8FPmmuTtH+z95HTmg==} cpu: [loong64] os: [linux] - '@rollup/rollup-linux-loong64-musl@4.57.1': - resolution: {integrity: sha512-xpObYIf+8gprgWaPP32xiN5RVTi/s5FCR+XMXSKmhfoJjrpRAjCuuqQXyxUa/eJTdAE6eJ+KDKaoEqjZQxh3Gw==} + '@rollup/rollup-linux-loong64-musl@4.58.0': + resolution: {integrity: sha512-68ofRgJNl/jYJbxFjCKE7IwhbfxOl1muPN4KbIqAIe32lm22KmU7E8OPvyy68HTNkI2iV/c8y2kSPSm2mW/Q9Q==} cpu: [loong64] os: [linux] - '@rollup/rollup-linux-ppc64-gnu@4.57.1': - resolution: {integrity: sha512-4BrCgrpZo4hvzMDKRqEaW1zeecScDCR+2nZ86ATLhAoJ5FQ+lbHVD3ttKe74/c7tNT9c6F2viwB3ufwp01Oh2w==} + '@rollup/rollup-linux-ppc64-gnu@4.58.0': + resolution: {integrity: sha512-dpz8vT0i+JqUKuSNPCP5SYyIV2Lh0sNL1+FhM7eLC457d5B9/BC3kDPp5BBftMmTNsBarcPcoz5UGSsnCiw4XQ==} cpu: [ppc64] os: [linux] - '@rollup/rollup-linux-ppc64-musl@4.57.1': - resolution: {integrity: sha512-NOlUuzesGauESAyEYFSe3QTUguL+lvrN1HtwEEsU2rOwdUDeTMJdO5dUYl/2hKf9jWydJrO9OL/XSSf65R5+Xw==} + '@rollup/rollup-linux-ppc64-musl@4.58.0': + resolution: {integrity: sha512-4gdkkf9UJ7tafnweBCR/mk4jf3Jfl0cKX9Np80t5i78kjIH0ZdezUv/JDI2VtruE5lunfACqftJ8dIMGN4oHew==} cpu: [ppc64] os: [linux] - '@rollup/rollup-linux-riscv64-gnu@4.57.1': - resolution: {integrity: sha512-ptA88htVp0AwUUqhVghwDIKlvJMD/fmL/wrQj99PRHFRAG6Z5nbWoWG4o81Nt9FT+IuqUQi+L31ZKAFeJ5Is+A==} + '@rollup/rollup-linux-riscv64-gnu@4.58.0': + resolution: {integrity: sha512-YFS4vPnOkDTD/JriUeeZurFYoJhPf9GQQEF/v4lltp3mVcBmnsAdjEWhr2cjUCZzZNzxCG0HZOvJU44UGHSdzw==} cpu: [riscv64] os: [linux] - '@rollup/rollup-linux-riscv64-musl@4.57.1': - resolution: {integrity: sha512-S51t7aMMTNdmAMPpBg7OOsTdn4tySRQvklmL3RpDRyknk87+Sp3xaumlatU+ppQ+5raY7sSTcC2beGgvhENfuw==} + '@rollup/rollup-linux-riscv64-musl@4.58.0': + resolution: {integrity: sha512-x2xgZlFne+QVNKV8b4wwaCS8pwq3y14zedZ5DqLzjdRITvreBk//4Knbcvm7+lWmms9V9qFp60MtUd0/t/PXPw==} cpu: [riscv64] os: [linux] - '@rollup/rollup-linux-s390x-gnu@4.57.1': - resolution: {integrity: sha512-Bl00OFnVFkL82FHbEqy3k5CUCKH6OEJL54KCyx2oqsmZnFTR8IoNqBF+mjQVcRCT5sB6yOvK8A37LNm/kPJiZg==} + '@rollup/rollup-linux-s390x-gnu@4.58.0': + resolution: {integrity: sha512-jIhrujyn4UnWF8S+DHSkAkDEO3hLX0cjzxJZPLF80xFyzyUIYgSMRcYQ3+uqEoyDD2beGq7Dj7edi8OnJcS/hg==} cpu: [s390x] os: [linux] - '@rollup/rollup-linux-x64-gnu@4.57.1': - resolution: {integrity: sha512-ABca4ceT4N+Tv/GtotnWAeXZUZuM/9AQyCyKYyKnpk4yoA7QIAuBt6Hkgpw8kActYlew2mvckXkvx0FfoInnLg==} + '@rollup/rollup-linux-x64-gnu@4.58.0': + resolution: {integrity: sha512-+410Srdoh78MKSJxTQ+hZ/Mx+ajd6RjjPwBPNd0R3J9FtL6ZA0GqiiyNjCO9In0IzZkCNrpGymSfn+kgyPQocg==} cpu: [x64] os: [linux] - '@rollup/rollup-linux-x64-musl@4.57.1': - resolution: {integrity: sha512-HFps0JeGtuOR2convgRRkHCekD7j+gdAuXM+/i6kGzQtFhlCtQkpwtNzkNj6QhCDp7DRJ7+qC/1Vg2jt5iSOFw==} + '@rollup/rollup-linux-x64-musl@4.58.0': + resolution: {integrity: sha512-ZjMyby5SICi227y1MTR3VYBpFTdZs823Rs/hpakufleBoufoOIB6jtm9FEoxn/cgO7l6PM2rCEl5Kre5vX0QrQ==} cpu: [x64] os: [linux] - '@rollup/rollup-openbsd-x64@4.57.1': - resolution: {integrity: sha512-H+hXEv9gdVQuDTgnqD+SQffoWoc0Of59AStSzTEj/feWTBAnSfSD3+Dql1ZruJQxmykT/JVY0dE8Ka7z0DH1hw==} + '@rollup/rollup-openbsd-x64@4.58.0': + resolution: {integrity: sha512-ds4iwfYkSQ0k1nb8LTcyXw//ToHOnNTJtceySpL3fa7tc/AsE+UpUFphW126A6fKBGJD5dhRvg8zw1rvoGFxmw==} cpu: [x64] os: [openbsd] - '@rollup/rollup-openharmony-arm64@4.57.1': - resolution: {integrity: sha512-4wYoDpNg6o/oPximyc/NG+mYUejZrCU2q+2w6YZqrAs2UcNUChIZXjtafAiiZSUc7On8v5NyNj34Kzj/Ltk6dQ==} + '@rollup/rollup-openharmony-arm64@4.58.0': + resolution: {integrity: sha512-fd/zpJniln4ICdPkjWFhZYeY/bpnaN9pGa6ko+5WD38I0tTqk9lXMgXZg09MNdhpARngmxiCg0B0XUamNw/5BQ==} cpu: [arm64] os: [openharmony] - '@rollup/rollup-win32-arm64-msvc@4.57.1': - resolution: {integrity: sha512-O54mtsV/6LW3P8qdTcamQmuC990HDfR71lo44oZMZlXU4tzLrbvTii87Ni9opq60ds0YzuAlEr/GNwuNluZyMQ==} + '@rollup/rollup-win32-arm64-msvc@4.58.0': + resolution: {integrity: sha512-YpG8dUOip7DCz3nr/JUfPbIUo+2d/dy++5bFzgi4ugOGBIox+qMbbqt/JoORwvI/C9Kn2tz6+Bieoqd5+B1CjA==} cpu: [arm64] os: [win32] - '@rollup/rollup-win32-ia32-msvc@4.57.1': - resolution: {integrity: sha512-P3dLS+IerxCT/7D2q2FYcRdWRl22dNbrbBEtxdWhXrfIMPP9lQhb5h4Du04mdl5Woq05jVCDPCMF7Ub0NAjIew==} + '@rollup/rollup-win32-ia32-msvc@4.58.0': + resolution: {integrity: sha512-b9DI8jpFQVh4hIXFr0/+N/TzLdpBIoPzjt0Rt4xJbW3mzguV3mduR9cNgiuFcuL/TeORejJhCWiAXe3E/6PxWA==} cpu: [ia32] os: [win32] - '@rollup/rollup-win32-x64-gnu@4.57.1': - resolution: {integrity: sha512-VMBH2eOOaKGtIJYleXsi2B8CPVADrh+TyNxJ4mWPnKfLB/DBUmzW+5m1xUrcwWoMfSLagIRpjUFeW5CO5hyciQ==} + '@rollup/rollup-win32-x64-gnu@4.58.0': + resolution: {integrity: sha512-CSrVpmoRJFN06LL9xhkitkwUcTZtIotYAF5p6XOR2zW0Zz5mzb3IPpcoPhB02frzMHFNo1reQ9xSF5fFm3hUsQ==} cpu: [x64] os: [win32] - '@rollup/rollup-win32-x64-msvc@4.57.1': - resolution: {integrity: sha512-mxRFDdHIWRxg3UfIIAwCm6NzvxG0jDX/wBN6KsQFTvKFqqg9vTrWUE68qEjHt19A5wwx5X5aUi2zuZT7YR0jrA==} + '@rollup/rollup-win32-x64-msvc@4.58.0': + resolution: {integrity: sha512-QFsBgQNTnh5K0t/sBsjJLq24YVqEIVkGpfN2VHsnN90soZyhaiA9UUHufcctVNL4ypJY0wrwad0wslx2KJQ1/w==} cpu: [x64] os: [win32] @@ -2300,8 +2300,8 @@ packages: resolution: {integrity: sha512-g6QUff04oZpHs0eG5p83rFLhHeV00ug/Yf9nZM6fLeUrPguBTkTQOdpAWWspMh55TZfVQDPaN3NQJfbVRAxdIw==} engines: {iojs: '>=1.0.0', node: '>=0.10.0'} - rollup@4.57.1: - resolution: {integrity: sha512-oQL6lgK3e2QZeQ7gcgIkS2YZPg5slw37hYufJ3edKlfQSGGm8ICoxswK15ntSzF/a8+h7ekRy7k7oWc3BQ7y8A==} + rollup@4.58.0: + resolution: {integrity: sha512-wbT0mBmWbIvvq8NeEYWWvevvxnOyhKChir47S66WCxw1SXqhw7ssIYejnQEVt7XYQpsj2y8F9PM+Cr3SNEa0gw==} engines: {node: '>=18.0.0', npm: '>=8.0.0'} hasBin: true @@ -3523,104 +3523,104 @@ snapshots: dependencies: quansync: 0.2.10 - '@rollup/plugin-terser@0.4.4(rollup@4.57.1)': + '@rollup/plugin-terser@0.4.4(rollup@4.58.0)': dependencies: serialize-javascript: 6.0.2 smob: 1.5.0 terser: 5.43.1 optionalDependencies: - rollup: 4.57.1 + rollup: 4.58.0 - '@rollup/plugin-typescript@12.3.0(rollup@4.57.1)(tslib@2.8.1)(typescript@5.8.3)': + '@rollup/plugin-typescript@12.3.0(rollup@4.58.0)(tslib@2.8.1)(typescript@5.8.3)': dependencies: - '@rollup/pluginutils': 5.2.0(rollup@4.57.1) + '@rollup/pluginutils': 5.2.0(rollup@4.58.0) resolve: 1.22.10 typescript: 5.8.3 optionalDependencies: - rollup: 4.57.1 + rollup: 4.58.0 tslib: 2.8.1 - '@rollup/pluginutils@5.2.0(rollup@4.57.1)': + '@rollup/pluginutils@5.2.0(rollup@4.58.0)': dependencies: '@types/estree': 1.0.8 estree-walker: 2.0.2 picomatch: 4.0.3 optionalDependencies: - rollup: 4.57.1 + rollup: 4.58.0 - '@rollup/rollup-android-arm-eabi@4.57.1': + '@rollup/rollup-android-arm-eabi@4.58.0': optional: true - '@rollup/rollup-android-arm64@4.57.1': + '@rollup/rollup-android-arm64@4.58.0': optional: true - '@rollup/rollup-darwin-arm64@4.57.1': + '@rollup/rollup-darwin-arm64@4.58.0': optional: true - '@rollup/rollup-darwin-x64@4.57.1': + '@rollup/rollup-darwin-x64@4.58.0': optional: true - '@rollup/rollup-freebsd-arm64@4.57.1': + '@rollup/rollup-freebsd-arm64@4.58.0': optional: true - '@rollup/rollup-freebsd-x64@4.57.1': + '@rollup/rollup-freebsd-x64@4.58.0': optional: true - '@rollup/rollup-linux-arm-gnueabihf@4.57.1': + '@rollup/rollup-linux-arm-gnueabihf@4.58.0': optional: true - '@rollup/rollup-linux-arm-musleabihf@4.57.1': + '@rollup/rollup-linux-arm-musleabihf@4.58.0': optional: true - '@rollup/rollup-linux-arm64-gnu@4.57.1': + '@rollup/rollup-linux-arm64-gnu@4.58.0': optional: true - '@rollup/rollup-linux-arm64-musl@4.57.1': + '@rollup/rollup-linux-arm64-musl@4.58.0': optional: true - '@rollup/rollup-linux-loong64-gnu@4.57.1': + '@rollup/rollup-linux-loong64-gnu@4.58.0': optional: true - '@rollup/rollup-linux-loong64-musl@4.57.1': + '@rollup/rollup-linux-loong64-musl@4.58.0': optional: true - '@rollup/rollup-linux-ppc64-gnu@4.57.1': + '@rollup/rollup-linux-ppc64-gnu@4.58.0': optional: true - '@rollup/rollup-linux-ppc64-musl@4.57.1': + '@rollup/rollup-linux-ppc64-musl@4.58.0': optional: true - '@rollup/rollup-linux-riscv64-gnu@4.57.1': + '@rollup/rollup-linux-riscv64-gnu@4.58.0': optional: true - '@rollup/rollup-linux-riscv64-musl@4.57.1': + '@rollup/rollup-linux-riscv64-musl@4.58.0': optional: true - '@rollup/rollup-linux-s390x-gnu@4.57.1': + '@rollup/rollup-linux-s390x-gnu@4.58.0': optional: true - '@rollup/rollup-linux-x64-gnu@4.57.1': + '@rollup/rollup-linux-x64-gnu@4.58.0': optional: true - '@rollup/rollup-linux-x64-musl@4.57.1': + '@rollup/rollup-linux-x64-musl@4.58.0': optional: true - '@rollup/rollup-openbsd-x64@4.57.1': + '@rollup/rollup-openbsd-x64@4.58.0': optional: true - '@rollup/rollup-openharmony-arm64@4.57.1': + '@rollup/rollup-openharmony-arm64@4.58.0': optional: true - '@rollup/rollup-win32-arm64-msvc@4.57.1': + '@rollup/rollup-win32-arm64-msvc@4.58.0': optional: true - '@rollup/rollup-win32-ia32-msvc@4.57.1': + '@rollup/rollup-win32-ia32-msvc@4.58.0': optional: true - '@rollup/rollup-win32-x64-gnu@4.57.1': + '@rollup/rollup-win32-x64-gnu@4.58.0': optional: true - '@rollup/rollup-win32-x64-msvc@4.57.1': + '@rollup/rollup-win32-x64-msvc@4.58.0': optional: true '@sindresorhus/is@7.2.0': {} @@ -4593,35 +4593,35 @@ snapshots: reusify@1.1.0: {} - rollup@4.57.1: + rollup@4.58.0: dependencies: '@types/estree': 1.0.8 optionalDependencies: - '@rollup/rollup-android-arm-eabi': 4.57.1 - '@rollup/rollup-android-arm64': 4.57.1 - '@rollup/rollup-darwin-arm64': 4.57.1 - '@rollup/rollup-darwin-x64': 4.57.1 - '@rollup/rollup-freebsd-arm64': 4.57.1 - '@rollup/rollup-freebsd-x64': 4.57.1 - '@rollup/rollup-linux-arm-gnueabihf': 4.57.1 - '@rollup/rollup-linux-arm-musleabihf': 4.57.1 - '@rollup/rollup-linux-arm64-gnu': 4.57.1 - '@rollup/rollup-linux-arm64-musl': 4.57.1 - '@rollup/rollup-linux-loong64-gnu': 4.57.1 - '@rollup/rollup-linux-loong64-musl': 4.57.1 - '@rollup/rollup-linux-ppc64-gnu': 4.57.1 - '@rollup/rollup-linux-ppc64-musl': 4.57.1 - '@rollup/rollup-linux-riscv64-gnu': 4.57.1 - '@rollup/rollup-linux-riscv64-musl': 4.57.1 - '@rollup/rollup-linux-s390x-gnu': 4.57.1 - '@rollup/rollup-linux-x64-gnu': 4.57.1 - '@rollup/rollup-linux-x64-musl': 4.57.1 - '@rollup/rollup-openbsd-x64': 4.57.1 - '@rollup/rollup-openharmony-arm64': 4.57.1 - '@rollup/rollup-win32-arm64-msvc': 4.57.1 - '@rollup/rollup-win32-ia32-msvc': 4.57.1 - '@rollup/rollup-win32-x64-gnu': 4.57.1 - '@rollup/rollup-win32-x64-msvc': 4.57.1 + '@rollup/rollup-android-arm-eabi': 4.58.0 + '@rollup/rollup-android-arm64': 4.58.0 + '@rollup/rollup-darwin-arm64': 4.58.0 + '@rollup/rollup-darwin-x64': 4.58.0 + '@rollup/rollup-freebsd-arm64': 4.58.0 + '@rollup/rollup-freebsd-x64': 4.58.0 + '@rollup/rollup-linux-arm-gnueabihf': 4.58.0 + '@rollup/rollup-linux-arm-musleabihf': 4.58.0 + '@rollup/rollup-linux-arm64-gnu': 4.58.0 + '@rollup/rollup-linux-arm64-musl': 4.58.0 + '@rollup/rollup-linux-loong64-gnu': 4.58.0 + '@rollup/rollup-linux-loong64-musl': 4.58.0 + '@rollup/rollup-linux-ppc64-gnu': 4.58.0 + '@rollup/rollup-linux-ppc64-musl': 4.58.0 + '@rollup/rollup-linux-riscv64-gnu': 4.58.0 + '@rollup/rollup-linux-riscv64-musl': 4.58.0 + '@rollup/rollup-linux-s390x-gnu': 4.58.0 + '@rollup/rollup-linux-x64-gnu': 4.58.0 + '@rollup/rollup-linux-x64-musl': 4.58.0 + '@rollup/rollup-openbsd-x64': 4.58.0 + '@rollup/rollup-openharmony-arm64': 4.58.0 + '@rollup/rollup-win32-arm64-msvc': 4.58.0 + '@rollup/rollup-win32-ia32-msvc': 4.58.0 + '@rollup/rollup-win32-x64-gnu': 4.58.0 + '@rollup/rollup-win32-x64-msvc': 4.58.0 fsevents: 2.3.3 run-parallel@1.2.0: @@ -4850,7 +4850,7 @@ snapshots: fdir: 6.5.0(picomatch@4.0.3) picomatch: 4.0.3 postcss: 8.5.6 - rollup: 4.57.1 + rollup: 4.58.0 tinyglobby: 0.2.15 optionalDependencies: '@types/node': 24.10.0 From 8d01abe3ae5f50a75cc930170d8a4aea88c3a2ae Mon Sep 17 00:00:00 2001 From: BiggerRain <15911122312@163.COM> Date: Thu, 26 Feb 2026 21:35:45 +0800 Subject: [PATCH 20/95] chore: fix clippy warnings (#14999) --- crates/tauri-bundler/src/bundle/macos/app.rs | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/crates/tauri-bundler/src/bundle/macos/app.rs b/crates/tauri-bundler/src/bundle/macos/app.rs index 703973c2b75a..c90f652d8405 100644 --- a/crates/tauri-bundler/src/bundle/macos/app.rs +++ b/crates/tauri-bundler/src/bundle/macos/app.rs @@ -136,7 +136,7 @@ pub fn bundle_project(settings: &Settings) -> crate::Result> { if matches!(e, NotarizeAuthError::MissingTeamId) { return Err(e.into()); } else { - log::warn!("skipping app notarization, {}", e.to_string()); + log::warn!("skipping app notarization, {e}"); } } } From eb4dd785939db4f2de124d06057558dbafe41fdc Mon Sep 17 00:00:00 2001 From: "renovate[bot]" <29139614+renovate[bot]@users.noreply.github.com> Date: Sat, 28 Feb 2026 22:07:20 +0800 Subject: [PATCH 21/95] chore(deps): update dependency rollup to v4.59.0 (#15001) Co-authored-by: renovate[bot] <29139614+renovate[bot]@users.noreply.github.com> --- packages/api/package.json | 2 +- pnpm-lock.yaml | 230 +++++++++++++++++++------------------- 2 files changed, 116 insertions(+), 116 deletions(-) diff --git a/packages/api/package.json b/packages/api/package.json index ae4a4871a25d..c5bcba505946 100644 --- a/packages/api/package.json +++ b/packages/api/package.json @@ -55,7 +55,7 @@ "eslint-plugin-security": "4.0.0", "fast-glob": "3.3.3", "globals": "^17.0.0", - "rollup": "4.58.0", + "rollup": "4.59.0", "tslib": "^2.8.1", "typescript": "^5.8.3", "typescript-eslint": "^8.56.0" diff --git a/pnpm-lock.yaml b/pnpm-lock.yaml index 9610511a2295..1875fdd48839 100644 --- a/pnpm-lock.yaml +++ b/pnpm-lock.yaml @@ -63,10 +63,10 @@ importers: version: 10.0.1(eslint@10.0.0(jiti@2.4.2)) '@rollup/plugin-terser': specifier: 0.4.4 - version: 0.4.4(rollup@4.58.0) + version: 0.4.4(rollup@4.59.0) '@rollup/plugin-typescript': specifier: 12.3.0 - version: 12.3.0(rollup@4.58.0)(tslib@2.8.1)(typescript@5.8.3) + version: 12.3.0(rollup@4.59.0)(tslib@2.8.1)(typescript@5.8.3) '@types/eslint': specifier: ^9.6.1 version: 9.6.1 @@ -89,8 +89,8 @@ importers: specifier: ^17.0.0 version: 17.0.0 rollup: - specifier: 4.58.0 - version: 4.58.0 + specifier: 4.59.0 + version: 4.59.0 tslib: specifier: ^2.8.1 version: 2.8.1 @@ -1318,128 +1318,128 @@ packages: rollup: optional: true - '@rollup/rollup-android-arm-eabi@4.58.0': - resolution: {integrity: sha512-mr0tmS/4FoVk1cnaeN244A/wjvGDNItZKR8hRhnmCzygyRXYtKF5jVDSIILR1U97CTzAYmbgIj/Dukg62ggG5w==} + '@rollup/rollup-android-arm-eabi@4.59.0': + resolution: {integrity: sha512-upnNBkA6ZH2VKGcBj9Fyl9IGNPULcjXRlg0LLeaioQWueH30p6IXtJEbKAgvyv+mJaMxSm1l6xwDXYjpEMiLMg==} cpu: [arm] os: [android] - '@rollup/rollup-android-arm64@4.58.0': - resolution: {integrity: sha512-+s++dbp+/RTte62mQD9wLSbiMTV+xr/PeRJEc/sFZFSBRlHPNPVaf5FXlzAL77Mr8FtSfQqCN+I598M8U41ccQ==} + '@rollup/rollup-android-arm64@4.59.0': + resolution: {integrity: sha512-hZ+Zxj3SySm4A/DylsDKZAeVg0mvi++0PYVceVyX7hemkw7OreKdCvW2oQ3T1FMZvCaQXqOTHb8qmBShoqk69Q==} cpu: [arm64] os: [android] - '@rollup/rollup-darwin-arm64@4.58.0': - resolution: {integrity: sha512-MFWBwTcYs0jZbINQBXHfSrpSQJq3IUOakcKPzfeSznONop14Pxuqa0Kg19GD0rNBMPQI2tFtu3UzapZpH0Uc1Q==} + '@rollup/rollup-darwin-arm64@4.59.0': + resolution: {integrity: sha512-W2Psnbh1J8ZJw0xKAd8zdNgF9HRLkdWwwdWqubSVk0pUuQkoHnv7rx4GiF9rT4t5DIZGAsConRE3AxCdJ4m8rg==} cpu: [arm64] os: [darwin] - '@rollup/rollup-darwin-x64@4.58.0': - resolution: {integrity: sha512-yiKJY7pj9c9JwzuKYLFaDZw5gma3fI9bkPEIyofvVfsPqjCWPglSHdpdwXpKGvDeYDms3Qal8qGMEHZ1M/4Udg==} + '@rollup/rollup-darwin-x64@4.59.0': + resolution: {integrity: sha512-ZW2KkwlS4lwTv7ZVsYDiARfFCnSGhzYPdiOU4IM2fDbL+QGlyAbjgSFuqNRbSthybLbIJ915UtZBtmuLrQAT/w==} cpu: [x64] os: [darwin] - '@rollup/rollup-freebsd-arm64@4.58.0': - resolution: {integrity: sha512-x97kCoBh5MOevpn/CNK9W1x8BEzO238541BGWBc315uOlN0AD/ifZ1msg+ZQB05Ux+VF6EcYqpiagfLJ8U3LvQ==} + '@rollup/rollup-freebsd-arm64@4.59.0': + resolution: {integrity: sha512-EsKaJ5ytAu9jI3lonzn3BgG8iRBjV4LxZexygcQbpiU0wU0ATxhNVEpXKfUa0pS05gTcSDMKpn3Sx+QB9RlTTA==} cpu: [arm64] os: [freebsd] - '@rollup/rollup-freebsd-x64@4.58.0': - resolution: {integrity: sha512-Aa8jPoZ6IQAG2eIrcXPpjRcMjROMFxCt1UYPZZtCxRV68WkuSigYtQ/7Zwrcr2IvtNJo7T2JfDXyMLxq5L4Jlg==} + '@rollup/rollup-freebsd-x64@4.59.0': + resolution: {integrity: sha512-d3DuZi2KzTMjImrxoHIAODUZYoUUMsuUiY4SRRcJy6NJoZ6iIqWnJu9IScV9jXysyGMVuW+KNzZvBLOcpdl3Vg==} cpu: [x64] os: [freebsd] - '@rollup/rollup-linux-arm-gnueabihf@4.58.0': - resolution: {integrity: sha512-Ob8YgT5kD/lSIYW2Rcngs5kNB/44Q2RzBSPz9brf2WEtcGR7/f/E9HeHn1wYaAwKBni+bdXEwgHvUd0x12lQSA==} + '@rollup/rollup-linux-arm-gnueabihf@4.59.0': + resolution: {integrity: sha512-t4ONHboXi/3E0rT6OZl1pKbl2Vgxf9vJfWgmUoCEVQVxhW6Cw/c8I6hbbu7DAvgp82RKiH7TpLwxnJeKv2pbsw==} cpu: [arm] os: [linux] - '@rollup/rollup-linux-arm-musleabihf@4.58.0': - resolution: {integrity: sha512-K+RI5oP1ceqoadvNt1FecL17Qtw/n9BgRSzxif3rTL2QlIu88ccvY+Y9nnHe/cmT5zbH9+bpiJuG1mGHRVwF4Q==} + '@rollup/rollup-linux-arm-musleabihf@4.59.0': + resolution: {integrity: sha512-CikFT7aYPA2ufMD086cVORBYGHffBo4K8MQ4uPS/ZnY54GKj36i196u8U+aDVT2LX4eSMbyHtyOh7D7Zvk2VvA==} cpu: [arm] os: [linux] - '@rollup/rollup-linux-arm64-gnu@4.58.0': - resolution: {integrity: sha512-T+17JAsCKUjmbopcKepJjHWHXSjeW7O5PL7lEFaeQmiVyw4kkc5/lyYKzrv6ElWRX/MrEWfPiJWqbTvfIvjM1Q==} + '@rollup/rollup-linux-arm64-gnu@4.59.0': + resolution: {integrity: sha512-jYgUGk5aLd1nUb1CtQ8E+t5JhLc9x5WdBKew9ZgAXg7DBk0ZHErLHdXM24rfX+bKrFe+Xp5YuJo54I5HFjGDAA==} cpu: [arm64] os: [linux] - '@rollup/rollup-linux-arm64-musl@4.58.0': - resolution: {integrity: sha512-cCePktb9+6R9itIJdeCFF9txPU7pQeEHB5AbHu/MKsfH/k70ZtOeq1k4YAtBv9Z7mmKI5/wOLYjQ+B9QdxR6LA==} + '@rollup/rollup-linux-arm64-musl@4.59.0': + resolution: {integrity: sha512-peZRVEdnFWZ5Bh2KeumKG9ty7aCXzzEsHShOZEFiCQlDEepP1dpUl/SrUNXNg13UmZl+gzVDPsiCwnV1uI0RUA==} cpu: [arm64] os: [linux] - '@rollup/rollup-linux-loong64-gnu@4.58.0': - resolution: {integrity: sha512-iekUaLkfliAsDl4/xSdoCJ1gnnIXvoNz85C8U8+ZxknM5pBStfZjeXgB8lXobDQvvPRCN8FPmmuTtH+z95HTmg==} + '@rollup/rollup-linux-loong64-gnu@4.59.0': + resolution: {integrity: sha512-gbUSW/97f7+r4gHy3Jlup8zDG190AuodsWnNiXErp9mT90iCy9NKKU0Xwx5k8VlRAIV2uU9CsMnEFg/xXaOfXg==} cpu: [loong64] os: [linux] - '@rollup/rollup-linux-loong64-musl@4.58.0': - resolution: {integrity: sha512-68ofRgJNl/jYJbxFjCKE7IwhbfxOl1muPN4KbIqAIe32lm22KmU7E8OPvyy68HTNkI2iV/c8y2kSPSm2mW/Q9Q==} + '@rollup/rollup-linux-loong64-musl@4.59.0': + resolution: {integrity: sha512-yTRONe79E+o0FWFijasoTjtzG9EBedFXJMl888NBEDCDV9I2wGbFFfJQQe63OijbFCUZqxpHz1GzpbtSFikJ4Q==} cpu: [loong64] os: [linux] - '@rollup/rollup-linux-ppc64-gnu@4.58.0': - resolution: {integrity: sha512-dpz8vT0i+JqUKuSNPCP5SYyIV2Lh0sNL1+FhM7eLC457d5B9/BC3kDPp5BBftMmTNsBarcPcoz5UGSsnCiw4XQ==} + '@rollup/rollup-linux-ppc64-gnu@4.59.0': + resolution: {integrity: sha512-sw1o3tfyk12k3OEpRddF68a1unZ5VCN7zoTNtSn2KndUE+ea3m3ROOKRCZxEpmT9nsGnogpFP9x6mnLTCaoLkA==} cpu: [ppc64] os: [linux] - '@rollup/rollup-linux-ppc64-musl@4.58.0': - resolution: {integrity: sha512-4gdkkf9UJ7tafnweBCR/mk4jf3Jfl0cKX9Np80t5i78kjIH0ZdezUv/JDI2VtruE5lunfACqftJ8dIMGN4oHew==} + '@rollup/rollup-linux-ppc64-musl@4.59.0': + resolution: {integrity: sha512-+2kLtQ4xT3AiIxkzFVFXfsmlZiG5FXYW7ZyIIvGA7Bdeuh9Z0aN4hVyXS/G1E9bTP/vqszNIN/pUKCk/BTHsKA==} cpu: [ppc64] os: [linux] - '@rollup/rollup-linux-riscv64-gnu@4.58.0': - resolution: {integrity: sha512-YFS4vPnOkDTD/JriUeeZurFYoJhPf9GQQEF/v4lltp3mVcBmnsAdjEWhr2cjUCZzZNzxCG0HZOvJU44UGHSdzw==} + '@rollup/rollup-linux-riscv64-gnu@4.59.0': + resolution: {integrity: sha512-NDYMpsXYJJaj+I7UdwIuHHNxXZ/b/N2hR15NyH3m2qAtb/hHPA4g4SuuvrdxetTdndfj9b1WOmy73kcPRoERUg==} cpu: [riscv64] os: [linux] - '@rollup/rollup-linux-riscv64-musl@4.58.0': - resolution: {integrity: sha512-x2xgZlFne+QVNKV8b4wwaCS8pwq3y14zedZ5DqLzjdRITvreBk//4Knbcvm7+lWmms9V9qFp60MtUd0/t/PXPw==} + '@rollup/rollup-linux-riscv64-musl@4.59.0': + resolution: {integrity: sha512-nLckB8WOqHIf1bhymk+oHxvM9D3tyPndZH8i8+35p/1YiVoVswPid2yLzgX7ZJP0KQvnkhM4H6QZ5m0LzbyIAg==} cpu: [riscv64] os: [linux] - '@rollup/rollup-linux-s390x-gnu@4.58.0': - resolution: {integrity: sha512-jIhrujyn4UnWF8S+DHSkAkDEO3hLX0cjzxJZPLF80xFyzyUIYgSMRcYQ3+uqEoyDD2beGq7Dj7edi8OnJcS/hg==} + '@rollup/rollup-linux-s390x-gnu@4.59.0': + resolution: {integrity: sha512-oF87Ie3uAIvORFBpwnCvUzdeYUqi2wY6jRFWJAy1qus/udHFYIkplYRW+wo+GRUP4sKzYdmE1Y3+rY5Gc4ZO+w==} cpu: [s390x] os: [linux] - '@rollup/rollup-linux-x64-gnu@4.58.0': - resolution: {integrity: sha512-+410Srdoh78MKSJxTQ+hZ/Mx+ajd6RjjPwBPNd0R3J9FtL6ZA0GqiiyNjCO9In0IzZkCNrpGymSfn+kgyPQocg==} + '@rollup/rollup-linux-x64-gnu@4.59.0': + resolution: {integrity: sha512-3AHmtQq/ppNuUspKAlvA8HtLybkDflkMuLK4DPo77DfthRb71V84/c4MlWJXixZz4uruIH4uaa07IqoAkG64fg==} cpu: [x64] os: [linux] - '@rollup/rollup-linux-x64-musl@4.58.0': - resolution: {integrity: sha512-ZjMyby5SICi227y1MTR3VYBpFTdZs823Rs/hpakufleBoufoOIB6jtm9FEoxn/cgO7l6PM2rCEl5Kre5vX0QrQ==} + '@rollup/rollup-linux-x64-musl@4.59.0': + resolution: {integrity: sha512-2UdiwS/9cTAx7qIUZB/fWtToJwvt0Vbo0zmnYt7ED35KPg13Q0ym1g442THLC7VyI6JfYTP4PiSOWyoMdV2/xg==} cpu: [x64] os: [linux] - '@rollup/rollup-openbsd-x64@4.58.0': - resolution: {integrity: sha512-ds4iwfYkSQ0k1nb8LTcyXw//ToHOnNTJtceySpL3fa7tc/AsE+UpUFphW126A6fKBGJD5dhRvg8zw1rvoGFxmw==} + '@rollup/rollup-openbsd-x64@4.59.0': + resolution: {integrity: sha512-M3bLRAVk6GOwFlPTIxVBSYKUaqfLrn8l0psKinkCFxl4lQvOSz8ZrKDz2gxcBwHFpci0B6rttydI4IpS4IS/jQ==} cpu: [x64] os: [openbsd] - '@rollup/rollup-openharmony-arm64@4.58.0': - resolution: {integrity: sha512-fd/zpJniln4ICdPkjWFhZYeY/bpnaN9pGa6ko+5WD38I0tTqk9lXMgXZg09MNdhpARngmxiCg0B0XUamNw/5BQ==} + '@rollup/rollup-openharmony-arm64@4.59.0': + resolution: {integrity: sha512-tt9KBJqaqp5i5HUZzoafHZX8b5Q2Fe7UjYERADll83O4fGqJ49O1FsL6LpdzVFQcpwvnyd0i+K/VSwu/o/nWlA==} cpu: [arm64] os: [openharmony] - '@rollup/rollup-win32-arm64-msvc@4.58.0': - resolution: {integrity: sha512-YpG8dUOip7DCz3nr/JUfPbIUo+2d/dy++5bFzgi4ugOGBIox+qMbbqt/JoORwvI/C9Kn2tz6+Bieoqd5+B1CjA==} + '@rollup/rollup-win32-arm64-msvc@4.59.0': + resolution: {integrity: sha512-V5B6mG7OrGTwnxaNUzZTDTjDS7F75PO1ae6MJYdiMu60sq0CqN5CVeVsbhPxalupvTX8gXVSU9gq+Rx1/hvu6A==} cpu: [arm64] os: [win32] - '@rollup/rollup-win32-ia32-msvc@4.58.0': - resolution: {integrity: sha512-b9DI8jpFQVh4hIXFr0/+N/TzLdpBIoPzjt0Rt4xJbW3mzguV3mduR9cNgiuFcuL/TeORejJhCWiAXe3E/6PxWA==} + '@rollup/rollup-win32-ia32-msvc@4.59.0': + resolution: {integrity: sha512-UKFMHPuM9R0iBegwzKF4y0C4J9u8C6MEJgFuXTBerMk7EJ92GFVFYBfOZaSGLu6COf7FxpQNqhNS4c4icUPqxA==} cpu: [ia32] os: [win32] - '@rollup/rollup-win32-x64-gnu@4.58.0': - resolution: {integrity: sha512-CSrVpmoRJFN06LL9xhkitkwUcTZtIotYAF5p6XOR2zW0Zz5mzb3IPpcoPhB02frzMHFNo1reQ9xSF5fFm3hUsQ==} + '@rollup/rollup-win32-x64-gnu@4.59.0': + resolution: {integrity: sha512-laBkYlSS1n2L8fSo1thDNGrCTQMmxjYY5G0WFWjFFYZkKPjsMBsgJfGf4TLxXrF6RyhI60L8TMOjBMvXiTcxeA==} cpu: [x64] os: [win32] - '@rollup/rollup-win32-x64-msvc@4.58.0': - resolution: {integrity: sha512-QFsBgQNTnh5K0t/sBsjJLq24YVqEIVkGpfN2VHsnN90soZyhaiA9UUHufcctVNL4ypJY0wrwad0wslx2KJQ1/w==} + '@rollup/rollup-win32-x64-msvc@4.59.0': + resolution: {integrity: sha512-2HRCml6OztYXyJXAvdDXPKcawukWY2GpR5/nxKp4iBgiO3wcoEGkAaqctIbZcNB6KlUQBIqt8VYkNSj2397EfA==} cpu: [x64] os: [win32] @@ -2300,8 +2300,8 @@ packages: resolution: {integrity: sha512-g6QUff04oZpHs0eG5p83rFLhHeV00ug/Yf9nZM6fLeUrPguBTkTQOdpAWWspMh55TZfVQDPaN3NQJfbVRAxdIw==} engines: {iojs: '>=1.0.0', node: '>=0.10.0'} - rollup@4.58.0: - resolution: {integrity: sha512-wbT0mBmWbIvvq8NeEYWWvevvxnOyhKChir47S66WCxw1SXqhw7ssIYejnQEVt7XYQpsj2y8F9PM+Cr3SNEa0gw==} + rollup@4.59.0: + resolution: {integrity: sha512-2oMpl67a3zCH9H79LeMcbDhXW/UmWG/y2zuqnF2jQq5uq9TbM9TVyXvA4+t+ne2IIkBdrLpAaRQAvo7YI/Yyeg==} engines: {node: '>=18.0.0', npm: '>=8.0.0'} hasBin: true @@ -3523,104 +3523,104 @@ snapshots: dependencies: quansync: 0.2.10 - '@rollup/plugin-terser@0.4.4(rollup@4.58.0)': + '@rollup/plugin-terser@0.4.4(rollup@4.59.0)': dependencies: serialize-javascript: 6.0.2 smob: 1.5.0 terser: 5.43.1 optionalDependencies: - rollup: 4.58.0 + rollup: 4.59.0 - '@rollup/plugin-typescript@12.3.0(rollup@4.58.0)(tslib@2.8.1)(typescript@5.8.3)': + '@rollup/plugin-typescript@12.3.0(rollup@4.59.0)(tslib@2.8.1)(typescript@5.8.3)': dependencies: - '@rollup/pluginutils': 5.2.0(rollup@4.58.0) + '@rollup/pluginutils': 5.2.0(rollup@4.59.0) resolve: 1.22.10 typescript: 5.8.3 optionalDependencies: - rollup: 4.58.0 + rollup: 4.59.0 tslib: 2.8.1 - '@rollup/pluginutils@5.2.0(rollup@4.58.0)': + '@rollup/pluginutils@5.2.0(rollup@4.59.0)': dependencies: '@types/estree': 1.0.8 estree-walker: 2.0.2 picomatch: 4.0.3 optionalDependencies: - rollup: 4.58.0 + rollup: 4.59.0 - '@rollup/rollup-android-arm-eabi@4.58.0': + '@rollup/rollup-android-arm-eabi@4.59.0': optional: true - '@rollup/rollup-android-arm64@4.58.0': + '@rollup/rollup-android-arm64@4.59.0': optional: true - '@rollup/rollup-darwin-arm64@4.58.0': + '@rollup/rollup-darwin-arm64@4.59.0': optional: true - '@rollup/rollup-darwin-x64@4.58.0': + '@rollup/rollup-darwin-x64@4.59.0': optional: true - '@rollup/rollup-freebsd-arm64@4.58.0': + '@rollup/rollup-freebsd-arm64@4.59.0': optional: true - '@rollup/rollup-freebsd-x64@4.58.0': + '@rollup/rollup-freebsd-x64@4.59.0': optional: true - '@rollup/rollup-linux-arm-gnueabihf@4.58.0': + '@rollup/rollup-linux-arm-gnueabihf@4.59.0': optional: true - '@rollup/rollup-linux-arm-musleabihf@4.58.0': + '@rollup/rollup-linux-arm-musleabihf@4.59.0': optional: true - '@rollup/rollup-linux-arm64-gnu@4.58.0': + '@rollup/rollup-linux-arm64-gnu@4.59.0': optional: true - '@rollup/rollup-linux-arm64-musl@4.58.0': + '@rollup/rollup-linux-arm64-musl@4.59.0': optional: true - '@rollup/rollup-linux-loong64-gnu@4.58.0': + '@rollup/rollup-linux-loong64-gnu@4.59.0': optional: true - '@rollup/rollup-linux-loong64-musl@4.58.0': + '@rollup/rollup-linux-loong64-musl@4.59.0': optional: true - '@rollup/rollup-linux-ppc64-gnu@4.58.0': + '@rollup/rollup-linux-ppc64-gnu@4.59.0': optional: true - '@rollup/rollup-linux-ppc64-musl@4.58.0': + '@rollup/rollup-linux-ppc64-musl@4.59.0': optional: true - '@rollup/rollup-linux-riscv64-gnu@4.58.0': + '@rollup/rollup-linux-riscv64-gnu@4.59.0': optional: true - '@rollup/rollup-linux-riscv64-musl@4.58.0': + '@rollup/rollup-linux-riscv64-musl@4.59.0': optional: true - '@rollup/rollup-linux-s390x-gnu@4.58.0': + '@rollup/rollup-linux-s390x-gnu@4.59.0': optional: true - '@rollup/rollup-linux-x64-gnu@4.58.0': + '@rollup/rollup-linux-x64-gnu@4.59.0': optional: true - '@rollup/rollup-linux-x64-musl@4.58.0': + '@rollup/rollup-linux-x64-musl@4.59.0': optional: true - '@rollup/rollup-openbsd-x64@4.58.0': + '@rollup/rollup-openbsd-x64@4.59.0': optional: true - '@rollup/rollup-openharmony-arm64@4.58.0': + '@rollup/rollup-openharmony-arm64@4.59.0': optional: true - '@rollup/rollup-win32-arm64-msvc@4.58.0': + '@rollup/rollup-win32-arm64-msvc@4.59.0': optional: true - '@rollup/rollup-win32-ia32-msvc@4.58.0': + '@rollup/rollup-win32-ia32-msvc@4.59.0': optional: true - '@rollup/rollup-win32-x64-gnu@4.58.0': + '@rollup/rollup-win32-x64-gnu@4.59.0': optional: true - '@rollup/rollup-win32-x64-msvc@4.58.0': + '@rollup/rollup-win32-x64-msvc@4.59.0': optional: true '@sindresorhus/is@7.2.0': {} @@ -4593,35 +4593,35 @@ snapshots: reusify@1.1.0: {} - rollup@4.58.0: + rollup@4.59.0: dependencies: '@types/estree': 1.0.8 optionalDependencies: - '@rollup/rollup-android-arm-eabi': 4.58.0 - '@rollup/rollup-android-arm64': 4.58.0 - '@rollup/rollup-darwin-arm64': 4.58.0 - '@rollup/rollup-darwin-x64': 4.58.0 - '@rollup/rollup-freebsd-arm64': 4.58.0 - '@rollup/rollup-freebsd-x64': 4.58.0 - '@rollup/rollup-linux-arm-gnueabihf': 4.58.0 - '@rollup/rollup-linux-arm-musleabihf': 4.58.0 - '@rollup/rollup-linux-arm64-gnu': 4.58.0 - '@rollup/rollup-linux-arm64-musl': 4.58.0 - '@rollup/rollup-linux-loong64-gnu': 4.58.0 - '@rollup/rollup-linux-loong64-musl': 4.58.0 - '@rollup/rollup-linux-ppc64-gnu': 4.58.0 - '@rollup/rollup-linux-ppc64-musl': 4.58.0 - '@rollup/rollup-linux-riscv64-gnu': 4.58.0 - '@rollup/rollup-linux-riscv64-musl': 4.58.0 - '@rollup/rollup-linux-s390x-gnu': 4.58.0 - '@rollup/rollup-linux-x64-gnu': 4.58.0 - '@rollup/rollup-linux-x64-musl': 4.58.0 - '@rollup/rollup-openbsd-x64': 4.58.0 - '@rollup/rollup-openharmony-arm64': 4.58.0 - '@rollup/rollup-win32-arm64-msvc': 4.58.0 - '@rollup/rollup-win32-ia32-msvc': 4.58.0 - '@rollup/rollup-win32-x64-gnu': 4.58.0 - '@rollup/rollup-win32-x64-msvc': 4.58.0 + '@rollup/rollup-android-arm-eabi': 4.59.0 + '@rollup/rollup-android-arm64': 4.59.0 + '@rollup/rollup-darwin-arm64': 4.59.0 + '@rollup/rollup-darwin-x64': 4.59.0 + '@rollup/rollup-freebsd-arm64': 4.59.0 + '@rollup/rollup-freebsd-x64': 4.59.0 + '@rollup/rollup-linux-arm-gnueabihf': 4.59.0 + '@rollup/rollup-linux-arm-musleabihf': 4.59.0 + '@rollup/rollup-linux-arm64-gnu': 4.59.0 + '@rollup/rollup-linux-arm64-musl': 4.59.0 + '@rollup/rollup-linux-loong64-gnu': 4.59.0 + '@rollup/rollup-linux-loong64-musl': 4.59.0 + '@rollup/rollup-linux-ppc64-gnu': 4.59.0 + '@rollup/rollup-linux-ppc64-musl': 4.59.0 + '@rollup/rollup-linux-riscv64-gnu': 4.59.0 + '@rollup/rollup-linux-riscv64-musl': 4.59.0 + '@rollup/rollup-linux-s390x-gnu': 4.59.0 + '@rollup/rollup-linux-x64-gnu': 4.59.0 + '@rollup/rollup-linux-x64-musl': 4.59.0 + '@rollup/rollup-openbsd-x64': 4.59.0 + '@rollup/rollup-openharmony-arm64': 4.59.0 + '@rollup/rollup-win32-arm64-msvc': 4.59.0 + '@rollup/rollup-win32-ia32-msvc': 4.59.0 + '@rollup/rollup-win32-x64-gnu': 4.59.0 + '@rollup/rollup-win32-x64-msvc': 4.59.0 fsevents: 2.3.3 run-parallel@1.2.0: @@ -4850,7 +4850,7 @@ snapshots: fdir: 6.5.0(picomatch@4.0.3) picomatch: 4.0.3 postcss: 8.5.6 - rollup: 4.58.0 + rollup: 4.59.0 tinyglobby: 0.2.15 optionalDependencies: '@types/node': 24.10.0 From e406931040dac38f818675ecb9e4740b1947e439 Mon Sep 17 00:00:00 2001 From: "dependabot[bot]" <49699333+dependabot[bot]@users.noreply.github.com> Date: Sun, 1 Mar 2026 11:27:29 +0800 Subject: [PATCH 22/95] chore(deps-dev): bump svelte from 5.51.5 to 5.53.5 (#15015) Bumps [svelte](https://github.com/sveltejs/svelte/tree/HEAD/packages/svelte) from 5.51.5 to 5.53.5. - [Release notes](https://github.com/sveltejs/svelte/releases) - [Changelog](https://github.com/sveltejs/svelte/blob/main/packages/svelte/CHANGELOG.md) - [Commits](https://github.com/sveltejs/svelte/commits/svelte@5.53.5/packages/svelte) --- updated-dependencies: - dependency-name: svelte dependency-version: 5.53.5 dependency-type: direct:development ... Signed-off-by: dependabot[bot] Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com> --- examples/api/package.json | 2 +- pnpm-lock.yaml | 32 ++++++++++++++++---------------- 2 files changed, 17 insertions(+), 17 deletions(-) diff --git a/examples/api/package.json b/examples/api/package.json index 0c8fbd693058..87445a35c275 100644 --- a/examples/api/package.json +++ b/examples/api/package.json @@ -17,7 +17,7 @@ "@iconify-json/ph": "^1.2.2", "@sveltejs/vite-plugin-svelte": "^6.0.0", "@unocss/extractor-svelte": "^66.3.3", - "svelte": "^5.51.5", + "svelte": "^5.53.5", "unocss": "^66.3.3", "vite": "^7.1.11" } diff --git a/pnpm-lock.yaml b/pnpm-lock.yaml index 1875fdd48839..2ddcf519e759 100644 --- a/pnpm-lock.yaml +++ b/pnpm-lock.yaml @@ -38,13 +38,13 @@ importers: version: 1.2.2 '@sveltejs/vite-plugin-svelte': specifier: ^6.0.0 - version: 6.0.0(svelte@5.51.5)(vite@7.1.11(@types/node@24.10.0)(jiti@2.4.2)(terser@5.43.1)) + version: 6.0.0(svelte@5.53.5)(vite@7.1.11(@types/node@24.10.0)(jiti@2.4.2)(terser@5.43.1)) '@unocss/extractor-svelte': specifier: ^66.3.3 version: 66.3.3 svelte: - specifier: ^5.51.5 - version: 5.51.5 + specifier: ^5.53.5 + version: 5.53.5 unocss: specifier: ^66.3.3 version: 66.3.3(postcss@8.5.6)(vite@7.1.11(@types/node@24.10.0)(jiti@2.4.2)(terser@5.43.1))(vue@3.5.17(typescript@5.8.3)) @@ -1734,8 +1734,8 @@ packages: argparse@2.0.1: resolution: {integrity: sha512-8+9WqebbFzpX9OR+Wa6O29asIogeRMzcGtAINdpMHHyAg10f05aSFVBbcEqGf/PXw1EjAZ+q2/bEBg3DvurK3Q==} - aria-query@5.3.2: - resolution: {integrity: sha512-COROpnaoap1E2F000S62r6A60uHZnmlvomhfyT2DlTcrY1OrBKn2UhH7qn5wTC9zMvD0AY7csdPSNwKP+7WiQw==} + aria-query@5.3.1: + resolution: {integrity: sha512-Z/ZeOgVl7bcSYZ/u/rh0fOpvEpq//LZmdbkXyc7syVzjPAhfOa9ebsdTSjEBDU4vs5nC98Kfduj1uFo0qyET3g==} engines: {node: '>= 0.4'} axobject-query@4.1.0: @@ -2384,8 +2384,8 @@ packages: resolution: {integrity: sha512-ot0WnXS9fgdkgIcePe6RHNk1WA8+muPa6cSjeR3V8K27q9BB1rTE3R1p7Hv0z1ZyAc8s6Vvv8DIyWf681MAt0w==} engines: {node: '>= 0.4'} - svelte@5.51.5: - resolution: {integrity: sha512-/4tR5cLsWOgH3wnNRXnFoWaJlwPGbJanZPSKSD6nHM2y01dvXeEF4Nx7jevoZ+UpJpkIHh6mY2tqDncuI4GHng==} + svelte@5.53.5: + resolution: {integrity: sha512-YkqERnF05g8KLdDZwZrF8/i1eSbj6Eoat8Jjr2IfruZz9StLuBqo8sfCSzjosNKd+ZrQ8DkKZDjpO5y3ht1Pow==} engines: {node: '>=18'} terser@5.43.1: @@ -3633,23 +3633,23 @@ snapshots: dependencies: acorn: 8.16.0 - '@sveltejs/vite-plugin-svelte-inspector@5.0.0(@sveltejs/vite-plugin-svelte@6.0.0(svelte@5.51.5)(vite@7.1.11(@types/node@24.10.0)(jiti@2.4.2)(terser@5.43.1)))(svelte@5.51.5)(vite@7.1.11(@types/node@24.10.0)(jiti@2.4.2)(terser@5.43.1))': + '@sveltejs/vite-plugin-svelte-inspector@5.0.0(@sveltejs/vite-plugin-svelte@6.0.0(svelte@5.53.5)(vite@7.1.11(@types/node@24.10.0)(jiti@2.4.2)(terser@5.43.1)))(svelte@5.53.5)(vite@7.1.11(@types/node@24.10.0)(jiti@2.4.2)(terser@5.43.1))': dependencies: - '@sveltejs/vite-plugin-svelte': 6.0.0(svelte@5.51.5)(vite@7.1.11(@types/node@24.10.0)(jiti@2.4.2)(terser@5.43.1)) + '@sveltejs/vite-plugin-svelte': 6.0.0(svelte@5.53.5)(vite@7.1.11(@types/node@24.10.0)(jiti@2.4.2)(terser@5.43.1)) debug: 4.4.3 - svelte: 5.51.5 + svelte: 5.53.5 vite: 7.1.11(@types/node@24.10.0)(jiti@2.4.2)(terser@5.43.1) transitivePeerDependencies: - supports-color - '@sveltejs/vite-plugin-svelte@6.0.0(svelte@5.51.5)(vite@7.1.11(@types/node@24.10.0)(jiti@2.4.2)(terser@5.43.1))': + '@sveltejs/vite-plugin-svelte@6.0.0(svelte@5.53.5)(vite@7.1.11(@types/node@24.10.0)(jiti@2.4.2)(terser@5.43.1))': dependencies: - '@sveltejs/vite-plugin-svelte-inspector': 5.0.0(@sveltejs/vite-plugin-svelte@6.0.0(svelte@5.51.5)(vite@7.1.11(@types/node@24.10.0)(jiti@2.4.2)(terser@5.43.1)))(svelte@5.51.5)(vite@7.1.11(@types/node@24.10.0)(jiti@2.4.2)(terser@5.43.1)) + '@sveltejs/vite-plugin-svelte-inspector': 5.0.0(@sveltejs/vite-plugin-svelte@6.0.0(svelte@5.53.5)(vite@7.1.11(@types/node@24.10.0)(jiti@2.4.2)(terser@5.43.1)))(svelte@5.53.5)(vite@7.1.11(@types/node@24.10.0)(jiti@2.4.2)(terser@5.43.1)) debug: 4.4.3 deepmerge: 4.3.1 kleur: 4.1.5 magic-string: 0.30.21 - svelte: 5.51.5 + svelte: 5.53.5 vite: 7.1.11(@types/node@24.10.0)(jiti@2.4.2)(terser@5.43.1) vitefu: 1.1.1(vite@7.1.11(@types/node@24.10.0)(jiti@2.4.2)(terser@5.43.1)) transitivePeerDependencies: @@ -4047,7 +4047,7 @@ snapshots: argparse@2.0.1: {} - aria-query@5.3.2: {} + aria-query@5.3.1: {} axobject-query@4.1.0: {} @@ -4718,7 +4718,7 @@ snapshots: supports-preserve-symlinks-flag@1.0.0: {} - svelte@5.51.5: + svelte@5.53.5: dependencies: '@jridgewell/remapping': 2.3.5 '@jridgewell/sourcemap-codec': 1.5.5 @@ -4726,7 +4726,7 @@ snapshots: '@types/estree': 1.0.8 '@types/trusted-types': 2.0.7 acorn: 8.16.0 - aria-query: 5.3.2 + aria-query: 5.3.1 axobject-query: 4.1.0 clsx: 2.1.1 devalue: 5.6.3 From 000f6a9ec7de3fe0f228b6bdcd0e5667ddd406c7 Mon Sep 17 00:00:00 2001 From: Tony <68118705+Legend-Master@users.noreply.github.com> Date: Tue, 3 Mar 2026 17:45:42 +0800 Subject: [PATCH 23/95] Add AI tool policy to contributing guide (#15002) * Add AI tool policy to contrubuting guide * Apply suggestions from code review Co-authored-by: Fabian-Lars <30730186+FabianLars@users.noreply.github.com> * nonsense -> nonsensical --------- Co-authored-by: Fabian-Lars <30730186+FabianLars@users.noreply.github.com> --- .github/CONTRIBUTING.md | 11 +++++++++++ 1 file changed, 11 insertions(+) diff --git a/.github/CONTRIBUTING.md b/.github/CONTRIBUTING.md index f0b35f439f2d..8e69134eb32c 100644 --- a/.github/CONTRIBUTING.md +++ b/.github/CONTRIBUTING.md @@ -5,6 +5,7 @@ Hi! We, the maintainers, are really excited that you are interested in contribut - [Issue Reporting Guidelines](#issue-reporting-guidelines) - [Pull Request Guidelines](#pull-request-guidelines) - [Development Guide](#development-guide) +- [AI Tool Policy](#ai-tool-policy) ## Issue Reporting Guidelines @@ -104,6 +105,16 @@ $ cargo +nightly doc --all-features --open The JS API provides bindings between the developer's JS in the Webview and the built-in Tauri APIs, written in Rust. Its code is located in [/packages/api](https://github.com/tauri-apps/tauri/tree/dev/packages/api). After making changes to the code, run `pnpm build` to build it. To test your changes, we recommend using the API example app, located in [/examples/api](https://github.com/tauri-apps/tauri/tree/dev/examples/api). It will automatically use your local copy of the JS API and provides a helpful UI to test the various commands. +## AI Tool Policy + +It takes a lot of time to review a Pull Request while it's very easy to make a nonsensical but plausible looking one using AI tools. +It is unfair for other contributors and the reviewers to spend much of the time dealing with this, hence these rules: + +1. Review and test all LLM-generated content before submitting, you're the one responsible for it, not the AI. +2. Don't use AI to respond to review comments (except for translations). + +We will close the Pull Request with a `ai-slop` tag if you failed to do so. + ## Financial Contribution Tauri is an MIT-licensed open source project. Its ongoing development can be supported via [GitHub Sponsors](https://github.com/sponsors/tauri-apps) or [Open Collective](https://opencollective.com/tauri). We prefer GitHub Sponsors as donations made are doubled through the matching fund program. From ff5dc1d579cdd91e4a812ca33a212534757a0de1 Mon Sep 17 00:00:00 2001 From: Tony <68118705+Legend-Master@users.noreply.github.com> Date: Tue, 3 Mar 2026 20:23:50 +0800 Subject: [PATCH 24/95] fix(cli): unusable empty password private keys (#15022) * fix(cli): unusable empty password private keys * Bump minisign to 0.9 and revert other changes * Lock to `=0.7.3` --- .changes/sign-no-password.md | 6 + Cargo.lock | 149 ++++++++---------- crates/tauri-cli/Cargo.toml | 4 +- .../src/helpers/updater_signature.rs | 22 ++- 4 files changed, 98 insertions(+), 83 deletions(-) create mode 100644 .changes/sign-no-password.md diff --git a/.changes/sign-no-password.md b/.changes/sign-no-password.md new file mode 100644 index 000000000000..c9a30d9381de --- /dev/null +++ b/.changes/sign-no-password.md @@ -0,0 +1,6 @@ +--- +"tauri-cli": patch:bug +"@tauri-apps/cli": patch:bug +--- + +Fix updater signing private keys generated using `tauri signer generate` with empty password can't be used (The keys generated during tauri were broken between v2.9.3 and v2.10.0, you'll need to regenerate them) diff --git a/Cargo.lock b/Cargo.lock index 0166651d0884..059dabbeeaf2 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -397,7 +397,7 @@ checksum = "0ae92a5119aa49cdbcf6b9f893fe4e1d98b04ccbf82ee0584ad948a44a734dea" dependencies = [ "proc-macro2", "quote", - "syn 2.0.95", + "syn 2.0.117", ] [[package]] @@ -483,7 +483,7 @@ checksum = "e539d3fca749fcee5236ab05e93a52867dd549cc157c8cb7f99595f3cedffdb5" dependencies = [ "proc-macro2", "quote", - "syn 2.0.95", + "syn 2.0.117", ] [[package]] @@ -858,7 +858,7 @@ dependencies = [ "proc-macro-crate 3.2.0", "proc-macro2", "quote", - "syn 2.0.95", + "syn 2.0.117", ] [[package]] @@ -1281,7 +1281,7 @@ dependencies = [ "heck 0.5.0", "proc-macro2", "quote", - "syn 2.0.95", + "syn 2.0.117", ] [[package]] @@ -1639,15 +1639,9 @@ source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "13b588ba4ac1a99f7f2964d24b3d896ddc6bf847ee3855dbd4366f058cfcd331" dependencies = [ "quote", - "syn 2.0.95", + "syn 2.0.117", ] -[[package]] -name = "ct-codecs" -version = "1.1.6" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "9b10589d1a5e400d61f9f38f12f884cfd080ff345de8f17efda36fe0e4a02aa8" - [[package]] name = "ctor" version = "0.2.9" @@ -1655,7 +1649,7 @@ source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "32a2785755761f3ddc1492979ce1e48d2c00d09311c39e4466429188f3dd6501" dependencies = [ "quote", - "syn 2.0.95", + "syn 2.0.117", ] [[package]] @@ -1718,7 +1712,7 @@ checksum = "f46882e17999c6cc590af592290432be3bce0428cb0d5f8b6715e4dc7b383eb3" dependencies = [ "proc-macro2", "quote", - "syn 2.0.95", + "syn 2.0.117", ] [[package]] @@ -1742,7 +1736,7 @@ dependencies = [ "proc-macro2", "quote", "strsim", - "syn 2.0.95", + "syn 2.0.117", ] [[package]] @@ -1753,7 +1747,7 @@ checksum = "d336a2a514f6ccccaa3e09b02d41d35330c07ddf03a62165fcec10bb561c7806" dependencies = [ "darling_core", "quote", - "syn 2.0.95", + "syn 2.0.117", ] [[package]] @@ -1820,7 +1814,7 @@ checksum = "30542c1ad912e0e3d22a1935c290e12e8a29d704a420177a31faad4a601a0800" dependencies = [ "proc-macro2", "quote", - "syn 2.0.95", + "syn 2.0.117", ] [[package]] @@ -1841,7 +1835,7 @@ dependencies = [ "darling", "proc-macro2", "quote", - "syn 2.0.95", + "syn 2.0.117", ] [[package]] @@ -1851,7 +1845,7 @@ source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "ab63b0e2bf4d5928aff72e83a7dace85d7bba5fe12dcc3c5a572d78caffd3f3c" dependencies = [ "derive_builder_core", - "syn 2.0.95", + "syn 2.0.117", ] [[package]] @@ -1864,7 +1858,7 @@ dependencies = [ "proc-macro2", "quote", "rustc_version", - "syn 2.0.95", + "syn 2.0.117", ] [[package]] @@ -1884,7 +1878,7 @@ checksum = "cb7330aeadfbe296029522e6c40f315320aba36fc43a5b3632f3795348f3bd22" dependencies = [ "proc-macro2", "quote", - "syn 2.0.95", + "syn 2.0.117", "unicode-xid", ] @@ -1996,7 +1990,7 @@ checksum = "97369cbbc041bc366949bc74d34658d6cda5621039731c6310521892a3a20ae0" dependencies = [ "proc-macro2", "quote", - "syn 2.0.95", + "syn 2.0.117", ] [[package]] @@ -2019,7 +2013,7 @@ checksum = "f2b99bf03862d7f545ebc28ddd33a665b50865f4dfd84031a393823879bd4c54" dependencies = [ "proc-macro2", "quote", - "syn 2.0.95", + "syn 2.0.117", ] [[package]] @@ -2271,7 +2265,7 @@ checksum = "ba7795da175654fe16979af73f81f26a8ea27638d8d9823d317016888a63dc4c" dependencies = [ "num-traits", "quote", - "syn 2.0.95", + "syn 2.0.117", ] [[package]] @@ -2560,7 +2554,7 @@ checksum = "1a5c6c585bc94aaf2c7b51dd4c2ba22680844aba4c687be581871a6f518c5742" dependencies = [ "proc-macro2", "quote", - "syn 2.0.95", + "syn 2.0.117", ] [[package]] @@ -2685,7 +2679,7 @@ checksum = "162ee34ebcb7c64a8abebc059ce0fee27c2262618d7b60ed8faf72fef13c3650" dependencies = [ "proc-macro2", "quote", - "syn 2.0.95", + "syn 2.0.117", ] [[package]] @@ -2872,11 +2866,9 @@ source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "26145e563e54f2cadc477553f1ec5ee650b00862f0a58bcd12cbdc5f0ea2d2f4" dependencies = [ "cfg-if", - "js-sys", "libc", "r-efi", "wasi 0.14.2+wasi-0.2.4", - "wasm-bindgen", ] [[package]] @@ -2971,7 +2963,7 @@ dependencies = [ "proc-macro-error", "proc-macro2", "quote", - "syn 2.0.95", + "syn 2.0.117", ] [[package]] @@ -3096,7 +3088,7 @@ dependencies = [ "proc-macro-error", "proc-macro2", "quote", - "syn 2.0.95", + "syn 2.0.117", ] [[package]] @@ -3602,7 +3594,7 @@ checksum = "1ec89e9337638ecdc08744df490b221a7399bf8d164eb52a665454e60e075ad6" dependencies = [ "proc-macro2", "quote", - "syn 2.0.95", + "syn 2.0.117", ] [[package]] @@ -3809,7 +3801,7 @@ checksum = "c34819042dc3d3971c46c2190835914dfbe0c3c13f61449b2997f4e9722dfa60" dependencies = [ "proc-macro2", "quote", - "syn 2.0.95", + "syn 2.0.117", ] [[package]] @@ -4503,7 +4495,7 @@ checksum = "88a9689d8d44bf9964484516275f5cd4c9b59457a6940c1d5d0ecbb94510a36b" dependencies = [ "proc-macro2", "quote", - "syn 2.0.95", + "syn 2.0.117", ] [[package]] @@ -4608,12 +4600,11 @@ checksum = "68354c5c6bd36d73ff3feceb05efa59b6acb7626617f4962be322a825e61f79a" [[package]] name = "minisign" -version = "0.8.0" +version = "0.7.3" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "e6bf96cef396a17a96f7600281aa4da9229860b7a082601b1f6db6eaa5f99ee5" +checksum = "b23ef13ff1d745b1e52397daaa247e333c607f3cff96d4df2b798dc252db974b" dependencies = [ - "ct-codecs", - "getrandom 0.3.3", + "getrandom 0.2.15", "rpassword", "scrypt", ] @@ -4693,7 +4684,7 @@ dependencies = [ "napi-derive-backend", "proc-macro2", "quote", - "syn 2.0.95", + "syn 2.0.117", ] [[package]] @@ -4706,7 +4697,7 @@ dependencies = [ "proc-macro2", "quote", "semver", - "syn 2.0.95", + "syn 2.0.117", ] [[package]] @@ -4949,7 +4940,7 @@ checksum = "ed3955f1a9c7c0c15e092f9c887db08b1fc683305fdf6eb6684f22555355e202" dependencies = [ "proc-macro2", "quote", - "syn 2.0.95", + "syn 2.0.117", ] [[package]] @@ -5026,7 +5017,7 @@ dependencies = [ "proc-macro-crate 3.2.0", "proc-macro2", "quote", - "syn 2.0.95", + "syn 2.0.117", ] [[package]] @@ -5276,7 +5267,7 @@ checksum = "a948666b637a0f465e8564c73e89d4dde00d72d4d473cc972f390fc3dcee7d9c" dependencies = [ "proc-macro2", "quote", - "syn 2.0.95", + "syn 2.0.117", ] [[package]] @@ -5383,7 +5374,7 @@ checksum = "e21f680e8c5f1900297d394627d495351b9e37761f7bbf90116bd5eeb6e80967" dependencies = [ "proc-macro2", "quote", - "syn 2.0.95", + "syn 2.0.117", ] [[package]] @@ -5422,7 +5413,7 @@ checksum = "ed71131e79889e226fb6510b90fa1a4a7495c8fdac43a4f505334fb0f1324e3e" dependencies = [ "proc-macro2", "quote", - "syn 2.0.95", + "syn 2.0.117", ] [[package]] @@ -5680,7 +5671,7 @@ dependencies = [ "proc-macro2", "proc-macro2-diagnostics", "quote", - "syn 2.0.95", + "syn 2.0.117", ] [[package]] @@ -5739,7 +5730,7 @@ dependencies = [ "pest_meta", "proc-macro2", "quote", - "syn 2.0.95", + "syn 2.0.117", ] [[package]] @@ -5924,7 +5915,7 @@ dependencies = [ "phf_shared 0.11.3", "proc-macro2", "quote", - "syn 2.0.95", + "syn 2.0.117", ] [[package]] @@ -5977,7 +5968,7 @@ checksum = "d56a66c0c55993aa927429d0f8a0abfd74f084e4d9c192cffed01e418d83eefb" dependencies = [ "proc-macro2", "quote", - "syn 2.0.95", + "syn 2.0.117", ] [[package]] @@ -6178,7 +6169,7 @@ checksum = "af066a9c399a26e020ada66a034357a868728e72cd426f3adcd35f80d88d88c8" dependencies = [ "proc-macro2", "quote", - "syn 2.0.95", + "syn 2.0.117", "version_check", "yansi", ] @@ -6199,7 +6190,7 @@ source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "a65f2e60fbf1063868558d69c6beacf412dc755f9fc020f514b7955fc914fe30" dependencies = [ "quote", - "syn 2.0.95", + "syn 2.0.117", ] [[package]] @@ -6605,7 +6596,7 @@ checksum = "bcc303e793d3734489387d205e9b186fac9c6cfacedd98cbb2e8a5943595f3e6" dependencies = [ "proc-macro2", "quote", - "syn 2.0.95", + "syn 2.0.117", ] [[package]] @@ -7295,7 +7286,7 @@ dependencies = [ "proc-macro2", "quote", "serde_derive_internals", - "syn 2.0.95", + "syn 2.0.117", ] [[package]] @@ -7321,7 +7312,7 @@ checksum = "7f81c2fde025af7e69b1d1420531c8a8811ca898919db177141a85313b1cb932" dependencies = [ "proc-macro2", "quote", - "syn 2.0.95", + "syn 2.0.117", ] [[package]] @@ -7511,7 +7502,7 @@ checksum = "d540f220d3187173da220f885ab66608367b6574e925011a9353e4badda91d79" dependencies = [ "proc-macro2", "quote", - "syn 2.0.95", + "syn 2.0.117", ] [[package]] @@ -7522,7 +7513,7 @@ checksum = "18d26a20a969b9e3fdf2fc2d9f21eda6c40e2de84c9408bb5d3b05d499aae711" dependencies = [ "proc-macro2", "quote", - "syn 2.0.95", + "syn 2.0.117", ] [[package]] @@ -7566,7 +7557,7 @@ checksum = "6c64451ba24fc7a6a2d60fc75dd9c83c90903b19028d4eff35e88fc1e86564e9" dependencies = [ "proc-macro2", "quote", - "syn 2.0.95", + "syn 2.0.117", ] [[package]] @@ -7626,7 +7617,7 @@ dependencies = [ "darling", "proc-macro2", "quote", - "syn 2.0.95", + "syn 2.0.117", ] [[package]] @@ -7664,7 +7655,7 @@ checksum = "5d69265a08751de7844521fd15003ae0a888e035773ba05695c5c759a6f89eef" dependencies = [ "proc-macro2", "quote", - "syn 2.0.95", + "syn 2.0.117", ] [[package]] @@ -7686,7 +7677,7 @@ checksum = "772ee033c0916d670af7860b6e1ef7d658a4629a6d0b4c8c3e67f09b3765b75d" dependencies = [ "proc-macro2", "quote", - "syn 2.0.95", + "syn 2.0.117", ] [[package]] @@ -8051,7 +8042,7 @@ dependencies = [ "Inflector", "proc-macro2", "quote", - "syn 2.0.95", + "syn 2.0.117", ] [[package]] @@ -8259,9 +8250,9 @@ dependencies = [ [[package]] name = "syn" -version = "2.0.95" +version = "2.0.117" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "46f71c0377baf4ef1cc3e3402ded576dccc315800fbc62dfc7fe04b009773b4a" +checksum = "e665b8803e7b1d2a727f4023456bbbbe74da67099c585258af0ad9c5013b9b99" dependencies = [ "proc-macro2", "quote", @@ -8303,7 +8294,7 @@ checksum = "c8af7666ab7b6390ab78131fb5b0fce11d6b7a6951602017c35fa82800708971" dependencies = [ "proc-macro2", "quote", - "syn 2.0.95", + "syn 2.0.117", ] [[package]] @@ -8401,7 +8392,7 @@ checksum = "f4e16beb8b2ac17db28eab8bca40e62dbfbb34c0fcdc6d9826b11b7b5d047dfd" dependencies = [ "proc-macro2", "quote", - "syn 2.0.95", + "syn 2.0.117", ] [[package]] @@ -8666,7 +8657,7 @@ dependencies = [ "serde", "serde_json", "sha2", - "syn 2.0.95", + "syn 2.0.117", "tauri-utils", "thiserror 2.0.12", "time", @@ -8744,7 +8735,7 @@ dependencies = [ "heck 0.5.0", "proc-macro2", "quote", - "syn 2.0.95", + "syn 2.0.117", "tauri-codegen", "tauri-utils", ] @@ -9016,7 +9007,7 @@ checksum = "4fee6c4efc90059e10f81e6d42c60a18f76588c3d74cb83a0b242a2b6c7504c1" dependencies = [ "proc-macro2", "quote", - "syn 2.0.95", + "syn 2.0.117", ] [[package]] @@ -9027,7 +9018,7 @@ checksum = "7f7cf42b4507d8ea322120659672cf1b9dbb93f8f2d4ecfd6e51350ff5b17a1d" dependencies = [ "proc-macro2", "quote", - "syn 2.0.95", + "syn 2.0.117", ] [[package]] @@ -9164,7 +9155,7 @@ checksum = "6e06d43f1345a3bcd39f6a56dbb7dcab2ba47e68e8ac134855e7e2bdbaf8cab8" dependencies = [ "proc-macro2", "quote", - "syn 2.0.95", + "syn 2.0.117", ] [[package]] @@ -9426,7 +9417,7 @@ checksum = "395ae124c09f9e6918a2310af6038fba074bcf474ac352496d5910dd59a2226d" dependencies = [ "proc-macro2", "quote", - "syn 2.0.95", + "syn 2.0.117", ] [[package]] @@ -10059,7 +10050,7 @@ dependencies = [ "bumpalo", "proc-macro2", "quote", - "syn 2.0.95", + "syn 2.0.117", "wasm-bindgen-shared", ] @@ -10185,7 +10176,7 @@ checksum = "1d228f15bba3b9d56dde8bddbee66fa24545bd17b48d5128ccf4a8742b18e431" dependencies = [ "proc-macro2", "quote", - "syn 2.0.95", + "syn 2.0.117", ] [[package]] @@ -10350,7 +10341,7 @@ checksum = "a47fddd13af08290e67f4acabf4b459f647552718f683a7b415d290ac744a836" dependencies = [ "proc-macro2", "quote", - "syn 2.0.95", + "syn 2.0.117", ] [[package]] @@ -10361,7 +10352,7 @@ checksum = "bd9211b69f8dcdfa817bfd14bf1c97c9188afa36f4750130fcdf3f400eca9fa8" dependencies = [ "proc-macro2", "quote", - "syn 2.0.95", + "syn 2.0.117", ] [[package]] @@ -10807,7 +10798,7 @@ dependencies = [ "async-trait", "proc-macro2", "quote", - "syn 2.0.95", + "syn 2.0.117", "wasm-bindgen", "wasm-bindgen-futures", "wasm-bindgen-macro-support", @@ -11049,7 +11040,7 @@ checksum = "2380878cad4ac9aac1e2435f3eb4020e8374b5f13c296cb75b4620ff8e229154" dependencies = [ "proc-macro2", "quote", - "syn 2.0.95", + "syn 2.0.117", "synstructure 0.13.1", ] @@ -11071,7 +11062,7 @@ checksum = "fa4f8080344d4671fb4e831a13ad1e68092748387dfc4f55e356242fae12ce3e" dependencies = [ "proc-macro2", "quote", - "syn 2.0.95", + "syn 2.0.117", ] [[package]] @@ -11091,7 +11082,7 @@ checksum = "595eed982f7d355beb85837f651fa22e90b3c044842dc7f2c2842c086f295808" dependencies = [ "proc-macro2", "quote", - "syn 2.0.95", + "syn 2.0.117", "synstructure 0.13.1", ] @@ -11112,7 +11103,7 @@ checksum = "ce36e65b0d2999d2aafac989fb249189a141aee1f53c612c1f37d72631959f69" dependencies = [ "proc-macro2", "quote", - "syn 2.0.95", + "syn 2.0.117", ] [[package]] @@ -11134,7 +11125,7 @@ checksum = "6eafa6dfb17584ea3e2bd6e76e0cc15ad7af12b09abdd1ca55961bed9b1063c6" dependencies = [ "proc-macro2", "quote", - "syn 2.0.95", + "syn 2.0.117", ] [[package]] diff --git a/crates/tauri-cli/Cargo.toml b/crates/tauri-cli/Cargo.toml index 25cef598ea34..5122a0aa16e4 100644 --- a/crates/tauri-cli/Cargo.toml +++ b/crates/tauri-cli/Cargo.toml @@ -70,7 +70,9 @@ jsonschema = { version = "0.33", default-features = false } handlebars = "6" include_dir = "0.7" dirs = "6" -minisign = "0.8" +# 0.7.4 to 0.8.0 were broken, 0.9 pulls in getrandom 0.4 with a high MSRV +# see https://github.com/tauri-apps/tauri/pull/15022 +minisign = "=0.7.3" base64 = "0.22" ureq = { version = "3", default-features = false, features = ["gzip"] } os_info = "3" diff --git a/crates/tauri-cli/src/helpers/updater_signature.rs b/crates/tauri-cli/src/helpers/updater_signature.rs index ba9012359398..c27a2c0e555d 100644 --- a/crates/tauri-cli/src/helpers/updater_signature.rs +++ b/crates/tauri-cli/src/helpers/updater_signature.rs @@ -158,6 +158,8 @@ where } /// Gets the updater secret key from the given private key and password. +/// +/// If `password` is `None`, a password is going to be prompted interactively. pub fn secret_key>( private_key: S, password: Option, @@ -204,16 +206,30 @@ where #[cfg(test)] mod tests { + use super::*; + + // This was encrypted with an empty string const PRIVATE_KEY: &str = "dW50cnVzdGVkIGNvbW1lbnQ6IHJzaWduIGVuY3J5cHRlZCBzZWNyZXQga2V5ClJXUlRZMEl5dkpDN09RZm5GeVAzc2RuYlNzWVVJelJRQnNIV2JUcGVXZUplWXZXYXpqUUFBQkFBQUFBQUFBQUFBQUlBQUFBQTZrN2RnWGh5dURxSzZiL1ZQSDdNcktiaHRxczQwMXdQelRHbjRNcGVlY1BLMTBxR2dpa3I3dDE1UTVDRDE4MXR4WlQwa1BQaXdxKy9UU2J2QmVSNXhOQWFDeG1GSVllbUNpTGJQRkhhTnROR3I5RmdUZi90OGtvaGhJS1ZTcjdZU0NyYzhQWlQ5cGM9Cg=="; - // minisign >=0.7.4,<0.8.0 couldn't handle empty passwords. + // minisign >=0.7.4,<0.8.0 couldn't handle empty passwords if the private key is encrypted with an empty string. #[test] fn empty_password_is_valid() { let path = std::env::temp_dir().join("minisign-password-text.txt"); std::fs::write(&path, b"TAURI").expect("failed to write test file"); let secret_key = - super::secret_key(PRIVATE_KEY, Some("".into())).expect("failed to resolve secret key"); - super::sign_file(&secret_key, &path).expect("failed to sign file"); + secret_key(PRIVATE_KEY, Some("".into())).expect("failed to resolve secret key"); + sign_file(&secret_key, &path).expect("failed to sign file"); + } + + // This tests the newly generated keys with empty string password works + // minisign >=0.7.4,<=0.8.0 generate keys unencrypted if the password is empty but is marked encrypted hence unusable + #[test] + fn generate_empty_password_keys_and_use() { + let KeyPair { pk, sk } = generate_key(Some("".to_owned())).unwrap(); + let pk = pub_key(pk).unwrap(); + let sk = secret_key(sk, Some("".into())).unwrap(); + let data = b"TAURI".as_slice(); + sign(Some(&pk), &sk, data, None, None).expect("failed to sign file"); } } From b345284f693613ff0845ad0e234d8a036e72fadb Mon Sep 17 00:00:00 2001 From: Tony <68118705+Legend-Master@users.noreply.github.com> Date: Tue, 3 Mar 2026 21:15:44 +0800 Subject: [PATCH 25/95] fix: resource path handles `./` path differently (#14662) * fix: resource path handles `./` path differently * Setup CI for tauri utils * Wrong job name * Fix tests * Always run tests and don't run doc tests * Add change file * Re-use `test-core` workflow * Format * Avoid path clone by calculating target first * Test tauri-utils first with step instead of matrix * Use `matrix.platform.command` * Document `current_dest` and `current_pattern` * More docs * Merge remote-tracking branch 'upstream/dev' into refactor-resource-path-iter * Test with doc tests * Revert "Test with doc tests" This reverts commit 388bee932865ac21e062e785db68b671184fdd3f. * Merge branch 'dev' into refactor-resource-path-iter * Merge branch 'dev' into refactor-resource-path-iter --- .changes/resource-path-cur-dir.md | 5 + .github/workflows/test-core.yml | 16 ++- crates/tauri-utils/src/resources.rs | 208 +++++++++++++++------------- 3 files changed, 130 insertions(+), 99 deletions(-) create mode 100644 .changes/resource-path-cur-dir.md diff --git a/.changes/resource-path-cur-dir.md b/.changes/resource-path-cur-dir.md new file mode 100644 index 000000000000..be4df9b3a88b --- /dev/null +++ b/.changes/resource-path-cur-dir.md @@ -0,0 +1,5 @@ +--- +"tauri-utils": patch:bug +--- + +Fix resource path handles `./` path differently (e.g. `./some-folder` should be the same as `some-folder`) diff --git a/.github/workflows/test-core.yml b/.github/workflows/test-core.yml index b84f4e09eb8c..59f393c314ef 100644 --- a/.github/workflows/test-core.yml +++ b/.github/workflows/test-core.yml @@ -93,11 +93,23 @@ jobs: prefix-key: v3 save-if: ${{ matrix.features.key == 'all' }} - - name: test + - name: test tauri-utils + if: ${{ !matrix.platform.cross }} + # Using --lib --bins --tests to skip doc tests + run: cargo ${{ matrix.platform.command }} --target ${{ matrix.platform.target }} ${{ matrix.features.args }} --lib --bins --tests --manifest-path crates/tauri-utils/Cargo.toml + + - name: test tauri-utils (using cross) + if: ${{ matrix.platform.cross }} + # Using --lib --bins --tests to skip doc tests + run: | + cargo install cross --git https://github.com/cross-rs/cross --rev 51f46f296253d8122c927c5bb933e3c4f27cc317 --locked + cross ${{ matrix.platform.command }} --target ${{ matrix.platform.target }} ${{ matrix.features.args }} --lib --bins --tests --manifest-path crates/tauri-utils/Cargo.toml + + - name: test tauri if: ${{ !matrix.platform.cross }} run: cargo ${{ matrix.features.key == 'no-default' && 'check' || matrix.platform.command }} --target ${{ matrix.platform.target }} ${{ matrix.features.args }} --manifest-path crates/tauri/Cargo.toml - - name: test (using cross) + - name: test tauri (using cross) if: ${{ matrix.platform.cross }} run: | cargo install cross --git https://github.com/cross-rs/cross --rev 51f46f296253d8122c927c5bb933e3c4f27cc317 --locked diff --git a/crates/tauri-utils/src/resources.rs b/crates/tauri-utils/src/resources.rs index dfba0746c960..3fd0290b78ac 100644 --- a/crates/tauri-utils/src/resources.rs +++ b/crates/tauri-utils/src/resources.rs @@ -97,9 +97,8 @@ impl<'a> ResourcePaths<'a> { iter: ResourcePathsIter { pattern_iter: PatternIter::Slice(patterns.iter()), allow_walk, - current_pattern: None, - walk_iter: None, - glob_iter: None, + current_dest: None, + current_iter: None, }, } } @@ -110,9 +109,8 @@ impl<'a> ResourcePaths<'a> { iter: ResourcePathsIter { pattern_iter: PatternIter::Map(patterns.iter()), allow_walk, - current_pattern: None, - walk_iter: None, - glob_iter: None, + current_dest: None, + current_iter: None, }, } } @@ -132,122 +130,139 @@ pub struct ResourcePathsIter<'a> { /// whether the resource paths allows directories or not. allow_walk: bool, - /// The (key, value) of map when `pattern_iter` is a [`PatternIter::Map`], + /// The value of map when [`Self::pattern_iter`] is a [`PatternIter::Map`], /// used for determining [`Resource::target`] - current_pattern: Option<(String, PathBuf)>, - - walk_iter: Option, - glob_iter: Option, + current_dest: Option, + /// The iter for the current pattern. The cycle goes like this: + /// [`ResourcePaths::next`] -> [`Self::next`] -> [`Self::pattern_iter::next`] -> [`Self::current_iter::next`] + current_iter: Option, } -impl ResourcePathsIter<'_> { - fn next_glob_iter(&mut self) -> Option> { - let entry = self.glob_iter.as_mut().unwrap().next()?; +#[derive(Debug)] +enum ResourcePathsInnerIter { + Walk { + iter: walkdir::IntoIter, + /// The key of map when [`ResourcePathsIter::pattern_iter`] is a [`PatternIter::Map`], + /// used for determining [`Resource::target`] + current_pattern: Option, + }, + Glob { + iter: glob::Paths, + }, +} - let entry = match entry { - Ok(entry) => entry, - Err(err) => return Some(Err(err.into())), - }; +impl Iterator for ResourcePathsInnerIter { + type Item = crate::Result; - self.next_current_path(normalize(&entry)) + fn next(&mut self) -> Option> { + match self { + ResourcePathsInnerIter::Walk { iter, .. } => Some( + iter + .next()? + .map(|entry| entry.into_path()) + .map_err(Into::into), + ), + ResourcePathsInnerIter::Glob { iter } => Some(iter.next()?.map_err(Into::into)), + } } +} - fn next_walk_iter(&mut self) -> Option> { - let entry = self.walk_iter.as_mut().unwrap().next()?; - - let entry = match entry { - Ok(entry) => entry, - Err(err) => return Some(Err(err.into())), - }; - - self.next_current_path(normalize(entry.path())) +impl ResourcePathsIter<'_> { + fn next_current_iter(&mut self) -> Option> { + let current_iter = self.current_iter.as_mut().unwrap(); + let entry = current_iter.next()?; + + Some(match entry { + Ok(entry) => { + // Skip directories + if entry.is_dir() { + self.next_current_iter()? + } else { + self.resource_from_path(normalize(&entry)) + } + } + Err(error) => Err(error), + }) } - fn resource_from_path(&mut self, path: &Path) -> crate::Result { + fn resource_from_path(&self, path: PathBuf) -> crate::Result { if !path.exists() { - return Err(crate::Error::ResourcePathNotFound(path.to_path_buf())); + return Err(crate::Error::ResourcePathNotFound(path)); } Ok(Resource { - path: path.to_path_buf(), - target: if let Some((pattern, dest)) = &self.current_pattern { - // if processing a directory, preserve directory structure under current_dest - if self.walk_iter.is_some() { - dest.join(path.strip_prefix(pattern).unwrap_or(path)) - } else if dest.components().count() == 0 { - // if current_dest is empty while processing a file pattern or glob - // we preserve the file name as it is - PathBuf::from(path.file_name().unwrap()) - } else if self.glob_iter.is_some() { - // if processing a glob and current_dest is not empty - // we put all globbed paths under current_dest - // preserving the file name as it is - dest.join(path.file_name().unwrap()) - } else { - dest.clone() + target: if let Some(dest) = &self.current_dest { + match &self.current_iter { + Some(current_iter) => match current_iter { + // if processing a directory, preserve directory structure under current_dest + ResourcePathsInnerIter::Walk { + current_pattern, .. + } => { + if let Some(pattern) = current_pattern { + dest.join(path.strip_prefix(pattern).unwrap_or(&path)) + } else { + dest.join(&path) + } + } + // if processing a glob and current_dest is not empty + // we put all globbed paths under current_dest + // preserving the file name as it is + ResourcePathsInnerIter::Glob { .. } => dest.join(path.file_name().unwrap()), + }, + None => dest.clone(), } } else { - // If `pattern_iter` is a [`PatternIter::Slice`] - resource_relpath(path) + // If [`ResourcePathsIter::pattern_iter`] is a [`PatternIter::Slice`] + resource_relpath(&path) }, + path, }) } - fn next_current_path(&mut self, path: PathBuf) -> Option> { - let is_dir = path.is_dir(); - - if is_dir { - if self.glob_iter.is_some() { - return self.next(); - } - - if !self.allow_walk { - return Some(Err(crate::Error::NotAllowedToWalkDir(path.to_path_buf()))); - } - - if self.walk_iter.is_none() { - self.walk_iter = Some(WalkDir::new(&path).into_iter()); - } - - match self.next_walk_iter() { - Some(resource) => Some(resource), - None => { - self.walk_iter = None; - self.next() - } - } - } else { - Some(self.resource_from_path(&path)) - } - } - fn next_pattern(&mut self) -> Option> { - self.current_pattern = None; + self.current_dest = None; let pattern = match &mut self.pattern_iter { PatternIter::Slice(iter) => iter.next()?, PatternIter::Map(iter) => { let (pattern, dest) = iter.next()?; - self.current_pattern = Some((pattern.clone(), resource_relpath(Path::new(dest)))); + self.current_dest = Some(resource_relpath(Path::new(dest))); pattern } }; if pattern.contains('*') { - self.glob_iter = match glob::glob(pattern) { - Ok(glob) => Some(glob), + self.current_iter = match glob::glob(pattern) { + Ok(glob) => Some(ResourcePathsInnerIter::Glob { iter: glob }), Err(error) => return Some(Err(error.into())), }; - match self.next_glob_iter() { + match self.next_current_iter() { Some(r) => return Some(r), None => { - self.glob_iter = None; + self.current_iter = None; return Some(Err(crate::Error::GlobPathNotFound(pattern.clone()))); } } + } else { + let path = normalize(Path::new(pattern)); + if path.is_dir() { + if !self.allow_walk { + return Some(Err(crate::Error::NotAllowedToWalkDir(path))); + } + self.current_iter = Some(ResourcePathsInnerIter::Walk { + iter: WalkDir::new(&path).into_iter(), + current_pattern: if matches!(self.pattern_iter, PatternIter::Map(_)) { + Some(path) + } else { + None + }, + }); + } else { + return Some(self.resource_from_path(path)); + } } - self.next_current_path(normalize(Path::new(pattern))) + self.next_current_iter() } } @@ -263,17 +278,10 @@ impl Iterator for ResourcePathsIter<'_> { type Item = crate::Result; fn next(&mut self) -> Option> { - if self.walk_iter.is_some() { - match self.next_walk_iter() { + if self.current_iter.is_some() { + match self.next_current_iter() { Some(r) => return Some(r), - None => self.walk_iter = None, - } - } - - if self.glob_iter.is_some() { - match self.next_glob_iter() { - Some(r) => return Some(r), - None => self.glob_iter = None, + None => self.current_iter = None, } } @@ -322,6 +330,7 @@ mod tests { "src-tauri/Cargo.toml", "src-tauri/Tauri.toml", "src-tauri/build.rs", + "src-tauri/some-folder/some-file.txt", "src/assets/javascript.svg", "src/assets/tauri.svg", "src/assets/rust.svg", @@ -403,11 +412,11 @@ mod tests { // From `../src/textures/**/*` ( "../src/textures/ground/earth.tex", - "_up_/src/textures/earth.tex", + "_up_/src/textures/ground/earth.tex", ), ( "../src/textures/ground/sand.tex", - "_up_/src/textures/sand.tex", + "_up_/src/textures/ground/sand.tex", ), ("../src/textures/water.tex", "_up_/src/textures/water.tex"), ("../src/textures/fire.tex", "_up_/src/textures/fire.tex"), @@ -483,6 +492,7 @@ mod tests { ("../src/tiles/**/*", "tiles"), ("*.toml", ""), ("*.conf.json", "json"), + ("./some-folder/", "some-target-folder/"), ("../non-existent-file", "asd"), // invalid case ("../non/*", "asd"), // invalid case ]), @@ -511,6 +521,10 @@ mod tests { ("Cargo.toml", "Cargo.toml"), ("Tauri.toml", "Tauri.toml"), ("tauri.conf.json", "json/tauri.conf.json"), + ( + "some-folder/some-file.txt", + "some-target-folder/some-file.txt", + ), ]); assert_eq!(resources.len(), expected.len()); @@ -584,7 +598,7 @@ mod tests { .iter() .collect::>(); - assert_eq!(resources.len(), 4); + assert_eq!(resources.len(), 5); assert!(resources.iter().all(|r| r.is_err())); @@ -617,7 +631,7 @@ mod tests { .iter() .filter(|r| matches!(r, Err(crate::Error::GlobPathNotFound(_)))) .count(), - 1 + 2 ); } } From 24c174c32745cd35501fe0508eecda9ee28b9c17 Mon Sep 17 00:00:00 2001 From: Tony <68118705+Legend-Master@users.noreply.github.com> Date: Tue, 3 Mar 2026 21:27:55 +0800 Subject: [PATCH 26/95] refactor(cli): reduce some nesting code (#14844) * refactor(cli): reduce some nesting code * Handle all paths and config file change not first * Bring back is_ignore --- crates/tauri-cli/src/dev.rs | 4 +- crates/tauri-cli/src/interface/rust.rs | 77 ++++++++++++++------------ 2 files changed, 42 insertions(+), 39 deletions(-) diff --git a/crates/tauri-cli/src/dev.rs b/crates/tauri-cli/src/dev.rs index 3a6d58140547..468aa2f92f9f 100644 --- a/crates/tauri-cli/src/dev.rs +++ b/crates/tauri-cli/src/dev.rs @@ -241,9 +241,7 @@ pub fn setup( .canonicalize() .fs_context("failed to canonicalize path", path.to_path_buf())?; - let ip = options - .host - .unwrap_or_else(|| Ipv4Addr::new(127, 0, 0, 1).into()); + let ip = options.host.unwrap_or_else(|| Ipv4Addr::LOCALHOST.into()); let server_url = builtin_dev_server::start(path, ip, options.port) .context("failed to start builtin dev server")?; diff --git a/crates/tauri-cli/src/interface/rust.rs b/crates/tauri-cli/src/interface/rust.rs index d6026b3b24dd..9bd46c585d00 100644 --- a/crates/tauri-cli/src/interface/rust.rs +++ b/crates/tauri-cli/src/interface/rust.rs @@ -29,7 +29,7 @@ use tauri_utils::config::{parse::is_configuration_file, DeepLinkProtocol, Runner use super::{AppSettings, DevProcess, ExitReason}; use crate::{ - error::{Context, Error, ErrorExt}, + error::{bail, Context, Error, ErrorExt}, helpers::{ app_paths::Dirs, config::{nsis_settings, reload_config, wix_settings, BundleResources, Config, ConfigMetadata}, @@ -144,9 +144,10 @@ impl Rust { } }) .unwrap(); + let manifest_path = tauri_dir.join("Cargo.toml"); watcher - .watch(tauri_dir.join("Cargo.toml"), RecursiveMode::NonRecursive) - .with_context(|| format!("failed to watch {}", tauri_dir.join("Cargo.toml").display()))?; + .watch(&manifest_path, RecursiveMode::NonRecursive) + .with_context(|| format!("failed to watch {}", manifest_path.display()))?; let (manifest, modified) = rewrite_manifest(config, tauri_dir)?; if modified { // Wait for the modified event so we don't trigger a re-build later on @@ -555,43 +556,47 @@ impl Rust { } } - loop { - if let Ok(events) = rx.recv() { - for event in events { - if event.kind.is_access() { - continue; - } + while let Ok(events) = rx.recv() { + let paths: Vec = events + .into_iter() + .filter(|event| !event.kind.is_access()) + .flat_map(|event| event.event.paths) + .filter(|path| !ignore_matcher.is_ignore(path, path.is_dir())) + .collect(); - if let Some(event_path) = event.paths.first() { - if !ignore_matcher.is_ignore(event_path, event_path.is_dir()) { - if is_configuration_file(self.app_settings.target_platform, event_path) - && reload_config(config, merge_configs, dirs.tauri).is_ok() - { - let (manifest, modified) = rewrite_manifest(config, dirs.tauri)?; - if modified { - *self.app_settings.manifest.lock().unwrap() = manifest; - // no need to run the watcher logic, the manifest was modified - // and it will trigger the watcher again - continue; - } - } - - log::info!( - "File {} changed. Rebuilding application...", - display_path(event_path.strip_prefix(dirs.frontend).unwrap_or(event_path)) - ); - - child.kill().context("failed to kill app process")?; - - // wait for the process to exit - // note that on mobile, kill() already waits for the process to exit (duct implementation) - let _ = child.wait(); - child = run(self, config)?; - } - } + let config_file_changed = paths + .iter() + .any(|path| is_configuration_file(self.app_settings.target_platform, path)); + if config_file_changed && reload_config(config, merge_configs, dirs.tauri).is_ok() { + let (manifest, modified) = rewrite_manifest(config, dirs.tauri)?; + if modified { + *self.app_settings.manifest.lock().unwrap() = manifest; + // no need to run the watcher logic, the manifest was modified + // and it will trigger the watcher again + continue; } } + + let Some(first_changed_path) = paths.first() else { + continue; + }; + + log::info!( + "File {} changed. Rebuilding application...", + display_path( + first_changed_path + .strip_prefix(dirs.frontend) + .unwrap_or(first_changed_path) + ) + ); + + child.kill().context("failed to kill app process")?; + // wait for the process to exit + // note that on mobile, kill() already waits for the process to exit (duct implementation) + let _ = child.wait(); + child = run(self, config)?; } + bail!("File watcher exited unexpectedly") } } From ceb6b65c860666ccaa7a95e49686d9d9f48acee3 Mon Sep 17 00:00:00 2001 From: Tony <68118705+Legend-Master@users.noreply.github.com> Date: Tue, 3 Mar 2026 22:37:10 +0800 Subject: [PATCH 27/95] fix(test): disable `resolve_resource_dir` on Android (#15026) --- crates/tauri-utils/src/platform.rs | 1 + 1 file changed, 1 insertion(+) diff --git a/crates/tauri-utils/src/platform.rs b/crates/tauri-utils/src/platform.rs index 6eaaf3ffe38a..4ce3d2fac403 100644 --- a/crates/tauri-utils/src/platform.rs +++ b/crates/tauri-utils/src/platform.rs @@ -398,6 +398,7 @@ mod tests { use crate::{Env, PackageInfo}; #[test] + #[cfg(not(target_os = "android"))] fn resolve_resource_dir() { let package_info = PackageInfo { name: "MyApp".into(), From 6f0f7124b7902f8d64cc29deda09aee3d9fe16b5 Mon Sep 17 00:00:00 2001 From: "github-actions[bot]" <41898282+github-actions[bot]@users.noreply.github.com> Date: Wed, 4 Mar 2026 16:37:29 +0800 Subject: [PATCH 28/95] apply version updates (#14897) Co-authored-by: github-actions[bot] <41898282+github-actions[bot]@users.noreply.github.com> --- .changes/features-separator.md | 6 ----- .changes/fix-missing-options.md | 6 ----- .../fix-nondeterministic-context-codegen.md | 7 ----- .changes/fix-wix-registry-search-order.md | 5 ---- .changes/log-binary-patching.md | 7 ----- .changes/resource-path-cur-dir.md | 5 ---- .changes/sign-no-password.md | 6 ----- Cargo.lock | 26 +++++++++---------- crates/tauri-build/CHANGELOG.md | 7 +++++ crates/tauri-build/Cargo.toml | 6 ++--- crates/tauri-bundler/CHANGELOG.md | 14 ++++++++++ crates/tauri-bundler/Cargo.toml | 4 +-- crates/tauri-cli/CHANGELOG.md | 17 ++++++++++++ crates/tauri-cli/Cargo.toml | 6 ++--- crates/tauri-cli/config.schema.json | 2 +- crates/tauri-cli/metadata-v2.json | 8 +++--- crates/tauri-codegen/CHANGELOG.md | 6 +++++ crates/tauri-codegen/Cargo.toml | 4 +-- crates/tauri-macros/CHANGELOG.md | 7 +++++ crates/tauri-macros/Cargo.toml | 6 ++--- crates/tauri-plugin/CHANGELOG.md | 6 +++++ crates/tauri-plugin/Cargo.toml | 4 +-- crates/tauri-runtime-wry/CHANGELOG.md | 7 +++++ crates/tauri-runtime-wry/Cargo.toml | 6 ++--- crates/tauri-runtime/CHANGELOG.md | 6 +++++ crates/tauri-runtime/Cargo.toml | 4 +-- .../schemas/config.schema.json | 2 +- crates/tauri-utils/CHANGELOG.md | 9 +++++++ crates/tauri-utils/Cargo.toml | 2 +- crates/tauri/CHANGELOG.md | 10 +++++++ crates/tauri/Cargo.toml | 14 +++++----- packages/cli/CHANGELOG.md | 16 ++++++++++++ packages/cli/package.json | 2 +- 33 files changed, 153 insertions(+), 90 deletions(-) delete mode 100644 .changes/features-separator.md delete mode 100644 .changes/fix-missing-options.md delete mode 100644 .changes/fix-nondeterministic-context-codegen.md delete mode 100644 .changes/fix-wix-registry-search-order.md delete mode 100644 .changes/log-binary-patching.md delete mode 100644 .changes/resource-path-cur-dir.md delete mode 100644 .changes/sign-no-password.md diff --git a/.changes/features-separator.md b/.changes/features-separator.md deleted file mode 100644 index 02277d87e07d..000000000000 --- a/.changes/features-separator.md +++ /dev/null @@ -1,6 +0,0 @@ ---- -"tauri-cli": patch:bug -"@tauri-apps/cli": patch:bug ---- - -Support comma-separated list of Cargo features on all commands. diff --git a/.changes/fix-missing-options.md b/.changes/fix-missing-options.md deleted file mode 100644 index 957f07a64f59..000000000000 --- a/.changes/fix-missing-options.md +++ /dev/null @@ -1,6 +0,0 @@ ---- -"tauri-cli": patch:bug -"@tauri-apps/cli": patch:bug ---- - -Fix missing Cargo args when running mobile dev and build commands. diff --git a/.changes/fix-nondeterministic-context-codegen.md b/.changes/fix-nondeterministic-context-codegen.md deleted file mode 100644 index 5b4d8237a072..000000000000 --- a/.changes/fix-nondeterministic-context-codegen.md +++ /dev/null @@ -1,7 +0,0 @@ ---- -'tauri-utils': 'patch:bug' ---- - -Sort csp/plugin/header configs when generating HashMap constructors so that `generate_context!` is deterministic. - -See: https://github.com/tauri-apps/tauri/issues/14978 for more information \ No newline at end of file diff --git a/.changes/fix-wix-registry-search-order.md b/.changes/fix-wix-registry-search-order.md deleted file mode 100644 index 10e11326ced6..000000000000 --- a/.changes/fix-wix-registry-search-order.md +++ /dev/null @@ -1,5 +0,0 @@ ---- -"tauri-bundler": patch:bug ---- - -Fix WIX installer registry search order so that the named `InstallDir` key takes priority over the NSIS default key, preventing install location from changing on updates. diff --git a/.changes/log-binary-patching.md b/.changes/log-binary-patching.md deleted file mode 100644 index fafcc316f437..000000000000 --- a/.changes/log-binary-patching.md +++ /dev/null @@ -1,7 +0,0 @@ ---- -"tauri-bundler": patch:changes -"tauri-cli": patch:changes -"@tauri-apps/cli": patch:changes ---- - -Log patching bundle type information again diff --git a/.changes/resource-path-cur-dir.md b/.changes/resource-path-cur-dir.md deleted file mode 100644 index be4df9b3a88b..000000000000 --- a/.changes/resource-path-cur-dir.md +++ /dev/null @@ -1,5 +0,0 @@ ---- -"tauri-utils": patch:bug ---- - -Fix resource path handles `./` path differently (e.g. `./some-folder` should be the same as `some-folder`) diff --git a/.changes/sign-no-password.md b/.changes/sign-no-password.md deleted file mode 100644 index c9a30d9381de..000000000000 --- a/.changes/sign-no-password.md +++ /dev/null @@ -1,6 +0,0 @@ ---- -"tauri-cli": patch:bug -"@tauri-apps/cli": patch:bug ---- - -Fix updater signing private keys generated using `tauri signer generate` with empty password can't be used (The keys generated during tauri were broken between v2.9.3 and v2.10.0, you'll need to regenerate them) diff --git a/Cargo.lock b/Cargo.lock index 059dabbeeaf2..ffa7c32f7962 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -1320,7 +1320,7 @@ source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "117725a109d387c937a1533ce01b450cbde6b88abceea8473c4d7a85853cda3c" dependencies = [ "lazy_static", - "windows-sys 0.59.0", + "windows-sys 0.48.0", ] [[package]] @@ -4319,7 +4319,7 @@ source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "fc2f4eb4bc735547cfed7c0a4922cbd04a4655978c09b54f1f7b228750664c34" dependencies = [ "cfg-if", - "windows-targets 0.52.6", + "windows-targets 0.48.5", ] [[package]] @@ -8420,7 +8420,7 @@ checksum = "61c41af27dd6d1e27b1b16b489db798443478cef1f06a660c96db617ba5de3b1" [[package]] name = "tauri" -version = "2.10.2" +version = "2.10.3" dependencies = [ "anyhow", "bytes", @@ -8481,7 +8481,7 @@ dependencies = [ [[package]] name = "tauri-build" -version = "2.5.5" +version = "2.5.6" dependencies = [ "anyhow", "cargo_toml", @@ -8503,7 +8503,7 @@ dependencies = [ [[package]] name = "tauri-bundler" -version = "2.8.0" +version = "2.8.1" dependencies = [ "anyhow", "ar", @@ -8549,7 +8549,7 @@ dependencies = [ [[package]] name = "tauri-cli" -version = "2.10.0" +version = "2.10.1" dependencies = [ "ar", "axum", @@ -8643,7 +8643,7 @@ dependencies = [ [[package]] name = "tauri-codegen" -version = "2.5.4" +version = "2.5.5" dependencies = [ "base64 0.22.1", "brotli", @@ -8730,7 +8730,7 @@ dependencies = [ [[package]] name = "tauri-macros" -version = "2.5.4" +version = "2.5.5" dependencies = [ "heck 0.5.0", "proc-macro2", @@ -8742,7 +8742,7 @@ dependencies = [ [[package]] name = "tauri-plugin" -version = "2.5.3" +version = "2.5.4" dependencies = [ "anyhow", "glob", @@ -8790,7 +8790,7 @@ dependencies = [ [[package]] name = "tauri-runtime" -version = "2.10.0" +version = "2.10.1" dependencies = [ "cookie", "dpi", @@ -8813,7 +8813,7 @@ dependencies = [ [[package]] name = "tauri-runtime-wry" -version = "2.10.0" +version = "2.10.1" dependencies = [ "gtk", "http 1.3.1", @@ -8863,7 +8863,7 @@ dependencies = [ [[package]] name = "tauri-utils" -version = "2.8.2" +version = "2.8.3" dependencies = [ "aes-gcm", "anyhow", @@ -10245,7 +10245,7 @@ version = "0.1.9" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "cf221c93e13a30d793f7645a0e7762c55d169dbb0a49671918a2319d289b10bb" dependencies = [ - "windows-sys 0.59.0", + "windows-sys 0.48.0", ] [[package]] diff --git a/crates/tauri-build/CHANGELOG.md b/crates/tauri-build/CHANGELOG.md index fb3464970c34..121ffcf8668d 100644 --- a/crates/tauri-build/CHANGELOG.md +++ b/crates/tauri-build/CHANGELOG.md @@ -1,5 +1,12 @@ # Changelog +## \[2.5.6] + +### Dependencies + +- Upgraded to `tauri-utils@2.8.3` +- Upgraded to `tauri-codegen@2.5.5` + ## \[2.5.5] ### Dependencies diff --git a/crates/tauri-build/Cargo.toml b/crates/tauri-build/Cargo.toml index 5c63381161ef..e12c041471b9 100644 --- a/crates/tauri-build/Cargo.toml +++ b/crates/tauri-build/Cargo.toml @@ -1,6 +1,6 @@ [package] name = "tauri-build" -version = "2.5.5" +version = "2.5.6" description = "build time code to pair with https://crates.io/crates/tauri" exclude = ["CHANGELOG.md", "/target"] readme = "README.md" @@ -26,8 +26,8 @@ targets = [ [dependencies] anyhow = "1" quote = { version = "1", optional = true } -tauri-codegen = { version = "2.5.4", path = "../tauri-codegen", optional = true } -tauri-utils = { version = "2.8.2", path = "../tauri-utils", features = [ +tauri-codegen = { version = "2.5.5", path = "../tauri-codegen", optional = true } +tauri-utils = { version = "2.8.3", path = "../tauri-utils", features = [ "build", "resources", ] } diff --git a/crates/tauri-bundler/CHANGELOG.md b/crates/tauri-bundler/CHANGELOG.md index 506d996ff8e4..b2fec9ab6a18 100644 --- a/crates/tauri-bundler/CHANGELOG.md +++ b/crates/tauri-bundler/CHANGELOG.md @@ -1,5 +1,19 @@ # Changelog +## \[2.8.1] + +### Bug Fixes + +- [`6252432f0`](https://www.github.com/tauri-apps/tauri/commit/6252432f0757d896d7a61819bbff127efac5a156) ([#14945](https://www.github.com/tauri-apps/tauri/pull/14945) by [@veeceey](https://www.github.com/tauri-apps/tauri/../../veeceey)) Fix WIX installer registry search order so that the named `InstallDir` key takes priority over the NSIS default key, preventing install location from changing on updates. + +### What's Changed + +- [`7be58a1c6`](https://www.github.com/tauri-apps/tauri/commit/7be58a1c643a7ed6d0f484a7e1134022618eb2b2) ([#14894](https://www.github.com/tauri-apps/tauri/pull/14894) by [@Legend-Master](https://www.github.com/tauri-apps/tauri/../../Legend-Master)) Log patching bundle type information again + +### Dependencies + +- Upgraded to `tauri-utils@2.8.3` + ## \[2.8.0] ### Enhancements diff --git a/crates/tauri-bundler/Cargo.toml b/crates/tauri-bundler/Cargo.toml index 428229385037..bacf6b64590a 100644 --- a/crates/tauri-bundler/Cargo.toml +++ b/crates/tauri-bundler/Cargo.toml @@ -1,6 +1,6 @@ [package] name = "tauri-bundler" -version = "2.8.0" +version = "2.8.1" authors = [ "George Burton ", "Tauri Programme within The Commons Conservancy", @@ -15,7 +15,7 @@ rust-version = "1.77.2" exclude = ["CHANGELOG.md", "/target", "rustfmt.toml"] [dependencies] -tauri-utils = { version = "2.8.2", path = "../tauri-utils", features = [ +tauri-utils = { version = "2.8.3", path = "../tauri-utils", features = [ "resources", ] } image = "0.25" diff --git a/crates/tauri-cli/CHANGELOG.md b/crates/tauri-cli/CHANGELOG.md index 4d38ef1c8340..601cffc02c65 100644 --- a/crates/tauri-cli/CHANGELOG.md +++ b/crates/tauri-cli/CHANGELOG.md @@ -1,5 +1,22 @@ # Changelog +## \[2.10.1] + +### Bug Fixes + +- [`35c35f27a`](https://www.github.com/tauri-apps/tauri/commit/35c35f27aedc430b602ec74059b271128c15ad36) ([#14931](https://www.github.com/tauri-apps/tauri/pull/14931) by [@lucasfernog](https://www.github.com/tauri-apps/tauri/../../lucasfernog)) Support comma-separated list of Cargo features on all commands. +- [`0d1cb83ba`](https://www.github.com/tauri-apps/tauri/commit/0d1cb83bab2aa482c7d73116893fd7ff6aa56283) ([#14932](https://www.github.com/tauri-apps/tauri/pull/14932) by [@lucasfernog](https://www.github.com/tauri-apps/tauri/../../lucasfernog)) Fix missing Cargo args when running mobile dev and build commands. +- [`33754ae5e`](https://www.github.com/tauri-apps/tauri/commit/33754ae5e3740d022483b6164511c5c001a3c24b) ([#15022](https://www.github.com/tauri-apps/tauri/pull/15022) by [@Legend-Master](https://www.github.com/tauri-apps/tauri/../../Legend-Master)) Fix updater signing private keys generated using `tauri signer generate` with empty password can't be used (The keys generated during tauri were broken between v2.9.3 and v2.10.0, you'll need to regenerate them) + +### What's Changed + +- [`7be58a1c6`](https://www.github.com/tauri-apps/tauri/commit/7be58a1c643a7ed6d0f484a7e1134022618eb2b2) ([#14894](https://www.github.com/tauri-apps/tauri/pull/14894) by [@Legend-Master](https://www.github.com/tauri-apps/tauri/../../Legend-Master)) Log patching bundle type information again + +### Dependencies + +- Upgraded to `tauri-utils@2.8.3` +- Upgraded to `tauri-bundler@2.8.1` + ## \[2.10.0] ### Enhancements diff --git a/crates/tauri-cli/Cargo.toml b/crates/tauri-cli/Cargo.toml index 5122a0aa16e4..370cdc623c7e 100644 --- a/crates/tauri-cli/Cargo.toml +++ b/crates/tauri-cli/Cargo.toml @@ -1,6 +1,6 @@ [package] name = "tauri-cli" -version = "2.10.0" +version = "2.10.1" authors = ["Tauri Programme within The Commons Conservancy"] edition = "2021" rust-version = "1.77.2" @@ -47,7 +47,7 @@ sublime_fuzzy = "0.7" clap_complete = "4" clap = { version = "4", features = ["derive", "env"] } thiserror = "2" -tauri-bundler = { version = "2.8.0", default-features = false, path = "../tauri-bundler" } +tauri-bundler = { version = "2.8.1", default-features = false, path = "../tauri-bundler" } colored = "2" serde = { version = "1", features = ["derive"] } serde_json = { version = "1", features = ["preserve_order"] } @@ -58,7 +58,7 @@ shared_child = "1" duct = "1.0" toml_edit = { version = "0.24", features = ["serde"] } json-patch = "3" -tauri-utils = { version = "2.8.2", path = "../tauri-utils", features = [ +tauri-utils = { version = "2.8.3", path = "../tauri-utils", features = [ "isolation", "schema", "config-json5", diff --git a/crates/tauri-cli/config.schema.json b/crates/tauri-cli/config.schema.json index b56437751f55..664b695e186a 100644 --- a/crates/tauri-cli/config.schema.json +++ b/crates/tauri-cli/config.schema.json @@ -1,6 +1,6 @@ { "$schema": "http://json-schema.org/draft-07/schema#", - "$id": "https://schema.tauri.app/config/2.10.2", + "$id": "https://schema.tauri.app/config/2.10.3", "title": "Config", "description": "The Tauri configuration object.\n It is read from a file where you can define your frontend assets,\n configure the bundler and define a tray icon.\n\n The configuration file is generated by the\n [`tauri init`](https://v2.tauri.app/reference/cli/#init) command that lives in\n your Tauri application source directory (src-tauri).\n\n Once generated, you may modify it at will to customize your Tauri application.\n\n ## File Formats\n\n By default, the configuration is defined as a JSON file named `tauri.conf.json`.\n\n Tauri also supports JSON5 and TOML files via the `config-json5` and `config-toml` Cargo features, respectively.\n The JSON5 file name must be either `tauri.conf.json` or `tauri.conf.json5`.\n The TOML file name is `Tauri.toml`.\n\n ## Platform-Specific Configuration\n\n In addition to the default configuration file, Tauri can\n read a platform-specific configuration from `tauri.linux.conf.json`,\n `tauri.windows.conf.json`, `tauri.macos.conf.json`, `tauri.android.conf.json` and `tauri.ios.conf.json`\n (or `Tauri.linux.toml`, `Tauri.windows.toml`, `Tauri.macos.toml`, `Tauri.android.toml` and `Tauri.ios.toml` if the `Tauri.toml` format is used),\n which gets merged with the main configuration object.\n\n ## Configuration Structure\n\n The configuration is composed of the following objects:\n\n - [`app`](#appconfig): The Tauri configuration\n - [`build`](#buildconfig): The build configuration\n - [`bundle`](#bundleconfig): The bundle configurations\n - [`plugins`](#pluginconfig): The plugins configuration\n\n Example tauri.config.json file:\n\n ```json\n {\n \"productName\": \"tauri-app\",\n \"version\": \"0.1.0\",\n \"build\": {\n \"beforeBuildCommand\": \"\",\n \"beforeDevCommand\": \"\",\n \"devUrl\": \"http://localhost:3000\",\n \"frontendDist\": \"../dist\"\n },\n \"app\": {\n \"security\": {\n \"csp\": null\n },\n \"windows\": [\n {\n \"fullscreen\": false,\n \"height\": 600,\n \"resizable\": true,\n \"title\": \"Tauri App\",\n \"width\": 800\n }\n ]\n },\n \"bundle\": {},\n \"plugins\": {}\n }\n ```", "type": "object", diff --git a/crates/tauri-cli/metadata-v2.json b/crates/tauri-cli/metadata-v2.json index 59f76420ee20..3e034233271e 100644 --- a/crates/tauri-cli/metadata-v2.json +++ b/crates/tauri-cli/metadata-v2.json @@ -1,9 +1,9 @@ { "cli.js": { - "version": "2.10.0", + "version": "2.10.1", "node": ">= 10.0.0" }, - "tauri": "2.10.2", - "tauri-build": "2.5.5", - "tauri-plugin": "2.5.3" + "tauri": "2.10.3", + "tauri-build": "2.5.6", + "tauri-plugin": "2.5.4" } diff --git a/crates/tauri-codegen/CHANGELOG.md b/crates/tauri-codegen/CHANGELOG.md index 3b721d32936c..d874ccd7631f 100644 --- a/crates/tauri-codegen/CHANGELOG.md +++ b/crates/tauri-codegen/CHANGELOG.md @@ -1,5 +1,11 @@ # Changelog +## \[2.5.5] + +### Dependencies + +- Upgraded to `tauri-utils@2.8.3` + ## \[2.5.4] ### Bug Fixes diff --git a/crates/tauri-codegen/Cargo.toml b/crates/tauri-codegen/Cargo.toml index 19130b902879..e1154e67687c 100644 --- a/crates/tauri-codegen/Cargo.toml +++ b/crates/tauri-codegen/Cargo.toml @@ -1,6 +1,6 @@ [package] name = "tauri-codegen" -version = "2.5.4" +version = "2.5.5" description = "code generation meant to be consumed inside of `tauri` through `tauri-build` or `tauri-macros`" exclude = ["CHANGELOG.md", "/target"] readme = "README.md" @@ -20,7 +20,7 @@ quote = "1" syn = "2" serde = { version = "1", features = ["derive"] } serde_json = "1" -tauri-utils = { version = "2.8.2", path = "../tauri-utils", features = [ +tauri-utils = { version = "2.8.3", path = "../tauri-utils", features = [ "build", ] } thiserror = "2" diff --git a/crates/tauri-macros/CHANGELOG.md b/crates/tauri-macros/CHANGELOG.md index 956c665e6d9d..2406a7af5f42 100644 --- a/crates/tauri-macros/CHANGELOG.md +++ b/crates/tauri-macros/CHANGELOG.md @@ -1,5 +1,12 @@ # Changelog +## \[2.5.5] + +### Dependencies + +- Upgraded to `tauri-utils@2.8.3` +- Upgraded to `tauri-codegen@2.5.5` + ## \[2.5.4] ### Dependencies diff --git a/crates/tauri-macros/Cargo.toml b/crates/tauri-macros/Cargo.toml index b18d1e20a847..29ba5044f629 100644 --- a/crates/tauri-macros/Cargo.toml +++ b/crates/tauri-macros/Cargo.toml @@ -1,6 +1,6 @@ [package] name = "tauri-macros" -version = "2.5.4" +version = "2.5.5" description = "Macros for the tauri crate." exclude = ["CHANGELOG.md", "/target"] readme = "README.md" @@ -20,8 +20,8 @@ proc-macro2 = { version = "1", features = ["span-locations"] } quote = "1" syn = { version = "2", features = ["full"] } heck = "0.5" -tauri-codegen = { version = "2.5.4", default-features = false, path = "../tauri-codegen" } -tauri-utils = { version = "2.8.2", path = "../tauri-utils" } +tauri-codegen = { version = "2.5.5", default-features = false, path = "../tauri-codegen" } +tauri-utils = { version = "2.8.3", path = "../tauri-utils" } [features] custom-protocol = [] diff --git a/crates/tauri-plugin/CHANGELOG.md b/crates/tauri-plugin/CHANGELOG.md index e0bf35196197..93a1115aa31e 100644 --- a/crates/tauri-plugin/CHANGELOG.md +++ b/crates/tauri-plugin/CHANGELOG.md @@ -1,5 +1,11 @@ # Changelog +## \[2.5.4] + +### Dependencies + +- Upgraded to `tauri-utils@2.8.3` + ## \[2.5.3] ### Dependencies diff --git a/crates/tauri-plugin/Cargo.toml b/crates/tauri-plugin/Cargo.toml index 4054b8298c87..c14998107a9e 100644 --- a/crates/tauri-plugin/Cargo.toml +++ b/crates/tauri-plugin/Cargo.toml @@ -1,6 +1,6 @@ [package] name = "tauri-plugin" -version = "2.5.3" +version = "2.5.4" description = "Build script and runtime Tauri plugin definitions" authors.workspace = true homepage.workspace = true @@ -28,7 +28,7 @@ runtime = [] [dependencies] anyhow = { version = "1", optional = true } serde = { version = "1", optional = true } -tauri-utils = { version = "2.8.2", default-features = false, features = [ +tauri-utils = { version = "2.8.3", default-features = false, features = [ "build", ], path = "../tauri-utils" } serde_json = { version = "1", optional = true } diff --git a/crates/tauri-runtime-wry/CHANGELOG.md b/crates/tauri-runtime-wry/CHANGELOG.md index ea93a76d08d8..3d01fa27e84b 100644 --- a/crates/tauri-runtime-wry/CHANGELOG.md +++ b/crates/tauri-runtime-wry/CHANGELOG.md @@ -1,5 +1,12 @@ # Changelog +## \[2.10.1] + +### Dependencies + +- Upgraded to `tauri-utils@2.8.3` +- Upgraded to `tauri-runtime@2.10.1` + ## \[2.10.0] ### Bug Fixes diff --git a/crates/tauri-runtime-wry/Cargo.toml b/crates/tauri-runtime-wry/Cargo.toml index 091d57b4fc25..10ad16be189c 100644 --- a/crates/tauri-runtime-wry/Cargo.toml +++ b/crates/tauri-runtime-wry/Cargo.toml @@ -1,6 +1,6 @@ [package] name = "tauri-runtime-wry" -version = "2.10.0" +version = "2.10.1" description = "Wry bindings to the Tauri runtime" exclude = ["CHANGELOG.md", "/target"] readme = "README.md" @@ -20,8 +20,8 @@ wry = { version = "0.54.0", default-features = false, features = [ "linux-body", ] } tao = { version = "0.34.5", default-features = false, features = ["rwh_06"] } -tauri-runtime = { version = "2.10.0", path = "../tauri-runtime" } -tauri-utils = { version = "2.8.2", path = "../tauri-utils" } +tauri-runtime = { version = "2.10.1", path = "../tauri-runtime" } +tauri-utils = { version = "2.8.3", path = "../tauri-utils" } raw-window-handle = "0.6" http = "1" url = "2" diff --git a/crates/tauri-runtime/CHANGELOG.md b/crates/tauri-runtime/CHANGELOG.md index 47f8abf4d5a1..47263c499fe9 100644 --- a/crates/tauri-runtime/CHANGELOG.md +++ b/crates/tauri-runtime/CHANGELOG.md @@ -1,5 +1,11 @@ # Changelog +## \[2.10.1] + +### Dependencies + +- Upgraded to `tauri-utils@2.8.3` + ## \[2.10.0] ### Bug Fixes diff --git a/crates/tauri-runtime/Cargo.toml b/crates/tauri-runtime/Cargo.toml index 014d59b2fa2e..c25f743ff62e 100644 --- a/crates/tauri-runtime/Cargo.toml +++ b/crates/tauri-runtime/Cargo.toml @@ -1,6 +1,6 @@ [package] name = "tauri-runtime" -version = "2.10.0" +version = "2.10.1" description = "Runtime for Tauri applications" exclude = ["CHANGELOG.md", "/target"] readme = "README.md" @@ -27,7 +27,7 @@ targets = [ serde = { version = "1", features = ["derive"] } serde_json = "1" thiserror = "2" -tauri-utils = { version = "2.8.2", path = "../tauri-utils" } +tauri-utils = { version = "2.8.3", path = "../tauri-utils" } http = "1" raw-window-handle = "0.6" url = { version = "2" } diff --git a/crates/tauri-schema-generator/schemas/config.schema.json b/crates/tauri-schema-generator/schemas/config.schema.json index b56437751f55..664b695e186a 100644 --- a/crates/tauri-schema-generator/schemas/config.schema.json +++ b/crates/tauri-schema-generator/schemas/config.schema.json @@ -1,6 +1,6 @@ { "$schema": "http://json-schema.org/draft-07/schema#", - "$id": "https://schema.tauri.app/config/2.10.2", + "$id": "https://schema.tauri.app/config/2.10.3", "title": "Config", "description": "The Tauri configuration object.\n It is read from a file where you can define your frontend assets,\n configure the bundler and define a tray icon.\n\n The configuration file is generated by the\n [`tauri init`](https://v2.tauri.app/reference/cli/#init) command that lives in\n your Tauri application source directory (src-tauri).\n\n Once generated, you may modify it at will to customize your Tauri application.\n\n ## File Formats\n\n By default, the configuration is defined as a JSON file named `tauri.conf.json`.\n\n Tauri also supports JSON5 and TOML files via the `config-json5` and `config-toml` Cargo features, respectively.\n The JSON5 file name must be either `tauri.conf.json` or `tauri.conf.json5`.\n The TOML file name is `Tauri.toml`.\n\n ## Platform-Specific Configuration\n\n In addition to the default configuration file, Tauri can\n read a platform-specific configuration from `tauri.linux.conf.json`,\n `tauri.windows.conf.json`, `tauri.macos.conf.json`, `tauri.android.conf.json` and `tauri.ios.conf.json`\n (or `Tauri.linux.toml`, `Tauri.windows.toml`, `Tauri.macos.toml`, `Tauri.android.toml` and `Tauri.ios.toml` if the `Tauri.toml` format is used),\n which gets merged with the main configuration object.\n\n ## Configuration Structure\n\n The configuration is composed of the following objects:\n\n - [`app`](#appconfig): The Tauri configuration\n - [`build`](#buildconfig): The build configuration\n - [`bundle`](#bundleconfig): The bundle configurations\n - [`plugins`](#pluginconfig): The plugins configuration\n\n Example tauri.config.json file:\n\n ```json\n {\n \"productName\": \"tauri-app\",\n \"version\": \"0.1.0\",\n \"build\": {\n \"beforeBuildCommand\": \"\",\n \"beforeDevCommand\": \"\",\n \"devUrl\": \"http://localhost:3000\",\n \"frontendDist\": \"../dist\"\n },\n \"app\": {\n \"security\": {\n \"csp\": null\n },\n \"windows\": [\n {\n \"fullscreen\": false,\n \"height\": 600,\n \"resizable\": true,\n \"title\": \"Tauri App\",\n \"width\": 800\n }\n ]\n },\n \"bundle\": {},\n \"plugins\": {}\n }\n ```", "type": "object", diff --git a/crates/tauri-utils/CHANGELOG.md b/crates/tauri-utils/CHANGELOG.md index bf6c59f4fb98..4ed8a4248dcb 100644 --- a/crates/tauri-utils/CHANGELOG.md +++ b/crates/tauri-utils/CHANGELOG.md @@ -1,5 +1,14 @@ # Changelog +## \[2.8.3] + +### Bug Fixes + +- [`7b16dafb1`](https://www.github.com/tauri-apps/tauri/commit/7b16dafb1dc417536ebb62df8eb66154dd97109d) ([#14986](https://www.github.com/tauri-apps/tauri/pull/14986) by [@montyc1999](https://www.github.com/tauri-apps/tauri/../../montyc1999)) Sort csp/plugin/header configs when generating HashMap constructors so that `generate_context!` is deterministic. + + See: https://github.com/tauri-apps/tauri/issues/14978 for more information +- [`c3cbff3f7`](https://www.github.com/tauri-apps/tauri/commit/c3cbff3f7430161715f80f82128b345a6f7140c9) ([#14662](https://www.github.com/tauri-apps/tauri/pull/14662) by [@Legend-Master](https://www.github.com/tauri-apps/tauri/../../Legend-Master)) Fix resource path handles `./` path differently (e.g. `./some-folder` should be the same as `some-folder`) + ## \[2.8.2] ### Enhancements diff --git a/crates/tauri-utils/Cargo.toml b/crates/tauri-utils/Cargo.toml index 2a8af14737e9..9a1d6637e558 100644 --- a/crates/tauri-utils/Cargo.toml +++ b/crates/tauri-utils/Cargo.toml @@ -1,6 +1,6 @@ [package] name = "tauri-utils" -version = "2.8.2" +version = "2.8.3" description = "Utilities for Tauri" exclude = ["CHANGELOG.md", "/target"] readme = "README.md" diff --git a/crates/tauri/CHANGELOG.md b/crates/tauri/CHANGELOG.md index 2dd574964db8..3572afd7ab04 100644 --- a/crates/tauri/CHANGELOG.md +++ b/crates/tauri/CHANGELOG.md @@ -1,5 +1,15 @@ # Changelog +## \[2.10.3] + +### Dependencies + +- Upgraded to `tauri-utils@2.8.3` +- Upgraded to `tauri-runtime@2.10.1` +- Upgraded to `tauri-runtime-wry@2.10.1` +- Upgraded to `tauri-macros@2.5.5` +- Upgraded to `tauri-build@2.5.6` + ## \[2.10.2] ### Dependencies diff --git a/crates/tauri/Cargo.toml b/crates/tauri/Cargo.toml index 0e71e5c35900..cdc4bc697197 100644 --- a/crates/tauri/Cargo.toml +++ b/crates/tauri/Cargo.toml @@ -1,6 +1,6 @@ [package] name = "tauri" -version = "2.10.2" +version = "2.10.3" description = "Make tiny, secure apps for all desktop platforms with Tauri" exclude = ["/test", "/.scripts", "CHANGELOG.md", "/target"] readme = "README.md" @@ -55,12 +55,12 @@ uuid = { version = "1", features = ["v4"], optional = true } url = "2" anyhow = "1" thiserror = "2" -tauri-runtime = { version = "2.10.0", path = "../tauri-runtime" } -tauri-macros = { version = "2.5.4", path = "../tauri-macros" } -tauri-utils = { version = "2.8.2", features = [ +tauri-runtime = { version = "2.10.1", path = "../tauri-runtime" } +tauri-macros = { version = "2.5.5", path = "../tauri-macros" } +tauri-utils = { version = "2.8.3", features = [ "resources", ], path = "../tauri-utils" } -tauri-runtime-wry = { version = "2.10.0", path = "../tauri-runtime-wry", default-features = false, optional = true } +tauri-runtime-wry = { version = "2.10.1", path = "../tauri-runtime-wry", default-features = false, optional = true } getrandom = "0.3" serde_repr = "0.1" http = "1" @@ -165,8 +165,8 @@ objc2-ui-kit = { version = "0.3.0", default-features = false, features = [ [build-dependencies] glob = "0.3" heck = "0.5" -tauri-build = { path = "../tauri-build/", default-features = false, version = "2.5.5" } -tauri-utils = { path = "../tauri-utils/", version = "2.8.2", features = [ +tauri-build = { path = "../tauri-build/", default-features = false, version = "2.5.6" } +tauri-utils = { path = "../tauri-utils/", version = "2.8.3", features = [ "build", ] } diff --git a/packages/cli/CHANGELOG.md b/packages/cli/CHANGELOG.md index 57848e69ba05..236ecc1d3e69 100644 --- a/packages/cli/CHANGELOG.md +++ b/packages/cli/CHANGELOG.md @@ -1,5 +1,21 @@ # Changelog +## \[2.10.1] + +### Bug Fixes + +- [`35c35f27a`](https://www.github.com/tauri-apps/tauri/commit/35c35f27aedc430b602ec74059b271128c15ad36) ([#14931](https://www.github.com/tauri-apps/tauri/pull/14931) by [@lucasfernog](https://www.github.com/tauri-apps/tauri/../../lucasfernog)) Support comma-separated list of Cargo features on all commands. +- [`0d1cb83ba`](https://www.github.com/tauri-apps/tauri/commit/0d1cb83bab2aa482c7d73116893fd7ff6aa56283) ([#14932](https://www.github.com/tauri-apps/tauri/pull/14932) by [@lucasfernog](https://www.github.com/tauri-apps/tauri/../../lucasfernog)) Fix missing Cargo args when running mobile dev and build commands. +- [`33754ae5e`](https://www.github.com/tauri-apps/tauri/commit/33754ae5e3740d022483b6164511c5c001a3c24b) ([#15022](https://www.github.com/tauri-apps/tauri/pull/15022) by [@Legend-Master](https://www.github.com/tauri-apps/tauri/../../Legend-Master)) Fix updater signing private keys generated using `tauri signer generate` with empty password can't be used (The keys generated during tauri were broken between v2.9.3 and v2.10.0, you'll need to regenerate them) + +### What's Changed + +- [`7be58a1c6`](https://www.github.com/tauri-apps/tauri/commit/7be58a1c643a7ed6d0f484a7e1134022618eb2b2) ([#14894](https://www.github.com/tauri-apps/tauri/pull/14894) by [@Legend-Master](https://www.github.com/tauri-apps/tauri/../../Legend-Master)) Log patching bundle type information again + +### Dependencies + +- Upgraded to `tauri-cli@2.10.1` + ## \[2.10.0] ### Enhancements diff --git a/packages/cli/package.json b/packages/cli/package.json index ab29b2c442e8..1574652b8144 100644 --- a/packages/cli/package.json +++ b/packages/cli/package.json @@ -1,6 +1,6 @@ { "name": "@tauri-apps/cli", - "version": "2.10.0", + "version": "2.10.1", "description": "Command line interface for building Tauri apps", "type": "commonjs", "funding": { From 32d6a2967b6f4a6875bd794bff51576b19b0a7d2 Mon Sep 17 00:00:00 2001 From: Tony <68118705+Legend-Master@users.noreply.github.com> Date: Wed, 4 Mar 2026 18:11:01 +0800 Subject: [PATCH 29/95] fix(ci): bump rustsec/audit-check to v2 and ignore time audit (#15030) * fix(ci): bump rustsec/audit-check to v2 * Run on pull requests * Add to ignore list --- .cargo/audit.toml | 2 ++ .github/workflows/audit.yml | 9 ++++++++- 2 files changed, 10 insertions(+), 1 deletion(-) diff --git a/.cargo/audit.toml b/.cargo/audit.toml index c67661d57351..b6dd47060380 100644 --- a/.cargo/audit.toml +++ b/.cargo/audit.toml @@ -6,4 +6,6 @@ ignore = [ "RUSTSEC-2020-0095", # proc-macro-error is unmaintained "RUSTSEC-2024-0370", + # time crate can't be updated in the repo because of MSRV, users are unaffected + "RUSTSEC-2026-0009", ] diff --git a/.github/workflows/audit.yml b/.github/workflows/audit.yml index 3702e4b0d136..d840272be8bd 100644 --- a/.github/workflows/audit.yml +++ b/.github/workflows/audit.yml @@ -8,6 +8,13 @@ on: workflow_dispatch: schedule: - cron: '0 0 * * *' + pull_request: + paths: + - '.github/workflows/audit.yml' + - '**/Cargo.lock' + - '**/Cargo.toml' + - '**/package.json' + - '**/pnpm-lock.yaml' push: paths: - '.github/workflows/audit.yml' @@ -26,7 +33,7 @@ jobs: steps: - uses: actions/checkout@v4 - name: rust audit - uses: rustsec/audit-check@v1 + uses: rustsec/audit-check@v2 with: token: ${{ secrets.GITHUB_TOKEN }} From 9dfe3c4992f6b1ed9193ab0984a2362a9616d03a Mon Sep 17 00:00:00 2001 From: Tony <68118705+Legend-Master@users.noreply.github.com> Date: Wed, 4 Mar 2026 21:10:25 +0800 Subject: [PATCH 30/95] chore: update js dependencies to fix audit (#15031) * chore: update js dependencies * Add serialize-javascript override --- crates/tauri-schema-worker/package.json | 2 +- examples/api/package.json | 12 +- package.json | 16 +- packages/api/package.json | 12 +- packages/cli/package.json | 6 +- pnpm-lock.yaml | 2840 ++++++++++------------- pnpm-workspace.yaml | 7 + 7 files changed, 1292 insertions(+), 1603 deletions(-) diff --git a/crates/tauri-schema-worker/package.json b/crates/tauri-schema-worker/package.json index 7dd991dbe910..7e7326a0dfb3 100644 --- a/crates/tauri-schema-worker/package.json +++ b/crates/tauri-schema-worker/package.json @@ -8,6 +8,6 @@ "dev": "wrangler dev" }, "devDependencies": { - "wrangler": "^4.61.1" + "wrangler": "^4.70.0" } } diff --git a/examples/api/package.json b/examples/api/package.json index 87445a35c275..84db2ff41f82 100644 --- a/examples/api/package.json +++ b/examples/api/package.json @@ -13,12 +13,12 @@ "@tauri-apps/api": "../../packages/api/dist" }, "devDependencies": { - "@iconify-json/codicon": "^1.2.24", + "@iconify-json/codicon": "^1.2.47", "@iconify-json/ph": "^1.2.2", - "@sveltejs/vite-plugin-svelte": "^6.0.0", - "@unocss/extractor-svelte": "^66.3.3", - "svelte": "^5.53.5", - "unocss": "^66.3.3", - "vite": "^7.1.11" + "@sveltejs/vite-plugin-svelte": "^6.2.4", + "@unocss/extractor-svelte": "^66.6.5", + "svelte": "^5.53.7", + "unocss": "^66.6.5", + "vite": "^7.3.1" } } diff --git a/package.json b/package.json index 2d55f6313252..3dc1a3601a1d 100644 --- a/package.json +++ b/package.json @@ -25,20 +25,8 @@ "example:api:dev": "pnpm run --filter \"api\" tauri dev" }, "devDependencies": { - "prettier": "^3.6.2" + "prettier": "^3.8.1" }, "minimumReleaseAge": 4320, - "packageManager": "pnpm@10.16.0", - "pnpm": { - "overrides": { - "brace-expansion@<4.0.1": ">=4.0.1", - "cross-spawn@>=7.0.0 <7.0.5": ">=7.0.5", - "cookie@<0.7.0": ">=0.7.0", - "tmp@<=0.2.3": ">=0.2.4" - }, - "onlyBuiltDependencies": [ - "esbuild", - "workerd" - ] - } + "packageManager": "pnpm@10.30.3" } diff --git a/packages/api/package.json b/packages/api/package.json index c5bcba505946..39391dd66b0a 100644 --- a/packages/api/package.json +++ b/packages/api/package.json @@ -45,19 +45,19 @@ "eslint:fix": "eslint src/**/*.ts --fix" }, "devDependencies": { - "@eslint/js": "^10.0.0", + "@eslint/js": "^10.0.1", "@rollup/plugin-terser": "0.4.4", "@rollup/plugin-typescript": "12.3.0", "@types/eslint": "^9.6.1", - "@types/node": "^24.0.0", - "eslint": "^10.0.0", + "@types/node": "^24.11.0", + "eslint": "^10.0.2", "eslint-config-prettier": "10.1.8", "eslint-plugin-security": "4.0.0", "fast-glob": "3.3.3", - "globals": "^17.0.0", + "globals": "^17.4.0", "rollup": "4.59.0", "tslib": "^2.8.1", - "typescript": "^5.8.3", - "typescript-eslint": "^8.56.0" + "typescript": "^5.9.3", + "typescript-eslint": "^8.56.1" } } diff --git a/packages/cli/package.json b/packages/cli/package.json index 1574652b8144..d289be61f669 100644 --- a/packages/cli/package.json +++ b/packages/cli/package.json @@ -41,10 +41,10 @@ ] }, "devDependencies": { - "@napi-rs/cli": "^3.4.1", - "@types/node": "^24.0.0", + "@napi-rs/cli": "^3.5.1", + "@types/node": "^24.11.0", "cross-env": "10.1.0", - "vitest": "^4.0.0" + "vitest": "^4.0.18" }, "engines": { "node": ">= 10" diff --git a/pnpm-lock.yaml b/pnpm-lock.yaml index 2ddcf519e759..7a46fc0ae25d 100644 --- a/pnpm-lock.yaml +++ b/pnpm-lock.yaml @@ -5,24 +5,21 @@ settings: excludeLinksFromLockfile: false overrides: - brace-expansion@<4.0.1: '>=4.0.1' - cross-spawn@>=7.0.0 <7.0.5: '>=7.0.5' - cookie@<0.7.0: '>=0.7.0' - tmp@<=0.2.3: '>=0.2.4' + serialize-javascript@<=7.0.2: '>=7.0.3' importers: .: devDependencies: prettier: - specifier: ^3.6.2 - version: 3.6.2 + specifier: ^3.8.1 + version: 3.8.1 crates/tauri-schema-worker: devDependencies: wrangler: - specifier: ^4.61.1 - version: 4.61.1 + specifier: ^4.70.0 + version: 4.70.0 examples/api: dependencies: @@ -31,26 +28,26 @@ importers: version: link:../../packages/api/dist devDependencies: '@iconify-json/codicon': - specifier: ^1.2.24 - version: 1.2.24 + specifier: ^1.2.47 + version: 1.2.47 '@iconify-json/ph': specifier: ^1.2.2 version: 1.2.2 '@sveltejs/vite-plugin-svelte': - specifier: ^6.0.0 - version: 6.0.0(svelte@5.53.5)(vite@7.1.11(@types/node@24.10.0)(jiti@2.4.2)(terser@5.43.1)) + specifier: ^6.2.4 + version: 6.2.4(svelte@5.53.7)(vite@7.3.1(@types/node@24.11.0)(jiti@2.6.1)(terser@5.46.0)) '@unocss/extractor-svelte': - specifier: ^66.3.3 - version: 66.3.3 + specifier: ^66.6.5 + version: 66.6.5 svelte: - specifier: ^5.53.5 - version: 5.53.5 + specifier: ^5.53.7 + version: 5.53.7 unocss: - specifier: ^66.3.3 - version: 66.3.3(postcss@8.5.6)(vite@7.1.11(@types/node@24.10.0)(jiti@2.4.2)(terser@5.43.1))(vue@3.5.17(typescript@5.8.3)) + specifier: ^66.6.5 + version: 66.6.5(vite@7.3.1(@types/node@24.11.0)(jiti@2.6.1)(terser@5.46.0)) vite: - specifier: ^7.1.11 - version: 7.1.11(@types/node@24.10.0)(jiti@2.4.2)(terser@5.43.1) + specifier: ^7.3.1 + version: 7.3.1(@types/node@24.11.0)(jiti@2.6.1)(terser@5.46.0) examples/file-associations: {} @@ -59,26 +56,26 @@ importers: packages/api: devDependencies: '@eslint/js': - specifier: ^10.0.0 - version: 10.0.1(eslint@10.0.0(jiti@2.4.2)) + specifier: ^10.0.1 + version: 10.0.1(eslint@10.0.2(jiti@2.6.1)) '@rollup/plugin-terser': specifier: 0.4.4 version: 0.4.4(rollup@4.59.0) '@rollup/plugin-typescript': specifier: 12.3.0 - version: 12.3.0(rollup@4.59.0)(tslib@2.8.1)(typescript@5.8.3) + version: 12.3.0(rollup@4.59.0)(tslib@2.8.1)(typescript@5.9.3) '@types/eslint': specifier: ^9.6.1 version: 9.6.1 '@types/node': - specifier: ^24.0.0 - version: 24.10.0 + specifier: ^24.11.0 + version: 24.11.0 eslint: - specifier: ^10.0.0 - version: 10.0.0(jiti@2.4.2) + specifier: ^10.0.2 + version: 10.0.2(jiti@2.6.1) eslint-config-prettier: specifier: 10.1.8 - version: 10.1.8(eslint@10.0.0(jiti@2.4.2)) + version: 10.1.8(eslint@10.0.2(jiti@2.6.1)) eslint-plugin-security: specifier: 4.0.0 version: 4.0.0 @@ -86,8 +83,8 @@ importers: specifier: 3.3.3 version: 3.3.3 globals: - specifier: ^17.0.0 - version: 17.0.0 + specifier: ^17.4.0 + version: 17.4.0 rollup: specifier: 4.59.0 version: 4.59.0 @@ -95,95 +92,71 @@ importers: specifier: ^2.8.1 version: 2.8.1 typescript: - specifier: ^5.8.3 - version: 5.8.3 + specifier: ^5.9.3 + version: 5.9.3 typescript-eslint: - specifier: ^8.56.0 - version: 8.56.0(eslint@10.0.0(jiti@2.4.2))(typescript@5.8.3) + specifier: ^8.56.1 + version: 8.56.1(eslint@10.0.2(jiti@2.6.1))(typescript@5.9.3) packages/cli: devDependencies: '@napi-rs/cli': - specifier: ^3.4.1 - version: 3.4.1(@emnapi/runtime@1.8.1)(@types/node@24.10.0) + specifier: ^3.5.1 + version: 3.5.1(@emnapi/runtime@1.8.1)(@types/node@24.11.0) '@types/node': - specifier: ^24.0.0 - version: 24.10.0 + specifier: ^24.11.0 + version: 24.11.0 cross-env: specifier: 10.1.0 version: 10.1.0 vitest: - specifier: ^4.0.0 - version: 4.0.6(@types/node@24.10.0)(jiti@2.4.2)(terser@5.43.1) + specifier: ^4.0.18 + version: 4.0.18(@types/node@24.11.0)(jiti@2.6.1)(terser@5.46.0) packages: - '@ampproject/remapping@2.3.0': - resolution: {integrity: sha512-30iZtAPgz+LTIYoeivqYo853f02jBYSd5uGnGpkFV0M3xOt9aN73erkgYAmZU43x4VfqcnLxW9Kpg3R5LC4YYw==} - engines: {node: '>=6.0.0'} - '@antfu/install-pkg@1.1.0': resolution: {integrity: sha512-MGQsmw10ZyI+EJo45CdSER4zEb+p31LpDAFp2Z3gkSd1yqVZGi0Ebx++YTEMonJy4oChEMLsxZ64j8FH6sSqtQ==} - '@antfu/utils@8.1.1': - resolution: {integrity: sha512-Mex9nXf9vR6AhcXmMrlz/HVgYYZpVGJ6YlPgwl7UnaFpnshXs6EK/oa5Gpf3CzENMjkvEx2tQtntGnb7UtSTOQ==} - - '@babel/helper-string-parser@7.27.1': - resolution: {integrity: sha512-qMlSxKbpRlAridDExk92nSobyDdpPijUq2DW6oDnUqd0iOGxmQjyqhMIihI9+zv4LPyZdRje2cavWPbCbWm3eA==} - engines: {node: '>=6.9.0'} - - '@babel/helper-validator-identifier@7.28.5': - resolution: {integrity: sha512-qSs4ifwzKJSV39ucNjsvc6WVHs6b7S03sOh2OcHF9UHfVPqWWALUsNUVzhSBiItjRZoLHx7nIarVjqKVusUZ1Q==} - engines: {node: '>=6.9.0'} - - '@babel/parser@7.29.0': - resolution: {integrity: sha512-IyDgFV5GeDUVX4YdF/3CPULtVGSXXMLh1xVIgdCgxApktqnQV0r7/8Nqthg+8YLGaAtdyIlo2qIdZrbCv4+7ww==} - engines: {node: '>=6.0.0'} - hasBin: true - - '@babel/types@7.29.0': - resolution: {integrity: sha512-LwdZHpScM4Qz8Xw2iKSzS+cfglZzJGvofQICy7W7v4caru4EaAmyUuO6BGrbyQ2mYV11W0U8j5mBhd14dd3B0A==} - engines: {node: '>=6.9.0'} - '@cloudflare/kv-asset-handler@0.4.2': resolution: {integrity: sha512-SIOD2DxrRRwQ+jgzlXCqoEFiKOFqaPjhnNTGKXSRLvp1HiOvapLaFG2kEr9dYQTYe8rKrd9uvDUzmAITeNyaHQ==} engines: {node: '>=18.0.0'} - '@cloudflare/unenv-preset@2.12.0': - resolution: {integrity: sha512-NK4vN+2Z/GbfGS4BamtbbVk1rcu5RmqaYGiyHJQrA09AoxdZPHDF3W/EhgI0YSK8p3vRo/VNCtbSJFPON7FWMQ==} + '@cloudflare/unenv-preset@2.14.0': + resolution: {integrity: sha512-XKAkWhi1nBdNsSEoNG9nkcbyvfUrSjSf+VYVPfOto3gLTZVc3F4g6RASCMh6IixBKCG2yDgZKQIHGKtjcnLnKg==} peerDependencies: unenv: 2.0.0-rc.24 - workerd: ^1.20260115.0 + workerd: ^1.20260218.0 peerDependenciesMeta: workerd: optional: true - '@cloudflare/workerd-darwin-64@1.20260128.0': - resolution: {integrity: sha512-XJN8zWWNG3JwAUqqwMLNKJ9fZfdlQkx/zTTHW/BB8wHat9LjKD6AzxqCu432YmfjR+NxEKCzUOxMu1YOxlVxmg==} + '@cloudflare/workerd-darwin-64@1.20260301.1': + resolution: {integrity: sha512-+kJvwociLrvy1JV9BAvoSVsMEIYD982CpFmo/yMEvBwxDIjltYsLTE8DLi0mCkGsQ8Ygidv2fD9wavzXeiY7OQ==} engines: {node: '>=16'} cpu: [x64] os: [darwin] - '@cloudflare/workerd-darwin-arm64@1.20260128.0': - resolution: {integrity: sha512-vKnRcmnm402GQ5DOdfT5H34qeR2m07nhnTtky8mTkNWP+7xmkz32AMdclwMmfO/iX9ncyKwSqmml2wPG32eq/w==} + '@cloudflare/workerd-darwin-arm64@1.20260301.1': + resolution: {integrity: sha512-PPIetY3e67YBr9O4UhILK8nbm5TqUDl14qx4rwFNrRSBOvlzuczzbd4BqgpAtbGVFxKp1PWpjAnBvGU/OI/tLQ==} engines: {node: '>=16'} cpu: [arm64] os: [darwin] - '@cloudflare/workerd-linux-64@1.20260128.0': - resolution: {integrity: sha512-RiaR+Qugof/c6oI5SagD2J5wJmIfI8wQWaV2Y9905Raj6sAYOFaEKfzkKnoLLLNYb4NlXicBrffJi1j7R/ypUA==} + '@cloudflare/workerd-linux-64@1.20260301.1': + resolution: {integrity: sha512-Gu5vaVTZuYl3cHa+u5CDzSVDBvSkfNyuAHi6Mdfut7TTUdcb3V5CIcR/mXRSyMXzEy9YxEWIfdKMxOMBjupvYQ==} engines: {node: '>=16'} cpu: [x64] os: [linux] - '@cloudflare/workerd-linux-arm64@1.20260128.0': - resolution: {integrity: sha512-U39U9vcXLXYDbrJ112Q7D0LDUUnM54oXfAxPgrL2goBwio7Z6RnsM25TRvm+Q06F4+FeDOC4D51JXlFHb9t1OA==} + '@cloudflare/workerd-linux-arm64@1.20260301.1': + resolution: {integrity: sha512-igL1pkyCXW6GiGpjdOAvqMi87UW0LMc/+yIQe/CSzuZJm5GzXoAMrwVTkCFnikk6JVGELrM5x0tGYlxa0sk5Iw==} engines: {node: '>=16'} cpu: [arm64] os: [linux] - '@cloudflare/workerd-windows-64@1.20260128.0': - resolution: {integrity: sha512-fdJwSqRkJsAJFJ7+jy0th2uMO6fwaDA8Ny6+iFCssfzlNkc4dP/twXo+3F66FMLMe/6NIqjzVts0cpiv7ERYbQ==} + '@cloudflare/workerd-windows-64@1.20260301.1': + resolution: {integrity: sha512-Q0wMJ4kcujXILwQKQFc1jaYamVsNvjuECzvRrTI8OxGFMx2yq9aOsswViE4X1gaS2YQQ5u0JGwuGi5WdT1Lt7A==} engines: {node: '>=16'} cpu: [x64] os: [win32] @@ -192,8 +165,8 @@ packages: resolution: {integrity: sha512-IchNf6dN4tHoMFIn/7OE8LWZ19Y6q/67Bmf6vnGREv8RSbBVb9LPJxEcnwrcwX6ixSvaiGoomAUvu4YSxXrVgw==} engines: {node: '>=12'} - '@emnapi/core@1.7.1': - resolution: {integrity: sha512-o1uhUASyo921r2XtHYOHy7gdkGLge8ghBEQHMWmyJFoXlpU58kIrhhN3w26lpQb6dspetweapMn2CSNwQ8I4wg==} + '@emnapi/core@1.8.1': + resolution: {integrity: sha512-AvT9QFpxK0Zd8J0jopedNm+w/2fIzvtPKPjqyw9jwvBaReTTqPBk9Hixaz7KbjimP+QNz605/XnjFcDAL2pqBg==} '@emnapi/runtime@1.8.1': resolution: {integrity: sha512-mehfKSMWjjNol8659Z8KxEMrdSJDDot5SXMq00dM8BN4o+CLNXQ0xH2V7EchNHV4RmbZLmmPdEaXZc5H2FXmDg==} @@ -204,308 +177,158 @@ packages: '@epic-web/invariant@1.0.0': resolution: {integrity: sha512-lrTPqgvfFQtR/eY/qkIzp98OGdNJu0m5ji3q/nJI8v3SXkRKEnWiOxMmbvcSoAIzv/cGiuvRy57k4suKQSAdwA==} - '@esbuild/aix-ppc64@0.25.4': - resolution: {integrity: sha512-1VCICWypeQKhVbE9oW/sJaAmjLxhVqacdkvPLEjwlttjfwENRSClS8EjBz0KzRyFSCPDIkuXW34Je/vk7zdB7Q==} + '@esbuild/aix-ppc64@0.27.3': + resolution: {integrity: sha512-9fJMTNFTWZMh5qwrBItuziu834eOCUcEqymSH7pY+zoMVEZg3gcPuBNxH1EvfVYe9h0x/Ptw8KBzv7qxb7l8dg==} engines: {node: '>=18'} cpu: [ppc64] os: [aix] - '@esbuild/aix-ppc64@0.27.0': - resolution: {integrity: sha512-KuZrd2hRjz01y5JK9mEBSD3Vj3mbCvemhT466rSuJYeE/hjuBrHfjjcjMdTm/sz7au+++sdbJZJmuBwQLuw68A==} - engines: {node: '>=18'} - cpu: [ppc64] - os: [aix] - - '@esbuild/android-arm64@0.25.4': - resolution: {integrity: sha512-bBy69pgfhMGtCnwpC/x5QhfxAz/cBgQ9enbtwjf6V9lnPI/hMyT9iWpR1arm0l3kttTr4L0KSLpKmLp/ilKS9A==} + '@esbuild/android-arm64@0.27.3': + resolution: {integrity: sha512-YdghPYUmj/FX2SYKJ0OZxf+iaKgMsKHVPF1MAq/P8WirnSpCStzKJFjOjzsW0QQ7oIAiccHdcqjbHmJxRb/dmg==} engines: {node: '>=18'} cpu: [arm64] os: [android] - '@esbuild/android-arm64@0.27.0': - resolution: {integrity: sha512-CC3vt4+1xZrs97/PKDkl0yN7w8edvU2vZvAFGD16n9F0Cvniy5qvzRXjfO1l94efczkkQE6g1x0i73Qf5uthOQ==} - engines: {node: '>=18'} - cpu: [arm64] - os: [android] - - '@esbuild/android-arm@0.25.4': - resolution: {integrity: sha512-QNdQEps7DfFwE3hXiU4BZeOV68HHzYwGd0Nthhd3uCkkEKK7/R6MTgM0P7H7FAs5pU/DIWsviMmEGxEoxIZ+ZQ==} + '@esbuild/android-arm@0.27.3': + resolution: {integrity: sha512-i5D1hPY7GIQmXlXhs2w8AWHhenb00+GxjxRncS2ZM7YNVGNfaMxgzSGuO8o8SJzRc/oZwU2bcScvVERk03QhzA==} engines: {node: '>=18'} cpu: [arm] os: [android] - '@esbuild/android-arm@0.27.0': - resolution: {integrity: sha512-j67aezrPNYWJEOHUNLPj9maeJte7uSMM6gMoxfPC9hOg8N02JuQi/T7ewumf4tNvJadFkvLZMlAq73b9uwdMyQ==} - engines: {node: '>=18'} - cpu: [arm] - os: [android] - - '@esbuild/android-x64@0.25.4': - resolution: {integrity: sha512-TVhdVtQIFuVpIIR282btcGC2oGQoSfZfmBdTip2anCaVYcqWlZXGcdcKIUklfX2wj0JklNYgz39OBqh2cqXvcQ==} + '@esbuild/android-x64@0.27.3': + resolution: {integrity: sha512-IN/0BNTkHtk8lkOM8JWAYFg4ORxBkZQf9zXiEOfERX/CzxW3Vg1ewAhU7QSWQpVIzTW+b8Xy+lGzdYXV6UZObQ==} engines: {node: '>=18'} cpu: [x64] os: [android] - '@esbuild/android-x64@0.27.0': - resolution: {integrity: sha512-wurMkF1nmQajBO1+0CJmcN17U4BP6GqNSROP8t0X/Jiw2ltYGLHpEksp9MpoBqkrFR3kv2/te6Sha26k3+yZ9Q==} - engines: {node: '>=18'} - cpu: [x64] - os: [android] - - '@esbuild/darwin-arm64@0.25.4': - resolution: {integrity: sha512-Y1giCfM4nlHDWEfSckMzeWNdQS31BQGs9/rouw6Ub91tkK79aIMTH3q9xHvzH8d0wDru5Ci0kWB8b3up/nl16g==} + '@esbuild/darwin-arm64@0.27.3': + resolution: {integrity: sha512-Re491k7ByTVRy0t3EKWajdLIr0gz2kKKfzafkth4Q8A5n1xTHrkqZgLLjFEHVD+AXdUGgQMq+Godfq45mGpCKg==} engines: {node: '>=18'} cpu: [arm64] os: [darwin] - '@esbuild/darwin-arm64@0.27.0': - resolution: {integrity: sha512-uJOQKYCcHhg07DL7i8MzjvS2LaP7W7Pn/7uA0B5S1EnqAirJtbyw4yC5jQ5qcFjHK9l6o/MX9QisBg12kNkdHg==} - engines: {node: '>=18'} - cpu: [arm64] - os: [darwin] - - '@esbuild/darwin-x64@0.25.4': - resolution: {integrity: sha512-CJsry8ZGM5VFVeyUYB3cdKpd/H69PYez4eJh1W/t38vzutdjEjtP7hB6eLKBoOdxcAlCtEYHzQ/PJ/oU9I4u0A==} - engines: {node: '>=18'} - cpu: [x64] - os: [darwin] - - '@esbuild/darwin-x64@0.27.0': - resolution: {integrity: sha512-8mG6arH3yB/4ZXiEnXof5MK72dE6zM9cDvUcPtxhUZsDjESl9JipZYW60C3JGreKCEP+p8P/72r69m4AZGJd5g==} + '@esbuild/darwin-x64@0.27.3': + resolution: {integrity: sha512-vHk/hA7/1AckjGzRqi6wbo+jaShzRowYip6rt6q7VYEDX4LEy1pZfDpdxCBnGtl+A5zq8iXDcyuxwtv3hNtHFg==} engines: {node: '>=18'} cpu: [x64] os: [darwin] - '@esbuild/freebsd-arm64@0.25.4': - resolution: {integrity: sha512-yYq+39NlTRzU2XmoPW4l5Ifpl9fqSk0nAJYM/V/WUGPEFfek1epLHJIkTQM6bBs1swApjO5nWgvr843g6TjxuQ==} - engines: {node: '>=18'} - cpu: [arm64] - os: [freebsd] - - '@esbuild/freebsd-arm64@0.27.0': - resolution: {integrity: sha512-9FHtyO988CwNMMOE3YIeci+UV+x5Zy8fI2qHNpsEtSF83YPBmE8UWmfYAQg6Ux7Gsmd4FejZqnEUZCMGaNQHQw==} + '@esbuild/freebsd-arm64@0.27.3': + resolution: {integrity: sha512-ipTYM2fjt3kQAYOvo6vcxJx3nBYAzPjgTCk7QEgZG8AUO3ydUhvelmhrbOheMnGOlaSFUoHXB6un+A7q4ygY9w==} engines: {node: '>=18'} cpu: [arm64] os: [freebsd] - '@esbuild/freebsd-x64@0.25.4': - resolution: {integrity: sha512-0FgvOJ6UUMflsHSPLzdfDnnBBVoCDtBTVyn/MrWloUNvq/5SFmh13l3dvgRPkDihRxb77Y17MbqbCAa2strMQQ==} + '@esbuild/freebsd-x64@0.27.3': + resolution: {integrity: sha512-dDk0X87T7mI6U3K9VjWtHOXqwAMJBNN2r7bejDsc+j03SEjtD9HrOl8gVFByeM0aJksoUuUVU9TBaZa2rgj0oA==} engines: {node: '>=18'} cpu: [x64] os: [freebsd] - '@esbuild/freebsd-x64@0.27.0': - resolution: {integrity: sha512-zCMeMXI4HS/tXvJz8vWGexpZj2YVtRAihHLk1imZj4efx1BQzN76YFeKqlDr3bUWI26wHwLWPd3rwh6pe4EV7g==} - engines: {node: '>=18'} - cpu: [x64] - os: [freebsd] - - '@esbuild/linux-arm64@0.25.4': - resolution: {integrity: sha512-+89UsQTfXdmjIvZS6nUnOOLoXnkUTB9hR5QAeLrQdzOSWZvNSAXAtcRDHWtqAUtAmv7ZM1WPOOeSxDzzzMogiQ==} - engines: {node: '>=18'} - cpu: [arm64] - os: [linux] - - '@esbuild/linux-arm64@0.27.0': - resolution: {integrity: sha512-AS18v0V+vZiLJyi/4LphvBE+OIX682Pu7ZYNsdUHyUKSoRwdnOsMf6FDekwoAFKej14WAkOef3zAORJgAtXnlQ==} + '@esbuild/linux-arm64@0.27.3': + resolution: {integrity: sha512-sZOuFz/xWnZ4KH3YfFrKCf1WyPZHakVzTiqji3WDc0BCl2kBwiJLCXpzLzUBLgmp4veFZdvN5ChW4Eq/8Fc2Fg==} engines: {node: '>=18'} cpu: [arm64] os: [linux] - '@esbuild/linux-arm@0.25.4': - resolution: {integrity: sha512-kro4c0P85GMfFYqW4TWOpvmF8rFShbWGnrLqlzp4X1TNWjRY3JMYUfDCtOxPKOIY8B0WC8HN51hGP4I4hz4AaQ==} - engines: {node: '>=18'} - cpu: [arm] - os: [linux] - - '@esbuild/linux-arm@0.27.0': - resolution: {integrity: sha512-t76XLQDpxgmq2cNXKTVEB7O7YMb42atj2Re2Haf45HkaUpjM2J0UuJZDuaGbPbamzZ7bawyGFUkodL+zcE+jvQ==} + '@esbuild/linux-arm@0.27.3': + resolution: {integrity: sha512-s6nPv2QkSupJwLYyfS+gwdirm0ukyTFNl3KTgZEAiJDd+iHZcbTPPcWCcRYH+WlNbwChgH2QkE9NSlNrMT8Gfw==} engines: {node: '>=18'} cpu: [arm] os: [linux] - '@esbuild/linux-ia32@0.25.4': - resolution: {integrity: sha512-yTEjoapy8UP3rv8dB0ip3AfMpRbyhSN3+hY8mo/i4QXFeDxmiYbEKp3ZRjBKcOP862Ua4b1PDfwlvbuwY7hIGQ==} - engines: {node: '>=18'} - cpu: [ia32] - os: [linux] - - '@esbuild/linux-ia32@0.27.0': - resolution: {integrity: sha512-Mz1jxqm/kfgKkc/KLHC5qIujMvnnarD9ra1cEcrs7qshTUSksPihGrWHVG5+osAIQ68577Zpww7SGapmzSt4Nw==} + '@esbuild/linux-ia32@0.27.3': + resolution: {integrity: sha512-yGlQYjdxtLdh0a3jHjuwOrxQjOZYD/C9PfdbgJJF3TIZWnm/tMd/RcNiLngiu4iwcBAOezdnSLAwQDPqTmtTYg==} engines: {node: '>=18'} cpu: [ia32] os: [linux] - '@esbuild/linux-loong64@0.25.4': - resolution: {integrity: sha512-NeqqYkrcGzFwi6CGRGNMOjWGGSYOpqwCjS9fvaUlX5s3zwOtn1qwg1s2iE2svBe4Q/YOG1q6875lcAoQK/F4VA==} + '@esbuild/linux-loong64@0.27.3': + resolution: {integrity: sha512-WO60Sn8ly3gtzhyjATDgieJNet/KqsDlX5nRC5Y3oTFcS1l0KWba+SEa9Ja1GfDqSF1z6hif/SkpQJbL63cgOA==} engines: {node: '>=18'} cpu: [loong64] os: [linux] - '@esbuild/linux-loong64@0.27.0': - resolution: {integrity: sha512-QbEREjdJeIreIAbdG2hLU1yXm1uu+LTdzoq1KCo4G4pFOLlvIspBm36QrQOar9LFduavoWX2msNFAAAY9j4BDg==} - engines: {node: '>=18'} - cpu: [loong64] - os: [linux] - - '@esbuild/linux-mips64el@0.25.4': - resolution: {integrity: sha512-IcvTlF9dtLrfL/M8WgNI/qJYBENP3ekgsHbYUIzEzq5XJzzVEV/fXY9WFPfEEXmu3ck2qJP8LG/p3Q8f7Zc2Xg==} + '@esbuild/linux-mips64el@0.27.3': + resolution: {integrity: sha512-APsymYA6sGcZ4pD6k+UxbDjOFSvPWyZhjaiPyl/f79xKxwTnrn5QUnXR5prvetuaSMsb4jgeHewIDCIWljrSxw==} engines: {node: '>=18'} cpu: [mips64el] os: [linux] - '@esbuild/linux-mips64el@0.27.0': - resolution: {integrity: sha512-sJz3zRNe4tO2wxvDpH/HYJilb6+2YJxo/ZNbVdtFiKDufzWq4JmKAiHy9iGoLjAV7r/W32VgaHGkk35cUXlNOg==} - engines: {node: '>=18'} - cpu: [mips64el] - os: [linux] - - '@esbuild/linux-ppc64@0.25.4': - resolution: {integrity: sha512-HOy0aLTJTVtoTeGZh4HSXaO6M95qu4k5lJcH4gxv56iaycfz1S8GO/5Jh6X4Y1YiI0h7cRyLi+HixMR+88swag==} + '@esbuild/linux-ppc64@0.27.3': + resolution: {integrity: sha512-eizBnTeBefojtDb9nSh4vvVQ3V9Qf9Df01PfawPcRzJH4gFSgrObw+LveUyDoKU3kxi5+9RJTCWlj4FjYXVPEA==} engines: {node: '>=18'} cpu: [ppc64] os: [linux] - '@esbuild/linux-ppc64@0.27.0': - resolution: {integrity: sha512-z9N10FBD0DCS2dmSABDBb5TLAyF1/ydVb+N4pi88T45efQ/w4ohr/F/QYCkxDPnkhkp6AIpIcQKQ8F0ANoA2JA==} - engines: {node: '>=18'} - cpu: [ppc64] - os: [linux] - - '@esbuild/linux-riscv64@0.25.4': - resolution: {integrity: sha512-i8JUDAufpz9jOzo4yIShCTcXzS07vEgWzyX3NH2G7LEFVgrLEhjwL3ajFE4fZI3I4ZgiM7JH3GQ7ReObROvSUA==} - engines: {node: '>=18'} - cpu: [riscv64] - os: [linux] - - '@esbuild/linux-riscv64@0.27.0': - resolution: {integrity: sha512-pQdyAIZ0BWIC5GyvVFn5awDiO14TkT/19FTmFcPdDec94KJ1uZcmFs21Fo8auMXzD4Tt+diXu1LW1gHus9fhFQ==} + '@esbuild/linux-riscv64@0.27.3': + resolution: {integrity: sha512-3Emwh0r5wmfm3ssTWRQSyVhbOHvqegUDRd0WhmXKX2mkHJe1SFCMJhagUleMq+Uci34wLSipf8Lagt4LlpRFWQ==} engines: {node: '>=18'} cpu: [riscv64] os: [linux] - '@esbuild/linux-s390x@0.25.4': - resolution: {integrity: sha512-jFnu+6UbLlzIjPQpWCNh5QtrcNfMLjgIavnwPQAfoGx4q17ocOU9MsQ2QVvFxwQoWpZT8DvTLooTvmOQXkO51g==} + '@esbuild/linux-s390x@0.27.3': + resolution: {integrity: sha512-pBHUx9LzXWBc7MFIEEL0yD/ZVtNgLytvx60gES28GcWMqil8ElCYR4kvbV2BDqsHOvVDRrOxGySBM9Fcv744hw==} engines: {node: '>=18'} cpu: [s390x] os: [linux] - '@esbuild/linux-s390x@0.27.0': - resolution: {integrity: sha512-hPlRWR4eIDDEci953RI1BLZitgi5uqcsjKMxwYfmi4LcwyWo2IcRP+lThVnKjNtk90pLS8nKdroXYOqW+QQH+w==} - engines: {node: '>=18'} - cpu: [s390x] - os: [linux] - - '@esbuild/linux-x64@0.25.4': - resolution: {integrity: sha512-6e0cvXwzOnVWJHq+mskP8DNSrKBr1bULBvnFLpc1KY+d+irZSgZ02TGse5FsafKS5jg2e4pbvK6TPXaF/A6+CA==} + '@esbuild/linux-x64@0.27.3': + resolution: {integrity: sha512-Czi8yzXUWIQYAtL/2y6vogER8pvcsOsk5cpwL4Gk5nJqH5UZiVByIY8Eorm5R13gq+DQKYg0+JyQoytLQas4dA==} engines: {node: '>=18'} cpu: [x64] os: [linux] - '@esbuild/linux-x64@0.27.0': - resolution: {integrity: sha512-1hBWx4OUJE2cab++aVZ7pObD6s+DK4mPGpemtnAORBvb5l/g5xFGk0vc0PjSkrDs0XaXj9yyob3d14XqvnQ4gw==} - engines: {node: '>=18'} - cpu: [x64] - os: [linux] - - '@esbuild/netbsd-arm64@0.25.4': - resolution: {integrity: sha512-vUnkBYxZW4hL/ie91hSqaSNjulOnYXE1VSLusnvHg2u3jewJBz3YzB9+oCw8DABeVqZGg94t9tyZFoHma8gWZQ==} - engines: {node: '>=18'} - cpu: [arm64] - os: [netbsd] - - '@esbuild/netbsd-arm64@0.27.0': - resolution: {integrity: sha512-6m0sfQfxfQfy1qRuecMkJlf1cIzTOgyaeXaiVaaki8/v+WB+U4hc6ik15ZW6TAllRlg/WuQXxWj1jx6C+dfy3w==} + '@esbuild/netbsd-arm64@0.27.3': + resolution: {integrity: sha512-sDpk0RgmTCR/5HguIZa9n9u+HVKf40fbEUt+iTzSnCaGvY9kFP0YKBWZtJaraonFnqef5SlJ8/TiPAxzyS+UoA==} engines: {node: '>=18'} cpu: [arm64] os: [netbsd] - '@esbuild/netbsd-x64@0.25.4': - resolution: {integrity: sha512-XAg8pIQn5CzhOB8odIcAm42QsOfa98SBeKUdo4xa8OvX8LbMZqEtgeWE9P/Wxt7MlG2QqvjGths+nq48TrUiKw==} + '@esbuild/netbsd-x64@0.27.3': + resolution: {integrity: sha512-P14lFKJl/DdaE00LItAukUdZO5iqNH7+PjoBm+fLQjtxfcfFE20Xf5CrLsmZdq5LFFZzb5JMZ9grUwvtVYzjiA==} engines: {node: '>=18'} cpu: [x64] os: [netbsd] - '@esbuild/netbsd-x64@0.27.0': - resolution: {integrity: sha512-xbbOdfn06FtcJ9d0ShxxvSn2iUsGd/lgPIO2V3VZIPDbEaIj1/3nBBe1AwuEZKXVXkMmpr6LUAgMkLD/4D2PPA==} - engines: {node: '>=18'} - cpu: [x64] - os: [netbsd] - - '@esbuild/openbsd-arm64@0.25.4': - resolution: {integrity: sha512-Ct2WcFEANlFDtp1nVAXSNBPDxyU+j7+tId//iHXU2f/lN5AmO4zLyhDcpR5Cz1r08mVxzt3Jpyt4PmXQ1O6+7A==} + '@esbuild/openbsd-arm64@0.27.3': + resolution: {integrity: sha512-AIcMP77AvirGbRl/UZFTq5hjXK+2wC7qFRGoHSDrZ5v5b8DK/GYpXW3CPRL53NkvDqb9D+alBiC/dV0Fb7eJcw==} engines: {node: '>=18'} cpu: [arm64] os: [openbsd] - '@esbuild/openbsd-arm64@0.27.0': - resolution: {integrity: sha512-fWgqR8uNbCQ/GGv0yhzttj6sU/9Z5/Sv/VGU3F5OuXK6J6SlriONKrQ7tNlwBrJZXRYk5jUhuWvF7GYzGguBZQ==} - engines: {node: '>=18'} - cpu: [arm64] - os: [openbsd] - - '@esbuild/openbsd-x64@0.25.4': - resolution: {integrity: sha512-xAGGhyOQ9Otm1Xu8NT1ifGLnA6M3sJxZ6ixylb+vIUVzvvd6GOALpwQrYrtlPouMqd/vSbgehz6HaVk4+7Afhw==} - engines: {node: '>=18'} - cpu: [x64] - os: [openbsd] - - '@esbuild/openbsd-x64@0.27.0': - resolution: {integrity: sha512-aCwlRdSNMNxkGGqQajMUza6uXzR/U0dIl1QmLjPtRbLOx3Gy3otfFu/VjATy4yQzo9yFDGTxYDo1FfAD9oRD2A==} + '@esbuild/openbsd-x64@0.27.3': + resolution: {integrity: sha512-DnW2sRrBzA+YnE70LKqnM3P+z8vehfJWHXECbwBmH/CU51z6FiqTQTHFenPlHmo3a8UgpLyH3PT+87OViOh1AQ==} engines: {node: '>=18'} cpu: [x64] os: [openbsd] - '@esbuild/openharmony-arm64@0.27.0': - resolution: {integrity: sha512-nyvsBccxNAsNYz2jVFYwEGuRRomqZ149A39SHWk4hV0jWxKM0hjBPm3AmdxcbHiFLbBSwG6SbpIcUbXjgyECfA==} + '@esbuild/openharmony-arm64@0.27.3': + resolution: {integrity: sha512-NinAEgr/etERPTsZJ7aEZQvvg/A6IsZG/LgZy+81wON2huV7SrK3e63dU0XhyZP4RKGyTm7aOgmQk0bGp0fy2g==} engines: {node: '>=18'} cpu: [arm64] os: [openharmony] - '@esbuild/sunos-x64@0.25.4': - resolution: {integrity: sha512-Mw+tzy4pp6wZEK0+Lwr76pWLjrtjmJyUB23tHKqEDP74R3q95luY/bXqXZeYl4NYlvwOqoRKlInQialgCKy67Q==} - engines: {node: '>=18'} - cpu: [x64] - os: [sunos] - - '@esbuild/sunos-x64@0.27.0': - resolution: {integrity: sha512-Q1KY1iJafM+UX6CFEL+F4HRTgygmEW568YMqDA5UV97AuZSm21b7SXIrRJDwXWPzr8MGr75fUZPV67FdtMHlHA==} + '@esbuild/sunos-x64@0.27.3': + resolution: {integrity: sha512-PanZ+nEz+eWoBJ8/f8HKxTTD172SKwdXebZ0ndd953gt1HRBbhMsaNqjTyYLGLPdoWHy4zLU7bDVJztF5f3BHA==} engines: {node: '>=18'} cpu: [x64] os: [sunos] - '@esbuild/win32-arm64@0.25.4': - resolution: {integrity: sha512-AVUP428VQTSddguz9dO9ngb+E5aScyg7nOeJDrF1HPYu555gmza3bDGMPhmVXL8svDSoqPCsCPjb265yG/kLKQ==} + '@esbuild/win32-arm64@0.27.3': + resolution: {integrity: sha512-B2t59lWWYrbRDw/tjiWOuzSsFh1Y/E95ofKz7rIVYSQkUYBjfSgf6oeYPNWHToFRr2zx52JKApIcAS/D5TUBnA==} engines: {node: '>=18'} cpu: [arm64] os: [win32] - '@esbuild/win32-arm64@0.27.0': - resolution: {integrity: sha512-W1eyGNi6d+8kOmZIwi/EDjrL9nxQIQ0MiGqe/AWc6+IaHloxHSGoeRgDRKHFISThLmsewZ5nHFvGFWdBYlgKPg==} - engines: {node: '>=18'} - cpu: [arm64] - os: [win32] - - '@esbuild/win32-ia32@0.25.4': - resolution: {integrity: sha512-i1sW+1i+oWvQzSgfRcxxG2k4I9n3O9NRqy8U+uugaT2Dy7kLO9Y7wI72haOahxceMX8hZAzgGou1FhndRldxRg==} - engines: {node: '>=18'} - cpu: [ia32] - os: [win32] - - '@esbuild/win32-ia32@0.27.0': - resolution: {integrity: sha512-30z1aKL9h22kQhilnYkORFYt+3wp7yZsHWus+wSKAJR8JtdfI76LJ4SBdMsCopTR3z/ORqVu5L1vtnHZWVj4cQ==} + '@esbuild/win32-ia32@0.27.3': + resolution: {integrity: sha512-QLKSFeXNS8+tHW7tZpMtjlNb7HKau0QDpwm49u0vUp9y1WOF+PEzkU84y9GqYaAVW8aH8f3GcBck26jh54cX4Q==} engines: {node: '>=18'} cpu: [ia32] os: [win32] - '@esbuild/win32-x64@0.25.4': - resolution: {integrity: sha512-nOT2vZNw6hJ+z43oP1SPea/G/6AbN6X+bGNhNuq8NtRHy4wsMhw765IKLNmnjek7GvjWBYQ8Q5VBoYTFg9y1UQ==} - engines: {node: '>=18'} - cpu: [x64] - os: [win32] - - '@esbuild/win32-x64@0.27.0': - resolution: {integrity: sha512-aIitBcjQeyOhMTImhLZmtxfdOcuNRpwlPNmlFKPcHQYPhEssw75Cl1TSXJXpMkzaua9FUetx/4OQKq7eJul5Cg==} + '@esbuild/win32-x64@0.27.3': + resolution: {integrity: sha512-4uJGhsxuptu3OcpVAzli+/gWusVGwZZHTlS63hh++ehExkVT8SgiEf7/uC/PclrPPkLhZqGgCTjd0VWLo6xMqA==} engines: {node: '>=18'} cpu: [x64] os: [win32] @@ -520,8 +343,8 @@ packages: resolution: {integrity: sha512-EriSTlt5OC9/7SXkRSCAhfSxxoSUgBm33OH+IkwbdpgoqsSsUg7y3uh+IICI/Qg4BBWr3U2i39RpmycbxMq4ew==} engines: {node: ^12.0.0 || ^14.0.0 || >=16.0.0} - '@eslint/config-array@0.23.1': - resolution: {integrity: sha512-uVSdg/V4dfQmTjJzR0szNczjOH/J+FyUMMjYtr07xFRXR7EDf9i1qdxrD0VusZH9knj1/ecxzCQQxyic5NzAiA==} + '@eslint/config-array@0.23.2': + resolution: {integrity: sha512-YF+fE6LV4v5MGWRGj7G404/OZzGNepVF8fxk7jqmqo3lrza7a0uUcDnROGRBG1WFC1omYUS/Wp1f42i0M+3Q3A==} engines: {node: ^20.19.0 || ^22.13.0 || >=24} '@eslint/config-helpers@0.5.2': @@ -541,8 +364,8 @@ packages: eslint: optional: true - '@eslint/object-schema@3.0.1': - resolution: {integrity: sha512-P9cq2dpr+LU8j3qbLygLcSZrl2/ds/pUpfnHNNuk5HW7mnngHs+6WSq5C9mO3rqRX8A1poxqLTC9cu0KOyJlBg==} + '@eslint/object-schema@3.0.2': + resolution: {integrity: sha512-HOy56KJt48Bx8KmJ+XGQNSUMT/6dZee/M54XyUyuvTvPXJmsERRvBchsUVx1UMe1WwIH49XLAczNC7V2INsuUw==} engines: {node: ^20.19.0 || ^22.13.0 || >=24} '@eslint/plugin-kit@0.6.0': @@ -553,24 +376,20 @@ packages: resolution: {integrity: sha512-5DyQ4+1JEUzejeK1JGICcideyfUbGixgS9jNgex5nqkW+cY7WZhxBigmieN5Qnw9ZosSNVC9KQKyb+GUaGyKUA==} engines: {node: '>=18.18.0'} - '@humanfs/node@0.16.6': - resolution: {integrity: sha512-YuI2ZHQL78Q5HbhDiBA1X4LmYdXCKCMQIfw0pw7piHJwyREFebJUvrQN4cMssyES6x+vfUbx1CIpaQUKYdQZOw==} + '@humanfs/node@0.16.7': + resolution: {integrity: sha512-/zUx+yOsIrG4Y43Eh2peDeKCxlRt/gET6aHfaKpuq267qXdYDFViVHfMaLyygZOnl0kGWxFIgsBy8QFuTLUXEQ==} engines: {node: '>=18.18.0'} '@humanwhocodes/module-importer@1.0.1': resolution: {integrity: sha512-bxveV4V8v5Yb4ncFTT3rPSgZBOpCkjfK0y4oVVVJwIuDVBRMDXrPyXRL988i5ap9m9bnyEEjWfm5WkBmtffLfA==} engines: {node: '>=12.22'} - '@humanwhocodes/retry@0.3.1': - resolution: {integrity: sha512-JBxkERygn7Bv/GbN5Rv8Ul6LVknS+5Bp6RgDC/O8gEBU/yeH5Ui5C/OlWrTb6qct7LjjfT6Re2NxB0ln0yYybA==} - engines: {node: '>=18.18'} - '@humanwhocodes/retry@0.4.3': resolution: {integrity: sha512-bV0Tgo9K4hfPCek+aMAn81RppFKv2ySDQeMoSZuvTASywNTnVJCArCZE2FWqpvIatKu7VMRLWlR1EazvVhDyhQ==} engines: {node: '>=18.18'} - '@iconify-json/codicon@1.2.24': - resolution: {integrity: sha512-NApoTjRdJbNRBSCrJrkvpQGYmORmJ3oG/Aj4tEQecaSKbBzn1LfOb9s4KmHELyDgiLPzHzTSEIh61BqdDi7Mgw==} + '@iconify-json/codicon@1.2.47': + resolution: {integrity: sha512-9z6Of5d3w8aJAv07IT2un0SgAmFZfXSCtG4LDqsf8b/yL4vBgQ6jaCVH6Y0mDegNZzLkJ+7ieIDfbZZlIXH7CA==} '@iconify-json/ph@1.2.2': resolution: {integrity: sha512-PgkEZNtqa8hBGjHXQa4pMwZa93hmfu8FUSjs/nv4oUU6yLsgv+gh9nu28Kqi8Fz9CCVu4hj1MZs9/60J57IzFw==} @@ -578,11 +397,11 @@ packages: '@iconify/types@2.0.0': resolution: {integrity: sha512-+wluvCrRhXrhyOmRDJ3q8mux9JkKy5SJ/v8ol2tu4FVjyYvtEzkc/3pK15ET6RKg4b4w4BmTk1+gsCUhf21Ykg==} - '@iconify/utils@2.3.0': - resolution: {integrity: sha512-GmQ78prtwYW6EtzXRU1rY+KwOKfz32PD7iJh6Iyqw68GiKuoZ2A6pRtzWONz5VQJbp50mEjXh/7NkumtrAgRKA==} + '@iconify/utils@3.1.0': + resolution: {integrity: sha512-Zlzem1ZXhI1iHeeERabLNzBHdOa4VhQbqAcOQaMKuTuyZCpwKbC2R4Dd0Zo3g9EAc+Y4fiarO8HIHRAth7+skw==} - '@img/colour@1.0.0': - resolution: {integrity: sha512-A5P/LfWGFSl6nsckYtjw9da+19jB8hkJ6ACTGcDfEJ0aE+l2n2El7dsVM7UVHZQ9s2lmYMWlrS21YLy2IR1LUw==} + '@img/colour@1.1.0': + resolution: {integrity: sha512-Td76q7j57o/tLVdgS746cYARfSyxk8iEfRxewL9h4OMzYhbW4TAcppl0mT4eyqXddh6L/jwoM75mo7ixa/pCeQ==} engines: {node: '>=18'} '@img/sharp-darwin-arm64@0.34.5': @@ -611,89 +430,105 @@ packages: resolution: {integrity: sha512-excjX8DfsIcJ10x1Kzr4RcWe1edC9PquDRRPx3YVCvQv+U5p7Yin2s32ftzikXojb1PIFc/9Mt28/y+iRklkrw==} cpu: [arm64] os: [linux] + libc: [glibc] '@img/sharp-libvips-linux-arm@1.2.4': resolution: {integrity: sha512-bFI7xcKFELdiNCVov8e44Ia4u2byA+l3XtsAj+Q8tfCwO6BQ8iDojYdvoPMqsKDkuoOo+X6HZA0s0q11ANMQ8A==} cpu: [arm] os: [linux] + libc: [glibc] '@img/sharp-libvips-linux-ppc64@1.2.4': resolution: {integrity: sha512-FMuvGijLDYG6lW+b/UvyilUWu5Ayu+3r2d1S8notiGCIyYU/76eig1UfMmkZ7vwgOrzKzlQbFSuQfgm7GYUPpA==} cpu: [ppc64] os: [linux] + libc: [glibc] '@img/sharp-libvips-linux-riscv64@1.2.4': resolution: {integrity: sha512-oVDbcR4zUC0ce82teubSm+x6ETixtKZBh/qbREIOcI3cULzDyb18Sr/Wcyx7NRQeQzOiHTNbZFF1UwPS2scyGA==} cpu: [riscv64] os: [linux] + libc: [glibc] '@img/sharp-libvips-linux-s390x@1.2.4': resolution: {integrity: sha512-qmp9VrzgPgMoGZyPvrQHqk02uyjA0/QrTO26Tqk6l4ZV0MPWIW6LTkqOIov+J1yEu7MbFQaDpwdwJKhbJvuRxQ==} cpu: [s390x] os: [linux] + libc: [glibc] '@img/sharp-libvips-linux-x64@1.2.4': resolution: {integrity: sha512-tJxiiLsmHc9Ax1bz3oaOYBURTXGIRDODBqhveVHonrHJ9/+k89qbLl0bcJns+e4t4rvaNBxaEZsFtSfAdquPrw==} cpu: [x64] os: [linux] + libc: [glibc] '@img/sharp-libvips-linuxmusl-arm64@1.2.4': resolution: {integrity: sha512-FVQHuwx1IIuNow9QAbYUzJ+En8KcVm9Lk5+uGUQJHaZmMECZmOlix9HnH7n1TRkXMS0pGxIJokIVB9SuqZGGXw==} cpu: [arm64] os: [linux] + libc: [musl] '@img/sharp-libvips-linuxmusl-x64@1.2.4': resolution: {integrity: sha512-+LpyBk7L44ZIXwz/VYfglaX/okxezESc6UxDSoyo2Ks6Jxc4Y7sGjpgU9s4PMgqgjj1gZCylTieNamqA1MF7Dg==} cpu: [x64] os: [linux] + libc: [musl] '@img/sharp-linux-arm64@0.34.5': resolution: {integrity: sha512-bKQzaJRY/bkPOXyKx5EVup7qkaojECG6NLYswgktOZjaXecSAeCWiZwwiFf3/Y+O1HrauiE3FVsGxFg8c24rZg==} engines: {node: ^18.17.0 || ^20.3.0 || >=21.0.0} cpu: [arm64] os: [linux] + libc: [glibc] '@img/sharp-linux-arm@0.34.5': resolution: {integrity: sha512-9dLqsvwtg1uuXBGZKsxem9595+ujv0sJ6Vi8wcTANSFpwV/GONat5eCkzQo/1O6zRIkh0m/8+5BjrRr7jDUSZw==} engines: {node: ^18.17.0 || ^20.3.0 || >=21.0.0} cpu: [arm] os: [linux] + libc: [glibc] '@img/sharp-linux-ppc64@0.34.5': resolution: {integrity: sha512-7zznwNaqW6YtsfrGGDA6BRkISKAAE1Jo0QdpNYXNMHu2+0dTrPflTLNkpc8l7MUP5M16ZJcUvysVWWrMefZquA==} engines: {node: ^18.17.0 || ^20.3.0 || >=21.0.0} cpu: [ppc64] os: [linux] + libc: [glibc] '@img/sharp-linux-riscv64@0.34.5': resolution: {integrity: sha512-51gJuLPTKa7piYPaVs8GmByo7/U7/7TZOq+cnXJIHZKavIRHAP77e3N2HEl3dgiqdD/w0yUfiJnII77PuDDFdw==} engines: {node: ^18.17.0 || ^20.3.0 || >=21.0.0} cpu: [riscv64] os: [linux] + libc: [glibc] '@img/sharp-linux-s390x@0.34.5': resolution: {integrity: sha512-nQtCk0PdKfho3eC5MrbQoigJ2gd1CgddUMkabUj+rBevs8tZ2cULOx46E7oyX+04WGfABgIwmMC0VqieTiR4jg==} engines: {node: ^18.17.0 || ^20.3.0 || >=21.0.0} cpu: [s390x] os: [linux] + libc: [glibc] '@img/sharp-linux-x64@0.34.5': resolution: {integrity: sha512-MEzd8HPKxVxVenwAa+JRPwEC7QFjoPWuS5NZnBt6B3pu7EG2Ge0id1oLHZpPJdn3OQK+BQDiw9zStiHBTJQQQQ==} engines: {node: ^18.17.0 || ^20.3.0 || >=21.0.0} cpu: [x64] os: [linux] + libc: [glibc] '@img/sharp-linuxmusl-arm64@0.34.5': resolution: {integrity: sha512-fprJR6GtRsMt6Kyfq44IsChVZeGN97gTD331weR1ex1c1rypDEABN6Tm2xa1wE6lYb5DdEnk03NZPqA7Id21yg==} engines: {node: ^18.17.0 || ^20.3.0 || >=21.0.0} cpu: [arm64] os: [linux] + libc: [musl] '@img/sharp-linuxmusl-x64@0.34.5': resolution: {integrity: sha512-Jg8wNT1MUzIvhBFxViqrEhWDGzqymo3sV7z7ZsaWbZNDLXRJZoRGrjulp60YYtV4wfY8VIKcWidjojlLcWrd8Q==} engines: {node: ^18.17.0 || ^20.3.0 || >=21.0.0} cpu: [x64] os: [linux] + libc: [musl] '@img/sharp-wasm32@0.34.5': resolution: {integrity: sha512-OdWTEiVkY2PHwqkbBI8frFxQQFekHaSSkUIJkwzclWZe64O1X4UlUjqqqLaPbUpMOQk6FBu/HtlGXNblIs0huw==} @@ -718,134 +553,134 @@ packages: cpu: [x64] os: [win32] - '@inquirer/ansi@1.0.2': - resolution: {integrity: sha512-S8qNSZiYzFd0wAcyG5AXCvUHC5Sr7xpZ9wZ2py9XR88jUz8wooStVx5M6dRzczbBWjic9NP7+rY0Xi7qqK/aMQ==} - engines: {node: '>=18'} + '@inquirer/ansi@2.0.3': + resolution: {integrity: sha512-g44zhR3NIKVs0zUesa4iMzExmZpLUdTLRMCStqX3GE5NT6VkPcxQGJ+uC8tDgBUC/vB1rUhUd55cOf++4NZcmw==} + engines: {node: '>=23.5.0 || ^22.13.0 || ^21.7.0 || ^20.12.0'} - '@inquirer/checkbox@4.3.2': - resolution: {integrity: sha512-VXukHf0RR1doGe6Sm4F0Em7SWYLTHSsbGfJdS9Ja2bX5/D5uwVOEjr07cncLROdBvmnvCATYEWlHqYmXv2IlQA==} - engines: {node: '>=18'} + '@inquirer/checkbox@5.1.0': + resolution: {integrity: sha512-/HjF1LN0a1h4/OFsbGKHNDtWICFU/dqXCdym719HFTyJo9IG7Otr+ziGWc9S0iQuohRZllh+WprSgd5UW5Fw0g==} + engines: {node: '>=23.5.0 || ^22.13.0 || ^21.7.0 || ^20.12.0'} peerDependencies: '@types/node': '>=18' peerDependenciesMeta: '@types/node': optional: true - '@inquirer/confirm@5.1.21': - resolution: {integrity: sha512-KR8edRkIsUayMXV+o3Gv+q4jlhENF9nMYUZs9PA2HzrXeHI8M5uDag70U7RJn9yyiMZSbtF5/UexBtAVtZGSbQ==} - engines: {node: '>=18'} + '@inquirer/confirm@6.0.8': + resolution: {integrity: sha512-Di6dgmiZ9xCSUxWUReWTqDtbhXCuG2MQm2xmgSAIruzQzBqNf49b8E07/vbCYY506kDe8BiwJbegXweG8M1klw==} + engines: {node: '>=23.5.0 || ^22.13.0 || ^21.7.0 || ^20.12.0'} peerDependencies: '@types/node': '>=18' peerDependenciesMeta: '@types/node': optional: true - '@inquirer/core@10.3.2': - resolution: {integrity: sha512-43RTuEbfP8MbKzedNqBrlhhNKVwoK//vUFNW3Q3vZ88BLcrs4kYpGg+B2mm5p2K/HfygoCxuKwJJiv8PbGmE0A==} - engines: {node: '>=18'} + '@inquirer/core@11.1.5': + resolution: {integrity: sha512-QQPAX+lka8GyLcZ7u7Nb1h6q72iZ/oy0blilC3IB2nSt1Qqxp7akt94Jqhi/DzARuN3Eo9QwJRvtl4tmVe4T5A==} + engines: {node: '>=23.5.0 || ^22.13.0 || ^21.7.0 || ^20.12.0'} peerDependencies: '@types/node': '>=18' peerDependenciesMeta: '@types/node': optional: true - '@inquirer/editor@4.2.23': - resolution: {integrity: sha512-aLSROkEwirotxZ1pBaP8tugXRFCxW94gwrQLxXfrZsKkfjOYC1aRvAZuhpJOb5cu4IBTJdsCigUlf2iCOu4ZDQ==} - engines: {node: '>=18'} + '@inquirer/editor@5.0.8': + resolution: {integrity: sha512-sLcpbb9B3XqUEGrj1N66KwhDhEckzZ4nI/W6SvLXyBX8Wic3LDLENlWRvkOGpCPoserabe+MxQkpiMoI8irvyA==} + engines: {node: '>=23.5.0 || ^22.13.0 || ^21.7.0 || ^20.12.0'} peerDependencies: '@types/node': '>=18' peerDependenciesMeta: '@types/node': optional: true - '@inquirer/expand@4.0.23': - resolution: {integrity: sha512-nRzdOyFYnpeYTTR2qFwEVmIWypzdAx/sIkCMeTNTcflFOovfqUk+HcFhQQVBftAh9gmGrpFj6QcGEqrDMDOiew==} - engines: {node: '>=18'} + '@inquirer/expand@5.0.8': + resolution: {integrity: sha512-QieW3F1prNw3j+hxO7/NKkG1pk3oz7pOB6+5Upwu3OIwADfPX0oZVppsqlL+Vl/uBHHDSOBY0BirLctLnXwGGg==} + engines: {node: '>=23.5.0 || ^22.13.0 || ^21.7.0 || ^20.12.0'} peerDependencies: '@types/node': '>=18' peerDependenciesMeta: '@types/node': optional: true - '@inquirer/external-editor@1.0.3': - resolution: {integrity: sha512-RWbSrDiYmO4LbejWY7ttpxczuwQyZLBUyygsA9Nsv95hpzUWwnNTVQmAq3xuh7vNwCp07UTmE5i11XAEExx4RA==} - engines: {node: '>=18'} + '@inquirer/external-editor@2.0.3': + resolution: {integrity: sha512-LgyI7Agbda74/cL5MvA88iDpvdXI2KuMBCGRkbCl2Dg1vzHeOgs+s0SDcXV7b+WZJrv2+ERpWSM65Fpi9VfY3w==} + engines: {node: '>=23.5.0 || ^22.13.0 || ^21.7.0 || ^20.12.0'} peerDependencies: '@types/node': '>=18' peerDependenciesMeta: '@types/node': optional: true - '@inquirer/figures@1.0.15': - resolution: {integrity: sha512-t2IEY+unGHOzAaVM5Xx6DEWKeXlDDcNPeDyUpsRc6CUhBfU3VQOEl+Vssh7VNp1dR8MdUJBWhuObjXCsVpjN5g==} - engines: {node: '>=18'} + '@inquirer/figures@2.0.3': + resolution: {integrity: sha512-y09iGt3JKoOCBQ3w4YrSJdokcD8ciSlMIWsD+auPu+OZpfxLuyz+gICAQ6GCBOmJJt4KEQGHuZSVff2jiNOy7g==} + engines: {node: '>=23.5.0 || ^22.13.0 || ^21.7.0 || ^20.12.0'} - '@inquirer/input@4.3.1': - resolution: {integrity: sha512-kN0pAM4yPrLjJ1XJBjDxyfDduXOuQHrBB8aLDMueuwUGn+vNpF7Gq7TvyVxx8u4SHlFFj4trmj+a2cbpG4Jn1g==} - engines: {node: '>=18'} + '@inquirer/input@5.0.8': + resolution: {integrity: sha512-p0IJslw0AmedLEkOU+yrEX3Aj2RTpQq7ZOf8nc1DIhjzaxRWrrgeuE5Kyh39fVRgtcACaMXx/9WNo8+GjgBOfw==} + engines: {node: '>=23.5.0 || ^22.13.0 || ^21.7.0 || ^20.12.0'} peerDependencies: '@types/node': '>=18' peerDependenciesMeta: '@types/node': optional: true - '@inquirer/number@3.0.23': - resolution: {integrity: sha512-5Smv0OK7K0KUzUfYUXDXQc9jrf8OHo4ktlEayFlelCjwMXz0299Y8OrI+lj7i4gCBY15UObk76q0QtxjzFcFcg==} - engines: {node: '>=18'} + '@inquirer/number@4.0.8': + resolution: {integrity: sha512-uGLiQah9A0F9UIvJBX52m0CnqtLaym0WpT9V4YZrjZ+YRDKZdwwoEPz06N6w8ChE2lrnsdyhY9sL+Y690Kh9gQ==} + engines: {node: '>=23.5.0 || ^22.13.0 || ^21.7.0 || ^20.12.0'} peerDependencies: '@types/node': '>=18' peerDependenciesMeta: '@types/node': optional: true - '@inquirer/password@4.0.23': - resolution: {integrity: sha512-zREJHjhT5vJBMZX/IUbyI9zVtVfOLiTO66MrF/3GFZYZ7T4YILW5MSkEYHceSii/KtRk+4i3RE7E1CUXA2jHcA==} - engines: {node: '>=18'} + '@inquirer/password@5.0.8': + resolution: {integrity: sha512-zt1sF4lYLdvPqvmvHdmjOzuUUjuCQ897pdUCO8RbXMUDKXJTTyOQgtn23le+jwcb+MpHl3VAFvzIdxRAf6aPlA==} + engines: {node: '>=23.5.0 || ^22.13.0 || ^21.7.0 || ^20.12.0'} peerDependencies: '@types/node': '>=18' peerDependenciesMeta: '@types/node': optional: true - '@inquirer/prompts@7.10.1': - resolution: {integrity: sha512-Dx/y9bCQcXLI5ooQ5KyvA4FTgeo2jYj/7plWfV5Ak5wDPKQZgudKez2ixyfz7tKXzcJciTxqLeK7R9HItwiByg==} - engines: {node: '>=18'} + '@inquirer/prompts@8.3.0': + resolution: {integrity: sha512-JAj66kjdH/F1+B7LCigjARbwstt3SNUOSzMdjpsvwJmzunK88gJeXmcm95L9nw1KynvFVuY4SzXh/3Y0lvtgSg==} + engines: {node: '>=23.5.0 || ^22.13.0 || ^21.7.0 || ^20.12.0'} peerDependencies: '@types/node': '>=18' peerDependenciesMeta: '@types/node': optional: true - '@inquirer/rawlist@4.1.11': - resolution: {integrity: sha512-+LLQB8XGr3I5LZN/GuAHo+GpDJegQwuPARLChlMICNdwW7OwV2izlCSCxN6cqpL0sMXmbKbFcItJgdQq5EBXTw==} - engines: {node: '>=18'} + '@inquirer/rawlist@5.2.4': + resolution: {integrity: sha512-fTuJ5Cq9W286isLxwj6GGyfTjx1Zdk4qppVEPexFuA6yioCCXS4V1zfKroQqw7QdbDPN73xs2DiIAlo55+kBqg==} + engines: {node: '>=23.5.0 || ^22.13.0 || ^21.7.0 || ^20.12.0'} peerDependencies: '@types/node': '>=18' peerDependenciesMeta: '@types/node': optional: true - '@inquirer/search@3.2.2': - resolution: {integrity: sha512-p2bvRfENXCZdWF/U2BXvnSI9h+tuA8iNqtUKb9UWbmLYCRQxd8WkvwWvYn+3NgYaNwdUkHytJMGG4MMLucI1kA==} - engines: {node: '>=18'} + '@inquirer/search@4.1.4': + resolution: {integrity: sha512-9yPTxq7LPmYjrGn3DRuaPuPbmC6u3fiWcsE9ggfLcdgO/ICHYgxq7mEy1yJ39brVvgXhtOtvDVjDh9slJxE4LQ==} + engines: {node: '>=23.5.0 || ^22.13.0 || ^21.7.0 || ^20.12.0'} peerDependencies: '@types/node': '>=18' peerDependenciesMeta: '@types/node': optional: true - '@inquirer/select@4.4.2': - resolution: {integrity: sha512-l4xMuJo55MAe+N7Qr4rX90vypFwCajSakx59qe/tMaC1aEHWLyw68wF4o0A4SLAY4E0nd+Vt+EyskeDIqu1M6w==} - engines: {node: '>=18'} + '@inquirer/select@5.1.0': + resolution: {integrity: sha512-OyYbKnchS1u+zRe14LpYrN8S0wH1vD0p2yKISvSsJdH2TpI87fh4eZdWnpdbrGauCRWDph3NwxRmM4Pcm/hx1Q==} + engines: {node: '>=23.5.0 || ^22.13.0 || ^21.7.0 || ^20.12.0'} peerDependencies: '@types/node': '>=18' peerDependenciesMeta: '@types/node': optional: true - '@inquirer/type@3.0.10': - resolution: {integrity: sha512-BvziSRxfz5Ov8ch0z/n3oijRSEcEsHnhggm4xFZe93DHcUCTlutlq9Ox4SVENAfcRD22UQq7T/atg9Wr3k09eA==} - engines: {node: '>=18'} + '@inquirer/type@4.0.3': + resolution: {integrity: sha512-cKZN7qcXOpj1h+1eTTcGDVLaBIHNMT1Rz9JqJP5MnEJ0JhgVWllx7H/tahUp5YEK1qaByH2Itb8wLG/iScD5kw==} + engines: {node: '>=23.5.0 || ^22.13.0 || ^21.7.0 || ^20.12.0'} peerDependencies: '@types/node': '>=18' peerDependenciesMeta: @@ -862,8 +697,8 @@ packages: resolution: {integrity: sha512-bRISgCIjP20/tbWSPWMEi54QVPRZExkuD9lJL+UIxUKtwVJA8wW1Trb1jMs1RFXo1CBTNZ/5hpC9QvmKWdopKw==} engines: {node: '>=6.0.0'} - '@jridgewell/source-map@0.3.6': - resolution: {integrity: sha512-1ZJTZebgqllO79ue2bm3rIGud/bOe0pP5BjSRCRxxYkEZS8STV7zN84UBbiYu7jy+eCKSnVIUgoWWE/tt+shMQ==} + '@jridgewell/source-map@0.3.11': + resolution: {integrity: sha512-ZMp1V8ZFcPG5dIWnQLr3NSI1MiCU7UETdS/A0G8V/XWHvJv3ZsFqutJn1Y5RPmAPX6F3BiE397OqveU/9NCuIA==} '@jridgewell/sourcemap-codec@1.5.5': resolution: {integrity: sha512-cYQ9310grqxueWbl+WuIUIaiUaDcj7WOq5fVhEljNVgRfOUhY9fy2zTvfoqWsnebh8Sl70VScFbICvJnLKB0Og==} @@ -874,12 +709,12 @@ packages: '@jridgewell/trace-mapping@0.3.9': resolution: {integrity: sha512-3Belt6tdc8bPgAtbcmdtNJlirVoTmEb5e2gC94PnkwEW9jI6CAHUeoG85tjWP5WquqfavoMtMwiG4P926ZKKuQ==} - '@napi-rs/cli@3.4.1': - resolution: {integrity: sha512-ayhm+NfrP5Hmh7vy5pfyYm/ktYtLh2PrgdLuqHTAubO7RoO2JkUE4F991AtgYxNewwXI8+guZLxU8itV7QnDrQ==} + '@napi-rs/cli@3.5.1': + resolution: {integrity: sha512-XBfLQRDcB3qhu6bazdMJsecWW55kR85l5/k0af9BIBELXQSsCFU0fzug7PX8eQp6vVdm7W/U3z6uP5WmITB2Gw==} engines: {node: '>= 16'} hasBin: true peerDependencies: - '@emnapi/runtime': ^1.5.0 + '@emnapi/runtime': ^1.7.1 peerDependenciesMeta: '@emnapi/runtime': optional: true @@ -960,42 +795,49 @@ packages: engines: {node: '>= 10'} cpu: [arm64] os: [linux] + libc: [glibc] '@napi-rs/lzma-linux-arm64-musl@1.4.5': resolution: {integrity: sha512-yWjcPDgJ2nIL3KNvi4536dlT/CcCWO0DUyEOlBs/SacG7BeD6IjGh6yYzd3/X1Y3JItCbZoDoLUH8iB1lTXo3w==} engines: {node: '>= 10'} cpu: [arm64] os: [linux] + libc: [musl] '@napi-rs/lzma-linux-ppc64-gnu@1.4.5': resolution: {integrity: sha512-0XRhKuIU/9ZjT4WDIG/qnX7Xz7mSQHYZo9Gb3MP2gcvBgr6BA4zywQ9k3gmQaPn9ECE+CZg2V7DV7kT+x2pUMQ==} engines: {node: '>= 10'} cpu: [ppc64] os: [linux] + libc: [glibc] '@napi-rs/lzma-linux-riscv64-gnu@1.4.5': resolution: {integrity: sha512-QrqDIPEUUB23GCpyQj/QFyMlr8SGxxyExeZz9OWFnHfb70kXdTLWrHS/hEI1Ru+lSbQ/6xRqeoGyQ4Aqdg+/RA==} engines: {node: '>= 10'} cpu: [riscv64] os: [linux] + libc: [glibc] '@napi-rs/lzma-linux-s390x-gnu@1.4.5': resolution: {integrity: sha512-k8RVM5aMhW86E9H0QXdquwojew4H3SwPxbRVbl49/COJQWCUjGi79X6mYruMnMPEznZinUiT1jgKbFo2A00NdA==} engines: {node: '>= 10'} cpu: [s390x] os: [linux] + libc: [glibc] '@napi-rs/lzma-linux-x64-gnu@1.4.5': resolution: {integrity: sha512-6rMtBgnIq2Wcl1rQdZsnM+rtCcVCbws1nF8S2NzaUsVaZv8bjrPiAa0lwg4Eqnn1d9lgwqT+cZgm5m+//K08Kw==} engines: {node: '>= 10'} cpu: [x64] os: [linux] + libc: [glibc] '@napi-rs/lzma-linux-x64-musl@1.4.5': resolution: {integrity: sha512-eiadGBKi7Vd0bCArBUOO/qqRYPHt/VQVvGyYvDFt6C2ZSIjlD+HuOl+2oS1sjf4CFjK4eDIog6EdXnL0NE6iyQ==} engines: {node: '>= 10'} cpu: [x64] os: [linux] + libc: [musl] '@napi-rs/lzma-wasm32-wasi@1.4.5': resolution: {integrity: sha512-+VyHHlr68dvey6fXc2hehw9gHVFIW3TtGF1XkcbAu65qVXsA9D/T+uuoRVqhE+JCyFHFrO0ixRbZDRK1XJt1sA==} @@ -1065,36 +907,42 @@ packages: engines: {node: '>= 10'} cpu: [arm64] os: [linux] + libc: [glibc] '@napi-rs/tar-linux-arm64-musl@1.1.0': resolution: {integrity: sha512-L/y1/26q9L/uBqiW/JdOb/Dc94egFvNALUZV2WCGKQXc6UByPBMgdiEyW2dtoYxYYYYc+AKD+jr+wQPcvX2vrQ==} engines: {node: '>= 10'} cpu: [arm64] os: [linux] + libc: [musl] '@napi-rs/tar-linux-ppc64-gnu@1.1.0': resolution: {integrity: sha512-EPE1K/80RQvPbLRJDJs1QmCIcH+7WRi0F73+oTe1582y9RtfGRuzAkzeBuAGRXAQEjRQw/RjtNqr6UTJ+8UuWQ==} engines: {node: '>= 10'} cpu: [ppc64] os: [linux] + libc: [glibc] '@napi-rs/tar-linux-s390x-gnu@1.1.0': resolution: {integrity: sha512-B2jhWiB1ffw1nQBqLUP1h4+J1ovAxBOoe5N2IqDMOc63fsPZKNqF1PvO/dIem8z7LL4U4bsfmhy3gBfu547oNQ==} engines: {node: '>= 10'} cpu: [s390x] os: [linux] + libc: [glibc] '@napi-rs/tar-linux-x64-gnu@1.1.0': resolution: {integrity: sha512-tbZDHnb9617lTnsDMGo/eAMZxnsQFnaRe+MszRqHguKfMwkisc9CCJnks/r1o84u5fECI+J/HOrKXgczq/3Oww==} engines: {node: '>= 10'} cpu: [x64] os: [linux] + libc: [glibc] '@napi-rs/tar-linux-x64-musl@1.1.0': resolution: {integrity: sha512-dV6cODlzbO8u6Anmv2N/ilQHq/AWz0xyltuXoLU3yUyXbZcnWYZuB2rL8OBGPmqNcD+x9NdScBNXh7vWN0naSQ==} engines: {node: '>= 10'} cpu: [x64] os: [linux] + libc: [musl] '@napi-rs/tar-wasm32-wasi@1.1.0': resolution: {integrity: sha512-jIa9nb2HzOrfH0F8QQ9g3WE4aMH5vSI5/1NYVNm9ysCmNjCCtMXCAhlI3WKCdm/DwHf0zLqdrrtDFXODcNaqMw==} @@ -1123,8 +971,8 @@ packages: resolution: {integrity: sha512-7cmzIu+Vbupriudo7UudoMRH2OA3cTw67vva8MxeoAe5S7vPFI7z0vp0pMXiA25S8IUJefImQ90FeJjl8fjEaQ==} engines: {node: '>= 10'} - '@napi-rs/wasm-runtime@1.0.7': - resolution: {integrity: sha512-SeDnOO0Tk7Okiq6DbXmmBODgOAb9dp9gjlphokTUxmt8U3liIP1ZsozBahH69j/RJv+Rfs6IwUKHTgQYJ/HBAw==} + '@napi-rs/wasm-runtime@1.1.1': + resolution: {integrity: sha512-p64ah1M1ld8xjWv3qbvFwHiFVWrq1yFvV4f7w+mzaqiR4IlSgkqhcRdHwsGgomwzBH51sRY4NEowLxnaBjcW/A==} '@napi-rs/wasm-tools-android-arm-eabi@1.0.1': resolution: {integrity: sha512-lr07E/l571Gft5v4aA1dI8koJEmF1F0UigBbsqg9OWNzg80H3lDPO+auv85y3T/NHE3GirDk7x/D3sLO57vayw==} @@ -1161,24 +1009,28 @@ packages: engines: {node: '>= 10'} cpu: [arm64] os: [linux] + libc: [glibc] '@napi-rs/wasm-tools-linux-arm64-musl@1.0.1': resolution: {integrity: sha512-jAasbIvjZXCgX0TCuEFQr+4D6Lla/3AAVx2LmDuMjgG4xoIXzjKWl7c4chuaD+TI+prWT0X6LJcdzFT+ROKGHQ==} engines: {node: '>= 10'} cpu: [arm64] os: [linux] + libc: [musl] '@napi-rs/wasm-tools-linux-x64-gnu@1.0.1': resolution: {integrity: sha512-Plgk5rPqqK2nocBGajkMVbGm010Z7dnUgq0wtnYRZbzWWxwWcXfZMPa8EYxrK4eE8SzpI7VlZP1tdVsdjgGwMw==} engines: {node: '>= 10'} cpu: [x64] os: [linux] + libc: [glibc] '@napi-rs/wasm-tools-linux-x64-musl@1.0.1': resolution: {integrity: sha512-GW7AzGuWxtQkyHknHWYFdR0CHmW6is8rG2Rf4V6GNmMpmwtXt/ItWYWtBe4zqJWycMNazpfZKSw/BpT7/MVCXQ==} engines: {node: '>= 10'} cpu: [x64] os: [linux] + libc: [musl] '@napi-rs/wasm-tools-wasm32-wasi@1.0.1': resolution: {integrity: sha512-/nQVSTrqSsn7YdAc2R7Ips/tnw5SPUcl3D7QrXCNGPqjbatIspnaexvaOYNyKMU6xPu+pc0BTnKVmqhlJJCPLA==} @@ -1223,23 +1075,23 @@ packages: resolution: {integrity: sha512-P4YJBPdPSpWTQ1NU4XYdvHvXJJDxM6YwpS0FZHRgP7YFkdVxsWcpWGy/NVqlAA7PcPCnMacXlRm1y2PFZRWL/w==} engines: {node: '>= 20'} - '@octokit/core@7.0.3': - resolution: {integrity: sha512-oNXsh2ywth5aowwIa7RKtawnkdH6LgU1ztfP9AIUCQCvzysB+WeU8o2kyyosDPwBZutPpjZDKPQGIzzrfTWweQ==} + '@octokit/core@7.0.6': + resolution: {integrity: sha512-DhGl4xMVFGVIyMwswXeyzdL4uXD5OGILGX5N8Y+f6W7LhC1Ze2poSNrkF/fedpVDHEEZ+PHFW0vL14I+mm8K3Q==} engines: {node: '>= 20'} - '@octokit/endpoint@11.0.0': - resolution: {integrity: sha512-hoYicJZaqISMAI3JfaDr1qMNi48OctWuOih1m80bkYow/ayPw6Jj52tqWJ6GEoFTk1gBqfanSoI1iY99Z5+ekQ==} + '@octokit/endpoint@11.0.3': + resolution: {integrity: sha512-FWFlNxghg4HrXkD3ifYbS/IdL/mDHjh9QcsNyhQjN8dplUoZbejsdpmuqdA76nxj2xoWPs7p8uX2SNr9rYu0Ag==} engines: {node: '>= 20'} - '@octokit/graphql@9.0.1': - resolution: {integrity: sha512-j1nQNU1ZxNFx2ZtKmL4sMrs4egy5h65OMDmSbVyuCzjOcwsHq6EaYjOTGXPQxgfiN8dJ4CriYHk6zF050WEULg==} + '@octokit/graphql@9.0.3': + resolution: {integrity: sha512-grAEuupr/C1rALFnXTv6ZQhFuL1D8G5y8CN04RgrO4FIPMrtm+mcZzFG7dcBm+nq+1ppNixu+Jd78aeJOYxlGA==} engines: {node: '>= 20'} - '@octokit/openapi-types@25.1.0': - resolution: {integrity: sha512-idsIggNXUKkk0+BExUn1dQ92sfysJrje03Q0bv0e+KPLrvyqZF8MnBpFz8UNfYDwB3Ie7Z0TByjWfzxt7vseaA==} + '@octokit/openapi-types@27.0.0': + resolution: {integrity: sha512-whrdktVs1h6gtR+09+QsNk2+FO+49j6ga1c55YZudfEG+oKJVvJLQi3zkOm5JjiUXAagWK2tI2kTGKJ2Ys7MGA==} - '@octokit/plugin-paginate-rest@13.1.1': - resolution: {integrity: sha512-q9iQGlZlxAVNRN2jDNskJW/Cafy7/XE52wjZ5TTvyhyOD904Cvx//DNyoO3J/MXJ0ve3rPoNWKEg5iZrisQSuw==} + '@octokit/plugin-paginate-rest@14.0.0': + resolution: {integrity: sha512-fNVRE7ufJiAA3XUrha2omTA39M6IXIc6GIZLvlbsm8QOQCYvpq/LkMNGyFlB1d8hTDzsAXa3OKtybdMAYsV/fw==} engines: {node: '>= 20'} peerDependencies: '@octokit/core': '>=6' @@ -1250,26 +1102,156 @@ packages: peerDependencies: '@octokit/core': '>=6' - '@octokit/plugin-rest-endpoint-methods@16.0.0': - resolution: {integrity: sha512-kJVUQk6/dx/gRNLWUnAWKFs1kVPn5O5CYZyssyEoNYaFedqZxsfYs7DwI3d67hGz4qOwaJ1dpm07hOAD1BXx6g==} + '@octokit/plugin-rest-endpoint-methods@17.0.0': + resolution: {integrity: sha512-B5yCyIlOJFPqUUeiD0cnBJwWJO8lkJs5d8+ze9QDP6SvfiXSz1BF+91+0MeI1d2yxgOhU/O+CvtiZ9jSkHhFAw==} engines: {node: '>= 20'} peerDependencies: '@octokit/core': '>=6' - '@octokit/request-error@7.0.0': - resolution: {integrity: sha512-KRA7VTGdVyJlh0cP5Tf94hTiYVVqmt2f3I6mnimmaVz4UG3gQV/k4mDJlJv3X67iX6rmN7gSHCF8ssqeMnmhZg==} + '@octokit/request-error@7.1.0': + resolution: {integrity: sha512-KMQIfq5sOPpkQYajXHwnhjCC0slzCNScLHs9JafXc4RAJI+9f+jNDlBNaIMTvazOPLgb4BnlhGJOTbnN0wIjPw==} engines: {node: '>= 20'} - '@octokit/request@10.0.3': - resolution: {integrity: sha512-V6jhKokg35vk098iBqp2FBKunk3kMTXlmq+PtbV9Gl3TfskWlebSofU9uunVKhUN7xl+0+i5vt0TGTG8/p/7HA==} + '@octokit/request@10.0.8': + resolution: {integrity: sha512-SJZNwY9pur9Agf7l87ywFi14W+Hd9Jg6Ifivsd33+/bGUQIjNujdFiXII2/qSlN2ybqUHfp5xpekMEjIBTjlSw==} engines: {node: '>= 20'} - '@octokit/rest@22.0.0': - resolution: {integrity: sha512-z6tmTu9BTnw51jYGulxrlernpsQYXpui1RK21vmXn8yF5bp6iX16yfTtJYGK5Mh1qDkvDOmp2n8sRMcQmR8jiA==} + '@octokit/rest@22.0.1': + resolution: {integrity: sha512-Jzbhzl3CEexhnivb1iQ0KJ7s5vvjMWcmRtq5aUsKmKDrRW6z3r84ngmiFKFvpZjpiU/9/S6ITPFRpn5s/3uQJw==} engines: {node: '>= 20'} - '@octokit/types@14.1.0': - resolution: {integrity: sha512-1y6DgTy8Jomcpu33N+p5w58l6xyt55Ar2I91RPiIA0xCJBXyUAhXCcmZaDWSANiha7R9a6qJJ2CRomGPZ6f46g==} + '@octokit/types@16.0.0': + resolution: {integrity: sha512-sKq+9r1Mm4efXW1FCk7hFSeJo4QKreL/tTbR0rz/qx/r1Oa2VV83LTA/H/MuCOX7uCIJmQVRKBcbmWoySjAnSg==} + + '@oxc-parser/binding-android-arm-eabi@0.115.0': + resolution: {integrity: sha512-VoB2rhgoqgYf64d6Qs5emONQW8ASiTc0xp+aUE4JUhxjX+0pE3gblTYDO0upcN5vt9UlBNmUhAwfSifkfre7nw==} + engines: {node: ^20.19.0 || >=22.12.0} + cpu: [arm] + os: [android] + + '@oxc-parser/binding-android-arm64@0.115.0': + resolution: {integrity: sha512-lWRX75u+gqfB4TF3pWCHuvhaeneAmRl2b2qNBcl4S6yJ0HtnT4VXOMEZrq747i4Zby1ZTxj6mtOe678Bg8gRLw==} + engines: {node: ^20.19.0 || >=22.12.0} + cpu: [arm64] + os: [android] + + '@oxc-parser/binding-darwin-arm64@0.115.0': + resolution: {integrity: sha512-ii/oOZjfGY1aszXTy29Z5DRyCEnBOrAXDVCvfdfXFQsOZlbbOa7NMHD7D+06YFe5qdxfmbWAYv4yn6QJi/0d2g==} + engines: {node: ^20.19.0 || >=22.12.0} + cpu: [arm64] + os: [darwin] + + '@oxc-parser/binding-darwin-x64@0.115.0': + resolution: {integrity: sha512-R/sW/p8l77wglbjpMcF+h/3rWbp9zk1mRP3U14mxTYIC2k3m+aLBpXXgk2zksqf9qKk5mcc4GIYsuCn9l8TgDg==} + engines: {node: ^20.19.0 || >=22.12.0} + cpu: [x64] + os: [darwin] + + '@oxc-parser/binding-freebsd-x64@0.115.0': + resolution: {integrity: sha512-CSJ5ldNm9wIGGkhaIJeGmxRMZbgxThRN+X1ufYQQUNi5jZDV/U3C2QDMywpP93fczNBj961hXtcUPO/oVGq4Pw==} + engines: {node: ^20.19.0 || >=22.12.0} + cpu: [x64] + os: [freebsd] + + '@oxc-parser/binding-linux-arm-gnueabihf@0.115.0': + resolution: {integrity: sha512-uWFwssE5dHfQ8lH+ktrsD9JA49+Qa0gtxZHUs62z1e91NgGz6O7jefHGI6aygNyKNS45pnnBSDSP/zV977MsOQ==} + engines: {node: ^20.19.0 || >=22.12.0} + cpu: [arm] + os: [linux] + + '@oxc-parser/binding-linux-arm-musleabihf@0.115.0': + resolution: {integrity: sha512-fZbqt8y/sKQ+v6bBCuv/mYYFoC0+fZI3mGDDEemmDOhT78+aUs2+4ZMdbd2btlXmnLaScl37r8IRbhnok5Ka9w==} + engines: {node: ^20.19.0 || >=22.12.0} + cpu: [arm] + os: [linux] + + '@oxc-parser/binding-linux-arm64-gnu@0.115.0': + resolution: {integrity: sha512-1ej/MjuTY9tJEunU/hUPIFmgH5PqgMQoRjNOvOkibtJ3Zqlw/+Lc+HGHDNET8sjbgIkWzdhX+p4J96A5CPdbag==} + engines: {node: ^20.19.0 || >=22.12.0} + cpu: [arm64] + os: [linux] + libc: [glibc] + + '@oxc-parser/binding-linux-arm64-musl@0.115.0': + resolution: {integrity: sha512-HjsZbJPH9mMd4swJRywVMsDZsJX0hyKb1iNHo5ijRl5yhtbO3lj7ImSrrL1oZ1VEg0te4iKmDGGz/6YPLd1G8w==} + engines: {node: ^20.19.0 || >=22.12.0} + cpu: [arm64] + os: [linux] + libc: [musl] + + '@oxc-parser/binding-linux-ppc64-gnu@0.115.0': + resolution: {integrity: sha512-zhhePoBrd7kQx3oClX/W6NldsuCbuMqaN9rRsY+6/WoorAb4j490PG/FjqgAXscWp2uSW2WV9L+ksn0wHrvsrg==} + engines: {node: ^20.19.0 || >=22.12.0} + cpu: [ppc64] + os: [linux] + libc: [glibc] + + '@oxc-parser/binding-linux-riscv64-gnu@0.115.0': + resolution: {integrity: sha512-t/IRojvUE9XrKu+/H1b8YINug+7Q6FLls5rsm2lxB5mnS8GN/eYAYrPgHkcg9/1SueRDSzGpDYu3lGWTObk1zw==} + engines: {node: ^20.19.0 || >=22.12.0} + cpu: [riscv64] + os: [linux] + libc: [glibc] + + '@oxc-parser/binding-linux-riscv64-musl@0.115.0': + resolution: {integrity: sha512-79jBHSSh/YpQRAmvYoaCfpyToRbJ/HBrdB7hxK2ku2JMehjopTVo+xMJss/RV7/ZYqeezgjvKDQzapJbgcjVZA==} + engines: {node: ^20.19.0 || >=22.12.0} + cpu: [riscv64] + os: [linux] + libc: [musl] + + '@oxc-parser/binding-linux-s390x-gnu@0.115.0': + resolution: {integrity: sha512-nA1TpxkhNTIOMMyiSSsa7XIVJVoOU/SsVrHIz3gHvWweB5PHCQfO7w+Lb2EP0lBWokv7HtA/KbF7aLDoXzmuMw==} + engines: {node: ^20.19.0 || >=22.12.0} + cpu: [s390x] + os: [linux] + libc: [glibc] + + '@oxc-parser/binding-linux-x64-gnu@0.115.0': + resolution: {integrity: sha512-9iVX789DoC3SaOOG+X6NcF/tVChgLp2vcHffzOC2/Z1JTPlz6bMG2ogvcW6/9s0BG2qvhNQImd+gbWYeQbOwVw==} + engines: {node: ^20.19.0 || >=22.12.0} + cpu: [x64] + os: [linux] + libc: [glibc] + + '@oxc-parser/binding-linux-x64-musl@0.115.0': + resolution: {integrity: sha512-RmQmk+mjCB0nMNfEYhaCxwofLo1Z95ebHw1AGvRiWGCd4zhCNOyskgCbMogIcQzSB3SuEKWgkssyaiQYVAA4hQ==} + engines: {node: ^20.19.0 || >=22.12.0} + cpu: [x64] + os: [linux] + libc: [musl] + + '@oxc-parser/binding-openharmony-arm64@0.115.0': + resolution: {integrity: sha512-viigraWWQhhDvX5aGq+wrQq58k00Xq3MHz/0R4AFMxGlZ8ogNonpEfNc73Q5Ly87Z6sU9BvxEdG0dnYTfVnmew==} + engines: {node: ^20.19.0 || >=22.12.0} + cpu: [arm64] + os: [openharmony] + + '@oxc-parser/binding-wasm32-wasi@0.115.0': + resolution: {integrity: sha512-IzGCrMwXhpb4kTXy/8lnqqqwjI7eOvy+r9AhVw+hsr8t1ecBBEHprcNy0aKatFHN6hsX7UMHHQmBAQjVvL/p1A==} + engines: {node: '>=14.0.0'} + cpu: [wasm32] + + '@oxc-parser/binding-win32-arm64-msvc@0.115.0': + resolution: {integrity: sha512-/ym+Absk/TLFvbhh3se9XYuI1D7BrUVHw4RaG/2dmWKgBenrZHaJsgnRb7NJtaOyjEOLIPtULx1wDdVL0SX2eg==} + engines: {node: ^20.19.0 || >=22.12.0} + cpu: [arm64] + os: [win32] + + '@oxc-parser/binding-win32-ia32-msvc@0.115.0': + resolution: {integrity: sha512-AQSZjIR+b+Te7uaO/hGTMjT8/oxlYrvKrOTi4KTHF/O6osjHEatUQ3y6ZW2+8+lJxy20zIcGz6iQFmFq/qDKkg==} + engines: {node: ^20.19.0 || >=22.12.0} + cpu: [ia32] + os: [win32] + + '@oxc-parser/binding-win32-x64-msvc@0.115.0': + resolution: {integrity: sha512-oxUl82N+fIO9jIaXPph8SPPHQXrA08BHokBBJW8ct9F/x6o6bZE6eUAhUtWajbtvFhL8UYcCWRMba+kww6MBlA==} + engines: {node: ^20.19.0 || >=22.12.0} + cpu: [x64] + os: [win32] + + '@oxc-project/types@0.115.0': + resolution: {integrity: sha512-4n91DKnebUS4yjUHl2g3/b2T+IUdCfmoZGhmwsovZCDaJSs+QkVAM+0AqqTxHSsHfeiMuueT75cZaZcT/m0pSw==} '@polka/url@1.0.0-next.29': resolution: {integrity: sha512-wwQAWhWSuHaag8c4q/KN/vCoeOJYshAIvMQwD4GpSb3OiZklFfvAgmj0VCBBImRpuF/aFgIRzllXlVX93Jevww==} @@ -1283,9 +1265,8 @@ packages: '@poppinss/exception@1.2.3': resolution: {integrity: sha512-dCED+QRChTVatE9ibtoaxc+WkdzOSjYTKi/+uacHWIsfodVfpsueo3+DKpgU5Px8qXjgmXkSvhXvSCz3fnP9lw==} - '@quansync/fs@0.1.3': - resolution: {integrity: sha512-G0OnZbMWEs5LhDyqy2UL17vGhSVHkQIfVojMtEWVenvj0V5S84VBgy86kJIuNsGDp2p7sTKlpSIpBUWdC35OKg==} - engines: {node: '>=20.0.0'} + '@quansync/fs@1.0.0': + resolution: {integrity: sha512-4TJ3DFtlf1L5LDMaM6CanJ/0lckGNtJcMjQ1NAV6zDmA0tEHKZtxNKin8EgPaVX1YzljbxckyT2tJrpQKAtngQ==} '@rollup/plugin-terser@0.4.4': resolution: {integrity: sha512-XHeJC5Bgvs8LfukDwWZp7yeqin6ns8RTl2B9avbejt6tZqsqvVoWI7ZTQrcNsfKEDWBTnTxM8nMDkO2IFFbd0A==} @@ -1309,8 +1290,8 @@ packages: tslib: optional: true - '@rollup/pluginutils@5.2.0': - resolution: {integrity: sha512-qWJ2ZTbmumwiLFomfzTyt5Kng4hwPi9rwCYN4SHb6eaRU1KNO4ccxINHr/VhH4GgPlt1XfSTLX2LBTme8ne4Zw==} + '@rollup/pluginutils@5.3.0': + resolution: {integrity: sha512-5EdhGZtnu3V88ces7s53hhfK5KSASnJZv8Lulpc04cWO3REESroJXg73DFsOmgbU2BhwV0E20bu2IDZb3VKW4Q==} engines: {node: '>=14.0.0'} peerDependencies: rollup: ^1.20.0||^2.0.0||^3.0.0||^4.0.0 @@ -1352,66 +1333,79 @@ packages: resolution: {integrity: sha512-t4ONHboXi/3E0rT6OZl1pKbl2Vgxf9vJfWgmUoCEVQVxhW6Cw/c8I6hbbu7DAvgp82RKiH7TpLwxnJeKv2pbsw==} cpu: [arm] os: [linux] + libc: [glibc] '@rollup/rollup-linux-arm-musleabihf@4.59.0': resolution: {integrity: sha512-CikFT7aYPA2ufMD086cVORBYGHffBo4K8MQ4uPS/ZnY54GKj36i196u8U+aDVT2LX4eSMbyHtyOh7D7Zvk2VvA==} cpu: [arm] os: [linux] + libc: [musl] '@rollup/rollup-linux-arm64-gnu@4.59.0': resolution: {integrity: sha512-jYgUGk5aLd1nUb1CtQ8E+t5JhLc9x5WdBKew9ZgAXg7DBk0ZHErLHdXM24rfX+bKrFe+Xp5YuJo54I5HFjGDAA==} cpu: [arm64] os: [linux] + libc: [glibc] '@rollup/rollup-linux-arm64-musl@4.59.0': resolution: {integrity: sha512-peZRVEdnFWZ5Bh2KeumKG9ty7aCXzzEsHShOZEFiCQlDEepP1dpUl/SrUNXNg13UmZl+gzVDPsiCwnV1uI0RUA==} cpu: [arm64] os: [linux] + libc: [musl] '@rollup/rollup-linux-loong64-gnu@4.59.0': resolution: {integrity: sha512-gbUSW/97f7+r4gHy3Jlup8zDG190AuodsWnNiXErp9mT90iCy9NKKU0Xwx5k8VlRAIV2uU9CsMnEFg/xXaOfXg==} cpu: [loong64] os: [linux] + libc: [glibc] '@rollup/rollup-linux-loong64-musl@4.59.0': resolution: {integrity: sha512-yTRONe79E+o0FWFijasoTjtzG9EBedFXJMl888NBEDCDV9I2wGbFFfJQQe63OijbFCUZqxpHz1GzpbtSFikJ4Q==} cpu: [loong64] os: [linux] + libc: [musl] '@rollup/rollup-linux-ppc64-gnu@4.59.0': resolution: {integrity: sha512-sw1o3tfyk12k3OEpRddF68a1unZ5VCN7zoTNtSn2KndUE+ea3m3ROOKRCZxEpmT9nsGnogpFP9x6mnLTCaoLkA==} cpu: [ppc64] os: [linux] + libc: [glibc] '@rollup/rollup-linux-ppc64-musl@4.59.0': resolution: {integrity: sha512-+2kLtQ4xT3AiIxkzFVFXfsmlZiG5FXYW7ZyIIvGA7Bdeuh9Z0aN4hVyXS/G1E9bTP/vqszNIN/pUKCk/BTHsKA==} cpu: [ppc64] os: [linux] + libc: [musl] '@rollup/rollup-linux-riscv64-gnu@4.59.0': resolution: {integrity: sha512-NDYMpsXYJJaj+I7UdwIuHHNxXZ/b/N2hR15NyH3m2qAtb/hHPA4g4SuuvrdxetTdndfj9b1WOmy73kcPRoERUg==} cpu: [riscv64] os: [linux] + libc: [glibc] '@rollup/rollup-linux-riscv64-musl@4.59.0': resolution: {integrity: sha512-nLckB8WOqHIf1bhymk+oHxvM9D3tyPndZH8i8+35p/1YiVoVswPid2yLzgX7ZJP0KQvnkhM4H6QZ5m0LzbyIAg==} cpu: [riscv64] os: [linux] + libc: [musl] '@rollup/rollup-linux-s390x-gnu@4.59.0': resolution: {integrity: sha512-oF87Ie3uAIvORFBpwnCvUzdeYUqi2wY6jRFWJAy1qus/udHFYIkplYRW+wo+GRUP4sKzYdmE1Y3+rY5Gc4ZO+w==} cpu: [s390x] os: [linux] + libc: [glibc] '@rollup/rollup-linux-x64-gnu@4.59.0': resolution: {integrity: sha512-3AHmtQq/ppNuUspKAlvA8HtLybkDflkMuLK4DPo77DfthRb71V84/c4MlWJXixZz4uruIH4uaa07IqoAkG64fg==} cpu: [x64] os: [linux] + libc: [glibc] '@rollup/rollup-linux-x64-musl@4.59.0': resolution: {integrity: sha512-2UdiwS/9cTAx7qIUZB/fWtToJwvt0Vbo0zmnYt7ED35KPg13Q0ym1g442THLC7VyI6JfYTP4PiSOWyoMdV2/xg==} cpu: [x64] os: [linux] + libc: [musl] '@rollup/rollup-openbsd-x64@4.59.0': resolution: {integrity: sha512-M3bLRAVk6GOwFlPTIxVBSYKUaqfLrn8l0psKinkCFxl4lQvOSz8ZrKDz2gxcBwHFpci0B6rttydI4IpS4IS/jQ==} @@ -1450,24 +1444,24 @@ packages: '@speed-highlight/core@1.2.14': resolution: {integrity: sha512-G4ewlBNhUtlLvrJTb88d2mdy2KRijzs4UhnlrOSRT4bmjh/IqNElZa3zkrZ+TC47TwtlDWzVLFADljF1Ijp5hA==} - '@standard-schema/spec@1.0.0': - resolution: {integrity: sha512-m2bOd0f2RT9k8QJx1JN85cZYyH1RqFBdlwtkSlf4tBDYLCiiZnv1fIIwacK6cqwXavOydf0NPToMQgpKq+dVlA==} + '@standard-schema/spec@1.1.0': + resolution: {integrity: sha512-l2aFy5jALhniG5HgqrD6jXLi/rUWrKvqN/qJx6yoJsgKhblVd+iqqU4RCXavm/jPityDo5TCvKMnpjKnOriy0w==} '@sveltejs/acorn-typescript@1.0.9': resolution: {integrity: sha512-lVJX6qEgs/4DOcRTpo56tmKzVPtoWAaVbL4hfO7t7NVwl9AAXzQR6cihesW1BmNMPl+bK6dreu2sOKBP2Q9CIA==} peerDependencies: acorn: ^8.9.0 - '@sveltejs/vite-plugin-svelte-inspector@5.0.0': - resolution: {integrity: sha512-iwQ8Z4ET6ZFSt/gC+tVfcsSBHwsqc6RumSaiLUkAurW3BCpJam65cmHw0oOlDMTO0u+PZi9hilBRYN+LZNHTUQ==} + '@sveltejs/vite-plugin-svelte-inspector@5.0.2': + resolution: {integrity: sha512-TZzRTcEtZffICSAoZGkPSl6Etsj2torOVrx6Uw0KpXxrec9Gg6jFWQ60Q3+LmNGfZSxHRCZL7vXVZIWmuV50Ig==} engines: {node: ^20.19 || ^22.12 || >=24} peerDependencies: '@sveltejs/vite-plugin-svelte': ^6.0.0-next.0 svelte: ^5.0.0 vite: ^6.3.0 || ^7.0.0 - '@sveltejs/vite-plugin-svelte@6.0.0': - resolution: {integrity: sha512-mma5GJ23pYiWpTNbN//g9XI3Hfob3aAlXPP42qRtvjgTAU6pfJyLyNPTdLjFuj+jfC9JslP4J3AkeiJNhjtLLA==} + '@sveltejs/vite-plugin-svelte@6.2.4': + resolution: {integrity: sha512-ou/d51QSdTyN26D7h6dSpusAKaZkAiGM55/AKYi+9AGZw7q85hElbjK3kEyzXHhLSnRISHOYzVge6x0jRZ7DXA==} engines: {node: ^20.19 || ^22.12 || >=24} peerDependencies: svelte: ^5.0.0 @@ -1476,8 +1470,8 @@ packages: '@tybys/wasm-util@0.10.1': resolution: {integrity: sha512-9tTaPJLSiejZKx+Bmog4uSubteqTvFrVrURwkmHixBo0G4seD0zUxp98E1DzUBJxLQ3NPwXrGKDiVjwx/DpPsg==} - '@types/chai@5.2.2': - resolution: {integrity: sha512-8kB30R7Hwqf40JPiKhVzodJs2Qc1ZJ5zuT3uzw5Hq/dhNCl3G3l83jfpdI1e20BP348+fV7VIL/+FxaXkqBmWg==} + '@types/chai@5.2.3': + resolution: {integrity: sha512-Mw558oeA9fFbv65/y4mHtXDs9bPnFMZAL/jxdPFUpOHHIXX91mcgEHbS5Lahr+pwZFR8A7GQleRWeI6cGFC2UA==} '@types/deep-eql@4.0.2': resolution: {integrity: sha512-c9h9dVVMigMPc4bwTvC5dxqtqJZwQPePsWjPlpSOnojbor6pGqdk541lfA7AqFQr5pB1BRdq0juY9db81BwyFw==} @@ -1494,165 +1488,151 @@ packages: '@types/json-schema@7.0.15': resolution: {integrity: sha512-5+fP8P8MFNC+AyZCDxrB2pkZFPGzqQWUzpSeuuVLvm8VMcorNYavBqoFcxK8bQz4Qsbn4oUEEem4wDLfcysGHA==} - '@types/node@24.10.0': - resolution: {integrity: sha512-qzQZRBqkFsYyaSWXuEHc2WR9c0a0CXwiE5FWUvn7ZM+vdy1uZLfCunD38UzhuB7YN/J11ndbDBcTmOdxJo9Q7A==} + '@types/node@24.11.0': + resolution: {integrity: sha512-fPxQqz4VTgPI/IQ+lj9r0h+fDR66bzoeMGHp8ASee+32OSGIkeASsoZuJixsQoVef1QJbeubcPBxKk22QVoWdw==} '@types/trusted-types@2.0.7': resolution: {integrity: sha512-ScaPdn1dQczgbl0QFTeTOmVHFULt394XJgOQNoyVhZ6r2vLnMLJfBPd53SB52T/3G36VI1/g2MZaX0cwDuXsfw==} - '@typescript-eslint/eslint-plugin@8.56.0': - resolution: {integrity: sha512-lRyPDLzNCuae71A3t9NEINBiTn7swyOhvUj3MyUOxb8x6g6vPEFoOU+ZRmGMusNC3X3YMhqMIX7i8ShqhT74Pw==} + '@typescript-eslint/eslint-plugin@8.56.1': + resolution: {integrity: sha512-Jz9ZztpB37dNC+HU2HI28Bs9QXpzCz+y/twHOwhyrIRdbuVDxSytJNDl6z/aAKlaRIwC7y8wJdkBv7FxYGgi0A==} engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0} peerDependencies: - '@typescript-eslint/parser': ^8.56.0 + '@typescript-eslint/parser': ^8.56.1 eslint: ^8.57.0 || ^9.0.0 || ^10.0.0 typescript: '>=4.8.4 <6.0.0' - '@typescript-eslint/parser@8.56.0': - resolution: {integrity: sha512-IgSWvLobTDOjnaxAfDTIHaECbkNlAlKv2j5SjpB2v7QHKv1FIfjwMy8FsDbVfDX/KjmCmYICcw7uGaXLhtsLNg==} + '@typescript-eslint/parser@8.56.1': + resolution: {integrity: sha512-klQbnPAAiGYFyI02+znpBRLyjL4/BrBd0nyWkdC0s/6xFLkXYQ8OoRrSkqacS1ddVxf/LDyODIKbQ5TgKAf/Fg==} engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0} peerDependencies: eslint: ^8.57.0 || ^9.0.0 || ^10.0.0 typescript: '>=4.8.4 <6.0.0' - '@typescript-eslint/project-service@8.56.0': - resolution: {integrity: sha512-M3rnyL1vIQOMeWxTWIW096/TtVP+8W3p/XnaFflhmcFp+U4zlxUxWj4XwNs6HbDeTtN4yun0GNTTDBw/SvufKg==} + '@typescript-eslint/project-service@8.56.1': + resolution: {integrity: sha512-TAdqQTzHNNvlVFfR+hu2PDJrURiwKsUvxFn1M0h95BB8ah5jejas08jUWG4dBA68jDMI988IvtfdAI53JzEHOQ==} engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0} peerDependencies: typescript: '>=4.8.4 <6.0.0' - '@typescript-eslint/scope-manager@8.56.0': - resolution: {integrity: sha512-7UiO/XwMHquH+ZzfVCfUNkIXlp/yQjjnlYUyYz7pfvlK3/EyyN6BK+emDmGNyQLBtLGaYrTAI6KOw8tFucWL2w==} + '@typescript-eslint/scope-manager@8.56.1': + resolution: {integrity: sha512-YAi4VDKcIZp0O4tz/haYKhmIDZFEUPOreKbfdAN3SzUDMcPhJ8QI99xQXqX+HoUVq8cs85eRKnD+rne2UAnj2w==} engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0} - '@typescript-eslint/tsconfig-utils@8.56.0': - resolution: {integrity: sha512-bSJoIIt4o3lKXD3xmDh9chZcjCz5Lk8xS7Rxn+6l5/pKrDpkCwtQNQQwZ2qRPk7TkUYhrq3WPIHXOXlbXP0itg==} + '@typescript-eslint/tsconfig-utils@8.56.1': + resolution: {integrity: sha512-qOtCYzKEeyr3aR9f28mPJqBty7+DBqsdd63eO0yyDwc6vgThj2UjWfJIcsFeSucYydqcuudMOprZ+x1SpF3ZuQ==} engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0} peerDependencies: typescript: '>=4.8.4 <6.0.0' - '@typescript-eslint/type-utils@8.56.0': - resolution: {integrity: sha512-qX2L3HWOU2nuDs6GzglBeuFXviDODreS58tLY/BALPC7iu3Fa+J7EOTwnX9PdNBxUI7Uh0ntP0YWGnxCkXzmfA==} + '@typescript-eslint/type-utils@8.56.1': + resolution: {integrity: sha512-yB/7dxi7MgTtGhZdaHCemf7PuwrHMenHjmzgUW1aJpO+bBU43OycnM3Wn+DdvDO/8zzA9HlhaJ0AUGuvri4oGg==} engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0} peerDependencies: eslint: ^8.57.0 || ^9.0.0 || ^10.0.0 typescript: '>=4.8.4 <6.0.0' - '@typescript-eslint/types@8.56.0': - resolution: {integrity: sha512-DBsLPs3GsWhX5HylbP9HNG15U0bnwut55Lx12bHB9MpXxQ+R5GC8MwQe+N1UFXxAeQDvEsEDY6ZYwX03K7Z6HQ==} + '@typescript-eslint/types@8.56.1': + resolution: {integrity: sha512-dbMkdIUkIkchgGDIv7KLUpa0Mda4IYjo4IAMJUZ+3xNoUXxMsk9YtKpTHSChRS85o+H9ftm51gsK1dZReY9CVw==} engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0} - '@typescript-eslint/typescript-estree@8.56.0': - resolution: {integrity: sha512-ex1nTUMWrseMltXUHmR2GAQ4d+WjkZCT4f+4bVsps8QEdh0vlBsaCokKTPlnqBFqqGaxilDNJG7b8dolW2m43Q==} + '@typescript-eslint/typescript-estree@8.56.1': + resolution: {integrity: sha512-qzUL1qgalIvKWAf9C1HpvBjif+Vm6rcT5wZd4VoMb9+Km3iS3Cv9DY6dMRMDtPnwRAFyAi7YXJpTIEXLvdfPxg==} engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0} peerDependencies: typescript: '>=4.8.4 <6.0.0' - '@typescript-eslint/utils@8.56.0': - resolution: {integrity: sha512-RZ3Qsmi2nFGsS+n+kjLAYDPVlrzf7UhTffrDIKr+h2yzAlYP/y5ZulU0yeDEPItos2Ph46JAL5P/On3pe7kDIQ==} + '@typescript-eslint/utils@8.56.1': + resolution: {integrity: sha512-HPAVNIME3tABJ61siYlHzSWCGtOoeP2RTIaHXFMPqjrQKCGB9OgUVdiNgH7TJS2JNIQ5qQ4RsAUDuGaGme/KOA==} engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0} peerDependencies: eslint: ^8.57.0 || ^9.0.0 || ^10.0.0 typescript: '>=4.8.4 <6.0.0' - '@typescript-eslint/visitor-keys@8.56.0': - resolution: {integrity: sha512-q+SL+b+05Ud6LbEE35qe4A99P+htKTKVbyiNEe45eCbJFyh/HVK9QXwlrbz+Q4L8SOW4roxSVwXYj4DMBT7Ieg==} + '@typescript-eslint/visitor-keys@8.56.1': + resolution: {integrity: sha512-KiROIzYdEV85YygXw6BI/Dx4fnBlFQu6Mq4QE4MOH9fFnhohw6wX/OAvDY2/C+ut0I3RSPKenvZJIVYqJNkhEw==} engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0} - '@unocss/astro@66.3.3': - resolution: {integrity: sha512-q26EfadSMmEXZpWDKsJF9anBCfhYDmWljVpDZ2Wo8K48IbZMUXrWfiAiUc6ijE/A/rADfHk8bp3a3GE01t3I9A==} - peerDependencies: - vite: ^2.9.0 || ^3.0.0-0 || ^4.0.0 || ^5.0.0-0 || ^6.0.0-0 || ^7.0.0-0 - peerDependenciesMeta: - vite: - optional: true - - '@unocss/cli@66.3.3': - resolution: {integrity: sha512-U0HoDcwi/DetqP5zDT3dfxG94pC3TI0PfxmpdTfPY7xEylIdLbV89fb70CvJVysDSQJIuw6TYwqS1ZlHoYNKTA==} + '@unocss/cli@66.6.5': + resolution: {integrity: sha512-UlETATpAZ+A5gOfj+z+BMXuIUcXCMjvlQteQE0VR2Yf0VIxz4sVO4z0VCXwXsxLTMfQiIMDpKVrGeczcYicvTA==} engines: {node: '>=14'} hasBin: true - '@unocss/config@66.3.3': - resolution: {integrity: sha512-D/UxnAmkabapqWU4tF85dWWhNfCUyNutWmd4AD2VsQRZOykufJedLV74r3Z3XhoPJn4IGr3BKZm5/rflf5viDg==} + '@unocss/config@66.6.4': + resolution: {integrity: sha512-iwHl5FG81cOAMalqigjw21Z2tMa0xjN0doQxnGOLx8KP+BllruXSjBj8CRk3m6Ny9fDxfpFY0ruYbIBA5AGwDQ==} engines: {node: '>=14'} - '@unocss/core@66.3.3': - resolution: {integrity: sha512-6WFLd92TJelVQARtCGaF+EgEoHKIVe43gkGXVoWILu0HUDRWdhv+cpcyX0RTJV22Y976AxeneU7/zmhAh+CXNg==} + '@unocss/core@66.6.4': + resolution: {integrity: sha512-Fii3lhVJVFrKUz6hMGAkq3sXBfNnXB2G8bldNHuBHJpDAoP1F0oO/SU/oSqSjCYvtcD5RtOn8qwzcHuuN3B/mg==} - '@unocss/extractor-arbitrary-variants@66.3.3': - resolution: {integrity: sha512-TXzjH6FcITQ8V2x7ETHgVOlAHf3ll/ysxL+W4fMROm8jP/o7jvsg36tRfOwU0sDGo/qoCPux82ix9e6/JW0oqQ==} + '@unocss/core@66.6.5': + resolution: {integrity: sha512-hzjo+0EF+pNbf+tb0OjRNZRF9BJoKECcZZgtufxRPpWJdlv+aYmNkH1p9fldlHHzYcn3ZqVnnHnmk7HwaolJbg==} - '@unocss/extractor-svelte@66.3.3': - resolution: {integrity: sha512-6ExejgiA59Afl0MByQKeG1hLY3kwBIjUSRhz8/g/3oXrycbD5IP/OsvgbdOKhkpuVpNDmt0z8DzJs8FlyM5VUw==} + '@unocss/extractor-arbitrary-variants@66.6.5': + resolution: {integrity: sha512-wqzRtbyy3I595WCwwb8VBmznJTHWcTdylzVT+WBgacJDjRlT1sXaq2fRlOsHvtTRj1qG70t3PwKc6XgU0hutNg==} - '@unocss/inspector@66.3.3': - resolution: {integrity: sha512-NsK1WRWez2Mzk4+ophtBdXel8nGaPkIDa9lYSFMdKLF/1jNW23txeEL8CsD6/CK8K0BsR11rhLKhUrzyrjfBSQ==} + '@unocss/extractor-svelte@66.6.5': + resolution: {integrity: sha512-Zg58V3L5jxSPzT2BEZY87+WH0gVMI4VKZuwNwFS3ht83RsCD32eGjJxrk6w5CuIYDV6MeGSkosyPIwLY+OFD3w==} - '@unocss/postcss@66.3.3': - resolution: {integrity: sha512-VKq+BtfPIZbLeAeZFprtKZJAyFBOqA8qpQm+vmWBiBia70JzkwfF2SMNIHiGt022yRo9ZmjnI9uRTxSzqXUsUQ==} - engines: {node: '>=14'} - peerDependencies: - postcss: ^8.4.21 - - '@unocss/preset-attributify@66.3.3': - resolution: {integrity: sha512-22+0Cqqu09q+xHfZ3Wk8Coxe5m6PmpgWz4U5xrEC8056UfG3Q1KEqoCxy2wySJIq8SqxQ30Nlll7oMa31B8Krw==} + '@unocss/inspector@66.6.5': + resolution: {integrity: sha512-rrXPlSeRfYajEL65FL1Ok9Hfhjy9zvuZZwqXh9P0qCJlou2r2IqDFO/Gf9j5yO89tnKIfJ8ff6jEyqUmzbKSMQ==} - '@unocss/preset-icons@66.3.3': - resolution: {integrity: sha512-Bmhiev05BN/horlgnyZ8gzQWZKd7oVpUBWD66X7U/dgkLdO6B5GIIsdO5Fi7JLeMDmyXm6vlYk0YQhiTbx8l9w==} + '@unocss/preset-attributify@66.6.5': + resolution: {integrity: sha512-fx+pKMZ0WgT+dfinVaLkNXlx6oZFwtMbZj5O/1SQia0UcfhnyS+G35HYpbgoc9GEAl3DclxxotzZjveZm++9fA==} - '@unocss/preset-mini@66.3.3': - resolution: {integrity: sha512-pz8rgvHRYS/6fsZNtG7iArLzwANnLy5GkHY/lbuqkWhO2S2Nf7kpJCbR/uV/XeuFsLnYcZW3NLOmelfvZvJamA==} + '@unocss/preset-icons@66.6.5': + resolution: {integrity: sha512-03ppAcTWD77w1WZhORT8c9beTHBtWu3cx+c4qfShOfY6LQmZgx5i7DhCij5Wcj/U1zYA4Vrh13CDEmpsdZO3Cw==} - '@unocss/preset-tagify@66.3.3': - resolution: {integrity: sha512-L1Ez7Y4uBaW+wiv1BOQygpfhseSt3EZ53jqkl7fxl1EKVsJy6SuZgJxlXEHUYp9xYdSp6EHq2CfL8UevaR+loA==} + '@unocss/preset-mini@66.6.5': + resolution: {integrity: sha512-Ber3k2jlE8JP0y507hw/lvdDvcxfY0t4zaGA7hVZdEqlH6Eus/TqIVZ9tdMH4u0VDWYeAs98YV+auUJmMqGXpg==} - '@unocss/preset-typography@66.3.3': - resolution: {integrity: sha512-aQXiGCObvWD9grfUpm0d5nzN+Cpvag0rHP39UjUKb0xSTzY09VzwDrua4kWVO5wJLNK6/L70osyhEgmC3qToxA==} + '@unocss/preset-tagify@66.6.5': + resolution: {integrity: sha512-YYk/eg1OWX4Nx7rK1YZLMHXXntzNRDHp6BIInJteQmlXw0sFgrtdMKj7fnxrORsBDHwxWMp4sWEucPvfCtTlVQ==} - '@unocss/preset-uno@66.3.3': - resolution: {integrity: sha512-Tiho4LidpuMHrB19GHTU6XrL0A5eFELHk9ebQ/3WeTy+K/9a6Hn5zsHJe5UCtOsEcUdKB33oZx0hXUp93hb/YQ==} + '@unocss/preset-typography@66.6.5': + resolution: {integrity: sha512-Cb63tdC0P2rgj/4t4DrSCl6RHebNpjUp9FQArg0KCnFnW75nWtKlsKpHuEXpi7KwrgOIx+rjlkwC1bDcsdNLHw==} - '@unocss/preset-web-fonts@66.3.3': - resolution: {integrity: sha512-ysKZeC7TXxRiqnNL9GxZFGMKFAHXrcaqozPaEOIJ40dvzbJt8IMLyFndZkcFMcgDCV0pFh/y37mGxxxARO9+pQ==} + '@unocss/preset-uno@66.6.5': + resolution: {integrity: sha512-feZfGyzt3dH4h6yP2kjsx5MuoI1gU7vY/VL5O+ObosaB7HzzOFCsu2WzlvWn/FTRBi+scvdq436hsfflVyHYfQ==} - '@unocss/preset-wind3@66.3.3': - resolution: {integrity: sha512-iXmjvPqvmPTo4z7epQDqHxzlGRsbLJEgfETqTrRJeagvFG7Gs+ajS8cQhbf6wL01dSRHjvhVXi3MsIvqfHHXOw==} + '@unocss/preset-web-fonts@66.6.5': + resolution: {integrity: sha512-u5jEHYTMeseykqinXd2VY2n7q9yFQlZotREpfSAft8ENNJdV7Yg/6It3lL68zT/k1AV/A8gk94KEuDh0fnoSxQ==} - '@unocss/preset-wind4@66.3.3': - resolution: {integrity: sha512-JSJTXVJel6kX+u4Ktt6JGnukYWYhKxmjgORTwclUpokRHgEoD+xsh0Rz4YGJ1fWSnzNslNQhWP9yDRByVPHWwA==} + '@unocss/preset-wind3@66.6.5': + resolution: {integrity: sha512-0ccQoJmHq4tTnn5C0UKhP598B/gG65AjqlfgfRpwt059yAWYqizGy6MRUGdLklyEK4H06E6qbMBqIjla2rOexQ==} - '@unocss/preset-wind@66.3.3': - resolution: {integrity: sha512-3Mxl/TDPcv8nNKdFe3WKdlXE6de+lCaaizEH86BILW3ZeyPU9aKzWcZIoxohla0a6zMxDQ2+Gf+7EwaOvpqo7Q==} + '@unocss/preset-wind4@66.6.5': + resolution: {integrity: sha512-JT57CU60PY3/PHBvxY+UG53I9K+awin/TodZTn4lqQNnF2v6fjkeBKiys9cxeoP4wbHuQWorrW4GqRLNDWIMcw==} - '@unocss/reset@66.3.3': - resolution: {integrity: sha512-VIeR/mIcCL89/1uA1KM1QCYca4aeIGqEHMTJL1nCD4v+7wk6XhNXhsp5gMIHo+V804SUSmATWaeHTiKpiFu7AQ==} + '@unocss/preset-wind@66.6.5': + resolution: {integrity: sha512-GLu7LzVF0LHqdZoHFZ8dbsCv8TD5ZH/r10CQbrL5qwmp4a/uyfDEmsre4Nsqim7JktRyXn3HK2XQmTB8AmXpgQ==} - '@unocss/rule-utils@66.3.3': - resolution: {integrity: sha512-QKgVGV5nRRnK44/reUKFLAc5UGyl98vz3hrfk8JI8pVza58vmQWTdAB2rIpNJ5a5j+EkWfDOUlGQaOrIeYGLdg==} + '@unocss/rule-utils@66.6.5': + resolution: {integrity: sha512-eDGXoMebb5aeEAFa2y4gnGLC+CHZPx93JYCt6uvEyf9xOoetwDcZaYC8brWdjaSKn+WVgsfxiZreC7F0rJywOQ==} engines: {node: '>=14'} - '@unocss/transformer-attributify-jsx@66.3.3': - resolution: {integrity: sha512-ENNYFk5wrI4jlxn0tWGeR9QGxflAfZue3X2ABg0KSVOiYyIOsrHqtdoiLYkuCA9idRlBZPQxePJKcPWt1r/tYA==} + '@unocss/transformer-attributify-jsx@66.6.5': + resolution: {integrity: sha512-/dVaRR7V/2Alskb2rUPmP/lhyb/YCxYyYNxp30kxxW0ew6mZWXQRzsxOJJVmGp23Uw7HxUW63t8zXzUdoI0b+g==} - '@unocss/transformer-compile-class@66.3.3': - resolution: {integrity: sha512-VTEFuwp3iajGWyEFwmO5LRvOjgZM1TK+4rX5Q79xyTAPkLAKgOa03Ne8+kU8oG0TQEa4mXVw6ul9McM7UBJh1w==} + '@unocss/transformer-compile-class@66.6.5': + resolution: {integrity: sha512-U/ukk5lyZOFNyz9hVzZBkxciayjgimyfPuQBa5PHSC4W3nDmnFd1zgXzUVaM6KduPmiTExzpJSDgELb2OTbpqg==} - '@unocss/transformer-directives@66.3.3': - resolution: {integrity: sha512-11T7fmYk/XZcqFDn4qiIvs04mJhUtAoha5Y99bVE+L3byWa6BT4jb5aSAKk+24q5aynwgB++4RgfQxarj69WTw==} + '@unocss/transformer-directives@66.6.5': + resolution: {integrity: sha512-QgofDdDedNK6dQ246+RXhM6gTzRz7NuetQQ8UnNgArm4PBHngVrrkjCzG1ByDTtEtoE8WR70UMR4Vf5dXTcHPw==} - '@unocss/transformer-variant-group@66.3.3': - resolution: {integrity: sha512-uhK81pbJfXJFYaXxOoIFVEG8/Kx1iaAkTwRB6c+WNUfl9GiKyYQcrI7bETgCPPbg230Z68jVICBgBATeLJ31vQ==} + '@unocss/transformer-variant-group@66.6.5': + resolution: {integrity: sha512-k6vQgn/P7ObHBRYw6o1+xwdQIfwc6b9O5TFFe87UmBB6hJ2zaHWRVuPB6oky7F9Gz8bPfXC3WJuv7UyIwRmBQQ==} - '@unocss/vite@66.3.3': - resolution: {integrity: sha512-uu3smeEW6q36ri6vydRx2GiTGF5O/J80Fr4GLmLiwfpt2YnPHraO7XHVR5/mwG2Oz5Kov0uGvxVsdgxZABKRgw==} + '@unocss/vite@66.6.5': + resolution: {integrity: sha512-J/QZa6h94ordZlZytIKQkuYa+G2GiWiS3y9O1uoHAAN2tzFSkgCXNUif7lHu1h4eCrgC0AOHJSYWg1LIASNDkg==} peerDependencies: - vite: ^2.9.0 || ^3.0.0-0 || ^4.0.0 || ^5.0.0-0 || ^6.0.0-0 || ^7.0.0-0 + vite: ^2.9.0 || ^3.0.0-0 || ^4.0.0 || ^5.0.0-0 || ^6.0.0-0 || ^7.0.0-0 || ^8.0.0-0 - '@vitest/expect@4.0.6': - resolution: {integrity: sha512-5j8UUlBVhOjhj4lR2Nt9sEV8b4WtbcYh8vnfhTNA2Kn5+smtevzjNq+xlBuVhnFGXiyPPNzGrOVvmyHWkS5QGg==} + '@vitest/expect@4.0.18': + resolution: {integrity: sha512-8sCWUyckXXYvx4opfzVY03EOiYVxyNrHS5QxX3DAIi5dpJAAkyJezHCP77VMX4HKA2LDT/Jpfo8i2r5BE3GnQQ==} - '@vitest/mocker@4.0.6': - resolution: {integrity: sha512-3COEIew5HqdzBFEYN9+u0dT3i/NCwppLnO1HkjGfAP1Vs3vti1Hxm/MvcbC4DAn3Szo1M7M3otiAaT83jvqIjA==} + '@vitest/mocker@4.0.18': + resolution: {integrity: sha512-HhVd0MDnzzsgevnOWCBj5Otnzobjy5wLBe4EdeeFGv8luMsGcYqDuFRMcttKWZA5vVO8RFjexVovXvAM4JoJDQ==} peerDependencies: msw: ^2.4.9 vite: ^6.0.0 || ^7.0.0-0 @@ -1662,49 +1642,20 @@ packages: vite: optional: true - '@vitest/pretty-format@4.0.6': - resolution: {integrity: sha512-4vptgNkLIA1W1Nn5X4x8rLJBzPiJwnPc+awKtfBE5hNMVsoAl/JCCPPzNrbf+L4NKgklsis5Yp2gYa+XAS442g==} - - '@vitest/runner@4.0.6': - resolution: {integrity: sha512-trPk5qpd7Jj+AiLZbV/e+KiiaGXZ8ECsRxtnPnCrJr9OW2mLB72Cb824IXgxVz/mVU3Aj4VebY+tDTPn++j1Og==} - - '@vitest/snapshot@4.0.6': - resolution: {integrity: sha512-PaYLt7n2YzuvxhulDDu6c9EosiRuIE+FI2ECKs6yvHyhoga+2TBWI8dwBjs+IeuQaMtZTfioa9tj3uZb7nev1g==} + '@vitest/pretty-format@4.0.18': + resolution: {integrity: sha512-P24GK3GulZWC5tz87ux0m8OADrQIUVDPIjjj65vBXYG17ZeU3qD7r+MNZ1RNv4l8CGU2vtTRqixrOi9fYk/yKw==} - '@vitest/spy@4.0.6': - resolution: {integrity: sha512-g9jTUYPV1LtRPRCQfhbMintW7BTQz1n6WXYQYRQ25qkyffA4bjVXjkROokZnv7t07OqfaFKw1lPzqKGk1hmNuQ==} + '@vitest/runner@4.0.18': + resolution: {integrity: sha512-rpk9y12PGa22Jg6g5M3UVVnTS7+zycIGk9ZNGN+m6tZHKQb7jrP7/77WfZy13Y/EUDd52NDsLRQhYKtv7XfPQw==} - '@vitest/utils@4.0.6': - resolution: {integrity: sha512-bG43VS3iYKrMIZXBo+y8Pti0O7uNju3KvNn6DrQWhQQKcLavMB+0NZfO1/QBAEbq0MaQ3QjNsnnXlGQvsh0Z6A==} + '@vitest/snapshot@4.0.18': + resolution: {integrity: sha512-PCiV0rcl7jKQjbgYqjtakly6T1uwv/5BQ9SwBLekVg/EaYeQFPiXcgrC2Y7vDMA8dM1SUEAEV82kgSQIlXNMvA==} - '@vue/compiler-core@3.5.17': - resolution: {integrity: sha512-Xe+AittLbAyV0pabcN7cP7/BenRBNcteM4aSDCtRvGw0d9OL+HG1u/XHLY/kt1q4fyMeZYXyIYrsHuPSiDPosA==} + '@vitest/spy@4.0.18': + resolution: {integrity: sha512-cbQt3PTSD7P2OARdVW3qWER5EGq7PHlvE+QfzSC0lbwO+xnt7+XH06ZzFjFRgzUX//JmpxrCu92VdwvEPlWSNw==} - '@vue/compiler-dom@3.5.17': - resolution: {integrity: sha512-+2UgfLKoaNLhgfhV5Ihnk6wB4ljyW1/7wUIog2puUqajiC29Lp5R/IKDdkebh9jTbTogTbsgB+OY9cEWzG95JQ==} - - '@vue/compiler-sfc@3.5.17': - resolution: {integrity: sha512-rQQxbRJMgTqwRugtjw0cnyQv9cP4/4BxWfTdRBkqsTfLOHWykLzbOc3C4GGzAmdMDxhzU/1Ija5bTjMVrddqww==} - - '@vue/compiler-ssr@3.5.17': - resolution: {integrity: sha512-hkDbA0Q20ZzGgpj5uZjb9rBzQtIHLS78mMilwrlpWk2Ep37DYntUz0PonQ6kr113vfOEdM+zTBuJDaceNIW0tQ==} - - '@vue/reactivity@3.5.17': - resolution: {integrity: sha512-l/rmw2STIscWi7SNJp708FK4Kofs97zc/5aEPQh4bOsReD/8ICuBcEmS7KGwDj5ODQLYWVN2lNibKJL1z5b+Lw==} - - '@vue/runtime-core@3.5.17': - resolution: {integrity: sha512-QQLXa20dHg1R0ri4bjKeGFKEkJA7MMBxrKo2G+gJikmumRS7PTD4BOU9FKrDQWMKowz7frJJGqBffYMgQYS96Q==} - - '@vue/runtime-dom@3.5.17': - resolution: {integrity: sha512-8El0M60TcwZ1QMz4/os2MdlQECgGoVHPuLnQBU3m9h3gdNRW9xRmI8iLS4t/22OQlOE6aJvNNlBiCzPHur4H9g==} - - '@vue/server-renderer@3.5.17': - resolution: {integrity: sha512-BOHhm8HalujY6lmC3DbqF6uXN/K00uWiEeF22LfEsm9Q93XeJ/plHTepGwf6tqFcF7GA5oGSSAAUock3VvzaCA==} - peerDependencies: - vue: 3.5.17 - - '@vue/shared@3.5.17': - resolution: {integrity: sha512-CabR+UN630VnsJO/jHWYBC1YVXyMq94KKp6iF5MQgZJs5I8cmjw6oVMO1oDbtBkENSHSSn/UadWlW/OAgdmKrg==} + '@vitest/utils@4.0.18': + resolution: {integrity: sha512-msMRKLMVLWygpK3u2Hybgi4MNjcYJvwTb0Ru09+fOyCXIgT5raYP041DRRdiJiI3k/2U6SEbAETB3YtBrUkCFA==} acorn-jsx@5.3.2: resolution: {integrity: sha512-rq9s+JNhf0IChjtDXxllJ7g41oZk5SlXtp0LHwyA5cejwn7vKmKp4pPri6YEePv2PU65sAsegbXtIinmDFDXgQ==} @@ -1716,20 +1667,8 @@ packages: engines: {node: '>=0.4.0'} hasBin: true - ajv@6.12.6: - resolution: {integrity: sha512-j3fVLgvTo527anyYyJOGTYJbG+vnnQYvE0m5mmkc1TK+nxAppkCLMIL0aZ4dblVCNoGShhm+kzE4ZUykBoMg4g==} - - ansi-regex@5.0.1: - resolution: {integrity: sha512-quJQXlTSUGL2LH9SUXo8VwsY4soanhgo6LNSm84E1LBcE8s3O0wpdiRzyR9z/ZZJMlMWv37qOOb9pdJlMUEKFQ==} - engines: {node: '>=8'} - - ansi-styles@4.3.0: - resolution: {integrity: sha512-zbB9rCJAT1rbjiVDb2hqKFHNYLxgtk8NURxZ3IZwD3F6NtxbXZQCnnSi1Lkx+IDohdPlFp222wVALIheZJQSEg==} - engines: {node: '>=8'} - - anymatch@3.1.3: - resolution: {integrity: sha512-KMReFUr0B4t+D+OBkjR3KYqvocp2XaSzO55UcB6mgQMd3KbcE+mWTyvVV7D/zsdEbNnV6acZUutkiHQXvTr1Rw==} - engines: {node: '>= 8'} + ajv@6.14.0: + resolution: {integrity: sha512-IWrosm/yrn43eiKqkfkHis7QioDleaXQHdDVPKg0FSwwd/DuvyX79TZnFOnYpB7dcsFAMmtFztZuXPDvSePkFw==} argparse@2.0.1: resolution: {integrity: sha512-8+9WqebbFzpX9OR+Wa6O29asIogeRMzcGtAINdpMHHyAg10f05aSFVBbcEqGf/PXw1EjAZ+q2/bEBg3DvurK3Q==} @@ -1738,27 +1677,27 @@ packages: resolution: {integrity: sha512-Z/ZeOgVl7bcSYZ/u/rh0fOpvEpq//LZmdbkXyc7syVzjPAhfOa9ebsdTSjEBDU4vs5nC98Kfduj1uFo0qyET3g==} engines: {node: '>= 0.4'} + assertion-error@2.0.1: + resolution: {integrity: sha512-Izi8RQcffqCeNVgFigKli1ssklIbpHnCYc6AknXGYoB6grJqyeby7jv12JUQgmTAnIDnbck1uxksT4dzN3PWBA==} + engines: {node: '>=12'} + axobject-query@4.1.0: resolution: {integrity: sha512-qIj0G9wZbMGNLjLmg1PT6v2mE9AH2zlnADJD/2tC6E00hgmhUOfEB6greHPAfLRSufHqROIUTkw6E+M3lH0PTQ==} engines: {node: '>= 0.4'} - balanced-match@4.0.3: - resolution: {integrity: sha512-1pHv8LX9CpKut1Zp4EXey7Z8OfH11ONNH6Dhi2WDUt31VVZFXZzKwXcysBgqSumFCmR+0dqjMK5v5JiFHzi0+g==} - engines: {node: 20 || >=22} + balanced-match@4.0.4: + resolution: {integrity: sha512-BLrgEcRTwX2o6gGxGOCNyMvGSp35YofuYzw9h1IMTRmKqttAZZVU67bdb9Pr2vUHA8+j3i2tJfjO6C6+4myGTA==} + engines: {node: 18 || 20 || >=22} before-after-hook@4.0.0: resolution: {integrity: sha512-q6tR3RPqIB1pMiTRMFcZwuG5T8vwp+vUvEG0vuI6B+Rikh5BfPp2fQ82c925FOs+b0lcFQ8CFrL+KbilfZFhOQ==} - binary-extensions@2.3.0: - resolution: {integrity: sha512-Ceh+7ox5qe7LJuLHoY0feh3pHuUDHAcRUeyL2VYghZwfpkNIy/+8Ocg0a3UuSoYzavmylwuLWQOf3hl0jjMMIw==} - engines: {node: '>=8'} - blake3-wasm@2.1.5: resolution: {integrity: sha512-F1+K8EbfOZE49dtoPtmxUQrpXaBIl3ICvasLh+nJta0xkz+9kF/7uet9fLnwKqhDrmj6g+6K3Tw9yQPUg2ka5g==} - brace-expansion@5.0.2: - resolution: {integrity: sha512-Pdk8c9poy+YhOgVWw1JNN22/HcivgKWwpxKq04M/jTmHyCZn12WPJebZxdjSa5TmBqISrUSgNYU3eRORljfCCw==} - engines: {node: 20 || >=22} + brace-expansion@5.0.4: + resolution: {integrity: sha512-h+DEnpVvxmfVefa4jFbCf5HdH5YMDXRsmKflpf1pILZWRFlTbJpxeU55nJl4Smt5HQaGzg1o6RHFPJaOqnmBDg==} + engines: {node: 18 || 20 || >=22} braces@3.0.3: resolution: {integrity: sha512-yQbXgO/OSZVD2IsiLlro+7Hf6Q18EJrKSEsdoMzKePKXct3gvD8oLcOQdIzGupr5Fj+EDe8gO/lxc1BzfMpxvA==} @@ -1771,16 +1710,16 @@ packages: resolution: {integrity: sha512-b6Ilus+c3RrdDk+JhLKUAQfzzgLEPy6wcXqS7f/xe1EETvsDP6GORG7SFuOs6cID5YkqchW/LXZbX5bc8j7ZcQ==} engines: {node: '>=8'} - chai@6.2.0: - resolution: {integrity: sha512-aUTnJc/JipRzJrNADXVvpVqi6CO0dn3nx4EVPxijri+fj3LUUDyZQOgVeW54Ob3Y1Xh9Iz8f+CgaCl8v0mn9bA==} + chai@6.2.2: + resolution: {integrity: sha512-NUPRluOfOiTKBKvWPtSD4PhFvWCqOi0BGStNWs57X9js7XGTprSmFoz5F0tWhR4WPjNeR9jXqdC7/UpSJTnlRg==} engines: {node: '>=18'} chardet@2.1.1: resolution: {integrity: sha512-PsezH1rqdV9VvyNhxxOW32/d75r01NY7TQCmOqomRo15ZSOKbpTFVsfjghxo6JloQUCGnH4k1LGu0R4yCLlWQQ==} - chokidar@3.6.0: - resolution: {integrity: sha512-7VT13fmjotKpGipCW9JEQAusEPE+Ei8nl6/g4FBAmIm0GOOLMua9NDDo/DWp0ZAxCr3cPq5ZpBqmPAQgDda2Pw==} - engines: {node: '>= 8.10.0'} + chokidar@5.0.0: + resolution: {integrity: sha512-TQMmc3w+5AxjpL8iIiwebF73dRDF4fBIieAqGn9RGCWaEVwQ6Fb2cGe31Yns0RRIzii5goJ1Y7xbMwo1TxMplw==} + engines: {node: '>= 20.19.0'} cli-width@4.1.0: resolution: {integrity: sha512-ouuZd4/dm2Sw5Gmqy6bGyNNNe1qt9RpmxveLSO7KcgsTnU7RXfsw+/bukWGo1abgBiMAic068rclZsO4IWmmxQ==} @@ -1795,13 +1734,6 @@ packages: resolution: {integrity: sha512-eYm0QWBtUrBWZWG0d386OGAw16Z995PiOVo2B7bjWSbHedGl5e0ZWaq65kOGgUSNesEIDkB9ISbTg/JK9dhCZA==} engines: {node: '>=6'} - color-convert@2.0.1: - resolution: {integrity: sha512-RRECPsj7iu/xb5oKYcsFHSppFNnsj/52OVTRKb4zP5onXwVF3zVmmToNcOfGC+CRDpfK/U584fMg38ZHCaElKQ==} - engines: {node: '>=7.0.0'} - - color-name@1.1.4: - resolution: {integrity: sha512-dOy+3AuW3a2wNbZHIuMZpTcgjGuLU/uBL/ubcZF9OXbDo8ff4O8yVp5Bf0efS8uEoYo5q4Fx7dY9OgQGXgAsQA==} - colorette@2.0.20: resolution: {integrity: sha512-IfEDxwoWIjkeXL1eXcDiow4UbKjhLdq6/EuSVR9GMN7KVH3r9gQ83e73hsz1Nd1T3ijd5xv1wcWRYO+D6kCI2w==} @@ -1811,9 +1743,6 @@ packages: confbox@0.1.8: resolution: {integrity: sha512-RMtmw0iFkeR4YV+fUOSucriAQNb9g8zFR52MWCtl+cCZOFRNL6zeB395vPzFhEjjn4fMxXudmELnl/KF/WrK6w==} - confbox@0.2.2: - resolution: {integrity: sha512-1NB+BKqhtNipMsov4xI/NnhCKp9XG9NamYp5PVm9klAT0fsrNPjaFICsCFhNhwZJKNh7zB/3q8qXz0E9oaMNtQ==} - consola@3.4.2: resolution: {integrity: sha512-5IKcdX0nnYavi6G7TtOhwkYzyjfJlatbjMjuLSfE2kYT5pMDOilZ4OvMhi637CcDICTmz3wARPoyhqyX1Y+XvA==} engines: {node: ^14.18.0 || >=16.10.0} @@ -1835,9 +1764,6 @@ packages: resolution: {integrity: sha512-0eW44TGN5SQXU1mWSkKwFstI/22X2bG1nYzZTYMAWjylYURhse752YgbE4Cx46AC+bAvI+/dYTPRk1LqSUnu6w==} engines: {node: ^10 || ^12.20.0 || ^14.13.0 || >=15.0.0} - csstype@3.2.3: - resolution: {integrity: sha512-z1HGKcYy2xA8AGQfwrn0PAy+PB7X/GSj3UVJW9qKyn43xWa+gl5nXmU4qqLMRzWVLFC8KusUX8T/0kCiOYpAIQ==} - debug@4.4.3: resolution: {integrity: sha512-RGwwWnwQvkVfavKVt22FGLw+xYSdzARwm0ru6DhTVA3umU5hZc28V3kO4stgYryrTlLpuvgI9GiijltAjNbcqA==} engines: {node: '>=6.0'} @@ -1870,37 +1796,25 @@ packages: duplexer@0.1.2: resolution: {integrity: sha512-jtD6YG370ZCIi/9GTaJKQxWTZD045+4R4hTk/x1UyoqadyJ9x9CgSi1RlVDQF8U2sxLLSnFkCaMihqljHIWgMg==} - emnapi@1.7.1: - resolution: {integrity: sha512-wlLK2xFq+T+rCBlY6+lPlFVDEyE93b7hSn9dMrfWBIcPf4ArwUvymvvMnN9M5WWuiryYQe9M+UJrkqw4trdyRA==} + emnapi@1.8.1: + resolution: {integrity: sha512-34i2BbgHx1LnEO4JCGQYo6h6s4e4KrdWtdTHfllBNLbXSHPmdIHplxKejfabsRK+ukNciqVdalB+fxMibqHdaQ==} peerDependencies: node-addon-api: '>= 6.1.0' peerDependenciesMeta: node-addon-api: optional: true - emoji-regex@8.0.0: - resolution: {integrity: sha512-MSjYzcWNOA0ewAHpz0MxpYFvwg6yjy1NG3xteoqz644VCo/RPgnr1/GGt+ic3iJTzQ8Eu3TdM14SawnVUmGE6A==} - - entities@4.5.0: - resolution: {integrity: sha512-V0hjH4dGPh9Ao5p0MoRY6BVqtwCjhz6vI5LT8AJ55H+4g9/4vbHx1I54fS0XuclLhDHArPQCiMjDxjaL8fPxhw==} - engines: {node: '>=0.12'} - error-stack-parser-es@1.0.5: resolution: {integrity: sha512-5qucVt2XcuGMcEGgWI7i+yZpmpByQ8J1lHhcL7PwqCwu9FPP3VUXzT4ltHe5i2z9dePwEHcDVOAfSnHsOlCXRA==} es-module-lexer@1.7.0: resolution: {integrity: sha512-jEQoCwk8hyb2AZziIOLhDqpm5+2ww5uIE6lkO/6jcOCusfk6LhMHpXXfBLXTZ7Ydyt0j4VoUQv6uGNYbdW+kBA==} - es-toolkit@1.42.0: - resolution: {integrity: sha512-SLHIyY7VfDJBM8clz4+T2oquwTQxEzu263AyhVK4jREOAwJ+8eebaa4wM3nlvnAqhDrMm2EsA6hWHaQsMPQ1nA==} + es-toolkit@1.45.1: + resolution: {integrity: sha512-/jhoOj/Fx+A+IIyDNOvO3TItGmlMKhtX8ISAHKE90c4b/k1tqaqEZ+uUqfpU8DMnW5cgNJv606zS55jGvza0Xw==} - esbuild@0.25.4: - resolution: {integrity: sha512-8pgjLUcUjcgDg+2Q4NYXnPbo/vncAY4UmyaCm0jZevERqCHZIaWwdJHkf8XQtu4AxSKCdvrUbT0XUr1IdZzI8Q==} - engines: {node: '>=18'} - hasBin: true - - esbuild@0.27.0: - resolution: {integrity: sha512-jd0f4NHbD6cALCyGElNpGAOtWxSq46l9X/sWB0Nzd5er4Kz2YTm+Vl0qKFT9KUJvD8+fiO8AvoHhFvEatfVixA==} + esbuild@0.27.3: + resolution: {integrity: sha512-8VwMnyGCONIs6cWue2IdpHxHnAjzxnw2Zr7MkVxB2vjmQ2ivqGFb4LEG3SMnv0Gb2F/G/2yA8zUaiL1gywDCCg==} engines: {node: '>=18'} hasBin: true @@ -1918,20 +1832,20 @@ packages: resolution: {integrity: sha512-tfuQT8K/Li1ZxhFzyD8wPIKtlzZxqBcPr9q0jFMQ77wWAbKBVEhaMPVQRTMTvCMUDhwBe5vPVqQPwAGk/ASfxQ==} engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0} - eslint-scope@9.1.0: - resolution: {integrity: sha512-CkWE42hOJsNj9FJRaoMX9waUFYhqY4jmyLFdAdzZr6VaCg3ynLYx4WnOdkaIifGfH4gsUcBTn4OZbHXkpLD0FQ==} + eslint-scope@9.1.1: + resolution: {integrity: sha512-GaUN0sWim5qc8KVErfPBWmc31LEsOkrUJbvJZV+xuL3u2phMUK4HIvXlWAakfC8W4nzlK+chPEAkYOYb5ZScIw==} engines: {node: ^20.19.0 || ^22.13.0 || >=24} eslint-visitor-keys@3.4.3: resolution: {integrity: sha512-wpc+LXeiyiisxPlEkUzU6svyS1frIO3Mgxj1fdy7Pm8Ygzguax2N3Fa/D/ag1WqbOprdI+uY6wMUl8/a2G+iag==} engines: {node: ^12.22.0 || ^14.17.0 || >=16.0.0} - eslint-visitor-keys@5.0.0: - resolution: {integrity: sha512-A0XeIi7CXU7nPlfHS9loMYEKxUaONu/hTEzHTGba9Huu94Cq1hPivf+DE5erJozZOky0LfvXAyrV/tcswpLI0Q==} + eslint-visitor-keys@5.0.1: + resolution: {integrity: sha512-tD40eHxA35h0PEIZNeIjkHoDR4YjjJp34biM0mDvplBe//mB+IHCqHDGV7pxF+7MklTvighcCPPZC7ynWyjdTA==} engines: {node: ^20.19.0 || ^22.13.0 || >=24} - eslint@10.0.0: - resolution: {integrity: sha512-O0piBKY36YSJhlFSG8p9VUdPV/SxxS4FYDWVpr/9GJuMaepzwlf4J8I4ov1b+ySQfDTPhc3DtLaxcT1fN0yqCg==} + eslint@10.0.2: + resolution: {integrity: sha512-uYixubwmqJZH+KLVYIVKY1JQt7tysXhtj21WSvjcSmU5SVNzMus1bgLe+pAt816yQ8opKfheVVoPLqvVMGejYw==} engines: {node: ^20.19.0 || ^22.13.0 || >=24} hasBin: true peerDependencies: @@ -1943,8 +1857,8 @@ packages: esm-env@1.2.2: resolution: {integrity: sha512-Epxrv+Nr/CaL4ZcFGPJIYLWFom+YeV1DqMLHJoEd9SYRxNbaFruBwfEX/kkHUJf55j2+TUbmDcmuilbP1TmXHA==} - espree@11.1.0: - resolution: {integrity: sha512-WFWYhO1fV4iYkqOOvq8FbqIhr2pYfoDY0kCotMkDeNtGpiGGkZ1iov2u8ydjtgM8yF8rzK7oaTbw2NAzbAbehw==} + espree@11.1.1: + resolution: {integrity: sha512-AVHPqQoZYc+RUM4/3Ly5udlZY/U4LS8pIG05jEjWM2lQMU/oaZ7qshzAl2YP1tfNmXfftH3ohurfwNAug+MnsQ==} engines: {node: ^20.19.0 || ^22.13.0 || >=24} esquery@1.7.0: @@ -1972,13 +1886,10 @@ packages: resolution: {integrity: sha512-kVscqXk4OCp68SZ0dkgEKVi6/8ij300KBWTJq32P/dYeWTSwK41WyTxalN1eRmA5Z9UU/LX9D7FWSmV9SAYx6g==} engines: {node: '>=0.10.0'} - expect-type@1.2.2: - resolution: {integrity: sha512-JhFGDVJ7tmDJItKhYgJCGLOWjuK9vPxiXoUFLwLDc99NlmklilbiQJwoctZtt13+xMw91MCk/REan6MWHqDjyA==} + expect-type@1.3.0: + resolution: {integrity: sha512-knvyeauYhqjOYvQ66MznSMs83wmHrCycNEN6Ao+2AeYEfxUIkuiVxdEa1qlGEPK+We3n0THiDciYSsCcgW/DoA==} engines: {node: '>=12.0.0'} - exsolve@1.0.7: - resolution: {integrity: sha512-VO5fQUzZtI6C+vx4w/4BWJpg3s/5l+6pRQEHzFRM8WFi4XffSP1Z+4qi7GbjWbvRQEbdIco5mIMq+zX4rPuLrw==} - fast-content-type-parse@3.0.0: resolution: {integrity: sha512-ZvLdcY8P+N8mGQJahJV5G4U88CSvT1rP8ApL6uETe88MBXrBHAkZlSEySdUlyztF7ccb+Znos3TFqaepHxdhBg==} @@ -1995,8 +1906,17 @@ packages: fast-levenshtein@2.0.6: resolution: {integrity: sha512-DCXu6Ifhqcks7TZKY3Hxp3y6qphY5SJZmrWMDrKcERSOXWQdMhU9Ig/PYrzyw/ul9jOIyh0N4M0tbC5hodg8dw==} - fastq@1.19.1: - resolution: {integrity: sha512-GwLTyxkCXjXbxqIhTsMI2Nui8huMPtnxg7krajPJAjnEG/iiOS7i+zCtWGZR9G0NBKbXKh6X9m9UIsYX/N6vvQ==} + fast-string-truncated-width@3.0.3: + resolution: {integrity: sha512-0jjjIEL6+0jag3l2XWWizO64/aZVtpiGE3t0Zgqxv0DPuxiMjvB3M24fCyhZUO4KomJQPj3LTSUnDP3GpdwC0g==} + + fast-string-width@3.0.2: + resolution: {integrity: sha512-gX8LrtNEI5hq8DVUfRQMbr5lpaS4nMIWV+7XEbXk2b8kiQIizgnlr12B4dA3ZEx3308ze0O4Q1R+cHts8kyUJg==} + + fast-wrap-ansi@0.2.0: + resolution: {integrity: sha512-rLV8JHxTyhVmFYhBJuMujcrHqOT2cnO5Zxj37qROj23CP39GXubJRBUFF0z8KFK77Uc0SukZUf7JZhsVEQ6n8w==} + + fastq@1.20.1: + resolution: {integrity: sha512-GGToxJ/w1x32s/D2EKND7kTil4n8OVk/9mycTc4VDza13lOvpUZTGX3mFSCtV9ksdGBVzvsyAVLM6mHFThxXxw==} fdir@6.5.0: resolution: {integrity: sha512-tIbYtZbucOs0BRGqPJkshJUYdL+SDH7dVM8gjy+ERp3WAUjLEFJE+02kanyHtwjWOnwrKYBiwAmM0p4kLJAnXg==} @@ -2023,8 +1943,8 @@ packages: resolution: {integrity: sha512-f7ccFPK3SXFHpx15UIGyRJ/FJQctuKZ0zVuN3frBo4HnK3cay9VEW0R6yPYFHC0AgqhukPzKjq22t5DmAyqGyw==} engines: {node: '>=16'} - flatted@3.3.3: - resolution: {integrity: sha512-GX+ysw4PBCz0PzosHDepZGANEuFCMLrnRTiEy9McGjmkCQYwRq4A/X786G/fjM/+OjsWSU1ZrY5qyARZmO/uwg==} + flatted@3.3.4: + resolution: {integrity: sha512-3+mMldrTAPdta5kjX2G2J7iX4zxtnwpdA8Tr2ZSjkyPSanvbZAcy6flmtnXbEybHrDcU9641lxrMfFuUxVz9vA==} fsevents@2.3.3: resolution: {integrity: sha512-5xoDfX+fL7faATnagmWPpbFtwh/R77WmMMqqHGS65C3vvB0YHrgF+B1YmZ3441tMj5n63k0212XNoJwzlhffQw==} @@ -2042,12 +1962,8 @@ packages: resolution: {integrity: sha512-XxwI8EOhVQgWp6iDL+3b0r86f4d6AX6zSU55HfB4ydCEuXLXc5FcYeOu+nnGftS4TEju/11rt4KJPTMgbfmv4A==} engines: {node: '>=10.13.0'} - globals@15.15.0: - resolution: {integrity: sha512-7ACyT3wmyp3I61S4fG682L0VA2RGD9otkqGJIwNUMF1SWUombIIk+af1unuDYgMm082aHYwD+mzJvv9Iu8dsgg==} - engines: {node: '>=18'} - - globals@17.0.0: - resolution: {integrity: sha512-gv5BeD2EssA793rlFWVPMMCqefTlpusw6/2TbAVMy0FzcG8wKJn4O+NqJ4+XWmmwrayJgw5TzrmWjFgmz1XPqw==} + globals@17.4.0: + resolution: {integrity: sha512-hjrNztw/VajQwOLsMNT1cbJiH2muO3OROCHnbehc8eY5JyD2gqz4AcMHPqgaOR59DjgUjYAYLeH699g/eWi2jw==} engines: {node: '>=18'} gzip-size@6.0.0: @@ -2058,8 +1974,8 @@ packages: resolution: {integrity: sha512-0hJU9SCPvmMzIBdZFqNPXWa6dqh7WdH0cII9y+CyS8rG3nL48Bclra9HmKhVVUHyPWNH5Y7xDwAB7bfgSjkUMQ==} engines: {node: '>= 0.4'} - iconv-lite@0.7.0: - resolution: {integrity: sha512-cf6L2Ds3h57VVmkZe+Pn+5APsT7FpqJtEhhieDCvrE2MK5Qk9MyffgQyuxQTm6BChfeZNtcOLHp9IcWRVcIcBQ==} + iconv-lite@0.7.2: + resolution: {integrity: sha512-im9DjEDQ55s9fL4EYzOAv0yMqmMBSZp6G0VvFyTMPKWxiSBHUj9NW/qqLmXUwXrrM7AvqSlTCfvqRb0cM8yYqw==} engines: {node: '>=0.10.0'} ignore@5.3.2: @@ -2074,10 +1990,6 @@ packages: resolution: {integrity: sha512-JmXMZ6wuvDmLiHEml9ykzqO6lwFbof0GG4IkcGaENdCRDDmMVnny7s5HsIgHCbaq0w2MyPhDqkhTUgS2LU2PHA==} engines: {node: '>=0.8.19'} - is-binary-path@2.1.0: - resolution: {integrity: sha512-ZMERYes6pDydyuGidse7OsHxtbI7WVeUEozgR/g7rd0xUimYNlvZRE/K2MgZTjWy725IfelLeVcEM97mmtRGXw==} - engines: {node: '>=8'} - is-core-module@2.16.1: resolution: {integrity: sha512-UfoeMA6fIJ8wTYFEUjelnaGI67v6+N7qXJEvQuIGa99l4xsCruSYOVSQ0uPANn4dAzm8lkYPaKLrrijLq7x23w==} engines: {node: '>= 0.4'} @@ -2086,10 +1998,6 @@ packages: resolution: {integrity: sha512-SbKbANkN603Vi4jEZv49LeVJMn4yGwsbzZworEoyEiutsN3nJYdbO36zfhGJ6QEDpOZIFkDtnq5JRxmvl3jsoQ==} engines: {node: '>=0.10.0'} - is-fullwidth-code-point@3.0.0: - resolution: {integrity: sha512-zymm5+u+sCsSWyD9qNaejV3DFvhCKclKdizYaJUuHA83RLjb7nSuGnddCHGv0hk+KY7BMAlsWeK4Ueg6EV6XQg==} - engines: {node: '>=8'} - is-glob@4.0.3: resolution: {integrity: sha512-xelSayHH36ZgE7ZWhli7pW34hNbNl8Ojv5KVmkJD4hBdD3th8Tfk9vYasLM+mXWOZhFkgZfxhLSnrwRr4elSSg==} engines: {node: '>=0.10.0'} @@ -2104,8 +2012,8 @@ packages: isexe@2.0.0: resolution: {integrity: sha512-RHxMLp9lnKHGHRng9QFhRCMbYAcVpn69smSGcq3f36xjgVVWThj4qqLbTLlq7Ssj8B+fIQ1EuCEGI2lKsyQeIw==} - jiti@2.4.2: - resolution: {integrity: sha512-rg9zJN+G4n2nfJl5MW3BMygZX56zKPNVEYYqq7adpmMh4Jn2QNEwhvQlFy6jPVdcod7txZtKHWnyZiA3a0zP7A==} + jiti@2.6.1: + resolution: {integrity: sha512-ekilCSN1jwRvIbgeg/57YFh8qQDNbwDb9xT/qu2DAHbFFZUicIl4ygVaAvzveMhMVr3LnpSKTNnwt8PoOfmKhQ==} hasBin: true js-yaml@4.1.1: @@ -2121,6 +2029,9 @@ packages: json-stable-stringify-without-jsonify@1.0.1: resolution: {integrity: sha512-Bdboy+l7tA3OGW6FjyFHWkP5LuByj1Tk33Ljyq0axyzdk9//JSi2u3fP1QSmd1KNwq6VOKYGlAu87CisVir6Pw==} + json-with-bigint@3.5.7: + resolution: {integrity: sha512-7ei3MdAI5+fJPVnKlW77TKNKwQ5ppSzWvhPuSuINT/GYW9ZOC1eRKOuhV9yHG5aEsUPj9BBx5JIekkmoLHxZOw==} + keyv@4.5.4: resolution: {integrity: sha512-oxVHkHR/EJf2CNXnWxRLW6mg7JyCCUcG0DtEGmL2ctUo1PNTin1PUil+r/+4r5MpVgC/fn1kjsx7mjSujKqIpw==} @@ -2128,17 +2039,10 @@ packages: resolution: {integrity: sha512-o+NO+8WrRiQEE4/7nwRJhN1HWpVmJm511pBHUxPLtp0BUISzlBplORYSmTclCnJvQq2tKu/sgl3xVpkc7ZWuQQ==} engines: {node: '>=6'} - kolorist@1.8.0: - resolution: {integrity: sha512-Y+60/zizpJ3HRH8DCss+q95yr6145JXZo46OTpFvDZWLfRCE4qChOyk1b26nMaNpfHHgxagk9dXT5OP0Tfe+dQ==} - levn@0.4.1: resolution: {integrity: sha512-+bT2uH4E5LGE7h/n3evcS/sQlJXCpIp6ym8OWJ5eV6+67Dsql/LaaT7qJBAt2rzfoa/5QBGBhxDix1dMt2kQKQ==} engines: {node: '>= 0.8.0'} - local-pkg@1.1.1: - resolution: {integrity: sha512-WunYko2W1NcdfAFpuLUoucsgULmgDBRkdxHxWQ7mK0cQqwPiy8E1enjuRBrhLtZkB5iScJ1XIPdhVEFK8aOLSg==} - engines: {node: '>=14'} - locate-character@3.0.0: resolution: {integrity: sha512-SW13ws7BjaeJ6p7Q6CO2nchbYEc3X3J6WrmTTDto7yMPqVSZTUyY5Tjbid+Ab8gLnATtygYtiDIJGQRRn2ZOiA==} @@ -2146,6 +2050,9 @@ packages: resolution: {integrity: sha512-iPZK6eYjbxRu3uB4/WZ3EsEIMJFMqAoopl3R+zuq0UjcAm/MO6KCweDgPfP3elTztoKP3KtnVHxTn2NHBSDVUw==} engines: {node: '>=10'} + magic-regexp@0.10.0: + resolution: {integrity: sha512-Uly1Bu4lO1hwHUW0CQeSWuRtzCMNO00CmXtS8N6fyvB3B979GOEEeAkiTUDsmbYLAbvpUS/Kt5c4ibosAzVyVg==} + magic-string@0.30.21: resolution: {integrity: sha512-vd2F4YUyEXKGcLHoq+TEyCjxueSeHnFxyyjNp80yg0XV4vUhnDer/lvvlqM/arB5bXQN5K2/3oinyCRyx8T2CQ==} @@ -2160,21 +2067,17 @@ packages: resolution: {integrity: sha512-PXwfBhYu0hBCPw8Dn0E+WDYb7af3dSLVWKi3HGv84IdF4TyFoC0ysxFd0Goxw7nSv4T/PzEJQxsYsEiFCKo2BA==} engines: {node: '>=8.6'} - miniflare@4.20260128.0: - resolution: {integrity: sha512-AVCn3vDRY+YXu1sP4mRn81ssno6VUqxo29uY2QVfgxXU2TMLvhRIoGwm7RglJ3Gzfuidit5R86CMQ6AvdFTGAw==} + miniflare@4.20260301.1: + resolution: {integrity: sha512-fqkHx0QMKswRH9uqQQQOU/RoaS3Wjckxy3CUX3YGJr0ZIMu7ObvI+NovdYi6RIsSPthNtq+3TPmRNxjeRiasog==} engines: {node: '>=18.0.0'} hasBin: true - minimatch@10.2.2: - resolution: {integrity: sha512-+G4CpNBxa5MprY+04MbgOw1v7So6n5JY166pFi9KfYwT78fxScCeSNQSNzp6dpPSW2rONOps6Ocam1wFhCgoVw==} + minimatch@10.2.4: + resolution: {integrity: sha512-oRjTw/97aTBN0RHbYCdtF1MQfvusSIBQM0IZEgzl6426+8jSC0nF1a/GmnVLpfB9yyr6g6FTqWqiZVbxrtaCIg==} engines: {node: 18 || 20 || >=22} - minimatch@9.0.5: - resolution: {integrity: sha512-G6T0ZX48xgozx7587koeX9Ys2NYy6Gmv//P89sEte9V9whIapMNF4idKxnW2QtCcLiTWlb/wfCabAtAFWhhBow==} - engines: {node: '>=16 || 14 >=14.17'} - - mlly@1.7.4: - resolution: {integrity: sha512-qmdSIPC4bDJXgZTCR7XosJiNKySV7O215tsPtDN9iEO/7q/76b/ijtgRu/+epFXSJhijtTCCGp3DWS549P3xKw==} + mlly@1.8.0: + resolution: {integrity: sha512-l8D9ODSRWLe2KHJSifWGwBqpTZXIXTeo8mlKjY+E2HAakaTeNpqAyBZ8GSqLzHgw4XmHmC8whvpjJNMbFZN7/g==} mrmime@2.0.1: resolution: {integrity: sha512-Y3wQdFg2Va6etvQ5I82yUhGdsKrcYox6p7FfL1LbK2J4V01F9TGlepTIhnK24t7koZibmg82KGglhA1XK5IsLQ==} @@ -2183,9 +2086,9 @@ packages: ms@2.1.3: resolution: {integrity: sha512-6FlzubTLZG3J2a/NVCAleEhjzq5oxgHyaCU9yYXvcLsvoVaHJq/s5xXI6/XXP6tz7R9xAOtHnSO/tXtF3WRTlA==} - mute-stream@2.0.0: - resolution: {integrity: sha512-WWdIxpyjEn+FhQJQQv9aQAYlHoNVdzIzUySNV1gHUPDSdZJ3yZn7pAAbQcV7B56Mvu881q9FZV+0Vx2xC44VWA==} - engines: {node: ^18.17.0 || >=20.5.0} + mute-stream@3.0.0: + resolution: {integrity: sha512-dkEJPVvun4FryqBmZ5KhDo0K9iDXAwn08tMLDinNdRBNPcYEDiWYysLcc6k3mjTMlbP9KyylvRpd4wFtwrT9rw==} + engines: {node: ^20.17.0 || >=22.9.0} nanoid@3.3.11: resolution: {integrity: sha512-N8SpfPUnUp1bK+PMYW8qSWdl9U+wwNWI4QKxOYDy9JAro3WMX7p2OeVRF9v+347pnakNevPmiHhNmZ2HbFA76w==} @@ -2195,20 +2098,28 @@ packages: natural-compare@1.4.0: resolution: {integrity: sha512-OWND8ei3VtNC9h7V60qff3SVobHr996CTwgxubgyQYEpg290h9J0buyECNNJexkFm5sOajh5G116RYA1c8ZMSw==} - node-fetch-native@1.6.6: - resolution: {integrity: sha512-8Mc2HhqPdlIfedsuZoc3yioPuzp6b+L5jRCRY1QzuWZh2EGJVQrGppC6V6cF0bLdbW0+O2YpqCA25aF/1lvipQ==} + node-fetch-native@1.6.7: + resolution: {integrity: sha512-g9yhqoedzIUm0nTnTqAQvueMPVOuIY16bqgAJJC8XOOubYFNwz6IER9qs0Gq2Xd0+CecCKFjtdDTMA4u4xG06Q==} - normalize-path@3.0.0: - resolution: {integrity: sha512-6eZs5Ls3WtCisHWp9S2GUy8dqkpGi4BVSz3GaqiE6ezub0512ESztXUwUB6C6IKbQkY2Pnb/mD4WYojCRwcwLA==} - engines: {node: '>=0.10.0'} + obug@2.1.1: + resolution: {integrity: sha512-uTqF9MuPraAQ+IsnPf366RG4cP9RtUi7MLO1N3KEc+wb0a6yKpeL0lmk2IB1jY5KHPAlTc6T/JRdC/YqxHNwkQ==} - ofetch@1.4.1: - resolution: {integrity: sha512-QZj2DfGplQAr2oj9KzceK9Hwz6Whxazmn85yYeVuS3u9XTMOGMRx0kO95MQ+vLsj/S/NwBDMMLU5hpxvI6Tklw==} + ofetch@1.5.1: + resolution: {integrity: sha512-2W4oUZlVaqAPAil6FUg/difl6YhqhUR7x2eZY4bQCko22UXg3hptq9KLQdqFClV+Wu85UX7hNtdGTngi/1BxcA==} optionator@0.9.4: resolution: {integrity: sha512-6IpQ7mKUxRcZNLIObR0hz7lxsapSSIYNZJwXPGeF0mTVqGKFIXj1DQcMoT22S3ROcLyY/rz0PWaWZ9ayWmad9g==} engines: {node: '>= 0.8.0'} + oxc-parser@0.115.0: + resolution: {integrity: sha512-2w7Xn3CbS/zwzSY82S5WLemrRu3CT57uF7Lx8llrE/2bul6iMTcJE4Rbls7GDNbLn3ttATI68PfOz2Pt3KZ2cQ==} + engines: {node: ^20.19.0 || >=22.12.0} + + oxc-walker@0.7.0: + resolution: {integrity: sha512-54B4KUhrzbzc4sKvKwVYm7E2PgeROpGba0/2nlNZMqfDyca+yOor5IMb4WLGBatGDT0nkzYdYuzylg7n3YfB7A==} + peerDependencies: + oxc-parser: '>=0.98.0' + p-limit@3.1.0: resolution: {integrity: sha512-TYOanM3wGwNGsZN2cVTYPArw454xnXj5qmWF1bEoAc4+cU/ol7GVh7odevjp1FNHduHc3KZMcFduxU5Xc6uJRQ==} engines: {node: '>=10'} @@ -2217,8 +2128,8 @@ packages: resolution: {integrity: sha512-LaNjtRWUBY++zB5nE/NwcaoMylSPk+S+ZHNB1TzdbMJMny6dynpAGt7X/tl/QYq3TIeE6nxHppbo2LGymrG5Pw==} engines: {node: '>=10'} - package-manager-detector@1.3.0: - resolution: {integrity: sha512-ZsEbbZORsyHuO00lY1kV3/t72yp6Ysay6Pd17ZAlNGuGwmWDLCJxFpRs0IzfXfj1o4icJOkUEioexFHzyPurSQ==} + package-manager-detector@1.6.0: + resolution: {integrity: sha512-61A5ThoTiDG/C8s8UMZwSorAGwMJ0ERVGj2OjoW5pAalsNOg15+iQiPzrLJ4jhZ1HJzmC2PIHT2oEiH3R5fzNA==} path-exists@4.0.0: resolution: {integrity: sha512-ak9Qy5Q7jYb2Wwcey5Fpvg2KoAc/ZIhLSLOSBmRmygPsGwkVVt0fZa0qrtMz+m6tJTAHfZQ8FnmB4MG4LWy7/w==} @@ -2237,8 +2148,8 @@ packages: pathe@2.0.3: resolution: {integrity: sha512-WUjGcAqP1gQacoQe+OBJsFA7Ld4DyXuUIjZ5cc75cLHvJ7dtNsTugphxIADwspS+AraAUePCKrSVtPLFj/F88w==} - perfect-debounce@1.0.0: - resolution: {integrity: sha512-xCy9V055GLEqoFaHoC1SoLIaLmWctgCUaBaWxDZ7/Zx4CTyX7cJQLJOok/orfjZAh9kEYpjJa4d0KcJmCbctZA==} + perfect-debounce@2.1.0: + resolution: {integrity: sha512-LjgdTytVFXeUgtHZr9WYViYSM/g8MkcTPYDlPa3cDqMirHjKiSZPYd6DoL7pK8AJQr+uWkQvCjHNdiMqsrJs+g==} picocolors@1.1.1: resolution: {integrity: sha512-xceH2snhtb5M9liqDsmEw56le376mTZkEX/jEb/RxNFyegNul7eNslCXP9FDj/Lcu0X8KEyMceP2ntpaHrDEVA==} @@ -2254,19 +2165,16 @@ packages: pkg-types@1.3.1: resolution: {integrity: sha512-/Jm5M4RvtBFVkKWRu2BLUTNP8/M2a+UwuAX+ae4770q1qVGtfjG+WTCupoZixokjmHiry8uI+dlY8KXYV5HVVQ==} - pkg-types@2.2.0: - resolution: {integrity: sha512-2SM/GZGAEkPp3KWORxQZns4M+WSeXbC2HEvmOIJe3Cmiv6ieAJvdVhDldtHqM5J1Y7MrR1XhkBT/rMlhh9FdqQ==} - - postcss@8.5.6: - resolution: {integrity: sha512-3Ybi1tAuwAP9s0r1UQ2J4n5Y0G05bJkpUIO0/bI9MhwmD70S5aTWbXGBwxHrelT+XM1k6dM0pk+SwNkpTRN7Pg==} + postcss@8.5.8: + resolution: {integrity: sha512-OW/rX8O/jXnm82Ey1k44pObPtdblfiuWnrd8X7GJ7emImCOstunGbXUpp7HdBrFQX6rJzn3sPT397Wp5aCwCHg==} engines: {node: ^10 || ^12 || >=14} prelude-ls@1.2.1: resolution: {integrity: sha512-vkcDPrRZo1QZLbn5RLGPpg/WmIQ65qoWWhcGKf/b5eplkkarX0m9z8ppCat4mlOqUsWpyNuYgO3VRyrYHSzX5g==} engines: {node: '>= 0.8.0'} - prettier@3.6.2: - resolution: {integrity: sha512-I7AIg5boAr5R0FFtJ6rCfD+LFsWHp81dolrFD8S79U9tb8Az2nGrJncnMSnys+bpQJfRUzqs9hnA81OAA3hCuQ==} + prettier@3.8.1: + resolution: {integrity: sha512-UOnG6LftzbdaHZcKoPFtOcCKztrQ57WkHDeRD9t/PTQtmT0NHSeWWepj6pS0z/N7+08BHFDQVUrfmfMRcZwbMg==} engines: {node: '>=14'} hasBin: true @@ -2274,25 +2182,22 @@ packages: resolution: {integrity: sha512-vYt7UD1U9Wg6138shLtLOvdAu+8DsC/ilFtEVHcH+wydcSpNE20AfSOduf6MkRFahL5FY7X1oU7nKVZFtfq8Fg==} engines: {node: '>=6'} - quansync@0.2.10: - resolution: {integrity: sha512-t41VRkMYbkHyCYmOvx/6URnN80H7k4X0lLdBMGsz+maAwrJQYB1djpV6vHrQIBE0WBSGqhtEHrK9U3DWWH8v7A==} + quansync@1.0.0: + resolution: {integrity: sha512-5xZacEEufv3HSTPQuchrvV6soaiACMFnq1H8wkVioctoH3TRha9Sz66lOxRwPK/qZj7HPiSveih9yAyh98gvqA==} queue-microtask@1.2.3: resolution: {integrity: sha512-NuaNSa6flKT5JaSYQzJok04JzTL1CA6aGhv5rfLW3PgqA+M2ChpZQnAC8h8i4ZFkBS8X5RqkDBHA7r4hej3K9A==} - randombytes@2.1.0: - resolution: {integrity: sha512-vYl3iOX+4CKUWuxGi9Ukhie6fsqXqS9FE2Zaic4tNFD2N2QQaXOMFbuKK4QmDHC0JO6B1Zp41J0LpT0oR68amQ==} - - readdirp@3.6.0: - resolution: {integrity: sha512-hOS089on8RduqdbhvQ5Z37A0ESjsqz6qnRcffsMU3495FuTdqSm+7bhJ29JvIOsBDEEnan5DPu9t3To9VRlMzA==} - engines: {node: '>=8.10.0'} + readdirp@5.0.0: + resolution: {integrity: sha512-9u/XQ1pvrQtYyMpZe7DXKv2p5CNvyVwzUB6uhLAnQwHMSgKMBR62lc7AHljaeteeHXn11XTAaLLUVZYVZyuRBQ==} + engines: {node: '>= 20.19.0'} regexp-tree@0.1.27: resolution: {integrity: sha512-iETxpjK6YoRWJG5o6hXLwvjYAoW+FEZn9os0PD/b6AP6xQwsa/Y7lCVgIixBbUPMfhu+i2LtdeAqVTgGlQarfA==} hasBin: true - resolve@1.22.10: - resolution: {integrity: sha512-NPRy+/ncIMeDlTAsuqwKIiferiawhefFJtkNSW0qZJEqMEb+qBt/77B/jGeeek+F0uOeN05CDa6HXbbIgtVX4w==} + resolve@1.22.11: + resolution: {integrity: sha512-RfqAvLnMl313r7c9oclB1HhUEAezcpLjz95wFH4LVuhk9JF/r22qmVP9AMmOU4vMX7Q8pN8jwNg/CSpdFnMjTQ==} engines: {node: '>= 0.4'} hasBin: true @@ -2308,22 +2213,20 @@ packages: run-parallel@1.2.0: resolution: {integrity: sha512-5l4VyZR86LZ/lDxZTR6jqL8AFE2S0IFLMP26AbjsLVADxHdhB/c0GUsH+y39UfCi3dzz8OlQuPmnaJOMoDHQBA==} - safe-buffer@5.2.1: - resolution: {integrity: sha512-rp3So07KcdmmKbGvgaNxQSJr7bGVSVk5S9Eq1F+ppbRo70+YeaDxkw5Dd8NPN+GD6bjnYm2VuPuCXmpuYvmCXQ==} - safe-regex@2.1.1: resolution: {integrity: sha512-rx+x8AMzKb5Q5lQ95Zoi6ZbJqwCLkqi3XuJXp5P3rT8OEc6sZCJG5AE5dU3lsgRr/F4Bs31jSlVN+j5KrsGu9A==} safer-buffer@2.1.2: resolution: {integrity: sha512-YZo3K82SD7Riyi0E1EQPojLz7kpepnSQI9IyPbHHg1XXXevb5dJI7tpyN2ADxGcQbHG7vcyRHk0cbwqcQriUtg==} - semver@7.7.3: - resolution: {integrity: sha512-SdsKMrI9TdgjdweUSR9MweHA4EJ8YxHn8DFaDisvhVlUOe4BF1tLD7GAj0lIqWVl+dPb/rExr0Btby5loQm20Q==} + semver@7.7.4: + resolution: {integrity: sha512-vFKC2IEtQnVhpT78h1Yp8wzwrf8CM+MzKMHGJZfBtzhZNycRFnXsHk6E5TxIkkMsgNS7mdX3AGB7x2QM2di4lA==} engines: {node: '>=10'} hasBin: true - serialize-javascript@6.0.2: - resolution: {integrity: sha512-Saa1xPByTTq2gdeFZYLLo+RFE35NHZkAbqZeWNd3BpzppeVisAqpDjcp8dyf6uIvEqJRd46jemmyA4iFIeVk8g==} + serialize-javascript@7.0.4: + resolution: {integrity: sha512-DuGdB+Po43Q5Jxwpzt1lhyFSYKryqoNjQSA9M92tyw0lyHIOur+XCalOUe0KTJpyqzT8+fQ5A0Jf7vCx/NKmIg==} + engines: {node: '>=20.0.0'} sharp@0.34.5: resolution: {integrity: sha512-Ou9I5Ft9WNcCbXrU9cMgPBcCK8LiwLqcbywW3t4oDV37n1pzpuNLsYiAV8eODnjbtQlSDwZ2cUEeQz4E54Hltg==} @@ -2344,12 +2247,13 @@ packages: resolution: {integrity: sha512-bzyZ1e88w9O1iNJbKnOlvYTrWPDl46O1bG0D3XInv+9tkPrxrN8jUUTiFlDkkmKWgn1M6CfIA13SuGqOa9Korw==} engines: {node: '>=14'} - sirv@3.0.1: - resolution: {integrity: sha512-FoqMu0NCGBLCcAkS1qA+XJIQTR6/JHfQXl+uGteNCQ76T91DMUjPa9xfmeqMY3z80nLSg9yQmNjK0Px6RWsH/A==} + sirv@3.0.2: + resolution: {integrity: sha512-2wcC/oGxHis/BoHkkPwldgiPSYcpZK3JU28WoMVv55yHJgcZ8rlXvuG9iZggz+sU1d4bRgIGASwyWqjxu3FM0g==} engines: {node: '>=18'} - smob@1.5.0: - resolution: {integrity: sha512-g6T+p7QO8npa+/hNx9ohv1E5pVCmWrVCUzUXJyLdMmftX6ER0oiWY/w9knEonLpnOp6b6FenKnMfR8gqwWdwig==} + smob@1.6.1: + resolution: {integrity: sha512-KAkBqZl3c2GvNgNhcoyJae1aKldDW0LO279wF9bk1PnluRTETKBq0WyzRXxEhoQLk56yHaOY4JCBEKDuJIET5g==} + engines: {node: '>=20.0.0'} source-map-js@1.2.1: resolution: {integrity: sha512-UXWMKhLOwVKb728IUtQPXxfYU+usdybtUrK/8uGE8CQMvrhOpwvzDBwj0QhSL7MQc7vIsISBG8VQ8+IDQxpfQA==} @@ -2362,19 +2266,11 @@ packages: resolution: {integrity: sha512-UjgapumWlbMhkBgzT7Ykc5YXUT46F0iKu8SGXq0bcwP5dz/h0Plj6enJqjz1Zbq2l5WaqYnrVbwWOWMyF3F47g==} engines: {node: '>=0.10.0'} - stackback@0.0.2: - resolution: {integrity: sha512-1XMJE5fQo1jGH6Y/7ebnwPOBEkIEnT4QF32d5R1+VXdXveM0IBMJt8zfaxX1P3QhVwrYe+576+jkANtSS2mBbw==} - - std-env@3.9.0: - resolution: {integrity: sha512-UGvjygr6F6tpH7o2qyqR6QYpwraIjKSdtzyBdyytFOHmPZY917kwdwLG0RbOjWOnKmnm3PeHjaoLLMie7kPLQw==} - - string-width@4.2.3: - resolution: {integrity: sha512-wKyQRQpjJ0sIp62ErSZdGsjMJWsap5oRNihHhu6G7JVO/9jIB6UyevL+tXuOqrng8j/cxKTWyWUwvSTriiZz/g==} - engines: {node: '>=8'} + stackback@0.0.2: + resolution: {integrity: sha512-1XMJE5fQo1jGH6Y/7ebnwPOBEkIEnT4QF32d5R1+VXdXveM0IBMJt8zfaxX1P3QhVwrYe+576+jkANtSS2mBbw==} - strip-ansi@6.0.1: - resolution: {integrity: sha512-Y38VPSHcqkFrCpFnQ9vuSXmquuv5oXOKpGeT6aGrr3o3Gc9AlVa6JBfUSOCnbxGGZF+/0ooI7KrPuUSztUdU5A==} - engines: {node: '>=8'} + std-env@3.10.0: + resolution: {integrity: sha512-5GS12FdOZNliM5mAOxFRg7Ir0pWz8MdpYm6AY6VPkGpbA7ZzmbzNcBJQ0GPvvyWgcY7QAhCgf9Uy89I03faLkg==} supports-color@10.2.2: resolution: {integrity: sha512-SS+jx45GF1QjgEXQx4NJZV9ImqmO2NPz5FNsIHrsDjh2YsHnawpan7SNQ1o8NuhrbHZy9AZhIoCUiCeaW/C80g==} @@ -2384,23 +2280,21 @@ packages: resolution: {integrity: sha512-ot0WnXS9fgdkgIcePe6RHNk1WA8+muPa6cSjeR3V8K27q9BB1rTE3R1p7Hv0z1ZyAc8s6Vvv8DIyWf681MAt0w==} engines: {node: '>= 0.4'} - svelte@5.53.5: - resolution: {integrity: sha512-YkqERnF05g8KLdDZwZrF8/i1eSbj6Eoat8Jjr2IfruZz9StLuBqo8sfCSzjosNKd+ZrQ8DkKZDjpO5y3ht1Pow==} + svelte@5.53.7: + resolution: {integrity: sha512-uxck1KI7JWtlfP3H6HOWi/94soAl23jsGJkBzN2BAWcQng0+lTrRNhxActFqORgnO9BHVd1hKJhG+ljRuIUWfQ==} engines: {node: '>=18'} - terser@5.43.1: - resolution: {integrity: sha512-+6erLbBm0+LROX2sPXlUYx/ux5PyE9K/a92Wrt6oA+WDAoFTdpHE5tCYCI5PNzq2y8df4rA+QgHLJuR4jNymsg==} + terser@5.46.0: + resolution: {integrity: sha512-jTwoImyr/QbOWFFso3YoU3ik0jBBDJ6JTOQiy/J2YxVJdZCc+5u7skhNwiOR3FQIygFqVUPHl7qbbxtjW2K3Qg==} engines: {node: '>=10'} hasBin: true tinybench@2.9.0: resolution: {integrity: sha512-0+DUvqWMValLmha6lr4kD8iAMK1HzV0/aKnCtWb9v9641TnP/MFb7Pc2bxoxQjTXAErryXVgUOfv2YqNllqGeg==} - tinyexec@0.3.2: - resolution: {integrity: sha512-KQQR9yN7R5+OSwaK0XQoj22pwHoTlgYqmUscPYoknOoWCWfj/5/ABTMRi69FrKU5ffPVh5QcFikpWJI/P1ocHA==} - - tinyexec@1.0.1: - resolution: {integrity: sha512-5uC6DDlmeqiOwCPmK9jMSdOuZTh8bU39Ys6yidB+UTt5hfZUPGAypSgFRiEp+jbi9qH40BLDvy85jIU88wKSqw==} + tinyexec@1.0.2: + resolution: {integrity: sha512-W/KYk+NFhkmsYpuHq5JykngiOCnxeVL8v8dFnqxSD8qEEdRfXk1SDM6JzNqcERbcGYj9tMrDQBYV9cjgnunFIg==} + engines: {node: '>=18'} tinyglobby@0.2.15: resolution: {integrity: sha512-j2Zq4NyQYG5XMST4cbs02Ak8iJUdxRM0XI5QyxXuZOzKOINmWurp3smXu3y5wDcJrptwpSjgXHzIQxR0omXljQ==} @@ -2434,23 +2328,29 @@ packages: resolution: {integrity: sha512-XleUoc9uwGXqjWwXaUTZAmzMcFZ5858QA2vvx1Ur5xIcixXIP+8LnFDgRplU30us6teqdlskFfu+ae4K79Ooew==} engines: {node: '>= 0.8.0'} - typescript-eslint@8.56.0: - resolution: {integrity: sha512-c7toRLrotJ9oixgdW7liukZpsnq5CZ7PuKztubGYlNppuTqhIoWfhgHo/7EU0v06gS2l/x0i2NEFK1qMIf0rIg==} + type-level-regexp@0.1.17: + resolution: {integrity: sha512-wTk4DH3cxwk196uGLK/E9pE45aLfeKJacKmcEgEOA/q5dnPGNxXt0cfYdFxb57L+sEpf1oJH4Dnx/pnRcku9jg==} + + typescript-eslint@8.56.1: + resolution: {integrity: sha512-U4lM6pjmBX7J5wk4szltF7I1cGBHXZopnAXCMXb3+fZ3B/0Z3hq3wS/CCUB2NZBNAExK92mCU2tEohWuwVMsDQ==} engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0} peerDependencies: eslint: ^8.57.0 || ^9.0.0 || ^10.0.0 typescript: '>=4.8.4 <6.0.0' - typescript@5.8.3: - resolution: {integrity: sha512-p1diW6TqL9L07nNxvRMM7hMMw4c5XOo/1ibL4aAIGmSAt9slTE1Xgw5KWuof2uTOvCg9BY7ZRi+GaF+7sfgPeQ==} + typescript@5.9.3: + resolution: {integrity: sha512-jl1vZzPDinLr9eUt3J/t7V6FgNEw9QjvBPdysz9KfQDD41fQrC2Y4vKQdiaUpFT4bXlb1RHhLpp8wtm6M5TgSw==} engines: {node: '>=14.17'} hasBin: true - ufo@1.6.1: - resolution: {integrity: sha512-9a4/uxlTWJ4+a5i0ooc1rU7C7YOw3wT+UGqdeNNHWnOF9qcMBgLRS+4IYUqbczewFx4mLEig6gawh7X6mFlEkA==} + ufo@1.6.3: + resolution: {integrity: sha512-yDJTmhydvl5lJzBmy/hyOAA0d+aqCBuwl818haVdYCRrWV84o7YyeVm4QlVHStqNrrJSTb6jKuFAVqAFsr+K3Q==} - unconfig@7.3.2: - resolution: {integrity: sha512-nqG5NNL2wFVGZ0NA/aCFw0oJ2pxSf1lwg4Z5ill8wd7K4KX/rQbHlwbh+bjctXL5Ly1xtzHenHGOK0b+lG6JVg==} + unconfig-core@7.5.0: + resolution: {integrity: sha512-Su3FauozOGP44ZmKdHy2oE6LPjk51M/TRRjHv2HNCWiDvfvCoxC2lno6jevMA91MYAdCdwP05QnWdWpSbncX/w==} + + unconfig@7.5.0: + resolution: {integrity: sha512-oi8Qy2JV4D3UQ0PsopR28CzdQ3S/5A1zwsUwp/rosSbfhJ5z7b90bIyTwi/F7hCLD4SGcZVjDzd4XoUQcEanvA==} undici-types@7.16.0: resolution: {integrity: sha512-Zz+aZWSj8LE6zoxD+xrjh4VfkIG8Ya6LvYkZqtUQGJPZjYl53ypCaUwWqo7eI0x66KBGeRo+mlBEkMSeSZ38Nw==} @@ -2465,27 +2365,34 @@ packages: universal-user-agent@7.0.3: resolution: {integrity: sha512-TmnEAEAsBJVZM/AADELsK76llnwcf9vMKuPz8JflO1frO8Lchitr0fNaN9d+Ap0BjKtqWqd/J17qeDnXh8CL2A==} - unocss@66.3.3: - resolution: {integrity: sha512-HSB+K4/EbouwYmxpPU52cg0exua7PUr2IAJZBV3iai6tPdMcJ0c8jXaw7G+2L+ffruVFTcS0e2kE4OrR8BKDLg==} + unocss@66.6.5: + resolution: {integrity: sha512-WlpPlV7yAzEPREcwaKeacP+1jOm6ImhyKJRkK18tIW2b2BRZZDKln7X8P+NzJtAr0kziNY/ttUKZNZRnSmzP1A==} engines: {node: '>=14'} peerDependencies: - '@unocss/webpack': 66.3.3 - vite: ^2.9.0 || ^3.0.0-0 || ^4.0.0 || ^5.0.0-0 || ^6.0.0-0 || ^7.0.0-0 + '@unocss/astro': 66.6.5 + '@unocss/postcss': 66.6.5 + '@unocss/webpack': 66.6.5 peerDependenciesMeta: - '@unocss/webpack': + '@unocss/astro': optional: true - vite: + '@unocss/postcss': + optional: true + '@unocss/webpack': optional: true - unplugin-utils@0.2.4: - resolution: {integrity: sha512-8U/MtpkPkkk3Atewj1+RcKIjb5WBimZ/WSLhhR3w6SsIj8XJuKTacSP8g+2JhfSGw0Cb125Y+2zA/IzJZDVbhA==} + unplugin-utils@0.3.1: + resolution: {integrity: sha512-5lWVjgi6vuHhJ526bI4nlCOmkCIF3nnfXkCMDeMJrtdvxTs6ZFCM8oNufGTsDbKv/tJ/xj8RpvXjRuPBZJuJog==} + engines: {node: '>=20.19.0'} + + unplugin@2.3.11: + resolution: {integrity: sha512-5uKD0nqiYVzlmCRs01Fhs2BdkEgBS3SAVP6ndrBsuK42iC2+JHyxM05Rm9G8+5mkmRtzMZGY8Ct5+mliZxU/Ww==} engines: {node: '>=18.12.0'} uri-js@4.4.1: resolution: {integrity: sha512-7rKUyy33Q1yc98pQ1DAmLtwX109F7TIfWlW1Ydo8Wl1ii1SeHieeh0HHfPeL2fMXK6z0s8ecKs9frCuLJvndBg==} - vite@7.1.11: - resolution: {integrity: sha512-uzcxnSDVjAopEUjljkWh8EIrg6tlzrjFUfMcR1EVsRDGwf/ccef0qQPRyOrROwhrTDaApueq+ja+KLPlzR/zdg==} + vite@7.3.1: + resolution: {integrity: sha512-w+N7Hifpc3gRjZ63vYBXA56dvvRlNWRczTdmCBBa+CotUzAPf5b7YMdMR/8CQoeYE5LX3W4wj6RYTgonm1b9DA==} engines: {node: ^20.19.0 || >=22.12.0} hasBin: true peerDependencies: @@ -2524,32 +2431,32 @@ packages: yaml: optional: true - vitefu@1.1.1: - resolution: {integrity: sha512-B/Fegf3i8zh0yFbpzZ21amWzHmuNlLlmJT6n7bu5e+pCHUKQIfXSYokrqOBGEMMe9UG2sostKQF9mml/vYaWJQ==} + vitefu@1.1.2: + resolution: {integrity: sha512-zpKATdUbzbsycPFBN71nS2uzBUQiVnFoOrr2rvqv34S1lcAgMKKkjWleLGeiJlZ8lwCXvtWaRn7R3ZC16SYRuw==} peerDependencies: - vite: ^3.0.0 || ^4.0.0 || ^5.0.0 || ^6.0.0 || ^7.0.0-beta.0 + vite: ^3.0.0 || ^4.0.0 || ^5.0.0 || ^6.0.0 || ^7.0.0 || ^8.0.0-beta.0 peerDependenciesMeta: vite: optional: true - vitest@4.0.6: - resolution: {integrity: sha512-gR7INfiVRwnEOkCk47faros/9McCZMp5LM+OMNWGLaDBSvJxIzwjgNFufkuePBNaesGRnLmNfW+ddbUJRZn0nQ==} + vitest@4.0.18: + resolution: {integrity: sha512-hOQuK7h0FGKgBAas7v0mSAsnvrIgAvWmRFjmzpJ7SwFHH3g1k2u37JtYwOwmEKhK6ZO3v9ggDBBm0La1LCK4uQ==} engines: {node: ^20.0.0 || ^22.0.0 || >=24.0.0} hasBin: true peerDependencies: '@edge-runtime/vm': '*' - '@types/debug': ^4.1.12 + '@opentelemetry/api': ^1.9.0 '@types/node': ^20.0.0 || ^22.0.0 || >=24.0.0 - '@vitest/browser-playwright': 4.0.6 - '@vitest/browser-preview': 4.0.6 - '@vitest/browser-webdriverio': 4.0.6 - '@vitest/ui': 4.0.6 + '@vitest/browser-playwright': 4.0.18 + '@vitest/browser-preview': 4.0.18 + '@vitest/browser-webdriverio': 4.0.18 + '@vitest/ui': 4.0.18 happy-dom: '*' jsdom: '*' peerDependenciesMeta: '@edge-runtime/vm': optional: true - '@types/debug': + '@opentelemetry/api': optional: true '@types/node': optional: true @@ -2566,18 +2473,8 @@ packages: jsdom: optional: true - vue-flow-layout@0.1.1: - resolution: {integrity: sha512-JdgRRUVrN0Y2GosA0M68DEbKlXMqJ7FQgsK8CjQD2vxvNSqAU6PZEpi4cfcTVtfM2GVOMjHo7GKKLbXxOBqDqA==} - peerDependencies: - vue: ^3.4.37 - - vue@3.5.17: - resolution: {integrity: sha512-LbHV3xPN9BeljML+Xctq4lbz2lVHCR6DtbpTf5XIO6gugpXUN49j2QQPcMj086r9+AkJ0FfUT8xjulKKBkkr9g==} - peerDependencies: - typescript: '*' - peerDependenciesMeta: - typescript: - optional: true + webpack-virtual-modules@0.6.2: + resolution: {integrity: sha512-66/V2i5hQanC51vBQKPH4aI8NMAcBW59FVBs+rC7eGHupMyfn34q7rZIE+ETlJ+XTevqfUhVVBgSUNSW2flEUQ==} which@2.0.2: resolution: {integrity: sha512-BLI3Tl1TW3Pvl70l3yq3Y64i+awpwXqsGBYWkkqMtnbXgrMD+yj7rhW0kuEDxzJaYXGjEW5ogapKNMEKNMjibA==} @@ -2593,25 +2490,21 @@ packages: resolution: {integrity: sha512-BN22B5eaMMI9UMtjrGd5g5eCYPpCPDUy0FJXbYsaT5zYxjFOckS53SQDE3pWkVoWpHXVb3BrYcEN4Twa55B5cA==} engines: {node: '>=0.10.0'} - workerd@1.20260128.0: - resolution: {integrity: sha512-EhLJGptSGFi8AEErLiamO3PoGpbRqL+v4Ve36H2B38VxmDgFOSmDhfepBnA14sCQzGf1AEaoZX2DCwZsmO74yQ==} + workerd@1.20260301.1: + resolution: {integrity: sha512-oterQ1IFd3h7PjCfT4znSFOkJCvNQ6YMOyZ40YsnO3nrSpgB4TbJVYWFOnyJAw71/RQuupfVqZZWKvsy8GO3fw==} engines: {node: '>=16'} hasBin: true - wrangler@4.61.1: - resolution: {integrity: sha512-hfYQ16VLPkNi8xE1/V3052S2stM5e+vq3Idpt83sXoDC3R7R1CLgMkK6M6+Qp3G+9GVDNyHCkvohMPdfFTaD4Q==} + wrangler@4.70.0: + resolution: {integrity: sha512-PNDZ9o4e+B5x+1bUbz62Hmwz6G9lw+I9pnYe/AguLddJFjfIyt2cmFOUOb3eOZSoXsrhcEPUg2YidYIbVwUkfw==} engines: {node: '>=20.0.0'} hasBin: true peerDependencies: - '@cloudflare/workers-types': ^4.20260128.0 + '@cloudflare/workers-types': ^4.20260226.1 peerDependenciesMeta: '@cloudflare/workers-types': optional: true - wrap-ansi@6.2.0: - resolution: {integrity: sha512-r6lPcBGxZXlIcymEu7InxDMhdW0KDxpLgoFLcguasxCaJ/SOIZwINatK9KY/tf+ZrlywOKU0UDj3ATXUBfxJXA==} - engines: {node: '>=8'} - ws@8.18.0: resolution: {integrity: sha512-8VbfWfHLbbwu3+N6OKsOMpBdT4kXPDDB9cJk2bJ6mh9ucxdlnNvH1e+roYkKmN9Nxw2yjz7VzeO9oOz2zJ04Pw==} engines: {node: '>=10.0.0'} @@ -2628,10 +2521,6 @@ packages: resolution: {integrity: sha512-rVksvsnNCdJ/ohGc6xgPwyN8eheCxsiLM8mxuE/t/mOVqJewPuO1miLpTHQiRgTKCLexL4MeAFVagts7HmNZ2Q==} engines: {node: '>=10'} - yoctocolors-cjs@2.1.3: - resolution: {integrity: sha512-U/PBtDf35ff0D8X8D0jfdzHYEPFxAI7jJlxZXwCSez5M3190m+QobIfh+sWDWSHMCWWJN2AWamkegn6vr6YBTw==} - engines: {node: '>=18'} - youch-core@0.3.3: resolution: {integrity: sha512-ho7XuGjLaJ2hWHoK8yFnsUGy2Y5uDpqSTq1FkHLK4/oqKtyUU1AFbOOxY4IpC9f0fTLjwYbslUz0Po5BpD1wrA==} @@ -2643,59 +2532,39 @@ packages: snapshots: - '@ampproject/remapping@2.3.0': - dependencies: - '@jridgewell/gen-mapping': 0.3.13 - '@jridgewell/trace-mapping': 0.3.31 - '@antfu/install-pkg@1.1.0': dependencies: - package-manager-detector: 1.3.0 - tinyexec: 1.0.1 - - '@antfu/utils@8.1.1': {} - - '@babel/helper-string-parser@7.27.1': {} - - '@babel/helper-validator-identifier@7.28.5': {} - - '@babel/parser@7.29.0': - dependencies: - '@babel/types': 7.29.0 - - '@babel/types@7.29.0': - dependencies: - '@babel/helper-string-parser': 7.27.1 - '@babel/helper-validator-identifier': 7.28.5 + package-manager-detector: 1.6.0 + tinyexec: 1.0.2 '@cloudflare/kv-asset-handler@0.4.2': {} - '@cloudflare/unenv-preset@2.12.0(unenv@2.0.0-rc.24)(workerd@1.20260128.0)': + '@cloudflare/unenv-preset@2.14.0(unenv@2.0.0-rc.24)(workerd@1.20260301.1)': dependencies: unenv: 2.0.0-rc.24 optionalDependencies: - workerd: 1.20260128.0 + workerd: 1.20260301.1 - '@cloudflare/workerd-darwin-64@1.20260128.0': + '@cloudflare/workerd-darwin-64@1.20260301.1': optional: true - '@cloudflare/workerd-darwin-arm64@1.20260128.0': + '@cloudflare/workerd-darwin-arm64@1.20260301.1': optional: true - '@cloudflare/workerd-linux-64@1.20260128.0': + '@cloudflare/workerd-linux-64@1.20260301.1': optional: true - '@cloudflare/workerd-linux-arm64@1.20260128.0': + '@cloudflare/workerd-linux-arm64@1.20260301.1': optional: true - '@cloudflare/workerd-windows-64@1.20260128.0': + '@cloudflare/workerd-windows-64@1.20260301.1': optional: true '@cspotcode/source-map-support@0.8.1': dependencies: '@jridgewell/trace-mapping': 0.3.9 - '@emnapi/core@1.7.1': + '@emnapi/core@1.8.1': dependencies: '@emnapi/wasi-threads': 1.1.0 tslib: 2.8.1 @@ -2713,171 +2582,96 @@ snapshots: '@epic-web/invariant@1.0.0': {} - '@esbuild/aix-ppc64@0.25.4': - optional: true - - '@esbuild/aix-ppc64@0.27.0': - optional: true - - '@esbuild/android-arm64@0.25.4': - optional: true - - '@esbuild/android-arm64@0.27.0': - optional: true - - '@esbuild/android-arm@0.25.4': - optional: true - - '@esbuild/android-arm@0.27.0': - optional: true - - '@esbuild/android-x64@0.25.4': - optional: true - - '@esbuild/android-x64@0.27.0': - optional: true - - '@esbuild/darwin-arm64@0.25.4': - optional: true - - '@esbuild/darwin-arm64@0.27.0': - optional: true - - '@esbuild/darwin-x64@0.25.4': - optional: true - - '@esbuild/darwin-x64@0.27.0': - optional: true - - '@esbuild/freebsd-arm64@0.25.4': - optional: true - - '@esbuild/freebsd-arm64@0.27.0': - optional: true - - '@esbuild/freebsd-x64@0.25.4': - optional: true - - '@esbuild/freebsd-x64@0.27.0': - optional: true - - '@esbuild/linux-arm64@0.25.4': - optional: true - - '@esbuild/linux-arm64@0.27.0': - optional: true - - '@esbuild/linux-arm@0.25.4': - optional: true - - '@esbuild/linux-arm@0.27.0': - optional: true - - '@esbuild/linux-ia32@0.25.4': - optional: true - - '@esbuild/linux-ia32@0.27.0': - optional: true - - '@esbuild/linux-loong64@0.25.4': - optional: true - - '@esbuild/linux-loong64@0.27.0': - optional: true - - '@esbuild/linux-mips64el@0.25.4': - optional: true - - '@esbuild/linux-mips64el@0.27.0': + '@esbuild/aix-ppc64@0.27.3': optional: true - '@esbuild/linux-ppc64@0.25.4': + '@esbuild/android-arm64@0.27.3': optional: true - '@esbuild/linux-ppc64@0.27.0': + '@esbuild/android-arm@0.27.3': optional: true - '@esbuild/linux-riscv64@0.25.4': + '@esbuild/android-x64@0.27.3': optional: true - '@esbuild/linux-riscv64@0.27.0': + '@esbuild/darwin-arm64@0.27.3': optional: true - '@esbuild/linux-s390x@0.25.4': + '@esbuild/darwin-x64@0.27.3': optional: true - '@esbuild/linux-s390x@0.27.0': + '@esbuild/freebsd-arm64@0.27.3': optional: true - '@esbuild/linux-x64@0.25.4': + '@esbuild/freebsd-x64@0.27.3': optional: true - '@esbuild/linux-x64@0.27.0': + '@esbuild/linux-arm64@0.27.3': optional: true - '@esbuild/netbsd-arm64@0.25.4': + '@esbuild/linux-arm@0.27.3': optional: true - '@esbuild/netbsd-arm64@0.27.0': + '@esbuild/linux-ia32@0.27.3': optional: true - '@esbuild/netbsd-x64@0.25.4': + '@esbuild/linux-loong64@0.27.3': optional: true - '@esbuild/netbsd-x64@0.27.0': + '@esbuild/linux-mips64el@0.27.3': optional: true - '@esbuild/openbsd-arm64@0.25.4': + '@esbuild/linux-ppc64@0.27.3': optional: true - '@esbuild/openbsd-arm64@0.27.0': + '@esbuild/linux-riscv64@0.27.3': optional: true - '@esbuild/openbsd-x64@0.25.4': + '@esbuild/linux-s390x@0.27.3': optional: true - '@esbuild/openbsd-x64@0.27.0': + '@esbuild/linux-x64@0.27.3': optional: true - '@esbuild/openharmony-arm64@0.27.0': + '@esbuild/netbsd-arm64@0.27.3': optional: true - '@esbuild/sunos-x64@0.25.4': + '@esbuild/netbsd-x64@0.27.3': optional: true - '@esbuild/sunos-x64@0.27.0': + '@esbuild/openbsd-arm64@0.27.3': optional: true - '@esbuild/win32-arm64@0.25.4': + '@esbuild/openbsd-x64@0.27.3': optional: true - '@esbuild/win32-arm64@0.27.0': + '@esbuild/openharmony-arm64@0.27.3': optional: true - '@esbuild/win32-ia32@0.25.4': + '@esbuild/sunos-x64@0.27.3': optional: true - '@esbuild/win32-ia32@0.27.0': + '@esbuild/win32-arm64@0.27.3': optional: true - '@esbuild/win32-x64@0.25.4': + '@esbuild/win32-ia32@0.27.3': optional: true - '@esbuild/win32-x64@0.27.0': + '@esbuild/win32-x64@0.27.3': optional: true - '@eslint-community/eslint-utils@4.9.1(eslint@10.0.0(jiti@2.4.2))': + '@eslint-community/eslint-utils@4.9.1(eslint@10.0.2(jiti@2.6.1))': dependencies: - eslint: 10.0.0(jiti@2.4.2) + eslint: 10.0.2(jiti@2.6.1) eslint-visitor-keys: 3.4.3 '@eslint-community/regexpp@4.12.2': {} - '@eslint/config-array@0.23.1': + '@eslint/config-array@0.23.2': dependencies: - '@eslint/object-schema': 3.0.1 + '@eslint/object-schema': 3.0.2 debug: 4.4.3 - minimatch: 10.2.2 + minimatch: 10.2.4 transitivePeerDependencies: - supports-color @@ -2889,11 +2683,11 @@ snapshots: dependencies: '@types/json-schema': 7.0.15 - '@eslint/js@10.0.1(eslint@10.0.0(jiti@2.4.2))': + '@eslint/js@10.0.1(eslint@10.0.2(jiti@2.6.1))': optionalDependencies: - eslint: 10.0.0(jiti@2.4.2) + eslint: 10.0.2(jiti@2.6.1) - '@eslint/object-schema@3.0.1': {} + '@eslint/object-schema@3.0.2': {} '@eslint/plugin-kit@0.6.0': dependencies: @@ -2902,18 +2696,16 @@ snapshots: '@humanfs/core@0.19.1': {} - '@humanfs/node@0.16.6': + '@humanfs/node@0.16.7': dependencies: '@humanfs/core': 0.19.1 - '@humanwhocodes/retry': 0.3.1 + '@humanwhocodes/retry': 0.4.3 '@humanwhocodes/module-importer@1.0.1': {} - '@humanwhocodes/retry@0.3.1': {} - '@humanwhocodes/retry@0.4.3': {} - '@iconify-json/codicon@1.2.24': + '@iconify-json/codicon@1.2.47': dependencies: '@iconify/types': 2.0.0 @@ -2923,20 +2715,13 @@ snapshots: '@iconify/types@2.0.0': {} - '@iconify/utils@2.3.0': + '@iconify/utils@3.1.0': dependencies: '@antfu/install-pkg': 1.1.0 - '@antfu/utils': 8.1.1 '@iconify/types': 2.0.0 - debug: 4.4.3 - globals: 15.15.0 - kolorist: 1.8.0 - local-pkg: 1.1.1 - mlly: 1.7.4 - transitivePeerDependencies: - - supports-color + mlly: 1.8.0 - '@img/colour@1.0.0': {} + '@img/colour@1.1.0': {} '@img/sharp-darwin-arm64@0.34.5': optionalDependencies: @@ -3032,130 +2817,124 @@ snapshots: '@img/sharp-win32-x64@0.34.5': optional: true - '@inquirer/ansi@1.0.2': {} + '@inquirer/ansi@2.0.3': {} - '@inquirer/checkbox@4.3.2(@types/node@24.10.0)': + '@inquirer/checkbox@5.1.0(@types/node@24.11.0)': dependencies: - '@inquirer/ansi': 1.0.2 - '@inquirer/core': 10.3.2(@types/node@24.10.0) - '@inquirer/figures': 1.0.15 - '@inquirer/type': 3.0.10(@types/node@24.10.0) - yoctocolors-cjs: 2.1.3 + '@inquirer/ansi': 2.0.3 + '@inquirer/core': 11.1.5(@types/node@24.11.0) + '@inquirer/figures': 2.0.3 + '@inquirer/type': 4.0.3(@types/node@24.11.0) optionalDependencies: - '@types/node': 24.10.0 + '@types/node': 24.11.0 - '@inquirer/confirm@5.1.21(@types/node@24.10.0)': + '@inquirer/confirm@6.0.8(@types/node@24.11.0)': dependencies: - '@inquirer/core': 10.3.2(@types/node@24.10.0) - '@inquirer/type': 3.0.10(@types/node@24.10.0) + '@inquirer/core': 11.1.5(@types/node@24.11.0) + '@inquirer/type': 4.0.3(@types/node@24.11.0) optionalDependencies: - '@types/node': 24.10.0 + '@types/node': 24.11.0 - '@inquirer/core@10.3.2(@types/node@24.10.0)': + '@inquirer/core@11.1.5(@types/node@24.11.0)': dependencies: - '@inquirer/ansi': 1.0.2 - '@inquirer/figures': 1.0.15 - '@inquirer/type': 3.0.10(@types/node@24.10.0) + '@inquirer/ansi': 2.0.3 + '@inquirer/figures': 2.0.3 + '@inquirer/type': 4.0.3(@types/node@24.11.0) cli-width: 4.1.0 - mute-stream: 2.0.0 + fast-wrap-ansi: 0.2.0 + mute-stream: 3.0.0 signal-exit: 4.1.0 - wrap-ansi: 6.2.0 - yoctocolors-cjs: 2.1.3 optionalDependencies: - '@types/node': 24.10.0 + '@types/node': 24.11.0 - '@inquirer/editor@4.2.23(@types/node@24.10.0)': + '@inquirer/editor@5.0.8(@types/node@24.11.0)': dependencies: - '@inquirer/core': 10.3.2(@types/node@24.10.0) - '@inquirer/external-editor': 1.0.3(@types/node@24.10.0) - '@inquirer/type': 3.0.10(@types/node@24.10.0) + '@inquirer/core': 11.1.5(@types/node@24.11.0) + '@inquirer/external-editor': 2.0.3(@types/node@24.11.0) + '@inquirer/type': 4.0.3(@types/node@24.11.0) optionalDependencies: - '@types/node': 24.10.0 + '@types/node': 24.11.0 - '@inquirer/expand@4.0.23(@types/node@24.10.0)': + '@inquirer/expand@5.0.8(@types/node@24.11.0)': dependencies: - '@inquirer/core': 10.3.2(@types/node@24.10.0) - '@inquirer/type': 3.0.10(@types/node@24.10.0) - yoctocolors-cjs: 2.1.3 + '@inquirer/core': 11.1.5(@types/node@24.11.0) + '@inquirer/type': 4.0.3(@types/node@24.11.0) optionalDependencies: - '@types/node': 24.10.0 + '@types/node': 24.11.0 - '@inquirer/external-editor@1.0.3(@types/node@24.10.0)': + '@inquirer/external-editor@2.0.3(@types/node@24.11.0)': dependencies: chardet: 2.1.1 - iconv-lite: 0.7.0 + iconv-lite: 0.7.2 optionalDependencies: - '@types/node': 24.10.0 + '@types/node': 24.11.0 - '@inquirer/figures@1.0.15': {} + '@inquirer/figures@2.0.3': {} - '@inquirer/input@4.3.1(@types/node@24.10.0)': + '@inquirer/input@5.0.8(@types/node@24.11.0)': dependencies: - '@inquirer/core': 10.3.2(@types/node@24.10.0) - '@inquirer/type': 3.0.10(@types/node@24.10.0) + '@inquirer/core': 11.1.5(@types/node@24.11.0) + '@inquirer/type': 4.0.3(@types/node@24.11.0) optionalDependencies: - '@types/node': 24.10.0 + '@types/node': 24.11.0 - '@inquirer/number@3.0.23(@types/node@24.10.0)': + '@inquirer/number@4.0.8(@types/node@24.11.0)': dependencies: - '@inquirer/core': 10.3.2(@types/node@24.10.0) - '@inquirer/type': 3.0.10(@types/node@24.10.0) + '@inquirer/core': 11.1.5(@types/node@24.11.0) + '@inquirer/type': 4.0.3(@types/node@24.11.0) optionalDependencies: - '@types/node': 24.10.0 + '@types/node': 24.11.0 - '@inquirer/password@4.0.23(@types/node@24.10.0)': + '@inquirer/password@5.0.8(@types/node@24.11.0)': dependencies: - '@inquirer/ansi': 1.0.2 - '@inquirer/core': 10.3.2(@types/node@24.10.0) - '@inquirer/type': 3.0.10(@types/node@24.10.0) + '@inquirer/ansi': 2.0.3 + '@inquirer/core': 11.1.5(@types/node@24.11.0) + '@inquirer/type': 4.0.3(@types/node@24.11.0) optionalDependencies: - '@types/node': 24.10.0 - - '@inquirer/prompts@7.10.1(@types/node@24.10.0)': - dependencies: - '@inquirer/checkbox': 4.3.2(@types/node@24.10.0) - '@inquirer/confirm': 5.1.21(@types/node@24.10.0) - '@inquirer/editor': 4.2.23(@types/node@24.10.0) - '@inquirer/expand': 4.0.23(@types/node@24.10.0) - '@inquirer/input': 4.3.1(@types/node@24.10.0) - '@inquirer/number': 3.0.23(@types/node@24.10.0) - '@inquirer/password': 4.0.23(@types/node@24.10.0) - '@inquirer/rawlist': 4.1.11(@types/node@24.10.0) - '@inquirer/search': 3.2.2(@types/node@24.10.0) - '@inquirer/select': 4.4.2(@types/node@24.10.0) + '@types/node': 24.11.0 + + '@inquirer/prompts@8.3.0(@types/node@24.11.0)': + dependencies: + '@inquirer/checkbox': 5.1.0(@types/node@24.11.0) + '@inquirer/confirm': 6.0.8(@types/node@24.11.0) + '@inquirer/editor': 5.0.8(@types/node@24.11.0) + '@inquirer/expand': 5.0.8(@types/node@24.11.0) + '@inquirer/input': 5.0.8(@types/node@24.11.0) + '@inquirer/number': 4.0.8(@types/node@24.11.0) + '@inquirer/password': 5.0.8(@types/node@24.11.0) + '@inquirer/rawlist': 5.2.4(@types/node@24.11.0) + '@inquirer/search': 4.1.4(@types/node@24.11.0) + '@inquirer/select': 5.1.0(@types/node@24.11.0) optionalDependencies: - '@types/node': 24.10.0 + '@types/node': 24.11.0 - '@inquirer/rawlist@4.1.11(@types/node@24.10.0)': + '@inquirer/rawlist@5.2.4(@types/node@24.11.0)': dependencies: - '@inquirer/core': 10.3.2(@types/node@24.10.0) - '@inquirer/type': 3.0.10(@types/node@24.10.0) - yoctocolors-cjs: 2.1.3 + '@inquirer/core': 11.1.5(@types/node@24.11.0) + '@inquirer/type': 4.0.3(@types/node@24.11.0) optionalDependencies: - '@types/node': 24.10.0 + '@types/node': 24.11.0 - '@inquirer/search@3.2.2(@types/node@24.10.0)': + '@inquirer/search@4.1.4(@types/node@24.11.0)': dependencies: - '@inquirer/core': 10.3.2(@types/node@24.10.0) - '@inquirer/figures': 1.0.15 - '@inquirer/type': 3.0.10(@types/node@24.10.0) - yoctocolors-cjs: 2.1.3 + '@inquirer/core': 11.1.5(@types/node@24.11.0) + '@inquirer/figures': 2.0.3 + '@inquirer/type': 4.0.3(@types/node@24.11.0) optionalDependencies: - '@types/node': 24.10.0 + '@types/node': 24.11.0 - '@inquirer/select@4.4.2(@types/node@24.10.0)': + '@inquirer/select@5.1.0(@types/node@24.11.0)': dependencies: - '@inquirer/ansi': 1.0.2 - '@inquirer/core': 10.3.2(@types/node@24.10.0) - '@inquirer/figures': 1.0.15 - '@inquirer/type': 3.0.10(@types/node@24.10.0) - yoctocolors-cjs: 2.1.3 + '@inquirer/ansi': 2.0.3 + '@inquirer/core': 11.1.5(@types/node@24.11.0) + '@inquirer/figures': 2.0.3 + '@inquirer/type': 4.0.3(@types/node@24.11.0) optionalDependencies: - '@types/node': 24.10.0 + '@types/node': 24.11.0 - '@inquirer/type@3.0.10(@types/node@24.10.0)': + '@inquirer/type@4.0.3(@types/node@24.11.0)': optionalDependencies: - '@types/node': 24.10.0 + '@types/node': 24.11.0 '@jridgewell/gen-mapping@0.3.13': dependencies: @@ -3169,7 +2948,7 @@ snapshots: '@jridgewell/resolve-uri@3.1.2': {} - '@jridgewell/source-map@0.3.6': + '@jridgewell/source-map@0.3.11': dependencies: '@jridgewell/gen-mapping': 0.3.13 '@jridgewell/trace-mapping': 0.3.31 @@ -3186,19 +2965,19 @@ snapshots: '@jridgewell/resolve-uri': 3.1.2 '@jridgewell/sourcemap-codec': 1.5.5 - '@napi-rs/cli@3.4.1(@emnapi/runtime@1.8.1)(@types/node@24.10.0)': + '@napi-rs/cli@3.5.1(@emnapi/runtime@1.8.1)(@types/node@24.11.0)': dependencies: - '@inquirer/prompts': 7.10.1(@types/node@24.10.0) + '@inquirer/prompts': 8.3.0(@types/node@24.11.0) '@napi-rs/cross-toolchain': 1.0.3 '@napi-rs/wasm-tools': 1.0.1 - '@octokit/rest': 22.0.0 + '@octokit/rest': 22.0.1 clipanion: 4.0.0-rc.4(typanion@3.14.0) colorette: 2.0.20 - debug: 4.4.3 - emnapi: 1.7.1 - es-toolkit: 1.42.0 + emnapi: 1.8.1 + es-toolkit: 1.45.1 js-yaml: 4.1.1 - semver: 7.7.3 + obug: 2.1.1 + semver: 7.7.4 typanion: 3.14.0 optionalDependencies: '@emnapi/runtime': 1.8.1 @@ -3266,7 +3045,7 @@ snapshots: '@napi-rs/lzma-wasm32-wasi@1.4.5': dependencies: - '@napi-rs/wasm-runtime': 1.0.7 + '@napi-rs/wasm-runtime': 1.1.1 optional: true '@napi-rs/lzma-win32-arm64-msvc@1.4.5': @@ -3336,7 +3115,7 @@ snapshots: '@napi-rs/tar-wasm32-wasi@1.1.0': dependencies: - '@napi-rs/wasm-runtime': 1.0.7 + '@napi-rs/wasm-runtime': 1.1.1 optional: true '@napi-rs/tar-win32-arm64-msvc@1.1.0': @@ -3367,9 +3146,9 @@ snapshots: '@napi-rs/tar-win32-ia32-msvc': 1.1.0 '@napi-rs/tar-win32-x64-msvc': 1.1.0 - '@napi-rs/wasm-runtime@1.0.7': + '@napi-rs/wasm-runtime@1.1.1': dependencies: - '@emnapi/core': 1.7.1 + '@emnapi/core': 1.8.1 '@emnapi/runtime': 1.8.1 '@tybys/wasm-util': 0.10.1 optional: true @@ -3403,7 +3182,7 @@ snapshots: '@napi-rs/wasm-tools-wasm32-wasi@1.0.1': dependencies: - '@napi-rs/wasm-runtime': 1.0.7 + '@napi-rs/wasm-runtime': 1.1.1 optional: true '@napi-rs/wasm-tools-win32-arm64-msvc@1.0.1': @@ -3441,69 +3220,134 @@ snapshots: '@nodelib/fs.walk@1.2.8': dependencies: '@nodelib/fs.scandir': 2.1.5 - fastq: 1.19.1 + fastq: 1.20.1 '@octokit/auth-token@6.0.0': {} - '@octokit/core@7.0.3': + '@octokit/core@7.0.6': dependencies: '@octokit/auth-token': 6.0.0 - '@octokit/graphql': 9.0.1 - '@octokit/request': 10.0.3 - '@octokit/request-error': 7.0.0 - '@octokit/types': 14.1.0 + '@octokit/graphql': 9.0.3 + '@octokit/request': 10.0.8 + '@octokit/request-error': 7.1.0 + '@octokit/types': 16.0.0 before-after-hook: 4.0.0 universal-user-agent: 7.0.3 - '@octokit/endpoint@11.0.0': + '@octokit/endpoint@11.0.3': dependencies: - '@octokit/types': 14.1.0 + '@octokit/types': 16.0.0 universal-user-agent: 7.0.3 - '@octokit/graphql@9.0.1': + '@octokit/graphql@9.0.3': dependencies: - '@octokit/request': 10.0.3 - '@octokit/types': 14.1.0 + '@octokit/request': 10.0.8 + '@octokit/types': 16.0.0 universal-user-agent: 7.0.3 - '@octokit/openapi-types@25.1.0': {} + '@octokit/openapi-types@27.0.0': {} - '@octokit/plugin-paginate-rest@13.1.1(@octokit/core@7.0.3)': + '@octokit/plugin-paginate-rest@14.0.0(@octokit/core@7.0.6)': dependencies: - '@octokit/core': 7.0.3 - '@octokit/types': 14.1.0 + '@octokit/core': 7.0.6 + '@octokit/types': 16.0.0 - '@octokit/plugin-request-log@6.0.0(@octokit/core@7.0.3)': + '@octokit/plugin-request-log@6.0.0(@octokit/core@7.0.6)': dependencies: - '@octokit/core': 7.0.3 + '@octokit/core': 7.0.6 - '@octokit/plugin-rest-endpoint-methods@16.0.0(@octokit/core@7.0.3)': + '@octokit/plugin-rest-endpoint-methods@17.0.0(@octokit/core@7.0.6)': dependencies: - '@octokit/core': 7.0.3 - '@octokit/types': 14.1.0 + '@octokit/core': 7.0.6 + '@octokit/types': 16.0.0 - '@octokit/request-error@7.0.0': + '@octokit/request-error@7.1.0': dependencies: - '@octokit/types': 14.1.0 + '@octokit/types': 16.0.0 - '@octokit/request@10.0.3': + '@octokit/request@10.0.8': dependencies: - '@octokit/endpoint': 11.0.0 - '@octokit/request-error': 7.0.0 - '@octokit/types': 14.1.0 + '@octokit/endpoint': 11.0.3 + '@octokit/request-error': 7.1.0 + '@octokit/types': 16.0.0 fast-content-type-parse: 3.0.0 + json-with-bigint: 3.5.7 universal-user-agent: 7.0.3 - '@octokit/rest@22.0.0': + '@octokit/rest@22.0.1': + dependencies: + '@octokit/core': 7.0.6 + '@octokit/plugin-paginate-rest': 14.0.0(@octokit/core@7.0.6) + '@octokit/plugin-request-log': 6.0.0(@octokit/core@7.0.6) + '@octokit/plugin-rest-endpoint-methods': 17.0.0(@octokit/core@7.0.6) + + '@octokit/types@16.0.0': dependencies: - '@octokit/core': 7.0.3 - '@octokit/plugin-paginate-rest': 13.1.1(@octokit/core@7.0.3) - '@octokit/plugin-request-log': 6.0.0(@octokit/core@7.0.3) - '@octokit/plugin-rest-endpoint-methods': 16.0.0(@octokit/core@7.0.3) + '@octokit/openapi-types': 27.0.0 + + '@oxc-parser/binding-android-arm-eabi@0.115.0': + optional: true + + '@oxc-parser/binding-android-arm64@0.115.0': + optional: true + + '@oxc-parser/binding-darwin-arm64@0.115.0': + optional: true + + '@oxc-parser/binding-darwin-x64@0.115.0': + optional: true + + '@oxc-parser/binding-freebsd-x64@0.115.0': + optional: true + + '@oxc-parser/binding-linux-arm-gnueabihf@0.115.0': + optional: true + + '@oxc-parser/binding-linux-arm-musleabihf@0.115.0': + optional: true + + '@oxc-parser/binding-linux-arm64-gnu@0.115.0': + optional: true + + '@oxc-parser/binding-linux-arm64-musl@0.115.0': + optional: true + + '@oxc-parser/binding-linux-ppc64-gnu@0.115.0': + optional: true + + '@oxc-parser/binding-linux-riscv64-gnu@0.115.0': + optional: true + + '@oxc-parser/binding-linux-riscv64-musl@0.115.0': + optional: true + + '@oxc-parser/binding-linux-s390x-gnu@0.115.0': + optional: true + + '@oxc-parser/binding-linux-x64-gnu@0.115.0': + optional: true + + '@oxc-parser/binding-linux-x64-musl@0.115.0': + optional: true + + '@oxc-parser/binding-openharmony-arm64@0.115.0': + optional: true - '@octokit/types@14.1.0': + '@oxc-parser/binding-wasm32-wasi@0.115.0': dependencies: - '@octokit/openapi-types': 25.1.0 + '@napi-rs/wasm-runtime': 1.1.1 + optional: true + + '@oxc-parser/binding-win32-arm64-msvc@0.115.0': + optional: true + + '@oxc-parser/binding-win32-ia32-msvc@0.115.0': + optional: true + + '@oxc-parser/binding-win32-x64-msvc@0.115.0': + optional: true + + '@oxc-project/types@0.115.0': {} '@polka/url@1.0.0-next.29': {} @@ -3519,28 +3363,28 @@ snapshots: '@poppinss/exception@1.2.3': {} - '@quansync/fs@0.1.3': + '@quansync/fs@1.0.0': dependencies: - quansync: 0.2.10 + quansync: 1.0.0 '@rollup/plugin-terser@0.4.4(rollup@4.59.0)': dependencies: - serialize-javascript: 6.0.2 - smob: 1.5.0 - terser: 5.43.1 + serialize-javascript: 7.0.4 + smob: 1.6.1 + terser: 5.46.0 optionalDependencies: rollup: 4.59.0 - '@rollup/plugin-typescript@12.3.0(rollup@4.59.0)(tslib@2.8.1)(typescript@5.8.3)': + '@rollup/plugin-typescript@12.3.0(rollup@4.59.0)(tslib@2.8.1)(typescript@5.9.3)': dependencies: - '@rollup/pluginutils': 5.2.0(rollup@4.59.0) - resolve: 1.22.10 - typescript: 5.8.3 + '@rollup/pluginutils': 5.3.0(rollup@4.59.0) + resolve: 1.22.11 + typescript: 5.9.3 optionalDependencies: rollup: 4.59.0 tslib: 2.8.1 - '@rollup/pluginutils@5.2.0(rollup@4.59.0)': + '@rollup/pluginutils@5.3.0(rollup@4.59.0)': dependencies: '@types/estree': 1.0.8 estree-walker: 2.0.2 @@ -3627,42 +3471,38 @@ snapshots: '@speed-highlight/core@1.2.14': {} - '@standard-schema/spec@1.0.0': {} + '@standard-schema/spec@1.1.0': {} '@sveltejs/acorn-typescript@1.0.9(acorn@8.16.0)': dependencies: acorn: 8.16.0 - '@sveltejs/vite-plugin-svelte-inspector@5.0.0(@sveltejs/vite-plugin-svelte@6.0.0(svelte@5.53.5)(vite@7.1.11(@types/node@24.10.0)(jiti@2.4.2)(terser@5.43.1)))(svelte@5.53.5)(vite@7.1.11(@types/node@24.10.0)(jiti@2.4.2)(terser@5.43.1))': + '@sveltejs/vite-plugin-svelte-inspector@5.0.2(@sveltejs/vite-plugin-svelte@6.2.4(svelte@5.53.7)(vite@7.3.1(@types/node@24.11.0)(jiti@2.6.1)(terser@5.46.0)))(svelte@5.53.7)(vite@7.3.1(@types/node@24.11.0)(jiti@2.6.1)(terser@5.46.0))': dependencies: - '@sveltejs/vite-plugin-svelte': 6.0.0(svelte@5.53.5)(vite@7.1.11(@types/node@24.10.0)(jiti@2.4.2)(terser@5.43.1)) - debug: 4.4.3 - svelte: 5.53.5 - vite: 7.1.11(@types/node@24.10.0)(jiti@2.4.2)(terser@5.43.1) - transitivePeerDependencies: - - supports-color + '@sveltejs/vite-plugin-svelte': 6.2.4(svelte@5.53.7)(vite@7.3.1(@types/node@24.11.0)(jiti@2.6.1)(terser@5.46.0)) + obug: 2.1.1 + svelte: 5.53.7 + vite: 7.3.1(@types/node@24.11.0)(jiti@2.6.1)(terser@5.46.0) - '@sveltejs/vite-plugin-svelte@6.0.0(svelte@5.53.5)(vite@7.1.11(@types/node@24.10.0)(jiti@2.4.2)(terser@5.43.1))': + '@sveltejs/vite-plugin-svelte@6.2.4(svelte@5.53.7)(vite@7.3.1(@types/node@24.11.0)(jiti@2.6.1)(terser@5.46.0))': dependencies: - '@sveltejs/vite-plugin-svelte-inspector': 5.0.0(@sveltejs/vite-plugin-svelte@6.0.0(svelte@5.53.5)(vite@7.1.11(@types/node@24.10.0)(jiti@2.4.2)(terser@5.43.1)))(svelte@5.53.5)(vite@7.1.11(@types/node@24.10.0)(jiti@2.4.2)(terser@5.43.1)) - debug: 4.4.3 + '@sveltejs/vite-plugin-svelte-inspector': 5.0.2(@sveltejs/vite-plugin-svelte@6.2.4(svelte@5.53.7)(vite@7.3.1(@types/node@24.11.0)(jiti@2.6.1)(terser@5.46.0)))(svelte@5.53.7)(vite@7.3.1(@types/node@24.11.0)(jiti@2.6.1)(terser@5.46.0)) deepmerge: 4.3.1 - kleur: 4.1.5 magic-string: 0.30.21 - svelte: 5.53.5 - vite: 7.1.11(@types/node@24.10.0)(jiti@2.4.2)(terser@5.43.1) - vitefu: 1.1.1(vite@7.1.11(@types/node@24.10.0)(jiti@2.4.2)(terser@5.43.1)) - transitivePeerDependencies: - - supports-color + obug: 2.1.1 + svelte: 5.53.7 + vite: 7.3.1(@types/node@24.11.0)(jiti@2.6.1)(terser@5.46.0) + vitefu: 1.1.2(vite@7.3.1(@types/node@24.11.0)(jiti@2.6.1)(terser@5.46.0)) '@tybys/wasm-util@0.10.1': dependencies: tslib: 2.8.1 optional: true - '@types/chai@5.2.2': + '@types/chai@5.2.3': dependencies: '@types/deep-eql': 4.0.2 + assertion-error: 2.0.1 '@types/deep-eql@4.0.2': {} @@ -3677,391 +3517,305 @@ snapshots: '@types/json-schema@7.0.15': {} - '@types/node@24.10.0': + '@types/node@24.11.0': dependencies: undici-types: 7.16.0 '@types/trusted-types@2.0.7': {} - '@typescript-eslint/eslint-plugin@8.56.0(@typescript-eslint/parser@8.56.0(eslint@10.0.0(jiti@2.4.2))(typescript@5.8.3))(eslint@10.0.0(jiti@2.4.2))(typescript@5.8.3)': + '@typescript-eslint/eslint-plugin@8.56.1(@typescript-eslint/parser@8.56.1(eslint@10.0.2(jiti@2.6.1))(typescript@5.9.3))(eslint@10.0.2(jiti@2.6.1))(typescript@5.9.3)': dependencies: '@eslint-community/regexpp': 4.12.2 - '@typescript-eslint/parser': 8.56.0(eslint@10.0.0(jiti@2.4.2))(typescript@5.8.3) - '@typescript-eslint/scope-manager': 8.56.0 - '@typescript-eslint/type-utils': 8.56.0(eslint@10.0.0(jiti@2.4.2))(typescript@5.8.3) - '@typescript-eslint/utils': 8.56.0(eslint@10.0.0(jiti@2.4.2))(typescript@5.8.3) - '@typescript-eslint/visitor-keys': 8.56.0 - eslint: 10.0.0(jiti@2.4.2) + '@typescript-eslint/parser': 8.56.1(eslint@10.0.2(jiti@2.6.1))(typescript@5.9.3) + '@typescript-eslint/scope-manager': 8.56.1 + '@typescript-eslint/type-utils': 8.56.1(eslint@10.0.2(jiti@2.6.1))(typescript@5.9.3) + '@typescript-eslint/utils': 8.56.1(eslint@10.0.2(jiti@2.6.1))(typescript@5.9.3) + '@typescript-eslint/visitor-keys': 8.56.1 + eslint: 10.0.2(jiti@2.6.1) ignore: 7.0.5 natural-compare: 1.4.0 - ts-api-utils: 2.4.0(typescript@5.8.3) - typescript: 5.8.3 + ts-api-utils: 2.4.0(typescript@5.9.3) + typescript: 5.9.3 transitivePeerDependencies: - supports-color - '@typescript-eslint/parser@8.56.0(eslint@10.0.0(jiti@2.4.2))(typescript@5.8.3)': + '@typescript-eslint/parser@8.56.1(eslint@10.0.2(jiti@2.6.1))(typescript@5.9.3)': dependencies: - '@typescript-eslint/scope-manager': 8.56.0 - '@typescript-eslint/types': 8.56.0 - '@typescript-eslint/typescript-estree': 8.56.0(typescript@5.8.3) - '@typescript-eslint/visitor-keys': 8.56.0 + '@typescript-eslint/scope-manager': 8.56.1 + '@typescript-eslint/types': 8.56.1 + '@typescript-eslint/typescript-estree': 8.56.1(typescript@5.9.3) + '@typescript-eslint/visitor-keys': 8.56.1 debug: 4.4.3 - eslint: 10.0.0(jiti@2.4.2) - typescript: 5.8.3 + eslint: 10.0.2(jiti@2.6.1) + typescript: 5.9.3 transitivePeerDependencies: - supports-color - '@typescript-eslint/project-service@8.56.0(typescript@5.8.3)': + '@typescript-eslint/project-service@8.56.1(typescript@5.9.3)': dependencies: - '@typescript-eslint/tsconfig-utils': 8.56.0(typescript@5.8.3) - '@typescript-eslint/types': 8.56.0 + '@typescript-eslint/tsconfig-utils': 8.56.1(typescript@5.9.3) + '@typescript-eslint/types': 8.56.1 debug: 4.4.3 - typescript: 5.8.3 + typescript: 5.9.3 transitivePeerDependencies: - supports-color - '@typescript-eslint/scope-manager@8.56.0': + '@typescript-eslint/scope-manager@8.56.1': dependencies: - '@typescript-eslint/types': 8.56.0 - '@typescript-eslint/visitor-keys': 8.56.0 + '@typescript-eslint/types': 8.56.1 + '@typescript-eslint/visitor-keys': 8.56.1 - '@typescript-eslint/tsconfig-utils@8.56.0(typescript@5.8.3)': + '@typescript-eslint/tsconfig-utils@8.56.1(typescript@5.9.3)': dependencies: - typescript: 5.8.3 + typescript: 5.9.3 - '@typescript-eslint/type-utils@8.56.0(eslint@10.0.0(jiti@2.4.2))(typescript@5.8.3)': + '@typescript-eslint/type-utils@8.56.1(eslint@10.0.2(jiti@2.6.1))(typescript@5.9.3)': dependencies: - '@typescript-eslint/types': 8.56.0 - '@typescript-eslint/typescript-estree': 8.56.0(typescript@5.8.3) - '@typescript-eslint/utils': 8.56.0(eslint@10.0.0(jiti@2.4.2))(typescript@5.8.3) + '@typescript-eslint/types': 8.56.1 + '@typescript-eslint/typescript-estree': 8.56.1(typescript@5.9.3) + '@typescript-eslint/utils': 8.56.1(eslint@10.0.2(jiti@2.6.1))(typescript@5.9.3) debug: 4.4.3 - eslint: 10.0.0(jiti@2.4.2) - ts-api-utils: 2.4.0(typescript@5.8.3) - typescript: 5.8.3 + eslint: 10.0.2(jiti@2.6.1) + ts-api-utils: 2.4.0(typescript@5.9.3) + typescript: 5.9.3 transitivePeerDependencies: - supports-color - '@typescript-eslint/types@8.56.0': {} + '@typescript-eslint/types@8.56.1': {} - '@typescript-eslint/typescript-estree@8.56.0(typescript@5.8.3)': + '@typescript-eslint/typescript-estree@8.56.1(typescript@5.9.3)': dependencies: - '@typescript-eslint/project-service': 8.56.0(typescript@5.8.3) - '@typescript-eslint/tsconfig-utils': 8.56.0(typescript@5.8.3) - '@typescript-eslint/types': 8.56.0 - '@typescript-eslint/visitor-keys': 8.56.0 + '@typescript-eslint/project-service': 8.56.1(typescript@5.9.3) + '@typescript-eslint/tsconfig-utils': 8.56.1(typescript@5.9.3) + '@typescript-eslint/types': 8.56.1 + '@typescript-eslint/visitor-keys': 8.56.1 debug: 4.4.3 - minimatch: 9.0.5 - semver: 7.7.3 + minimatch: 10.2.4 + semver: 7.7.4 tinyglobby: 0.2.15 - ts-api-utils: 2.4.0(typescript@5.8.3) - typescript: 5.8.3 + ts-api-utils: 2.4.0(typescript@5.9.3) + typescript: 5.9.3 transitivePeerDependencies: - supports-color - '@typescript-eslint/utils@8.56.0(eslint@10.0.0(jiti@2.4.2))(typescript@5.8.3)': + '@typescript-eslint/utils@8.56.1(eslint@10.0.2(jiti@2.6.1))(typescript@5.9.3)': dependencies: - '@eslint-community/eslint-utils': 4.9.1(eslint@10.0.0(jiti@2.4.2)) - '@typescript-eslint/scope-manager': 8.56.0 - '@typescript-eslint/types': 8.56.0 - '@typescript-eslint/typescript-estree': 8.56.0(typescript@5.8.3) - eslint: 10.0.0(jiti@2.4.2) - typescript: 5.8.3 + '@eslint-community/eslint-utils': 4.9.1(eslint@10.0.2(jiti@2.6.1)) + '@typescript-eslint/scope-manager': 8.56.1 + '@typescript-eslint/types': 8.56.1 + '@typescript-eslint/typescript-estree': 8.56.1(typescript@5.9.3) + eslint: 10.0.2(jiti@2.6.1) + typescript: 5.9.3 transitivePeerDependencies: - supports-color - '@typescript-eslint/visitor-keys@8.56.0': - dependencies: - '@typescript-eslint/types': 8.56.0 - eslint-visitor-keys: 5.0.0 - - '@unocss/astro@66.3.3(vite@7.1.11(@types/node@24.10.0)(jiti@2.4.2)(terser@5.43.1))(vue@3.5.17(typescript@5.8.3))': + '@typescript-eslint/visitor-keys@8.56.1': dependencies: - '@unocss/core': 66.3.3 - '@unocss/reset': 66.3.3 - '@unocss/vite': 66.3.3(vite@7.1.11(@types/node@24.10.0)(jiti@2.4.2)(terser@5.43.1))(vue@3.5.17(typescript@5.8.3)) - optionalDependencies: - vite: 7.1.11(@types/node@24.10.0)(jiti@2.4.2)(terser@5.43.1) - transitivePeerDependencies: - - vue + '@typescript-eslint/types': 8.56.1 + eslint-visitor-keys: 5.0.1 - '@unocss/cli@66.3.3': + '@unocss/cli@66.6.5': dependencies: - '@ampproject/remapping': 2.3.0 - '@unocss/config': 66.3.3 - '@unocss/core': 66.3.3 - '@unocss/preset-uno': 66.3.3 + '@jridgewell/remapping': 2.3.5 + '@unocss/config': 66.6.4 + '@unocss/core': 66.6.5 + '@unocss/preset-wind3': 66.6.5 + '@unocss/preset-wind4': 66.6.5 + '@unocss/transformer-directives': 66.6.5 cac: 6.7.14 - chokidar: 3.6.0 + chokidar: 5.0.0 colorette: 2.0.20 consola: 3.4.2 magic-string: 0.30.21 pathe: 2.0.3 - perfect-debounce: 1.0.0 + perfect-debounce: 2.1.0 tinyglobby: 0.2.15 - unplugin-utils: 0.2.4 + unplugin-utils: 0.3.1 - '@unocss/config@66.3.3': + '@unocss/config@66.6.4': dependencies: - '@unocss/core': 66.3.3 - unconfig: 7.3.2 + '@unocss/core': 66.6.4 + colorette: 2.0.20 + consola: 3.4.2 + unconfig: 7.5.0 + + '@unocss/core@66.6.4': {} - '@unocss/core@66.3.3': {} + '@unocss/core@66.6.5': {} - '@unocss/extractor-arbitrary-variants@66.3.3': + '@unocss/extractor-arbitrary-variants@66.6.5': dependencies: - '@unocss/core': 66.3.3 + '@unocss/core': 66.6.5 - '@unocss/extractor-svelte@66.3.3': {} + '@unocss/extractor-svelte@66.6.5': {} - '@unocss/inspector@66.3.3(vue@3.5.17(typescript@5.8.3))': + '@unocss/inspector@66.6.5': dependencies: - '@unocss/core': 66.3.3 - '@unocss/rule-utils': 66.3.3 + '@unocss/core': 66.6.5 + '@unocss/rule-utils': 66.6.5 colorette: 2.0.20 gzip-size: 6.0.0 - sirv: 3.0.1 - vue-flow-layout: 0.1.1(vue@3.5.17(typescript@5.8.3)) - transitivePeerDependencies: - - vue - - '@unocss/postcss@66.3.3(postcss@8.5.6)': - dependencies: - '@unocss/config': 66.3.3 - '@unocss/core': 66.3.3 - '@unocss/rule-utils': 66.3.3 - css-tree: 3.1.0 - postcss: 8.5.6 - tinyglobby: 0.2.15 + sirv: 3.0.2 - '@unocss/preset-attributify@66.3.3': + '@unocss/preset-attributify@66.6.5': dependencies: - '@unocss/core': 66.3.3 + '@unocss/core': 66.6.5 - '@unocss/preset-icons@66.3.3': + '@unocss/preset-icons@66.6.5': dependencies: - '@iconify/utils': 2.3.0 - '@unocss/core': 66.3.3 - ofetch: 1.4.1 - transitivePeerDependencies: - - supports-color + '@iconify/utils': 3.1.0 + '@unocss/core': 66.6.5 + ofetch: 1.5.1 - '@unocss/preset-mini@66.3.3': + '@unocss/preset-mini@66.6.5': dependencies: - '@unocss/core': 66.3.3 - '@unocss/extractor-arbitrary-variants': 66.3.3 - '@unocss/rule-utils': 66.3.3 + '@unocss/core': 66.6.5 + '@unocss/extractor-arbitrary-variants': 66.6.5 + '@unocss/rule-utils': 66.6.5 - '@unocss/preset-tagify@66.3.3': + '@unocss/preset-tagify@66.6.5': dependencies: - '@unocss/core': 66.3.3 + '@unocss/core': 66.6.5 - '@unocss/preset-typography@66.3.3': + '@unocss/preset-typography@66.6.5': dependencies: - '@unocss/core': 66.3.3 - '@unocss/preset-mini': 66.3.3 - '@unocss/rule-utils': 66.3.3 + '@unocss/core': 66.6.5 + '@unocss/rule-utils': 66.6.5 - '@unocss/preset-uno@66.3.3': + '@unocss/preset-uno@66.6.5': dependencies: - '@unocss/core': 66.3.3 - '@unocss/preset-wind3': 66.3.3 + '@unocss/core': 66.6.5 + '@unocss/preset-wind3': 66.6.5 - '@unocss/preset-web-fonts@66.3.3': + '@unocss/preset-web-fonts@66.6.5': dependencies: - '@unocss/core': 66.3.3 - ofetch: 1.4.1 + '@unocss/core': 66.6.5 + ofetch: 1.5.1 - '@unocss/preset-wind3@66.3.3': + '@unocss/preset-wind3@66.6.5': dependencies: - '@unocss/core': 66.3.3 - '@unocss/preset-mini': 66.3.3 - '@unocss/rule-utils': 66.3.3 + '@unocss/core': 66.6.5 + '@unocss/preset-mini': 66.6.5 + '@unocss/rule-utils': 66.6.5 - '@unocss/preset-wind4@66.3.3': + '@unocss/preset-wind4@66.6.5': dependencies: - '@unocss/core': 66.3.3 - '@unocss/extractor-arbitrary-variants': 66.3.3 - '@unocss/rule-utils': 66.3.3 + '@unocss/core': 66.6.5 + '@unocss/extractor-arbitrary-variants': 66.6.5 + '@unocss/rule-utils': 66.6.5 - '@unocss/preset-wind@66.3.3': + '@unocss/preset-wind@66.6.5': dependencies: - '@unocss/core': 66.3.3 - '@unocss/preset-wind3': 66.3.3 - - '@unocss/reset@66.3.3': {} + '@unocss/core': 66.6.5 + '@unocss/preset-wind3': 66.6.5 - '@unocss/rule-utils@66.3.3': + '@unocss/rule-utils@66.6.5': dependencies: - '@unocss/core': 66.3.3 + '@unocss/core': 66.6.5 magic-string: 0.30.21 - '@unocss/transformer-attributify-jsx@66.3.3': + '@unocss/transformer-attributify-jsx@66.6.5': dependencies: - '@unocss/core': 66.3.3 + '@unocss/core': 66.6.5 + oxc-parser: 0.115.0 + oxc-walker: 0.7.0(oxc-parser@0.115.0) - '@unocss/transformer-compile-class@66.3.3': + '@unocss/transformer-compile-class@66.6.5': dependencies: - '@unocss/core': 66.3.3 + '@unocss/core': 66.6.5 - '@unocss/transformer-directives@66.3.3': + '@unocss/transformer-directives@66.6.5': dependencies: - '@unocss/core': 66.3.3 - '@unocss/rule-utils': 66.3.3 + '@unocss/core': 66.6.5 + '@unocss/rule-utils': 66.6.5 css-tree: 3.1.0 - '@unocss/transformer-variant-group@66.3.3': + '@unocss/transformer-variant-group@66.6.5': dependencies: - '@unocss/core': 66.3.3 + '@unocss/core': 66.6.5 - '@unocss/vite@66.3.3(vite@7.1.11(@types/node@24.10.0)(jiti@2.4.2)(terser@5.43.1))(vue@3.5.17(typescript@5.8.3))': + '@unocss/vite@66.6.5(vite@7.3.1(@types/node@24.11.0)(jiti@2.6.1)(terser@5.46.0))': dependencies: - '@ampproject/remapping': 2.3.0 - '@unocss/config': 66.3.3 - '@unocss/core': 66.3.3 - '@unocss/inspector': 66.3.3(vue@3.5.17(typescript@5.8.3)) - chokidar: 3.6.0 + '@jridgewell/remapping': 2.3.5 + '@unocss/config': 66.6.4 + '@unocss/core': 66.6.5 + '@unocss/inspector': 66.6.5 + chokidar: 5.0.0 magic-string: 0.30.21 pathe: 2.0.3 tinyglobby: 0.2.15 - unplugin-utils: 0.2.4 - vite: 7.1.11(@types/node@24.10.0)(jiti@2.4.2)(terser@5.43.1) - transitivePeerDependencies: - - vue + unplugin-utils: 0.3.1 + vite: 7.3.1(@types/node@24.11.0)(jiti@2.6.1)(terser@5.46.0) - '@vitest/expect@4.0.6': + '@vitest/expect@4.0.18': dependencies: - '@standard-schema/spec': 1.0.0 - '@types/chai': 5.2.2 - '@vitest/spy': 4.0.6 - '@vitest/utils': 4.0.6 - chai: 6.2.0 + '@standard-schema/spec': 1.1.0 + '@types/chai': 5.2.3 + '@vitest/spy': 4.0.18 + '@vitest/utils': 4.0.18 + chai: 6.2.2 tinyrainbow: 3.0.3 - '@vitest/mocker@4.0.6(vite@7.1.11(@types/node@24.10.0)(jiti@2.4.2)(terser@5.43.1))': + '@vitest/mocker@4.0.18(vite@7.3.1(@types/node@24.11.0)(jiti@2.6.1)(terser@5.46.0))': dependencies: - '@vitest/spy': 4.0.6 + '@vitest/spy': 4.0.18 estree-walker: 3.0.3 magic-string: 0.30.21 optionalDependencies: - vite: 7.1.11(@types/node@24.10.0)(jiti@2.4.2)(terser@5.43.1) + vite: 7.3.1(@types/node@24.11.0)(jiti@2.6.1)(terser@5.46.0) - '@vitest/pretty-format@4.0.6': + '@vitest/pretty-format@4.0.18': dependencies: tinyrainbow: 3.0.3 - '@vitest/runner@4.0.6': + '@vitest/runner@4.0.18': dependencies: - '@vitest/utils': 4.0.6 + '@vitest/utils': 4.0.18 pathe: 2.0.3 - '@vitest/snapshot@4.0.6': + '@vitest/snapshot@4.0.18': dependencies: - '@vitest/pretty-format': 4.0.6 + '@vitest/pretty-format': 4.0.18 magic-string: 0.30.21 pathe: 2.0.3 - '@vitest/spy@4.0.6': {} + '@vitest/spy@4.0.18': {} - '@vitest/utils@4.0.6': + '@vitest/utils@4.0.18': dependencies: - '@vitest/pretty-format': 4.0.6 + '@vitest/pretty-format': 4.0.18 tinyrainbow: 3.0.3 - '@vue/compiler-core@3.5.17': - dependencies: - '@babel/parser': 7.29.0 - '@vue/shared': 3.5.17 - entities: 4.5.0 - estree-walker: 2.0.2 - source-map-js: 1.2.1 - - '@vue/compiler-dom@3.5.17': - dependencies: - '@vue/compiler-core': 3.5.17 - '@vue/shared': 3.5.17 - - '@vue/compiler-sfc@3.5.17': - dependencies: - '@babel/parser': 7.29.0 - '@vue/compiler-core': 3.5.17 - '@vue/compiler-dom': 3.5.17 - '@vue/compiler-ssr': 3.5.17 - '@vue/shared': 3.5.17 - estree-walker: 2.0.2 - magic-string: 0.30.21 - postcss: 8.5.6 - source-map-js: 1.2.1 - - '@vue/compiler-ssr@3.5.17': - dependencies: - '@vue/compiler-dom': 3.5.17 - '@vue/shared': 3.5.17 - - '@vue/reactivity@3.5.17': - dependencies: - '@vue/shared': 3.5.17 - - '@vue/runtime-core@3.5.17': - dependencies: - '@vue/reactivity': 3.5.17 - '@vue/shared': 3.5.17 - - '@vue/runtime-dom@3.5.17': - dependencies: - '@vue/reactivity': 3.5.17 - '@vue/runtime-core': 3.5.17 - '@vue/shared': 3.5.17 - csstype: 3.2.3 - - '@vue/server-renderer@3.5.17(vue@3.5.17(typescript@5.8.3))': - dependencies: - '@vue/compiler-ssr': 3.5.17 - '@vue/shared': 3.5.17 - vue: 3.5.17(typescript@5.8.3) - - '@vue/shared@3.5.17': {} - acorn-jsx@5.3.2(acorn@8.16.0): dependencies: acorn: 8.16.0 acorn@8.16.0: {} - ajv@6.12.6: + ajv@6.14.0: dependencies: fast-deep-equal: 3.1.3 fast-json-stable-stringify: 2.1.0 json-schema-traverse: 0.4.1 uri-js: 4.4.1 - ansi-regex@5.0.1: {} - - ansi-styles@4.3.0: - dependencies: - color-convert: 2.0.1 - - anymatch@3.1.3: - dependencies: - normalize-path: 3.0.0 - picomatch: 2.3.1 - argparse@2.0.1: {} aria-query@5.3.1: {} + assertion-error@2.0.1: {} + axobject-query@4.1.0: {} - balanced-match@4.0.3: {} + balanced-match@4.0.4: {} before-after-hook@4.0.0: {} - binary-extensions@2.3.0: {} - blake3-wasm@2.1.5: {} - brace-expansion@5.0.2: + brace-expansion@5.0.4: dependencies: - balanced-match: 4.0.3 + balanced-match: 4.0.4 braces@3.0.3: dependencies: @@ -4071,21 +3825,13 @@ snapshots: cac@6.7.14: {} - chai@6.2.0: {} + chai@6.2.2: {} chardet@2.1.1: {} - chokidar@3.6.0: + chokidar@5.0.0: dependencies: - anymatch: 3.1.3 - braces: 3.0.3 - glob-parent: 5.1.2 - is-binary-path: 2.1.0 - is-glob: 4.0.3 - normalize-path: 3.0.0 - readdirp: 3.6.0 - optionalDependencies: - fsevents: 2.3.3 + readdirp: 5.0.0 cli-width@4.1.0: {} @@ -4095,20 +3841,12 @@ snapshots: clsx@2.1.1: {} - color-convert@2.0.1: - dependencies: - color-name: 1.1.4 - - color-name@1.1.4: {} - colorette@2.0.20: {} commander@2.20.3: {} confbox@0.1.8: {} - confbox@0.2.2: {} - consola@3.4.2: {} cookie@1.1.1: {} @@ -4129,8 +3867,6 @@ snapshots: mdn-data: 2.12.2 source-map-js: 1.2.1 - csstype@3.2.3: {} - debug@4.4.3: dependencies: ms: 2.1.3 @@ -4149,86 +3885,54 @@ snapshots: duplexer@0.1.2: {} - emnapi@1.7.1: {} - - emoji-regex@8.0.0: {} - - entities@4.5.0: {} + emnapi@1.8.1: {} error-stack-parser-es@1.0.5: {} es-module-lexer@1.7.0: {} - es-toolkit@1.42.0: {} + es-toolkit@1.45.1: {} - esbuild@0.25.4: + esbuild@0.27.3: optionalDependencies: - '@esbuild/aix-ppc64': 0.25.4 - '@esbuild/android-arm': 0.25.4 - '@esbuild/android-arm64': 0.25.4 - '@esbuild/android-x64': 0.25.4 - '@esbuild/darwin-arm64': 0.25.4 - '@esbuild/darwin-x64': 0.25.4 - '@esbuild/freebsd-arm64': 0.25.4 - '@esbuild/freebsd-x64': 0.25.4 - '@esbuild/linux-arm': 0.25.4 - '@esbuild/linux-arm64': 0.25.4 - '@esbuild/linux-ia32': 0.25.4 - '@esbuild/linux-loong64': 0.25.4 - '@esbuild/linux-mips64el': 0.25.4 - '@esbuild/linux-ppc64': 0.25.4 - '@esbuild/linux-riscv64': 0.25.4 - '@esbuild/linux-s390x': 0.25.4 - '@esbuild/linux-x64': 0.25.4 - '@esbuild/netbsd-arm64': 0.25.4 - '@esbuild/netbsd-x64': 0.25.4 - '@esbuild/openbsd-arm64': 0.25.4 - '@esbuild/openbsd-x64': 0.25.4 - '@esbuild/sunos-x64': 0.25.4 - '@esbuild/win32-arm64': 0.25.4 - '@esbuild/win32-ia32': 0.25.4 - '@esbuild/win32-x64': 0.25.4 - - esbuild@0.27.0: - optionalDependencies: - '@esbuild/aix-ppc64': 0.27.0 - '@esbuild/android-arm': 0.27.0 - '@esbuild/android-arm64': 0.27.0 - '@esbuild/android-x64': 0.27.0 - '@esbuild/darwin-arm64': 0.27.0 - '@esbuild/darwin-x64': 0.27.0 - '@esbuild/freebsd-arm64': 0.27.0 - '@esbuild/freebsd-x64': 0.27.0 - '@esbuild/linux-arm': 0.27.0 - '@esbuild/linux-arm64': 0.27.0 - '@esbuild/linux-ia32': 0.27.0 - '@esbuild/linux-loong64': 0.27.0 - '@esbuild/linux-mips64el': 0.27.0 - '@esbuild/linux-ppc64': 0.27.0 - '@esbuild/linux-riscv64': 0.27.0 - '@esbuild/linux-s390x': 0.27.0 - '@esbuild/linux-x64': 0.27.0 - '@esbuild/netbsd-arm64': 0.27.0 - '@esbuild/netbsd-x64': 0.27.0 - '@esbuild/openbsd-arm64': 0.27.0 - '@esbuild/openbsd-x64': 0.27.0 - '@esbuild/openharmony-arm64': 0.27.0 - '@esbuild/sunos-x64': 0.27.0 - '@esbuild/win32-arm64': 0.27.0 - '@esbuild/win32-ia32': 0.27.0 - '@esbuild/win32-x64': 0.27.0 + '@esbuild/aix-ppc64': 0.27.3 + '@esbuild/android-arm': 0.27.3 + '@esbuild/android-arm64': 0.27.3 + '@esbuild/android-x64': 0.27.3 + '@esbuild/darwin-arm64': 0.27.3 + '@esbuild/darwin-x64': 0.27.3 + '@esbuild/freebsd-arm64': 0.27.3 + '@esbuild/freebsd-x64': 0.27.3 + '@esbuild/linux-arm': 0.27.3 + '@esbuild/linux-arm64': 0.27.3 + '@esbuild/linux-ia32': 0.27.3 + '@esbuild/linux-loong64': 0.27.3 + '@esbuild/linux-mips64el': 0.27.3 + '@esbuild/linux-ppc64': 0.27.3 + '@esbuild/linux-riscv64': 0.27.3 + '@esbuild/linux-s390x': 0.27.3 + '@esbuild/linux-x64': 0.27.3 + '@esbuild/netbsd-arm64': 0.27.3 + '@esbuild/netbsd-x64': 0.27.3 + '@esbuild/openbsd-arm64': 0.27.3 + '@esbuild/openbsd-x64': 0.27.3 + '@esbuild/openharmony-arm64': 0.27.3 + '@esbuild/sunos-x64': 0.27.3 + '@esbuild/win32-arm64': 0.27.3 + '@esbuild/win32-ia32': 0.27.3 + '@esbuild/win32-x64': 0.27.3 escape-string-regexp@4.0.0: {} - eslint-config-prettier@10.1.8(eslint@10.0.0(jiti@2.4.2)): + eslint-config-prettier@10.1.8(eslint@10.0.2(jiti@2.6.1)): dependencies: - eslint: 10.0.0(jiti@2.4.2) + eslint: 10.0.2(jiti@2.6.1) eslint-plugin-security@4.0.0: dependencies: safe-regex: 2.1.1 - eslint-scope@9.1.0: + eslint-scope@9.1.1: dependencies: '@types/esrecurse': 4.3.1 '@types/estree': 1.0.8 @@ -4237,27 +3941,27 @@ snapshots: eslint-visitor-keys@3.4.3: {} - eslint-visitor-keys@5.0.0: {} + eslint-visitor-keys@5.0.1: {} - eslint@10.0.0(jiti@2.4.2): + eslint@10.0.2(jiti@2.6.1): dependencies: - '@eslint-community/eslint-utils': 4.9.1(eslint@10.0.0(jiti@2.4.2)) + '@eslint-community/eslint-utils': 4.9.1(eslint@10.0.2(jiti@2.6.1)) '@eslint-community/regexpp': 4.12.2 - '@eslint/config-array': 0.23.1 + '@eslint/config-array': 0.23.2 '@eslint/config-helpers': 0.5.2 '@eslint/core': 1.1.0 '@eslint/plugin-kit': 0.6.0 - '@humanfs/node': 0.16.6 + '@humanfs/node': 0.16.7 '@humanwhocodes/module-importer': 1.0.1 '@humanwhocodes/retry': 0.4.3 '@types/estree': 1.0.8 - ajv: 6.12.6 + ajv: 6.14.0 cross-spawn: 7.0.6 debug: 4.4.3 escape-string-regexp: 4.0.0 - eslint-scope: 9.1.0 - eslint-visitor-keys: 5.0.0 - espree: 11.1.0 + eslint-scope: 9.1.1 + eslint-visitor-keys: 5.0.1 + espree: 11.1.1 esquery: 1.7.0 esutils: 2.0.3 fast-deep-equal: 3.1.3 @@ -4268,21 +3972,21 @@ snapshots: imurmurhash: 0.1.4 is-glob: 4.0.3 json-stable-stringify-without-jsonify: 1.0.1 - minimatch: 10.2.2 + minimatch: 10.2.4 natural-compare: 1.4.0 optionator: 0.9.4 optionalDependencies: - jiti: 2.4.2 + jiti: 2.6.1 transitivePeerDependencies: - supports-color esm-env@1.2.2: {} - espree@11.1.0: + espree@11.1.1: dependencies: acorn: 8.16.0 acorn-jsx: 5.3.2(acorn@8.16.0) - eslint-visitor-keys: 5.0.0 + eslint-visitor-keys: 5.0.1 esquery@1.7.0: dependencies: @@ -4306,9 +4010,7 @@ snapshots: esutils@2.0.3: {} - expect-type@1.2.2: {} - - exsolve@1.0.7: {} + expect-type@1.3.0: {} fast-content-type-parse@3.0.0: {} @@ -4326,7 +4028,17 @@ snapshots: fast-levenshtein@2.0.6: {} - fastq@1.19.1: + fast-string-truncated-width@3.0.3: {} + + fast-string-width@3.0.2: + dependencies: + fast-string-truncated-width: 3.0.3 + + fast-wrap-ansi@0.2.0: + dependencies: + fast-string-width: 3.0.2 + + fastq@1.20.1: dependencies: reusify: 1.1.0 @@ -4349,10 +4061,10 @@ snapshots: flat-cache@4.0.1: dependencies: - flatted: 3.3.3 + flatted: 3.3.4 keyv: 4.5.4 - flatted@3.3.3: {} + flatted@3.3.4: {} fsevents@2.3.3: optional: true @@ -4367,9 +4079,7 @@ snapshots: dependencies: is-glob: 4.0.3 - globals@15.15.0: {} - - globals@17.0.0: {} + globals@17.4.0: {} gzip-size@6.0.0: dependencies: @@ -4379,7 +4089,7 @@ snapshots: dependencies: function-bind: 1.1.2 - iconv-lite@0.7.0: + iconv-lite@0.7.2: dependencies: safer-buffer: 2.1.2 @@ -4389,18 +4099,12 @@ snapshots: imurmurhash@0.1.4: {} - is-binary-path@2.1.0: - dependencies: - binary-extensions: 2.3.0 - is-core-module@2.16.1: dependencies: hasown: 2.0.2 is-extglob@2.1.1: {} - is-fullwidth-code-point@3.0.0: {} - is-glob@4.0.3: dependencies: is-extglob: 2.1.1 @@ -4413,7 +4117,7 @@ snapshots: isexe@2.0.0: {} - jiti@2.4.2: {} + jiti@2.6.1: {} js-yaml@4.1.1: dependencies: @@ -4425,31 +4129,35 @@ snapshots: json-stable-stringify-without-jsonify@1.0.1: {} + json-with-bigint@3.5.7: {} + keyv@4.5.4: dependencies: json-buffer: 3.0.1 kleur@4.1.5: {} - kolorist@1.8.0: {} - levn@0.4.1: dependencies: prelude-ls: 1.2.1 type-check: 0.4.0 - local-pkg@1.1.1: - dependencies: - mlly: 1.7.4 - pkg-types: 2.2.0 - quansync: 0.2.10 - locate-character@3.0.0: {} locate-path@6.0.0: dependencies: p-locate: 5.0.0 + magic-regexp@0.10.0: + dependencies: + estree-walker: 3.0.3 + magic-string: 0.30.21 + mlly: 1.8.0 + regexp-tree: 0.1.27 + type-level-regexp: 0.1.17 + ufo: 1.6.3 + unplugin: 2.3.11 + magic-string@0.30.21: dependencies: '@jridgewell/sourcemap-codec': 1.5.5 @@ -4463,52 +4171,48 @@ snapshots: braces: 3.0.3 picomatch: 2.3.1 - miniflare@4.20260128.0: + miniflare@4.20260301.1: dependencies: '@cspotcode/source-map-support': 0.8.1 sharp: 0.34.5 undici: 7.18.2 - workerd: 1.20260128.0 + workerd: 1.20260301.1 ws: 8.18.0 youch: 4.1.0-beta.10 transitivePeerDependencies: - bufferutil - utf-8-validate - minimatch@10.2.2: - dependencies: - brace-expansion: 5.0.2 - - minimatch@9.0.5: + minimatch@10.2.4: dependencies: - brace-expansion: 5.0.2 + brace-expansion: 5.0.4 - mlly@1.7.4: + mlly@1.8.0: dependencies: acorn: 8.16.0 pathe: 2.0.3 pkg-types: 1.3.1 - ufo: 1.6.1 + ufo: 1.6.3 mrmime@2.0.1: {} ms@2.1.3: {} - mute-stream@2.0.0: {} + mute-stream@3.0.0: {} nanoid@3.3.11: {} natural-compare@1.4.0: {} - node-fetch-native@1.6.6: {} + node-fetch-native@1.6.7: {} - normalize-path@3.0.0: {} + obug@2.1.1: {} - ofetch@1.4.1: + ofetch@1.5.1: dependencies: destr: 2.0.5 - node-fetch-native: 1.6.6 - ufo: 1.6.1 + node-fetch-native: 1.6.7 + ufo: 1.6.3 optionator@0.9.4: dependencies: @@ -4519,6 +4223,36 @@ snapshots: type-check: 0.4.0 word-wrap: 1.2.5 + oxc-parser@0.115.0: + dependencies: + '@oxc-project/types': 0.115.0 + optionalDependencies: + '@oxc-parser/binding-android-arm-eabi': 0.115.0 + '@oxc-parser/binding-android-arm64': 0.115.0 + '@oxc-parser/binding-darwin-arm64': 0.115.0 + '@oxc-parser/binding-darwin-x64': 0.115.0 + '@oxc-parser/binding-freebsd-x64': 0.115.0 + '@oxc-parser/binding-linux-arm-gnueabihf': 0.115.0 + '@oxc-parser/binding-linux-arm-musleabihf': 0.115.0 + '@oxc-parser/binding-linux-arm64-gnu': 0.115.0 + '@oxc-parser/binding-linux-arm64-musl': 0.115.0 + '@oxc-parser/binding-linux-ppc64-gnu': 0.115.0 + '@oxc-parser/binding-linux-riscv64-gnu': 0.115.0 + '@oxc-parser/binding-linux-riscv64-musl': 0.115.0 + '@oxc-parser/binding-linux-s390x-gnu': 0.115.0 + '@oxc-parser/binding-linux-x64-gnu': 0.115.0 + '@oxc-parser/binding-linux-x64-musl': 0.115.0 + '@oxc-parser/binding-openharmony-arm64': 0.115.0 + '@oxc-parser/binding-wasm32-wasi': 0.115.0 + '@oxc-parser/binding-win32-arm64-msvc': 0.115.0 + '@oxc-parser/binding-win32-ia32-msvc': 0.115.0 + '@oxc-parser/binding-win32-x64-msvc': 0.115.0 + + oxc-walker@0.7.0(oxc-parser@0.115.0): + dependencies: + magic-regexp: 0.10.0 + oxc-parser: 0.115.0 + p-limit@3.1.0: dependencies: yocto-queue: 0.1.0 @@ -4527,7 +4261,7 @@ snapshots: dependencies: p-limit: 3.1.0 - package-manager-detector@1.3.0: {} + package-manager-detector@1.6.0: {} path-exists@4.0.0: {} @@ -4539,7 +4273,7 @@ snapshots: pathe@2.0.3: {} - perfect-debounce@1.0.0: {} + perfect-debounce@2.1.0: {} picocolors@1.1.1: {} @@ -4550,16 +4284,10 @@ snapshots: pkg-types@1.3.1: dependencies: confbox: 0.1.8 - mlly: 1.7.4 - pathe: 2.0.3 - - pkg-types@2.2.0: - dependencies: - confbox: 0.2.2 - exsolve: 1.0.7 + mlly: 1.8.0 pathe: 2.0.3 - postcss@8.5.6: + postcss@8.5.8: dependencies: nanoid: 3.3.11 picocolors: 1.1.1 @@ -4567,25 +4295,19 @@ snapshots: prelude-ls@1.2.1: {} - prettier@3.6.2: {} + prettier@3.8.1: {} punycode@2.3.1: {} - quansync@0.2.10: {} + quansync@1.0.0: {} queue-microtask@1.2.3: {} - randombytes@2.1.0: - dependencies: - safe-buffer: 5.2.1 - - readdirp@3.6.0: - dependencies: - picomatch: 2.3.1 + readdirp@5.0.0: {} regexp-tree@0.1.27: {} - resolve@1.22.10: + resolve@1.22.11: dependencies: is-core-module: 2.16.1 path-parse: 1.0.7 @@ -4628,25 +4350,21 @@ snapshots: dependencies: queue-microtask: 1.2.3 - safe-buffer@5.2.1: {} - safe-regex@2.1.1: dependencies: regexp-tree: 0.1.27 safer-buffer@2.1.2: {} - semver@7.7.3: {} + semver@7.7.4: {} - serialize-javascript@6.0.2: - dependencies: - randombytes: 2.1.0 + serialize-javascript@7.0.4: {} sharp@0.34.5: dependencies: - '@img/colour': 1.0.0 + '@img/colour': 1.1.0 detect-libc: 2.1.2 - semver: 7.7.3 + semver: 7.7.4 optionalDependencies: '@img/sharp-darwin-arm64': 0.34.5 '@img/sharp-darwin-x64': 0.34.5 @@ -4683,13 +4401,13 @@ snapshots: signal-exit@4.1.0: {} - sirv@3.0.1: + sirv@3.0.2: dependencies: '@polka/url': 1.0.0-next.29 mrmime: 2.0.1 totalist: 3.0.1 - smob@1.5.0: {} + smob@1.6.1: {} source-map-js@1.2.1: {} @@ -4702,23 +4420,13 @@ snapshots: stackback@0.0.2: {} - std-env@3.9.0: {} - - string-width@4.2.3: - dependencies: - emoji-regex: 8.0.0 - is-fullwidth-code-point: 3.0.0 - strip-ansi: 6.0.1 - - strip-ansi@6.0.1: - dependencies: - ansi-regex: 5.0.1 + std-env@3.10.0: {} supports-color@10.2.2: {} supports-preserve-symlinks-flag@1.0.0: {} - svelte@5.53.5: + svelte@5.53.7: dependencies: '@jridgewell/remapping': 2.3.5 '@jridgewell/sourcemap-codec': 1.5.5 @@ -4737,18 +4445,16 @@ snapshots: magic-string: 0.30.21 zimmerframe: 1.1.4 - terser@5.43.1: + terser@5.46.0: dependencies: - '@jridgewell/source-map': 0.3.6 + '@jridgewell/source-map': 0.3.11 acorn: 8.16.0 commander: 2.20.3 source-map-support: 0.5.21 tinybench@2.9.0: {} - tinyexec@0.3.2: {} - - tinyexec@1.0.1: {} + tinyexec@1.0.2: {} tinyglobby@0.2.15: dependencies: @@ -4763,9 +4469,9 @@ snapshots: totalist@3.0.1: {} - ts-api-utils@2.4.0(typescript@5.8.3): + ts-api-utils@2.4.0(typescript@5.9.3): dependencies: - typescript: 5.8.3 + typescript: 5.9.3 tslib@2.8.1: {} @@ -4775,27 +4481,35 @@ snapshots: dependencies: prelude-ls: 1.2.1 - typescript-eslint@8.56.0(eslint@10.0.0(jiti@2.4.2))(typescript@5.8.3): + type-level-regexp@0.1.17: {} + + typescript-eslint@8.56.1(eslint@10.0.2(jiti@2.6.1))(typescript@5.9.3): dependencies: - '@typescript-eslint/eslint-plugin': 8.56.0(@typescript-eslint/parser@8.56.0(eslint@10.0.0(jiti@2.4.2))(typescript@5.8.3))(eslint@10.0.0(jiti@2.4.2))(typescript@5.8.3) - '@typescript-eslint/parser': 8.56.0(eslint@10.0.0(jiti@2.4.2))(typescript@5.8.3) - '@typescript-eslint/typescript-estree': 8.56.0(typescript@5.8.3) - '@typescript-eslint/utils': 8.56.0(eslint@10.0.0(jiti@2.4.2))(typescript@5.8.3) - eslint: 10.0.0(jiti@2.4.2) - typescript: 5.8.3 + '@typescript-eslint/eslint-plugin': 8.56.1(@typescript-eslint/parser@8.56.1(eslint@10.0.2(jiti@2.6.1))(typescript@5.9.3))(eslint@10.0.2(jiti@2.6.1))(typescript@5.9.3) + '@typescript-eslint/parser': 8.56.1(eslint@10.0.2(jiti@2.6.1))(typescript@5.9.3) + '@typescript-eslint/typescript-estree': 8.56.1(typescript@5.9.3) + '@typescript-eslint/utils': 8.56.1(eslint@10.0.2(jiti@2.6.1))(typescript@5.9.3) + eslint: 10.0.2(jiti@2.6.1) + typescript: 5.9.3 transitivePeerDependencies: - supports-color - typescript@5.8.3: {} + typescript@5.9.3: {} - ufo@1.6.1: {} + ufo@1.6.3: {} + + unconfig-core@7.5.0: + dependencies: + '@quansync/fs': 1.0.0 + quansync: 1.0.0 - unconfig@7.3.2: + unconfig@7.5.0: dependencies: - '@quansync/fs': 0.1.3 + '@quansync/fs': 1.0.0 defu: 6.1.4 - jiti: 2.4.2 - quansync: 0.2.10 + jiti: 2.6.1 + quansync: 1.0.0 + unconfig-core: 7.5.0 undici-types@7.16.0: {} @@ -4807,85 +4521,86 @@ snapshots: universal-user-agent@7.0.3: {} - unocss@66.3.3(postcss@8.5.6)(vite@7.1.11(@types/node@24.10.0)(jiti@2.4.2)(terser@5.43.1))(vue@3.5.17(typescript@5.8.3)): - dependencies: - '@unocss/astro': 66.3.3(vite@7.1.11(@types/node@24.10.0)(jiti@2.4.2)(terser@5.43.1))(vue@3.5.17(typescript@5.8.3)) - '@unocss/cli': 66.3.3 - '@unocss/core': 66.3.3 - '@unocss/postcss': 66.3.3(postcss@8.5.6) - '@unocss/preset-attributify': 66.3.3 - '@unocss/preset-icons': 66.3.3 - '@unocss/preset-mini': 66.3.3 - '@unocss/preset-tagify': 66.3.3 - '@unocss/preset-typography': 66.3.3 - '@unocss/preset-uno': 66.3.3 - '@unocss/preset-web-fonts': 66.3.3 - '@unocss/preset-wind': 66.3.3 - '@unocss/preset-wind3': 66.3.3 - '@unocss/preset-wind4': 66.3.3 - '@unocss/transformer-attributify-jsx': 66.3.3 - '@unocss/transformer-compile-class': 66.3.3 - '@unocss/transformer-directives': 66.3.3 - '@unocss/transformer-variant-group': 66.3.3 - '@unocss/vite': 66.3.3(vite@7.1.11(@types/node@24.10.0)(jiti@2.4.2)(terser@5.43.1))(vue@3.5.17(typescript@5.8.3)) - optionalDependencies: - vite: 7.1.11(@types/node@24.10.0)(jiti@2.4.2)(terser@5.43.1) + unocss@66.6.5(vite@7.3.1(@types/node@24.11.0)(jiti@2.6.1)(terser@5.46.0)): + dependencies: + '@unocss/cli': 66.6.5 + '@unocss/core': 66.6.5 + '@unocss/preset-attributify': 66.6.5 + '@unocss/preset-icons': 66.6.5 + '@unocss/preset-mini': 66.6.5 + '@unocss/preset-tagify': 66.6.5 + '@unocss/preset-typography': 66.6.5 + '@unocss/preset-uno': 66.6.5 + '@unocss/preset-web-fonts': 66.6.5 + '@unocss/preset-wind': 66.6.5 + '@unocss/preset-wind3': 66.6.5 + '@unocss/preset-wind4': 66.6.5 + '@unocss/transformer-attributify-jsx': 66.6.5 + '@unocss/transformer-compile-class': 66.6.5 + '@unocss/transformer-directives': 66.6.5 + '@unocss/transformer-variant-group': 66.6.5 + '@unocss/vite': 66.6.5(vite@7.3.1(@types/node@24.11.0)(jiti@2.6.1)(terser@5.46.0)) transitivePeerDependencies: - - postcss - - supports-color - - vue + - vite - unplugin-utils@0.2.4: + unplugin-utils@0.3.1: dependencies: pathe: 2.0.3 picomatch: 4.0.3 + unplugin@2.3.11: + dependencies: + '@jridgewell/remapping': 2.3.5 + acorn: 8.16.0 + picomatch: 4.0.3 + webpack-virtual-modules: 0.6.2 + uri-js@4.4.1: dependencies: punycode: 2.3.1 - vite@7.1.11(@types/node@24.10.0)(jiti@2.4.2)(terser@5.43.1): + vite@7.3.1(@types/node@24.11.0)(jiti@2.6.1)(terser@5.46.0): dependencies: - esbuild: 0.25.4 + esbuild: 0.27.3 fdir: 6.5.0(picomatch@4.0.3) picomatch: 4.0.3 - postcss: 8.5.6 + postcss: 8.5.8 rollup: 4.59.0 tinyglobby: 0.2.15 optionalDependencies: - '@types/node': 24.10.0 + '@types/node': 24.11.0 fsevents: 2.3.3 - jiti: 2.4.2 - terser: 5.43.1 + jiti: 2.6.1 + terser: 5.46.0 - vitefu@1.1.1(vite@7.1.11(@types/node@24.10.0)(jiti@2.4.2)(terser@5.43.1)): + vitefu@1.1.2(vite@7.3.1(@types/node@24.11.0)(jiti@2.6.1)(terser@5.46.0)): optionalDependencies: - vite: 7.1.11(@types/node@24.10.0)(jiti@2.4.2)(terser@5.43.1) + vite: 7.3.1(@types/node@24.11.0)(jiti@2.6.1)(terser@5.46.0) - vitest@4.0.6(@types/node@24.10.0)(jiti@2.4.2)(terser@5.43.1): + vitest@4.0.18(@types/node@24.11.0)(jiti@2.6.1)(terser@5.46.0): dependencies: - '@vitest/expect': 4.0.6 - '@vitest/mocker': 4.0.6(vite@7.1.11(@types/node@24.10.0)(jiti@2.4.2)(terser@5.43.1)) - '@vitest/pretty-format': 4.0.6 - '@vitest/runner': 4.0.6 - '@vitest/snapshot': 4.0.6 - '@vitest/spy': 4.0.6 - '@vitest/utils': 4.0.6 - debug: 4.4.3 + '@vitest/expect': 4.0.18 + '@vitest/mocker': 4.0.18(vite@7.3.1(@types/node@24.11.0)(jiti@2.6.1)(terser@5.46.0)) + '@vitest/pretty-format': 4.0.18 + '@vitest/runner': 4.0.18 + '@vitest/snapshot': 4.0.18 + '@vitest/spy': 4.0.18 + '@vitest/utils': 4.0.18 es-module-lexer: 1.7.0 - expect-type: 1.2.2 + expect-type: 1.3.0 magic-string: 0.30.21 + obug: 2.1.1 pathe: 2.0.3 picomatch: 4.0.3 - std-env: 3.9.0 + std-env: 3.10.0 tinybench: 2.9.0 - tinyexec: 0.3.2 + tinyexec: 1.0.2 tinyglobby: 0.2.15 tinyrainbow: 3.0.3 - vite: 7.1.11(@types/node@24.10.0)(jiti@2.4.2)(terser@5.43.1) + vite: 7.3.1(@types/node@24.11.0)(jiti@2.6.1)(terser@5.46.0) why-is-node-running: 2.3.0 optionalDependencies: - '@types/node': 24.10.0 + '@types/node': 24.11.0 transitivePeerDependencies: - jiti - less @@ -4895,24 +4610,11 @@ snapshots: - sass-embedded - stylus - sugarss - - supports-color - terser - tsx - yaml - vue-flow-layout@0.1.1(vue@3.5.17(typescript@5.8.3)): - dependencies: - vue: 3.5.17(typescript@5.8.3) - - vue@3.5.17(typescript@5.8.3): - dependencies: - '@vue/compiler-dom': 3.5.17 - '@vue/compiler-sfc': 3.5.17 - '@vue/runtime-dom': 3.5.17 - '@vue/server-renderer': 3.5.17(vue@3.5.17(typescript@5.8.3)) - '@vue/shared': 3.5.17 - optionalDependencies: - typescript: 5.8.3 + webpack-virtual-modules@0.6.2: {} which@2.0.2: dependencies: @@ -4925,42 +4627,34 @@ snapshots: word-wrap@1.2.5: {} - workerd@1.20260128.0: + workerd@1.20260301.1: optionalDependencies: - '@cloudflare/workerd-darwin-64': 1.20260128.0 - '@cloudflare/workerd-darwin-arm64': 1.20260128.0 - '@cloudflare/workerd-linux-64': 1.20260128.0 - '@cloudflare/workerd-linux-arm64': 1.20260128.0 - '@cloudflare/workerd-windows-64': 1.20260128.0 + '@cloudflare/workerd-darwin-64': 1.20260301.1 + '@cloudflare/workerd-darwin-arm64': 1.20260301.1 + '@cloudflare/workerd-linux-64': 1.20260301.1 + '@cloudflare/workerd-linux-arm64': 1.20260301.1 + '@cloudflare/workerd-windows-64': 1.20260301.1 - wrangler@4.61.1: + wrangler@4.70.0: dependencies: '@cloudflare/kv-asset-handler': 0.4.2 - '@cloudflare/unenv-preset': 2.12.0(unenv@2.0.0-rc.24)(workerd@1.20260128.0) + '@cloudflare/unenv-preset': 2.14.0(unenv@2.0.0-rc.24)(workerd@1.20260301.1) blake3-wasm: 2.1.5 - esbuild: 0.27.0 - miniflare: 4.20260128.0 + esbuild: 0.27.3 + miniflare: 4.20260301.1 path-to-regexp: 6.3.0 unenv: 2.0.0-rc.24 - workerd: 1.20260128.0 + workerd: 1.20260301.1 optionalDependencies: fsevents: 2.3.3 transitivePeerDependencies: - bufferutil - utf-8-validate - wrap-ansi@6.2.0: - dependencies: - ansi-styles: 4.3.0 - string-width: 4.2.3 - strip-ansi: 6.0.1 - ws@8.18.0: {} yocto-queue@0.1.0: {} - yoctocolors-cjs@2.1.3: {} - youch-core@0.3.3: dependencies: '@poppinss/exception': 1.2.3 diff --git a/pnpm-workspace.yaml b/pnpm-workspace.yaml index 2a46905e59d5..9a484e821213 100644 --- a/pnpm-workspace.yaml +++ b/pnpm-workspace.yaml @@ -5,3 +5,10 @@ packages: - examples/api - examples/resources - examples/file-associations + +onlyBuiltDependencies: + - esbuild + - workerd + +overrides: + serialize-javascript@<=7.0.2: '>=7.0.3' From df6140095844440c2dd92a45dff867aad988b7af Mon Sep 17 00:00:00 2001 From: Tony <68118705+Legend-Master@users.noreply.github.com> Date: Thu, 5 Mar 2026 11:38:02 +0800 Subject: [PATCH 31/95] enhance(cli): add context before prompting password (#15033) * enhance(cli): add context before prompting password * Add change file --- .changes/prompt-signing-key-password-context.md | 6 ++++++ crates/tauri-cli/src/bundle.rs | 3 +++ 2 files changed, 9 insertions(+) create mode 100644 .changes/prompt-signing-key-password-context.md diff --git a/.changes/prompt-signing-key-password-context.md b/.changes/prompt-signing-key-password-context.md new file mode 100644 index 000000000000..59f9fbb9bf17 --- /dev/null +++ b/.changes/prompt-signing-key-password-context.md @@ -0,0 +1,6 @@ +--- +"tauri-cli": patch:enhance +"@tauri-apps/cli": patch:enhance +--- + +Show the context before prompting for updater signing key password diff --git a/crates/tauri-cli/src/bundle.rs b/crates/tauri-cli/src/bundle.rs index 3db831c1849a..d40dba652bf8 100644 --- a/crates/tauri-cli/src/bundle.rs +++ b/crates/tauri-cli/src/bundle.rs @@ -287,6 +287,9 @@ fn sign_updaters( } else { private_key }; + if password.is_none() { + log::info!("Decrypting updater signing key, expect a prompt for password") + } let secret_key = updater_signature::secret_key(private_key, password).context("failed to decode secret key")?; let public_key = updater_signature::pub_key(pubkey).context("failed to decode pubkey")?; From c4af2dbf43dd8d6ba72a867762adf3060433b1ad Mon Sep 17 00:00:00 2001 From: Fabian-Lars <30730186+FabianLars@users.noreply.github.com> Date: Fri, 6 Mar 2026 13:40:41 +0100 Subject: [PATCH 32/95] ci(test-core): split cache per target (#15048) --- .github/workflows/publish-cli-js.yml | 2 +- .github/workflows/test-core.yml | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/.github/workflows/publish-cli-js.yml b/.github/workflows/publish-cli-js.yml index 3e4f76081c18..a2a53afab4e0 100644 --- a/.github/workflows/publish-cli-js.yml +++ b/.github/workflows/publish-cli-js.yml @@ -120,7 +120,7 @@ jobs: if: ${{ !matrix.settings.docker }} with: targets: ${{ matrix.settings.target }} - - uses: Swatinem/rust-cache@v1 + - uses: Swatinem/rust-cache@v2 with: key: ${{ matrix.settings.target }} if: ${{ matrix.settings.docker }} diff --git a/.github/workflows/test-core.yml b/.github/workflows/test-core.yml index 59f393c314ef..6ab8092b923a 100644 --- a/.github/workflows/test-core.yml +++ b/.github/workflows/test-core.yml @@ -90,7 +90,7 @@ jobs: - uses: Swatinem/rust-cache@v2 with: - prefix-key: v3 + key: ${{ matrix.platform.target }} save-if: ${{ matrix.features.key == 'all' }} - name: test tauri-utils From 6ecc81d34def54a9ee7d142aef88eeba5cf61a50 Mon Sep 17 00:00:00 2001 From: Rohit Singh <27754873+razein97@users.noreply.github.com> Date: Fri, 6 Mar 2026 22:08:23 +0530 Subject: [PATCH 33/95] Add changelog for PR 14923 Add changelog for PR 14923 with patch updates and a fix for arm system detection in tauri-bundler. --- .changes/change-pr-14923.md | 18 ++++++++++++++++++ 1 file changed, 18 insertions(+) create mode 100644 .changes/change-pr-14923.md diff --git a/.changes/change-pr-14923.md b/.changes/change-pr-14923.md new file mode 100644 index 000000000000..d4ab557a9f78 --- /dev/null +++ b/.changes/change-pr-14923.md @@ -0,0 +1,18 @@ +--- +"@tauri-apps/api": patch +"tauri-utils": patch +"tauri-macos-sign": patch +"tauri-bundler": patch +"tauri-runtime": patch +"tauri-runtime-wry": patch +"tauri-codegen": patch +"tauri-macros": patch +"tauri-plugin": patch +"tauri-build": patch +"tauri": patch +"@tauri-apps/cli": patch +"tauri-cli": patch +"tauri-driver": patch +--- + +fix(windows): tauri-bundler detect arm system From 5228f8968bbeaa12cd5a08ec9de30ece2a08b090 Mon Sep 17 00:00:00 2001 From: Tony <68118705+Legend-Master@users.noreply.github.com> Date: Sun, 8 Mar 2026 17:54:28 +0800 Subject: [PATCH 34/95] chore(deps): update `@rollup/plugin-terser` to v1 (#15057) --- packages/api/package.json | 2 +- pnpm-lock.yaml | 15 ++++++--------- pnpm-workspace.yaml | 3 --- 3 files changed, 7 insertions(+), 13 deletions(-) diff --git a/packages/api/package.json b/packages/api/package.json index 39391dd66b0a..db3744fc2446 100644 --- a/packages/api/package.json +++ b/packages/api/package.json @@ -46,7 +46,7 @@ }, "devDependencies": { "@eslint/js": "^10.0.1", - "@rollup/plugin-terser": "0.4.4", + "@rollup/plugin-terser": "1.0.0", "@rollup/plugin-typescript": "12.3.0", "@types/eslint": "^9.6.1", "@types/node": "^24.11.0", diff --git a/pnpm-lock.yaml b/pnpm-lock.yaml index 7a46fc0ae25d..34c0a30cfa71 100644 --- a/pnpm-lock.yaml +++ b/pnpm-lock.yaml @@ -4,9 +4,6 @@ settings: autoInstallPeers: true excludeLinksFromLockfile: false -overrides: - serialize-javascript@<=7.0.2: '>=7.0.3' - importers: .: @@ -59,8 +56,8 @@ importers: specifier: ^10.0.1 version: 10.0.1(eslint@10.0.2(jiti@2.6.1)) '@rollup/plugin-terser': - specifier: 0.4.4 - version: 0.4.4(rollup@4.59.0) + specifier: 1.0.0 + version: 1.0.0(rollup@4.59.0) '@rollup/plugin-typescript': specifier: 12.3.0 version: 12.3.0(rollup@4.59.0)(tslib@2.8.1)(typescript@5.9.3) @@ -1268,9 +1265,9 @@ packages: '@quansync/fs@1.0.0': resolution: {integrity: sha512-4TJ3DFtlf1L5LDMaM6CanJ/0lckGNtJcMjQ1NAV6zDmA0tEHKZtxNKin8EgPaVX1YzljbxckyT2tJrpQKAtngQ==} - '@rollup/plugin-terser@0.4.4': - resolution: {integrity: sha512-XHeJC5Bgvs8LfukDwWZp7yeqin6ns8RTl2B9avbejt6tZqsqvVoWI7ZTQrcNsfKEDWBTnTxM8nMDkO2IFFbd0A==} - engines: {node: '>=14.0.0'} + '@rollup/plugin-terser@1.0.0': + resolution: {integrity: sha512-FnCxhTBx6bMOYQrar6C8h3scPt8/JwIzw3+AJ2K++6guogH5fYaIFia+zZuhqv0eo1RN7W1Pz630SyvLbDjhtQ==} + engines: {node: '>=20.0.0'} peerDependencies: rollup: ^2.0.0||^3.0.0||^4.0.0 peerDependenciesMeta: @@ -3367,7 +3364,7 @@ snapshots: dependencies: quansync: 1.0.0 - '@rollup/plugin-terser@0.4.4(rollup@4.59.0)': + '@rollup/plugin-terser@1.0.0(rollup@4.59.0)': dependencies: serialize-javascript: 7.0.4 smob: 1.6.1 diff --git a/pnpm-workspace.yaml b/pnpm-workspace.yaml index 9a484e821213..f0a696121145 100644 --- a/pnpm-workspace.yaml +++ b/pnpm-workspace.yaml @@ -9,6 +9,3 @@ packages: onlyBuiltDependencies: - esbuild - workerd - -overrides: - serialize-javascript@<=7.0.2: '>=7.0.3' From 2f2b73f507054543766bef30917e1edafc09e590 Mon Sep 17 00:00:00 2001 From: Amr Bashir Date: Tue, 10 Mar 2026 14:14:58 +0200 Subject: [PATCH 35/95] refactor(macos-sign): use base64 crate instead of Command (#15038) * refactor(macos-sign): use base64 crate instead of Command * add base64 crate as a dependency * add change file --------- Co-authored-by: Lucas Nogueira --- .changes/base64.md | 5 ++++ Cargo.lock | 1 + crates/tauri-macos-sign/Cargo.toml | 1 + crates/tauri-macos-sign/src/lib.rs | 43 +++++++++++------------------- 4 files changed, 23 insertions(+), 27 deletions(-) create mode 100644 .changes/base64.md diff --git a/.changes/base64.md b/.changes/base64.md new file mode 100644 index 000000000000..2fb599baba49 --- /dev/null +++ b/.changes/base64.md @@ -0,0 +1,5 @@ +--- +"tauri-macos-sign": patch:enhance +--- + +Do not rely on system base64 CLI to decode certificates. diff --git a/Cargo.lock b/Cargo.lock index ffa7c32f7962..8b9b0da50813 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -8712,6 +8712,7 @@ name = "tauri-macos-sign" version = "2.3.3" dependencies = [ "apple-codesign", + "base64 0.22.1", "chrono", "dirs 6.0.0", "log", diff --git a/crates/tauri-macos-sign/Cargo.toml b/crates/tauri-macos-sign/Cargo.toml index af15c66fa8e5..fa4c429fd0f3 100644 --- a/crates/tauri-macos-sign/Cargo.toml +++ b/crates/tauri-macos-sign/Cargo.toml @@ -25,3 +25,4 @@ log = { version = "0.4.21", features = ["kv"] } apple-codesign = { version = "0.27", default-features = false } chrono = "0.4" p12 = "0.6" +base64 = "0.22" diff --git a/crates/tauri-macos-sign/src/lib.rs b/crates/tauri-macos-sign/src/lib.rs index 87e30fdeea62..c6e93821a66e 100644 --- a/crates/tauri-macos-sign/src/lib.rs +++ b/crates/tauri-macos-sign/src/lib.rs @@ -64,6 +64,8 @@ pub enum Error { }, #[error("failed to encode DER: {error}")] FailedToEncodeDER { error: std::io::Error }, + #[error("failed to decode base64 certificate: {0}")] + Base64Decode(base64::DecodeError), #[error("certificate missing common name")] CertificateMissingCommonName, #[error("certificate missing organization unit for common name {common_name}")] @@ -329,36 +331,23 @@ impl NotarytoolCmdExt for Command { } } -fn decode_base64(base64: &OsStr, out_path: &Path) -> Result<()> { - let tmp_dir = tempfile::tempdir().map_err(Error::TempDir)?; +fn decode_base64(base64_input: &OsStr, out_path: &Path) -> Result<()> { + use base64::Engine; - let src_path = tmp_dir.path().join("src"); - let base64 = base64 + let input = base64_input .to_str() - .expect("failed to convert base64 to string") - .as_bytes(); - - // as base64 contain whitespace decoding may be broken - // https://github.com/marshallpierce/rust-base64/issues/105 - // we'll use builtin base64 command from the OS - std::fs::write(&src_path, base64).map_err(|error| Error::Fs { - context: "failed to write base64 to temp file", - path: src_path.clone(), - error, - })?; + .expect("failed to convert base64 to string"); - assert_command( - std::process::Command::new("base64") - .arg("--decode") - .arg("-i") - .arg(&src_path) - .arg("-o") - .arg(out_path) - .piped(), - "failed to decode certificate", - ) - .map_err(|error| Error::CommandFailed { - command: "base64 --decode".to_string(), + // strip whitespace before decoding + let cleaned: String = input.chars().filter(|c| !c.is_ascii_whitespace()).collect(); + + let decoded = base64::engine::general_purpose::STANDARD + .decode(&cleaned) + .map_err(Error::Base64Decode)?; + + std::fs::write(out_path, &decoded).map_err(|error| Error::Fs { + context: "failed to write decoded certificate", + path: out_path.to_path_buf(), error, })?; From f1925b8bc913f9e4a04e1e9a7ef0b4ce919c23a6 Mon Sep 17 00:00:00 2001 From: Amr Bashir Date: Tue, 10 Mar 2026 14:25:41 +0200 Subject: [PATCH 36/95] feat: add `data-tauri-drag-region="deep"` (#15062) * feat: add `data-tauri-drag-region="deep"` supersedes #6362 * Update data-tauri-drag-region-deep.md * summary is also clickable --------- Co-authored-by: Lucas Nogueira --- .changes/data-tauri-drag-region-deep.md | 5 ++ crates/tauri/src/window/scripts/drag.js | 80 +++++++++++++++++++------ 2 files changed, 68 insertions(+), 17 deletions(-) create mode 100644 .changes/data-tauri-drag-region-deep.md diff --git a/.changes/data-tauri-drag-region-deep.md b/.changes/data-tauri-drag-region-deep.md new file mode 100644 index 000000000000..1391ff5ac589 --- /dev/null +++ b/.changes/data-tauri-drag-region-deep.md @@ -0,0 +1,5 @@ +--- +"tauri": minor:feat +--- + +Add `data-tauri-drag-region="deep"` so clicks on non-clickable children will drag as well. Can still opt out of drag on some regions using `data-tauri-drag-region="false"` diff --git a/crates/tauri/src/window/scripts/drag.js b/crates/tauri/src/window/scripts/drag.js index 1c9461b63d76..b22d46f20faa 100644 --- a/crates/tauri/src/window/scripts/drag.js +++ b/crates/tauri/src/window/scripts/drag.js @@ -3,30 +3,78 @@ // SPDX-License-Identifier: MIT ;(function () { - const osName = __TEMPLATE_os_name__ - //-----------------------// // drag on mousedown and maximize on double click on Windows and Linux - // while macOS macos maximization should be on mouseup and if the mouse + // while macOS maximization should be on mouseup and if the mouse // moves after the double click, it should be cancelled (see https://github.com/tauri-apps/tauri/issues/8306) //-----------------------// const TAURI_DRAG_REGION_ATTR = 'data-tauri-drag-region' + function isClickableElement(el) { + const tag = el.tagName && el.tagName.toLowerCase() + + return ( + tag === 'a' + || tag === 'button' + || tag === 'input' + || tag === 'select' + || tag === 'textarea' + || tag === 'label' + || tag === 'summary' + || (el.hasAttribute('contenteditable') + && el.getAttribute('contenteditable') !== 'false') + || (el.hasAttribute('tabindex') && el.getAttribute('tabindex') !== '-1') + ) + } + + // Walk the composed path from target upward. If a clickable element or a + // data-tauri-drag-region="false" element is encountered, return false (don't drag). + // Otherwise return true. + // + // Supported values for data-tauri-drag-region: + // (bare / no value) → self: only direct clicks on this element trigger drag + // "deep" → deep: clicks anywhere in the subtree trigger drag + // "false" → disabled: drag is blocked here (and for ancestors) + function isDragRegion(composedPath) { + for (const el of composedPath) { + if (!(el instanceof HTMLElement)) continue + + // if we hit a clickable element or a disabled drag region, don't drag + if ( + isClickableElement(el) + || el.getAttribute(TAURI_DRAG_REGION_ATTR) === 'false' + ) { + return false + } + + const attr = el.getAttribute(TAURI_DRAG_REGION_ATTR) + if (attr !== null) { + // deep: the whole subtree is a drag region + if (attr === 'deep') return true + // bare (or any unrecognized value): self-only + if (el === composedPath[0]) return true + // click was on a child of a self-only region — stop walking, don't drag + return false + } + } + + return false + } + + const osName = __TEMPLATE_os_name__ + // initial mousedown position for macOS let initialX = 0 let initialY = 0 document.addEventListener('mousedown', (e) => { - const attr = e.target.getAttribute(TAURI_DRAG_REGION_ATTR) if ( - // element has the magic data attribute - attr !== null - // and not false - && attr !== 'false' - // and was left mouse button - && e.button === 0 + // was left mouse button + e.button === 0 // and was normal click to drag or double click to maximize && (e.detail === 1 || e.detail === 2) + // and is drag region + && isDragRegion(e.composedPath()) ) { // macOS maximization happens on `mouseup`, // so we save needed state and early return @@ -48,23 +96,21 @@ window.__TAURI_INTERNALS__.invoke('plugin:window|' + cmd) } }) + // on macOS we maximize on mouseup instead, to match the system behavior where maximization can be canceled // if the mouse moves outside the data-tauri-drag-region if (osName === 'macos') { document.addEventListener('mouseup', (e) => { - const attr = e.target.getAttribute(TAURI_DRAG_REGION_ATTR) if ( - // element has the magic data attribute - attr !== null - // and not false - && attr !== 'false' - // and was left mouse button - && e.button === 0 + // was left mouse button + e.button === 0 // and was double click && e.detail === 2 // and the cursor hasn't moved from initial mousedown && e.clientX === initialX && e.clientY === initialY + // and the event path contains a drag region (with no clickable element in between) + && isDragRegion(e.composedPath()) ) { window.__TAURI_INTERNALS__.invoke( 'plugin:window|internal_toggle_maximize' From 8ec47f966caebc0cce336369942706ca53633a1e Mon Sep 17 00:00:00 2001 From: Lucas Nogueira Date: Tue, 10 Mar 2026 14:39:01 -0300 Subject: [PATCH 37/95] fix: drag.js generated CSP regression from #15062 --- crates/tauri/src/window/scripts/drag.js | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/crates/tauri/src/window/scripts/drag.js b/crates/tauri/src/window/scripts/drag.js index b22d46f20faa..2b533549a895 100644 --- a/crates/tauri/src/window/scripts/drag.js +++ b/crates/tauri/src/window/scripts/drag.js @@ -32,9 +32,9 @@ // Otherwise return true. // // Supported values for data-tauri-drag-region: - // (bare / no value) → self: only direct clicks on this element trigger drag - // "deep" → deep: clicks anywhere in the subtree trigger drag - // "false" → disabled: drag is blocked here (and for ancestors) + // (bare / no value) -> self: only direct clicks on this element trigger drag + // "deep" -> deep: clicks anywhere in the subtree trigger drag + // "false" -> disabled: drag is blocked here (and for ancestors) function isDragRegion(composedPath) { for (const el of composedPath) { if (!(el instanceof HTMLElement)) continue @@ -53,7 +53,7 @@ if (attr === 'deep') return true // bare (or any unrecognized value): self-only if (el === composedPath[0]) return true - // click was on a child of a self-only region — stop walking, don't drag + // click was on a child of a self-only region - stop walking, don't drag return false } } From 5b0b9b747544d666dd449f081065f572009f7921 Mon Sep 17 00:00:00 2001 From: Eden Lundie Date: Thu, 12 Mar 2026 15:27:49 +0000 Subject: [PATCH 38/95] fix(ios): fix deadlock during Swift plugin command handling (#15101) --- crates/tauri/src/plugin/mobile.rs | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/crates/tauri/src/plugin/mobile.rs b/crates/tauri/src/plugin/mobile.rs index 64aff828f4d7..8aae62980143 100644 --- a/crates/tauri/src/plugin/mobile.rs +++ b/crates/tauri/src/plugin/mobile.rs @@ -373,12 +373,12 @@ pub(crate) fn run_command, F: FnOnce(PluginResponse) + CStr::from_ptr(payload) }; - if let Some(handler) = PENDING_PLUGIN_CALLS + let handler = PENDING_PLUGIN_CALLS .get_or_init(Default::default) .lock() .unwrap() - .remove(&id) - { + .remove(&id); + if let Some(handler) = handler { let json = payload.to_str().unwrap(); match serde_json::from_str(json) { Ok(payload) => { From 103f3d6cae5d74f51cabe820e3b5e8a7cac08843 Mon Sep 17 00:00:00 2001 From: Shaun Hamilton Date: Thu, 12 Mar 2026 23:36:04 +0200 Subject: [PATCH 39/95] fix(bundler): set linuxdeploy arch to i386 (#15102) Co-authored-by: Fabian-Lars <30730186+FabianLars@users.noreply.github.com> --- .changes/linux-deploy-link.md | 5 +++++ .../tauri-bundler/src/bundle/linux/appimage/linuxdeploy.rs | 2 +- 2 files changed, 6 insertions(+), 1 deletion(-) create mode 100644 .changes/linux-deploy-link.md diff --git a/.changes/linux-deploy-link.md b/.changes/linux-deploy-link.md new file mode 100644 index 000000000000..c3c3486871f5 --- /dev/null +++ b/.changes/linux-deploy-link.md @@ -0,0 +1,5 @@ +--- +"tauri-bundler": patch:bug +--- + +Correct GitHub Release URL path for Linux i686 tooling. diff --git a/crates/tauri-bundler/src/bundle/linux/appimage/linuxdeploy.rs b/crates/tauri-bundler/src/bundle/linux/appimage/linuxdeploy.rs index dccc3b5a2df6..cbc86ec21f6d 100644 --- a/crates/tauri-bundler/src/bundle/linux/appimage/linuxdeploy.rs +++ b/crates/tauri-bundler/src/bundle/linux/appimage/linuxdeploy.rs @@ -232,7 +232,7 @@ fn prepare_tools(tools_path: &Path, arch: &str, verbose: bool) -> crate::Result< write_and_make_executable(&apprun, data)?; } - let linuxdeploy_arch = if arch == "i686" { "i383" } else { arch }; + let linuxdeploy_arch = if arch == "i686" { "i386" } else { arch }; let linuxdeploy = tools_path.join(format!("linuxdeploy-{linuxdeploy_arch}.AppImage")); if !linuxdeploy.exists() { let data = download(&format!("https://github.com/tauri-apps/binary-releases/releases/download/linuxdeploy/linuxdeploy-{linuxdeploy_arch}.AppImage"))?; From 8ee913a4994b4ad594f4d8536ea2f5cee71d3fca Mon Sep 17 00:00:00 2001 From: Tony <68118705+Legend-Master@users.noreply.github.com> Date: Fri, 13 Mar 2026 19:25:29 +0800 Subject: [PATCH 40/95] ci: fix duplicated audit runs (#15104) --- .github/workflows/audit.yml | 2 ++ 1 file changed, 2 insertions(+) diff --git a/.github/workflows/audit.yml b/.github/workflows/audit.yml index d840272be8bd..157717061338 100644 --- a/.github/workflows/audit.yml +++ b/.github/workflows/audit.yml @@ -16,6 +16,8 @@ on: - '**/package.json' - '**/pnpm-lock.yaml' push: + branches: + - dev paths: - '.github/workflows/audit.yml' - '**/Cargo.lock' From 4b878cd50b96f195c266ab6f6cff43331608c9c5 Mon Sep 17 00:00:00 2001 From: "renovate[bot]" <29139614+renovate[bot]@users.noreply.github.com> Date: Fri, 13 Mar 2026 20:03:56 +0800 Subject: [PATCH 41/95] chore(deps): update dependency vite to v8 and @sveltejs/vite-plugin-svelte to v7 (#15103) * chore(deps): update dependency @sveltejs/vite-plugin-svelte to v7 * Update vite to v8 * Update devalue --------- Co-authored-by: renovate[bot] <29139614+renovate[bot]@users.noreply.github.com> Co-authored-by: Tony Co-authored-by: Tony <68118705+Legend-Master@users.noreply.github.com> --- .../__example-api/tauri-app/package.json | 4 +- examples/api/package.json | 12 +- pnpm-lock.yaml | 716 +++++++++++++----- 3 files changed, 536 insertions(+), 196 deletions(-) diff --git a/crates/tauri-cli/templates/plugin/__example-api/tauri-app/package.json b/crates/tauri-cli/templates/plugin/__example-api/tauri-app/package.json index 6217d62bd8e5..c660a10807c1 100644 --- a/crates/tauri-cli/templates/plugin/__example-api/tauri-app/package.json +++ b/crates/tauri-cli/templates/plugin/__example-api/tauri-app/package.json @@ -14,9 +14,9 @@ "tauri-plugin-{{ plugin_name }}-api": "file:../../" }, "devDependencies": { - "@sveltejs/vite-plugin-svelte": "^6.0.0", + "@sveltejs/vite-plugin-svelte": "^7.0.0", "svelte": "^5.0.0", - "vite": "^7.0.0", + "vite": "^8.0.0", "@tauri-apps/cli": "^2.0.0" } } diff --git a/examples/api/package.json b/examples/api/package.json index 84db2ff41f82..55f43f5df387 100644 --- a/examples/api/package.json +++ b/examples/api/package.json @@ -13,12 +13,12 @@ "@tauri-apps/api": "../../packages/api/dist" }, "devDependencies": { - "@iconify-json/codicon": "^1.2.47", + "@iconify-json/codicon": "^1.2.49", "@iconify-json/ph": "^1.2.2", - "@sveltejs/vite-plugin-svelte": "^6.2.4", - "@unocss/extractor-svelte": "^66.6.5", - "svelte": "^5.53.7", - "unocss": "^66.6.5", - "vite": "^7.3.1" + "@sveltejs/vite-plugin-svelte": "^7.0.0", + "@unocss/extractor-svelte": "^66.6.6", + "svelte": "^5.53.11", + "unocss": "^66.6.6", + "vite": "^8.0.0" } } diff --git a/pnpm-lock.yaml b/pnpm-lock.yaml index 34c0a30cfa71..92d25f0788b9 100644 --- a/pnpm-lock.yaml +++ b/pnpm-lock.yaml @@ -25,26 +25,26 @@ importers: version: link:../../packages/api/dist devDependencies: '@iconify-json/codicon': - specifier: ^1.2.47 - version: 1.2.47 + specifier: ^1.2.49 + version: 1.2.49 '@iconify-json/ph': specifier: ^1.2.2 version: 1.2.2 '@sveltejs/vite-plugin-svelte': - specifier: ^6.2.4 - version: 6.2.4(svelte@5.53.7)(vite@7.3.1(@types/node@24.11.0)(jiti@2.6.1)(terser@5.46.0)) + specifier: ^7.0.0 + version: 7.0.0(svelte@5.53.11)(vite@8.0.0(@types/node@24.11.0)(esbuild@0.27.3)(jiti@2.6.1)(terser@5.46.0)) '@unocss/extractor-svelte': - specifier: ^66.6.5 - version: 66.6.5 + specifier: ^66.6.6 + version: 66.6.6 svelte: - specifier: ^5.53.7 - version: 5.53.7 + specifier: ^5.53.11 + version: 5.53.11 unocss: - specifier: ^66.6.5 - version: 66.6.5(vite@7.3.1(@types/node@24.11.0)(jiti@2.6.1)(terser@5.46.0)) + specifier: ^66.6.6 + version: 66.6.6(vite@8.0.0(@types/node@24.11.0)(esbuild@0.27.3)(jiti@2.6.1)(terser@5.46.0)) vite: - specifier: ^7.3.1 - version: 7.3.1(@types/node@24.11.0)(jiti@2.6.1)(terser@5.46.0) + specifier: ^8.0.0 + version: 8.0.0(@types/node@24.11.0)(esbuild@0.27.3)(jiti@2.6.1)(terser@5.46.0) examples/file-associations: {} @@ -108,7 +108,7 @@ importers: version: 10.1.0 vitest: specifier: ^4.0.18 - version: 4.0.18(@types/node@24.11.0)(jiti@2.6.1)(terser@5.46.0) + version: 4.0.18(@types/node@24.11.0)(jiti@2.6.1)(lightningcss@1.32.0)(terser@5.46.0) packages: @@ -385,8 +385,8 @@ packages: resolution: {integrity: sha512-bV0Tgo9K4hfPCek+aMAn81RppFKv2ySDQeMoSZuvTASywNTnVJCArCZE2FWqpvIatKu7VMRLWlR1EazvVhDyhQ==} engines: {node: '>=18.18'} - '@iconify-json/codicon@1.2.47': - resolution: {integrity: sha512-9z6Of5d3w8aJAv07IT2un0SgAmFZfXSCtG4LDqsf8b/yL4vBgQ6jaCVH6Y0mDegNZzLkJ+7ieIDfbZZlIXH7CA==} + '@iconify-json/codicon@1.2.49': + resolution: {integrity: sha512-Ljl9BWw7e8xYm0l5Npnj5/aN/lEFEQDfhl7UHspPYIlZgw3ZvPOvo0gAr78aorb6X1+LZJqI0BNFAgO5r2sjIQ==} '@iconify-json/ph@1.2.2': resolution: {integrity: sha512-PgkEZNtqa8hBGjHXQa4pMwZa93hmfu8FUSjs/nv4oUU6yLsgv+gh9nu28Kqi8Fz9CCVu4hj1MZs9/60J57IzFw==} @@ -1247,6 +1247,10 @@ packages: cpu: [x64] os: [win32] + '@oxc-project/runtime@0.115.0': + resolution: {integrity: sha512-Rg8Wlt5dCbXhQnsXPrkOjL1DTSvXLgb2R/KYfnf1/K+R0k6UMLEmbQXPM+kwrWqSmWA2t0B1EtHy2/3zikQpvQ==} + engines: {node: ^20.19.0 || >=22.12.0} + '@oxc-project/types@0.115.0': resolution: {integrity: sha512-4n91DKnebUS4yjUHl2g3/b2T+IUdCfmoZGhmwsovZCDaJSs+QkVAM+0AqqTxHSsHfeiMuueT75cZaZcT/m0pSw==} @@ -1265,6 +1269,104 @@ packages: '@quansync/fs@1.0.0': resolution: {integrity: sha512-4TJ3DFtlf1L5LDMaM6CanJ/0lckGNtJcMjQ1NAV6zDmA0tEHKZtxNKin8EgPaVX1YzljbxckyT2tJrpQKAtngQ==} + '@rolldown/binding-android-arm64@1.0.0-rc.9': + resolution: {integrity: sha512-lcJL0bN5hpgJfSIz/8PIf02irmyL43P+j1pTCfbD1DbLkmGRuFIA4DD3B3ZOvGqG0XiVvRznbKtN0COQVaKUTg==} + engines: {node: ^20.19.0 || >=22.12.0} + cpu: [arm64] + os: [android] + + '@rolldown/binding-darwin-arm64@1.0.0-rc.9': + resolution: {integrity: sha512-J7Zk3kLYFsLtuH6U+F4pS2sYVzac0qkjcO5QxHS7OS7yZu2LRs+IXo+uvJ/mvpyUljDJ3LROZPoQfgBIpCMhdQ==} + engines: {node: ^20.19.0 || >=22.12.0} + cpu: [arm64] + os: [darwin] + + '@rolldown/binding-darwin-x64@1.0.0-rc.9': + resolution: {integrity: sha512-iwtmmghy8nhfRGeNAIltcNXzD0QMNaaA5U/NyZc1Ia4bxrzFByNMDoppoC+hl7cDiUq5/1CnFthpT9n+UtfFyg==} + engines: {node: ^20.19.0 || >=22.12.0} + cpu: [x64] + os: [darwin] + + '@rolldown/binding-freebsd-x64@1.0.0-rc.9': + resolution: {integrity: sha512-DLFYI78SCiZr5VvdEplsVC2Vx53lnA4/Ga5C65iyldMVaErr86aiqCoNBLl92PXPfDtUYjUh+xFFor40ueNs4Q==} + engines: {node: ^20.19.0 || >=22.12.0} + cpu: [x64] + os: [freebsd] + + '@rolldown/binding-linux-arm-gnueabihf@1.0.0-rc.9': + resolution: {integrity: sha512-CsjTmTwd0Hri6iTw/DRMK7kOZ7FwAkrO4h8YWKoX/kcj833e4coqo2wzIFywtch/8Eb5enQ/lwLM7w6JX1W5RQ==} + engines: {node: ^20.19.0 || >=22.12.0} + cpu: [arm] + os: [linux] + + '@rolldown/binding-linux-arm64-gnu@1.0.0-rc.9': + resolution: {integrity: sha512-2x9O2JbSPxpxMDhP9Z74mahAStibTlrBMW0520+epJH5sac7/LwZW5Bmg/E6CXuEF53JJFW509uP+lSedaUNxg==} + engines: {node: ^20.19.0 || >=22.12.0} + cpu: [arm64] + os: [linux] + libc: [glibc] + + '@rolldown/binding-linux-arm64-musl@1.0.0-rc.9': + resolution: {integrity: sha512-JA1QRW31ogheAIRhIg9tjMfsYbglXXYGNPLdPEYrwFxdbkQCAzvpSCSHCDWNl4hTtrol8WeboCSEpjdZK8qrCg==} + engines: {node: ^20.19.0 || >=22.12.0} + cpu: [arm64] + os: [linux] + libc: [musl] + + '@rolldown/binding-linux-ppc64-gnu@1.0.0-rc.9': + resolution: {integrity: sha512-aOKU9dJheda8Kj8Y3w9gnt9QFOO+qKPAl8SWd7JPHP+Cu0EuDAE5wokQubLzIDQWg2myXq2XhTpOVS07qqvT+w==} + engines: {node: ^20.19.0 || >=22.12.0} + cpu: [ppc64] + os: [linux] + libc: [glibc] + + '@rolldown/binding-linux-s390x-gnu@1.0.0-rc.9': + resolution: {integrity: sha512-OalO94fqj7IWRn3VdXWty75jC5dk4C197AWEuMhIpvVv2lw9fiPhud0+bW2ctCxb3YoBZor71QHbY+9/WToadA==} + engines: {node: ^20.19.0 || >=22.12.0} + cpu: [s390x] + os: [linux] + libc: [glibc] + + '@rolldown/binding-linux-x64-gnu@1.0.0-rc.9': + resolution: {integrity: sha512-cVEl1vZtBsBZna3YMjGXNvnYYrOJ7RzuWvZU0ffvJUexWkukMaDuGhUXn0rjnV0ptzGVkvc+vW9Yqy6h8YX4pg==} + engines: {node: ^20.19.0 || >=22.12.0} + cpu: [x64] + os: [linux] + libc: [glibc] + + '@rolldown/binding-linux-x64-musl@1.0.0-rc.9': + resolution: {integrity: sha512-UzYnKCIIc4heAKgI4PZ3dfBGUZefGCJ1TPDuLHoCzgrMYPb5Rv6TLFuYtyM4rWyHM7hymNdsg5ik2C+UD9VDbA==} + engines: {node: ^20.19.0 || >=22.12.0} + cpu: [x64] + os: [linux] + libc: [musl] + + '@rolldown/binding-openharmony-arm64@1.0.0-rc.9': + resolution: {integrity: sha512-+6zoiF+RRyf5cdlFQP7nm58mq7+/2PFaY2DNQeD4B87N36JzfF/l9mdBkkmTvSYcYPE8tMh/o3cRlsx1ldLfog==} + engines: {node: ^20.19.0 || >=22.12.0} + cpu: [arm64] + os: [openharmony] + + '@rolldown/binding-wasm32-wasi@1.0.0-rc.9': + resolution: {integrity: sha512-rgFN6sA/dyebil3YTlL2evvi/M+ivhfnyxec7AccTpRPccno/rPoNlqybEZQBkcbZu8Hy+eqNJCqfBR8P7Pg8g==} + engines: {node: '>=14.0.0'} + cpu: [wasm32] + + '@rolldown/binding-win32-arm64-msvc@1.0.0-rc.9': + resolution: {integrity: sha512-lHVNUG/8nlF1IQk1C0Ci574qKYyty2goMiPlRqkC5R+3LkXDkL5Dhx8ytbxq35m+pkHVIvIxviD+TWLdfeuadA==} + engines: {node: ^20.19.0 || >=22.12.0} + cpu: [arm64] + os: [win32] + + '@rolldown/binding-win32-x64-msvc@1.0.0-rc.9': + resolution: {integrity: sha512-G0oA4+w1iY5AGi5HcDTxWsoxF509hrFIPB2rduV5aDqS9FtDg1CAfa7V34qImbjfhIcA8C+RekocJZA96EarwQ==} + engines: {node: ^20.19.0 || >=22.12.0} + cpu: [x64] + os: [win32] + + '@rolldown/pluginutils@1.0.0-rc.9': + resolution: {integrity: sha512-w6oiRWgEBl04QkFZgmW+jnU1EC9b57Oihi2ot3HNWIQRqgHp5PnYDia5iZ5FF7rpa4EQdiqMDXjlqKGXBhsoXw==} + '@rollup/plugin-terser@1.0.0': resolution: {integrity: sha512-FnCxhTBx6bMOYQrar6C8h3scPt8/JwIzw3+AJ2K++6guogH5fYaIFia+zZuhqv0eo1RN7W1Pz630SyvLbDjhtQ==} engines: {node: '>=20.0.0'} @@ -1449,20 +1551,12 @@ packages: peerDependencies: acorn: ^8.9.0 - '@sveltejs/vite-plugin-svelte-inspector@5.0.2': - resolution: {integrity: sha512-TZzRTcEtZffICSAoZGkPSl6Etsj2torOVrx6Uw0KpXxrec9Gg6jFWQ60Q3+LmNGfZSxHRCZL7vXVZIWmuV50Ig==} + '@sveltejs/vite-plugin-svelte@7.0.0': + resolution: {integrity: sha512-ILXmxC7HAsnkK2eslgPetrqqW1BKSL7LktsFgqzNj83MaivMGZzluWq32m25j2mDOjmSKX7GGWahePhuEs7P/g==} engines: {node: ^20.19 || ^22.12 || >=24} peerDependencies: - '@sveltejs/vite-plugin-svelte': ^6.0.0-next.0 - svelte: ^5.0.0 - vite: ^6.3.0 || ^7.0.0 - - '@sveltejs/vite-plugin-svelte@6.2.4': - resolution: {integrity: sha512-ou/d51QSdTyN26D7h6dSpusAKaZkAiGM55/AKYi+9AGZw7q85hElbjK3kEyzXHhLSnRISHOYzVge6x0jRZ7DXA==} - engines: {node: ^20.19 || ^22.12 || >=24} - peerDependencies: - svelte: ^5.0.0 - vite: ^6.3.0 || ^7.0.0 + svelte: ^5.46.4 + vite: ^8.0.0-beta.7 || ^8.0.0 '@tybys/wasm-util@0.10.1': resolution: {integrity: sha512-9tTaPJLSiejZKx+Bmog4uSubteqTvFrVrURwkmHixBo0G4seD0zUxp98E1DzUBJxLQ3NPwXrGKDiVjwx/DpPsg==} @@ -1550,78 +1644,75 @@ packages: resolution: {integrity: sha512-KiROIzYdEV85YygXw6BI/Dx4fnBlFQu6Mq4QE4MOH9fFnhohw6wX/OAvDY2/C+ut0I3RSPKenvZJIVYqJNkhEw==} engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0} - '@unocss/cli@66.6.5': - resolution: {integrity: sha512-UlETATpAZ+A5gOfj+z+BMXuIUcXCMjvlQteQE0VR2Yf0VIxz4sVO4z0VCXwXsxLTMfQiIMDpKVrGeczcYicvTA==} + '@unocss/cli@66.6.6': + resolution: {integrity: sha512-78SY8j4hAVelK+vP/adsDGaSjEITasYLFECJLHWxUJSzK+G9UIc5wtL/u4jA+zKvwVkHcDvbkcO5K6wwwpAixg==} engines: {node: '>=14'} hasBin: true - '@unocss/config@66.6.4': - resolution: {integrity: sha512-iwHl5FG81cOAMalqigjw21Z2tMa0xjN0doQxnGOLx8KP+BllruXSjBj8CRk3m6Ny9fDxfpFY0ruYbIBA5AGwDQ==} + '@unocss/config@66.6.6': + resolution: {integrity: sha512-menlnkqAFX/4wR2aandY8hSqrt01JE+rOzvtQxWaBt8kf1du62b0sS72FE5Z40n6HlEsEbF91N9FCfhnzG6i6g==} engines: {node: '>=14'} - '@unocss/core@66.6.4': - resolution: {integrity: sha512-Fii3lhVJVFrKUz6hMGAkq3sXBfNnXB2G8bldNHuBHJpDAoP1F0oO/SU/oSqSjCYvtcD5RtOn8qwzcHuuN3B/mg==} - - '@unocss/core@66.6.5': - resolution: {integrity: sha512-hzjo+0EF+pNbf+tb0OjRNZRF9BJoKECcZZgtufxRPpWJdlv+aYmNkH1p9fldlHHzYcn3ZqVnnHnmk7HwaolJbg==} + '@unocss/core@66.6.6': + resolution: {integrity: sha512-Sbbx0ZQqmV8K2lg8E+z9MJzWb1MgRtJnvqzxDIrNuBjXasKhbcFt5wEMBtEZJOr63Z4ck0xThhZK53HmYT2jmg==} - '@unocss/extractor-arbitrary-variants@66.6.5': - resolution: {integrity: sha512-wqzRtbyy3I595WCwwb8VBmznJTHWcTdylzVT+WBgacJDjRlT1sXaq2fRlOsHvtTRj1qG70t3PwKc6XgU0hutNg==} + '@unocss/extractor-arbitrary-variants@66.6.6': + resolution: {integrity: sha512-uMzekF2miZRUwSZGvy3yYQiBAcSAs9LiXK8e3NjldxEw8xcRDWgTErxgStRoBeAD6UyzDcg/Cvwtf2guMbtR+g==} - '@unocss/extractor-svelte@66.6.5': - resolution: {integrity: sha512-Zg58V3L5jxSPzT2BEZY87+WH0gVMI4VKZuwNwFS3ht83RsCD32eGjJxrk6w5CuIYDV6MeGSkosyPIwLY+OFD3w==} + '@unocss/extractor-svelte@66.6.6': + resolution: {integrity: sha512-5+Et3jiSFlMqxkoyVLsoT2/Rd8x/Jd65i5KzIyXMtQccDmqN2wSXuyvB2h5sLauHn4bBe/qOWO3PfGjbXBGWOA==} - '@unocss/inspector@66.6.5': - resolution: {integrity: sha512-rrXPlSeRfYajEL65FL1Ok9Hfhjy9zvuZZwqXh9P0qCJlou2r2IqDFO/Gf9j5yO89tnKIfJ8ff6jEyqUmzbKSMQ==} + '@unocss/inspector@66.6.6': + resolution: {integrity: sha512-CpXIsqHwxCXJtUjUz6S29diHCIA+EJ1u5WML/6m2YPI4ObgWAVKrExy09inSg2icS52lFkWWdWQSeqc9kl5W6Q==} - '@unocss/preset-attributify@66.6.5': - resolution: {integrity: sha512-fx+pKMZ0WgT+dfinVaLkNXlx6oZFwtMbZj5O/1SQia0UcfhnyS+G35HYpbgoc9GEAl3DclxxotzZjveZm++9fA==} + '@unocss/preset-attributify@66.6.6': + resolution: {integrity: sha512-3H12UI1rBt60PQy+S4IEeFYWu1/WQFuc2yhJ5mu/RCvX5/qwlIGanBpuh+xzTPXU1fWBlZN68yyO9uWOQgTqZQ==} - '@unocss/preset-icons@66.6.5': - resolution: {integrity: sha512-03ppAcTWD77w1WZhORT8c9beTHBtWu3cx+c4qfShOfY6LQmZgx5i7DhCij5Wcj/U1zYA4Vrh13CDEmpsdZO3Cw==} + '@unocss/preset-icons@66.6.6': + resolution: {integrity: sha512-HfIEEqf3jyKexOB2Sux556n0NkPoUftb2H4+Cf7prJvKHopMkZ/OUkXjwvUlxt1e5UpAEaIa0A2Ir7+ApxXoGA==} - '@unocss/preset-mini@66.6.5': - resolution: {integrity: sha512-Ber3k2jlE8JP0y507hw/lvdDvcxfY0t4zaGA7hVZdEqlH6Eus/TqIVZ9tdMH4u0VDWYeAs98YV+auUJmMqGXpg==} + '@unocss/preset-mini@66.6.6': + resolution: {integrity: sha512-k+/95PKMPOK57cJcSmz34VkIFem8BlujRRx6/L0Yusw7vLJMh98k0rPhC5s+NomZ/d9ZPgbNylskLhItJlak3w==} - '@unocss/preset-tagify@66.6.5': - resolution: {integrity: sha512-YYk/eg1OWX4Nx7rK1YZLMHXXntzNRDHp6BIInJteQmlXw0sFgrtdMKj7fnxrORsBDHwxWMp4sWEucPvfCtTlVQ==} + '@unocss/preset-tagify@66.6.6': + resolution: {integrity: sha512-KgBXYPYS0g4TVC3NLiIB78YIqUlvDLanz1EHIDo34rOTUfMgY8Uf5VuDJAzMu4Sc0LiwwBJbk6nIG9/Zm7ufWg==} - '@unocss/preset-typography@66.6.5': - resolution: {integrity: sha512-Cb63tdC0P2rgj/4t4DrSCl6RHebNpjUp9FQArg0KCnFnW75nWtKlsKpHuEXpi7KwrgOIx+rjlkwC1bDcsdNLHw==} + '@unocss/preset-typography@66.6.6': + resolution: {integrity: sha512-SM1km5nqt15z4sTabfOobSC633I5Ol5nnme6JFTra4wiyCUNs+Cg31nJ6jnopWDUT4SEAXqfUH7jKSSoCnI6ZA==} - '@unocss/preset-uno@66.6.5': - resolution: {integrity: sha512-feZfGyzt3dH4h6yP2kjsx5MuoI1gU7vY/VL5O+ObosaB7HzzOFCsu2WzlvWn/FTRBi+scvdq436hsfflVyHYfQ==} + '@unocss/preset-uno@66.6.6': + resolution: {integrity: sha512-40PcBDtlhW7QP7e/WOxC684IhN5T1dXvj1dgx9ZzK+8lEDGjcX7bN2noW4aSenzSrHymeSsMrL/0ltL4ED/5Zw==} - '@unocss/preset-web-fonts@66.6.5': - resolution: {integrity: sha512-u5jEHYTMeseykqinXd2VY2n7q9yFQlZotREpfSAft8ENNJdV7Yg/6It3lL68zT/k1AV/A8gk94KEuDh0fnoSxQ==} + '@unocss/preset-web-fonts@66.6.6': + resolution: {integrity: sha512-5ikwgrJB8VPzKd0bqgGNgYUGix90KFnVtKJPjWTP5qsv3+ZtZnea1rRbAFl8i2t52hg35msNBsQo+40IC3xB6A==} - '@unocss/preset-wind3@66.6.5': - resolution: {integrity: sha512-0ccQoJmHq4tTnn5C0UKhP598B/gG65AjqlfgfRpwt059yAWYqizGy6MRUGdLklyEK4H06E6qbMBqIjla2rOexQ==} + '@unocss/preset-wind3@66.6.6': + resolution: {integrity: sha512-rk6gPPIQ7z2DVucOqp7XZ4vGpKAuzBV1vtUDvDh5WscxzO/QlqaeTfTALk5YgGpmLaF4+ns6FrTgLjV+wHgHuQ==} - '@unocss/preset-wind4@66.6.5': - resolution: {integrity: sha512-JT57CU60PY3/PHBvxY+UG53I9K+awin/TodZTn4lqQNnF2v6fjkeBKiys9cxeoP4wbHuQWorrW4GqRLNDWIMcw==} + '@unocss/preset-wind4@66.6.6': + resolution: {integrity: sha512-caTDM9rZSlp4tyPWWAnwMvQr2PXq53LsEYwd3N8zj0ou2hcsqptJvF+mFvyhvGF66x26wWJr/FwuUEhh7qycaw==} - '@unocss/preset-wind@66.6.5': - resolution: {integrity: sha512-GLu7LzVF0LHqdZoHFZ8dbsCv8TD5ZH/r10CQbrL5qwmp4a/uyfDEmsre4Nsqim7JktRyXn3HK2XQmTB8AmXpgQ==} + '@unocss/preset-wind@66.6.6': + resolution: {integrity: sha512-TMy3lZ35FP/4QqDHOLWZmV+RoOGWUDqnDEOTjOKI1CQARGta0ppUmq+IZMuI1ZJLuOa4OZ9V6SfnwMXwRLgXmw==} - '@unocss/rule-utils@66.6.5': - resolution: {integrity: sha512-eDGXoMebb5aeEAFa2y4gnGLC+CHZPx93JYCt6uvEyf9xOoetwDcZaYC8brWdjaSKn+WVgsfxiZreC7F0rJywOQ==} + '@unocss/rule-utils@66.6.6': + resolution: {integrity: sha512-krWtQKGshOaqQMuxeGq1NOA8NL35VdpYlmQEWOe39BY6TACT51bgQFu40MRfsAIMZZtoGS2YYTrnHojgR92omw==} engines: {node: '>=14'} - '@unocss/transformer-attributify-jsx@66.6.5': - resolution: {integrity: sha512-/dVaRR7V/2Alskb2rUPmP/lhyb/YCxYyYNxp30kxxW0ew6mZWXQRzsxOJJVmGp23Uw7HxUW63t8zXzUdoI0b+g==} + '@unocss/transformer-attributify-jsx@66.6.6': + resolution: {integrity: sha512-NnDchmN2EeFLy4lfVqDgNe9j1+w2RLL2L9zKECXs5g6rDVfeeEK6FNgxSq3XnPcKltjNCy1pF4MaDOROG7r8yA==} - '@unocss/transformer-compile-class@66.6.5': - resolution: {integrity: sha512-U/ukk5lyZOFNyz9hVzZBkxciayjgimyfPuQBa5PHSC4W3nDmnFd1zgXzUVaM6KduPmiTExzpJSDgELb2OTbpqg==} + '@unocss/transformer-compile-class@66.6.6': + resolution: {integrity: sha512-KKssJxU8fZ9x84yznIirbtta2sB0LN/3lm0bp+Wl1298HITaNiVeG2n26iStQ3N7r240xRN2RarxncSVCMFwWw==} - '@unocss/transformer-directives@66.6.5': - resolution: {integrity: sha512-QgofDdDedNK6dQ246+RXhM6gTzRz7NuetQQ8UnNgArm4PBHngVrrkjCzG1ByDTtEtoE8WR70UMR4Vf5dXTcHPw==} + '@unocss/transformer-directives@66.6.6': + resolution: {integrity: sha512-CReFTcBfMtKkRvzIqxL20VptWt5C1Om27dwoKzyVFBXv0jzViWysbu0y0AQg3bsgD4cFqndFyAGyeL84j0nbKg==} - '@unocss/transformer-variant-group@66.6.5': - resolution: {integrity: sha512-k6vQgn/P7ObHBRYw6o1+xwdQIfwc6b9O5TFFe87UmBB6hJ2zaHWRVuPB6oky7F9Gz8bPfXC3WJuv7UyIwRmBQQ==} + '@unocss/transformer-variant-group@66.6.6': + resolution: {integrity: sha512-j4L/0Tw6AdMVB2dDnuBlDbevyL1/0CAk88a77VF/VjgEIBwB9VXsCCUsxz+2Dohcl7N2GMm7+kpaWA6qt2PSaA==} - '@unocss/vite@66.6.5': - resolution: {integrity: sha512-J/QZa6h94ordZlZytIKQkuYa+G2GiWiS3y9O1uoHAAN2tzFSkgCXNUif7lHu1h4eCrgC0AOHJSYWg1LIASNDkg==} + '@unocss/vite@66.6.6': + resolution: {integrity: sha512-DgG7KcUUMtoDhPOlFf2l4dR+66xZ23SdZvTYpikk5nZfLCzZd62vedutD7x0bTR6VpK2YRq39B+F+Z6TktNY/w==} peerDependencies: vite: ^2.9.0 || ^3.0.0-0 || ^4.0.0 || ^5.0.0-0 || ^6.0.0-0 || ^7.0.0-0 || ^8.0.0-0 @@ -1787,8 +1878,8 @@ packages: resolution: {integrity: sha512-Btj2BOOO83o3WyH59e8MgXsxEQVcarkUOpEYrubB0urwnN10yQ364rsiByU11nZlqWYZm05i/of7io4mzihBtQ==} engines: {node: '>=8'} - devalue@5.6.3: - resolution: {integrity: sha512-nc7XjUU/2Lb+SvEFVGcWLiKkzfw8+qHI7zn8WYXKkLMgfGSHbgCEaR6bJpev8Cm6Rmrb19Gfd/tZvGqx9is3wg==} + devalue@5.6.4: + resolution: {integrity: sha512-Gp6rDldRsFh/7XuouDbxMH3Mx8GMCcgzIb1pDTvNyn8pZGQ22u+Wa+lGV9dQCltFQ7uVw0MhRyb8XDskNFOReA==} duplexer@0.1.2: resolution: {integrity: sha512-jtD6YG370ZCIi/9GTaJKQxWTZD045+4R4hTk/x1UyoqadyJ9x9CgSi1RlVDQF8U2sxLLSnFkCaMihqljHIWgMg==} @@ -2040,6 +2131,80 @@ packages: resolution: {integrity: sha512-+bT2uH4E5LGE7h/n3evcS/sQlJXCpIp6ym8OWJ5eV6+67Dsql/LaaT7qJBAt2rzfoa/5QBGBhxDix1dMt2kQKQ==} engines: {node: '>= 0.8.0'} + lightningcss-android-arm64@1.32.0: + resolution: {integrity: sha512-YK7/ClTt4kAK0vo6w3X+Pnm0D2cf2vPHbhOXdoNti1Ga0al1P4TBZhwjATvjNwLEBCnKvjJc2jQgHXH0NEwlAg==} + engines: {node: '>= 12.0.0'} + cpu: [arm64] + os: [android] + + lightningcss-darwin-arm64@1.32.0: + resolution: {integrity: sha512-RzeG9Ju5bag2Bv1/lwlVJvBE3q6TtXskdZLLCyfg5pt+HLz9BqlICO7LZM7VHNTTn/5PRhHFBSjk5lc4cmscPQ==} + engines: {node: '>= 12.0.0'} + cpu: [arm64] + os: [darwin] + + lightningcss-darwin-x64@1.32.0: + resolution: {integrity: sha512-U+QsBp2m/s2wqpUYT/6wnlagdZbtZdndSmut/NJqlCcMLTWp5muCrID+K5UJ6jqD2BFshejCYXniPDbNh73V8w==} + engines: {node: '>= 12.0.0'} + cpu: [x64] + os: [darwin] + + lightningcss-freebsd-x64@1.32.0: + resolution: {integrity: sha512-JCTigedEksZk3tHTTthnMdVfGf61Fky8Ji2E4YjUTEQX14xiy/lTzXnu1vwiZe3bYe0q+SpsSH/CTeDXK6WHig==} + engines: {node: '>= 12.0.0'} + cpu: [x64] + os: [freebsd] + + lightningcss-linux-arm-gnueabihf@1.32.0: + resolution: {integrity: sha512-x6rnnpRa2GL0zQOkt6rts3YDPzduLpWvwAF6EMhXFVZXD4tPrBkEFqzGowzCsIWsPjqSK+tyNEODUBXeeVHSkw==} + engines: {node: '>= 12.0.0'} + cpu: [arm] + os: [linux] + + lightningcss-linux-arm64-gnu@1.32.0: + resolution: {integrity: sha512-0nnMyoyOLRJXfbMOilaSRcLH3Jw5z9HDNGfT/gwCPgaDjnx0i8w7vBzFLFR1f6CMLKF8gVbebmkUN3fa/kQJpQ==} + engines: {node: '>= 12.0.0'} + cpu: [arm64] + os: [linux] + libc: [glibc] + + lightningcss-linux-arm64-musl@1.32.0: + resolution: {integrity: sha512-UpQkoenr4UJEzgVIYpI80lDFvRmPVg6oqboNHfoH4CQIfNA+HOrZ7Mo7KZP02dC6LjghPQJeBsvXhJod/wnIBg==} + engines: {node: '>= 12.0.0'} + cpu: [arm64] + os: [linux] + libc: [musl] + + lightningcss-linux-x64-gnu@1.32.0: + resolution: {integrity: sha512-V7Qr52IhZmdKPVr+Vtw8o+WLsQJYCTd8loIfpDaMRWGUZfBOYEJeyJIkqGIDMZPwPx24pUMfwSxxI8phr/MbOA==} + engines: {node: '>= 12.0.0'} + cpu: [x64] + os: [linux] + libc: [glibc] + + lightningcss-linux-x64-musl@1.32.0: + resolution: {integrity: sha512-bYcLp+Vb0awsiXg/80uCRezCYHNg1/l3mt0gzHnWV9XP1W5sKa5/TCdGWaR/zBM2PeF/HbsQv/j2URNOiVuxWg==} + engines: {node: '>= 12.0.0'} + cpu: [x64] + os: [linux] + libc: [musl] + + lightningcss-win32-arm64-msvc@1.32.0: + resolution: {integrity: sha512-8SbC8BR40pS6baCM8sbtYDSwEVQd4JlFTOlaD3gWGHfThTcABnNDBda6eTZeqbofalIJhFx0qKzgHJmcPTnGdw==} + engines: {node: '>= 12.0.0'} + cpu: [arm64] + os: [win32] + + lightningcss-win32-x64-msvc@1.32.0: + resolution: {integrity: sha512-Amq9B/SoZYdDi1kFrojnoqPLxYhQ4Wo5XiL8EVJrVsB8ARoC1PWW6VGtT0WKCemjy8aC+louJnjS7U18x3b06Q==} + engines: {node: '>= 12.0.0'} + cpu: [x64] + os: [win32] + + lightningcss@1.32.0: + resolution: {integrity: sha512-NXYBzinNrblfraPGyrbPoD19C1h9lfI/1mzgWYvXUTe414Gz/X1FD2XBZSZM7rRTrMA8JL3OtAaGifrIKhQ5yQ==} + engines: {node: '>= 12.0.0'} + locate-character@3.0.0: resolution: {integrity: sha512-SW13ws7BjaeJ6p7Q6CO2nchbYEc3X3J6WrmTTDto7yMPqVSZTUyY5Tjbid+Ab8gLnATtygYtiDIJGQRRn2ZOiA==} @@ -2202,6 +2367,11 @@ packages: resolution: {integrity: sha512-g6QUff04oZpHs0eG5p83rFLhHeV00ug/Yf9nZM6fLeUrPguBTkTQOdpAWWspMh55TZfVQDPaN3NQJfbVRAxdIw==} engines: {iojs: '>=1.0.0', node: '>=0.10.0'} + rolldown@1.0.0-rc.9: + resolution: {integrity: sha512-9EbgWge7ZH+yqb4d2EnELAntgPTWbfL8ajiTW+SyhJEC4qhBbkCKbqFV4Ge4zmu5ziQuVbWxb/XwLZ+RIO7E8Q==} + engines: {node: ^20.19.0 || >=22.12.0} + hasBin: true + rollup@4.59.0: resolution: {integrity: sha512-2oMpl67a3zCH9H79LeMcbDhXW/UmWG/y2zuqnF2jQq5uq9TbM9TVyXvA4+t+ne2IIkBdrLpAaRQAvo7YI/Yyeg==} engines: {node: '>=18.0.0', npm: '>=8.0.0'} @@ -2277,8 +2447,8 @@ packages: resolution: {integrity: sha512-ot0WnXS9fgdkgIcePe6RHNk1WA8+muPa6cSjeR3V8K27q9BB1rTE3R1p7Hv0z1ZyAc8s6Vvv8DIyWf681MAt0w==} engines: {node: '>= 0.4'} - svelte@5.53.7: - resolution: {integrity: sha512-uxck1KI7JWtlfP3H6HOWi/94soAl23jsGJkBzN2BAWcQng0+lTrRNhxActFqORgnO9BHVd1hKJhG+ljRuIUWfQ==} + svelte@5.53.11: + resolution: {integrity: sha512-GYmqRjRhJYLQBonfdfGAt28gkfWEShrtXKGXcFGneXi502aBE+I1dJcs/YQriByvP6xqXRz/OdBGC6tfvUQHyQ==} engines: {node: '>=18'} terser@5.46.0: @@ -2362,13 +2532,13 @@ packages: universal-user-agent@7.0.3: resolution: {integrity: sha512-TmnEAEAsBJVZM/AADELsK76llnwcf9vMKuPz8JflO1frO8Lchitr0fNaN9d+Ap0BjKtqWqd/J17qeDnXh8CL2A==} - unocss@66.6.5: - resolution: {integrity: sha512-WlpPlV7yAzEPREcwaKeacP+1jOm6ImhyKJRkK18tIW2b2BRZZDKln7X8P+NzJtAr0kziNY/ttUKZNZRnSmzP1A==} + unocss@66.6.6: + resolution: {integrity: sha512-PRKK945e2oZKHV664MA5Z9CDHbvY/V79IvTOUWKZ514jpl3UsJU3sS+skgxmKJSmwrWvXE5OVcmPthJrD/7vxg==} engines: {node: '>=14'} peerDependencies: - '@unocss/astro': 66.6.5 - '@unocss/postcss': 66.6.5 - '@unocss/webpack': 66.6.5 + '@unocss/astro': 66.6.6 + '@unocss/postcss': 66.6.6 + '@unocss/webpack': 66.6.6 peerDependenciesMeta: '@unocss/astro': optional: true @@ -2428,6 +2598,49 @@ packages: yaml: optional: true + vite@8.0.0: + resolution: {integrity: sha512-fPGaRNj9Zytaf8LEiBhY7Z6ijnFKdzU/+mL8EFBaKr7Vw1/FWcTBAMW0wLPJAGMPX38ZPVCVgLceWiEqeoqL2Q==} + engines: {node: ^20.19.0 || >=22.12.0} + hasBin: true + peerDependencies: + '@types/node': ^20.19.0 || >=22.12.0 + '@vitejs/devtools': ^0.0.0-alpha.31 + esbuild: ^0.27.0 + jiti: '>=1.21.0' + less: ^4.0.0 + sass: ^1.70.0 + sass-embedded: ^1.70.0 + stylus: '>=0.54.8' + sugarss: ^5.0.0 + terser: ^5.16.0 + tsx: ^4.8.1 + yaml: ^2.4.2 + peerDependenciesMeta: + '@types/node': + optional: true + '@vitejs/devtools': + optional: true + esbuild: + optional: true + jiti: + optional: true + less: + optional: true + sass: + optional: true + sass-embedded: + optional: true + stylus: + optional: true + sugarss: + optional: true + terser: + optional: true + tsx: + optional: true + yaml: + optional: true + vitefu@1.1.2: resolution: {integrity: sha512-zpKATdUbzbsycPFBN71nS2uzBUQiVnFoOrr2rvqv34S1lcAgMKKkjWleLGeiJlZ8lwCXvtWaRn7R3ZC16SYRuw==} peerDependencies: @@ -2702,7 +2915,7 @@ snapshots: '@humanwhocodes/retry@0.4.3': {} - '@iconify-json/codicon@1.2.47': + '@iconify-json/codicon@1.2.49': dependencies: '@iconify/types': 2.0.0 @@ -3344,6 +3557,8 @@ snapshots: '@oxc-parser/binding-win32-x64-msvc@0.115.0': optional: true + '@oxc-project/runtime@0.115.0': {} + '@oxc-project/types@0.115.0': {} '@polka/url@1.0.0-next.29': {} @@ -3364,6 +3579,55 @@ snapshots: dependencies: quansync: 1.0.0 + '@rolldown/binding-android-arm64@1.0.0-rc.9': + optional: true + + '@rolldown/binding-darwin-arm64@1.0.0-rc.9': + optional: true + + '@rolldown/binding-darwin-x64@1.0.0-rc.9': + optional: true + + '@rolldown/binding-freebsd-x64@1.0.0-rc.9': + optional: true + + '@rolldown/binding-linux-arm-gnueabihf@1.0.0-rc.9': + optional: true + + '@rolldown/binding-linux-arm64-gnu@1.0.0-rc.9': + optional: true + + '@rolldown/binding-linux-arm64-musl@1.0.0-rc.9': + optional: true + + '@rolldown/binding-linux-ppc64-gnu@1.0.0-rc.9': + optional: true + + '@rolldown/binding-linux-s390x-gnu@1.0.0-rc.9': + optional: true + + '@rolldown/binding-linux-x64-gnu@1.0.0-rc.9': + optional: true + + '@rolldown/binding-linux-x64-musl@1.0.0-rc.9': + optional: true + + '@rolldown/binding-openharmony-arm64@1.0.0-rc.9': + optional: true + + '@rolldown/binding-wasm32-wasi@1.0.0-rc.9': + dependencies: + '@napi-rs/wasm-runtime': 1.1.1 + optional: true + + '@rolldown/binding-win32-arm64-msvc@1.0.0-rc.9': + optional: true + + '@rolldown/binding-win32-x64-msvc@1.0.0-rc.9': + optional: true + + '@rolldown/pluginutils@1.0.0-rc.9': {} + '@rollup/plugin-terser@1.0.0(rollup@4.59.0)': dependencies: serialize-javascript: 7.0.4 @@ -3474,22 +3738,14 @@ snapshots: dependencies: acorn: 8.16.0 - '@sveltejs/vite-plugin-svelte-inspector@5.0.2(@sveltejs/vite-plugin-svelte@6.2.4(svelte@5.53.7)(vite@7.3.1(@types/node@24.11.0)(jiti@2.6.1)(terser@5.46.0)))(svelte@5.53.7)(vite@7.3.1(@types/node@24.11.0)(jiti@2.6.1)(terser@5.46.0))': - dependencies: - '@sveltejs/vite-plugin-svelte': 6.2.4(svelte@5.53.7)(vite@7.3.1(@types/node@24.11.0)(jiti@2.6.1)(terser@5.46.0)) - obug: 2.1.1 - svelte: 5.53.7 - vite: 7.3.1(@types/node@24.11.0)(jiti@2.6.1)(terser@5.46.0) - - '@sveltejs/vite-plugin-svelte@6.2.4(svelte@5.53.7)(vite@7.3.1(@types/node@24.11.0)(jiti@2.6.1)(terser@5.46.0))': + '@sveltejs/vite-plugin-svelte@7.0.0(svelte@5.53.11)(vite@8.0.0(@types/node@24.11.0)(esbuild@0.27.3)(jiti@2.6.1)(terser@5.46.0))': dependencies: - '@sveltejs/vite-plugin-svelte-inspector': 5.0.2(@sveltejs/vite-plugin-svelte@6.2.4(svelte@5.53.7)(vite@7.3.1(@types/node@24.11.0)(jiti@2.6.1)(terser@5.46.0)))(svelte@5.53.7)(vite@7.3.1(@types/node@24.11.0)(jiti@2.6.1)(terser@5.46.0)) deepmerge: 4.3.1 magic-string: 0.30.21 obug: 2.1.1 - svelte: 5.53.7 - vite: 7.3.1(@types/node@24.11.0)(jiti@2.6.1)(terser@5.46.0) - vitefu: 1.1.2(vite@7.3.1(@types/node@24.11.0)(jiti@2.6.1)(terser@5.46.0)) + svelte: 5.53.11 + vite: 8.0.0(@types/node@24.11.0)(esbuild@0.27.3)(jiti@2.6.1)(terser@5.46.0) + vitefu: 1.1.2(vite@8.0.0(@types/node@24.11.0)(esbuild@0.27.3)(jiti@2.6.1)(terser@5.46.0)) '@tybys/wasm-util@0.10.1': dependencies: @@ -3611,14 +3867,14 @@ snapshots: '@typescript-eslint/types': 8.56.1 eslint-visitor-keys: 5.0.1 - '@unocss/cli@66.6.5': + '@unocss/cli@66.6.6': dependencies: '@jridgewell/remapping': 2.3.5 - '@unocss/config': 66.6.4 - '@unocss/core': 66.6.5 - '@unocss/preset-wind3': 66.6.5 - '@unocss/preset-wind4': 66.6.5 - '@unocss/transformer-directives': 66.6.5 + '@unocss/config': 66.6.6 + '@unocss/core': 66.6.6 + '@unocss/preset-wind3': 66.6.6 + '@unocss/preset-wind4': 66.6.6 + '@unocss/transformer-directives': 66.6.6 cac: 6.7.14 chokidar: 5.0.0 colorette: 2.0.20 @@ -3629,120 +3885,118 @@ snapshots: tinyglobby: 0.2.15 unplugin-utils: 0.3.1 - '@unocss/config@66.6.4': + '@unocss/config@66.6.6': dependencies: - '@unocss/core': 66.6.4 + '@unocss/core': 66.6.6 colorette: 2.0.20 consola: 3.4.2 unconfig: 7.5.0 - '@unocss/core@66.6.4': {} + '@unocss/core@66.6.6': {} - '@unocss/core@66.6.5': {} - - '@unocss/extractor-arbitrary-variants@66.6.5': + '@unocss/extractor-arbitrary-variants@66.6.6': dependencies: - '@unocss/core': 66.6.5 + '@unocss/core': 66.6.6 - '@unocss/extractor-svelte@66.6.5': {} + '@unocss/extractor-svelte@66.6.6': {} - '@unocss/inspector@66.6.5': + '@unocss/inspector@66.6.6': dependencies: - '@unocss/core': 66.6.5 - '@unocss/rule-utils': 66.6.5 + '@unocss/core': 66.6.6 + '@unocss/rule-utils': 66.6.6 colorette: 2.0.20 gzip-size: 6.0.0 sirv: 3.0.2 - '@unocss/preset-attributify@66.6.5': + '@unocss/preset-attributify@66.6.6': dependencies: - '@unocss/core': 66.6.5 + '@unocss/core': 66.6.6 - '@unocss/preset-icons@66.6.5': + '@unocss/preset-icons@66.6.6': dependencies: '@iconify/utils': 3.1.0 - '@unocss/core': 66.6.5 + '@unocss/core': 66.6.6 ofetch: 1.5.1 - '@unocss/preset-mini@66.6.5': + '@unocss/preset-mini@66.6.6': dependencies: - '@unocss/core': 66.6.5 - '@unocss/extractor-arbitrary-variants': 66.6.5 - '@unocss/rule-utils': 66.6.5 + '@unocss/core': 66.6.6 + '@unocss/extractor-arbitrary-variants': 66.6.6 + '@unocss/rule-utils': 66.6.6 - '@unocss/preset-tagify@66.6.5': + '@unocss/preset-tagify@66.6.6': dependencies: - '@unocss/core': 66.6.5 + '@unocss/core': 66.6.6 - '@unocss/preset-typography@66.6.5': + '@unocss/preset-typography@66.6.6': dependencies: - '@unocss/core': 66.6.5 - '@unocss/rule-utils': 66.6.5 + '@unocss/core': 66.6.6 + '@unocss/rule-utils': 66.6.6 - '@unocss/preset-uno@66.6.5': + '@unocss/preset-uno@66.6.6': dependencies: - '@unocss/core': 66.6.5 - '@unocss/preset-wind3': 66.6.5 + '@unocss/core': 66.6.6 + '@unocss/preset-wind3': 66.6.6 - '@unocss/preset-web-fonts@66.6.5': + '@unocss/preset-web-fonts@66.6.6': dependencies: - '@unocss/core': 66.6.5 + '@unocss/core': 66.6.6 ofetch: 1.5.1 - '@unocss/preset-wind3@66.6.5': + '@unocss/preset-wind3@66.6.6': dependencies: - '@unocss/core': 66.6.5 - '@unocss/preset-mini': 66.6.5 - '@unocss/rule-utils': 66.6.5 + '@unocss/core': 66.6.6 + '@unocss/preset-mini': 66.6.6 + '@unocss/rule-utils': 66.6.6 - '@unocss/preset-wind4@66.6.5': + '@unocss/preset-wind4@66.6.6': dependencies: - '@unocss/core': 66.6.5 - '@unocss/extractor-arbitrary-variants': 66.6.5 - '@unocss/rule-utils': 66.6.5 + '@unocss/core': 66.6.6 + '@unocss/extractor-arbitrary-variants': 66.6.6 + '@unocss/rule-utils': 66.6.6 - '@unocss/preset-wind@66.6.5': + '@unocss/preset-wind@66.6.6': dependencies: - '@unocss/core': 66.6.5 - '@unocss/preset-wind3': 66.6.5 + '@unocss/core': 66.6.6 + '@unocss/preset-wind3': 66.6.6 - '@unocss/rule-utils@66.6.5': + '@unocss/rule-utils@66.6.6': dependencies: - '@unocss/core': 66.6.5 + '@unocss/core': 66.6.6 magic-string: 0.30.21 - '@unocss/transformer-attributify-jsx@66.6.5': + '@unocss/transformer-attributify-jsx@66.6.6': dependencies: - '@unocss/core': 66.6.5 + '@unocss/core': 66.6.6 oxc-parser: 0.115.0 oxc-walker: 0.7.0(oxc-parser@0.115.0) - '@unocss/transformer-compile-class@66.6.5': + '@unocss/transformer-compile-class@66.6.6': dependencies: - '@unocss/core': 66.6.5 + '@unocss/core': 66.6.6 - '@unocss/transformer-directives@66.6.5': + '@unocss/transformer-directives@66.6.6': dependencies: - '@unocss/core': 66.6.5 - '@unocss/rule-utils': 66.6.5 + '@unocss/core': 66.6.6 + '@unocss/rule-utils': 66.6.6 css-tree: 3.1.0 - '@unocss/transformer-variant-group@66.6.5': + '@unocss/transformer-variant-group@66.6.6': dependencies: - '@unocss/core': 66.6.5 + '@unocss/core': 66.6.6 - '@unocss/vite@66.6.5(vite@7.3.1(@types/node@24.11.0)(jiti@2.6.1)(terser@5.46.0))': + '@unocss/vite@66.6.6(vite@8.0.0(@types/node@24.11.0)(esbuild@0.27.3)(jiti@2.6.1)(terser@5.46.0))': dependencies: '@jridgewell/remapping': 2.3.5 - '@unocss/config': 66.6.4 - '@unocss/core': 66.6.5 - '@unocss/inspector': 66.6.5 + '@unocss/config': 66.6.6 + '@unocss/core': 66.6.6 + '@unocss/inspector': 66.6.6 chokidar: 5.0.0 magic-string: 0.30.21 pathe: 2.0.3 tinyglobby: 0.2.15 unplugin-utils: 0.3.1 - vite: 7.3.1(@types/node@24.11.0)(jiti@2.6.1)(terser@5.46.0) + vite: 8.0.0(@types/node@24.11.0)(esbuild@0.27.3)(jiti@2.6.1)(terser@5.46.0) '@vitest/expect@4.0.18': dependencies: @@ -3753,13 +4007,13 @@ snapshots: chai: 6.2.2 tinyrainbow: 3.0.3 - '@vitest/mocker@4.0.18(vite@7.3.1(@types/node@24.11.0)(jiti@2.6.1)(terser@5.46.0))': + '@vitest/mocker@4.0.18(vite@7.3.1(@types/node@24.11.0)(jiti@2.6.1)(lightningcss@1.32.0)(terser@5.46.0))': dependencies: '@vitest/spy': 4.0.18 estree-walker: 3.0.3 magic-string: 0.30.21 optionalDependencies: - vite: 7.3.1(@types/node@24.11.0)(jiti@2.6.1)(terser@5.46.0) + vite: 7.3.1(@types/node@24.11.0)(jiti@2.6.1)(lightningcss@1.32.0)(terser@5.46.0) '@vitest/pretty-format@4.0.18': dependencies: @@ -3878,7 +4132,7 @@ snapshots: detect-libc@2.1.2: {} - devalue@5.6.3: {} + devalue@5.6.4: {} duplexer@0.1.2: {} @@ -4139,6 +4393,55 @@ snapshots: prelude-ls: 1.2.1 type-check: 0.4.0 + lightningcss-android-arm64@1.32.0: + optional: true + + lightningcss-darwin-arm64@1.32.0: + optional: true + + lightningcss-darwin-x64@1.32.0: + optional: true + + lightningcss-freebsd-x64@1.32.0: + optional: true + + lightningcss-linux-arm-gnueabihf@1.32.0: + optional: true + + lightningcss-linux-arm64-gnu@1.32.0: + optional: true + + lightningcss-linux-arm64-musl@1.32.0: + optional: true + + lightningcss-linux-x64-gnu@1.32.0: + optional: true + + lightningcss-linux-x64-musl@1.32.0: + optional: true + + lightningcss-win32-arm64-msvc@1.32.0: + optional: true + + lightningcss-win32-x64-msvc@1.32.0: + optional: true + + lightningcss@1.32.0: + dependencies: + detect-libc: 2.1.2 + optionalDependencies: + lightningcss-android-arm64: 1.32.0 + lightningcss-darwin-arm64: 1.32.0 + lightningcss-darwin-x64: 1.32.0 + lightningcss-freebsd-x64: 1.32.0 + lightningcss-linux-arm-gnueabihf: 1.32.0 + lightningcss-linux-arm64-gnu: 1.32.0 + lightningcss-linux-arm64-musl: 1.32.0 + lightningcss-linux-x64-gnu: 1.32.0 + lightningcss-linux-x64-musl: 1.32.0 + lightningcss-win32-arm64-msvc: 1.32.0 + lightningcss-win32-x64-msvc: 1.32.0 + locate-character@3.0.0: {} locate-path@6.0.0: @@ -4312,6 +4615,27 @@ snapshots: reusify@1.1.0: {} + rolldown@1.0.0-rc.9: + dependencies: + '@oxc-project/types': 0.115.0 + '@rolldown/pluginutils': 1.0.0-rc.9 + optionalDependencies: + '@rolldown/binding-android-arm64': 1.0.0-rc.9 + '@rolldown/binding-darwin-arm64': 1.0.0-rc.9 + '@rolldown/binding-darwin-x64': 1.0.0-rc.9 + '@rolldown/binding-freebsd-x64': 1.0.0-rc.9 + '@rolldown/binding-linux-arm-gnueabihf': 1.0.0-rc.9 + '@rolldown/binding-linux-arm64-gnu': 1.0.0-rc.9 + '@rolldown/binding-linux-arm64-musl': 1.0.0-rc.9 + '@rolldown/binding-linux-ppc64-gnu': 1.0.0-rc.9 + '@rolldown/binding-linux-s390x-gnu': 1.0.0-rc.9 + '@rolldown/binding-linux-x64-gnu': 1.0.0-rc.9 + '@rolldown/binding-linux-x64-musl': 1.0.0-rc.9 + '@rolldown/binding-openharmony-arm64': 1.0.0-rc.9 + '@rolldown/binding-wasm32-wasi': 1.0.0-rc.9 + '@rolldown/binding-win32-arm64-msvc': 1.0.0-rc.9 + '@rolldown/binding-win32-x64-msvc': 1.0.0-rc.9 + rollup@4.59.0: dependencies: '@types/estree': 1.0.8 @@ -4423,7 +4747,7 @@ snapshots: supports-preserve-symlinks-flag@1.0.0: {} - svelte@5.53.7: + svelte@5.53.11: dependencies: '@jridgewell/remapping': 2.3.5 '@jridgewell/sourcemap-codec': 1.5.5 @@ -4434,7 +4758,7 @@ snapshots: aria-query: 5.3.1 axobject-query: 4.1.0 clsx: 2.1.1 - devalue: 5.6.3 + devalue: 5.6.4 esm-env: 1.2.2 esrap: 2.2.3 is-reference: 3.0.3 @@ -4518,25 +4842,25 @@ snapshots: universal-user-agent@7.0.3: {} - unocss@66.6.5(vite@7.3.1(@types/node@24.11.0)(jiti@2.6.1)(terser@5.46.0)): - dependencies: - '@unocss/cli': 66.6.5 - '@unocss/core': 66.6.5 - '@unocss/preset-attributify': 66.6.5 - '@unocss/preset-icons': 66.6.5 - '@unocss/preset-mini': 66.6.5 - '@unocss/preset-tagify': 66.6.5 - '@unocss/preset-typography': 66.6.5 - '@unocss/preset-uno': 66.6.5 - '@unocss/preset-web-fonts': 66.6.5 - '@unocss/preset-wind': 66.6.5 - '@unocss/preset-wind3': 66.6.5 - '@unocss/preset-wind4': 66.6.5 - '@unocss/transformer-attributify-jsx': 66.6.5 - '@unocss/transformer-compile-class': 66.6.5 - '@unocss/transformer-directives': 66.6.5 - '@unocss/transformer-variant-group': 66.6.5 - '@unocss/vite': 66.6.5(vite@7.3.1(@types/node@24.11.0)(jiti@2.6.1)(terser@5.46.0)) + unocss@66.6.6(vite@8.0.0(@types/node@24.11.0)(esbuild@0.27.3)(jiti@2.6.1)(terser@5.46.0)): + dependencies: + '@unocss/cli': 66.6.6 + '@unocss/core': 66.6.6 + '@unocss/preset-attributify': 66.6.6 + '@unocss/preset-icons': 66.6.6 + '@unocss/preset-mini': 66.6.6 + '@unocss/preset-tagify': 66.6.6 + '@unocss/preset-typography': 66.6.6 + '@unocss/preset-uno': 66.6.6 + '@unocss/preset-web-fonts': 66.6.6 + '@unocss/preset-wind': 66.6.6 + '@unocss/preset-wind3': 66.6.6 + '@unocss/preset-wind4': 66.6.6 + '@unocss/transformer-attributify-jsx': 66.6.6 + '@unocss/transformer-compile-class': 66.6.6 + '@unocss/transformer-directives': 66.6.6 + '@unocss/transformer-variant-group': 66.6.6 + '@unocss/vite': 66.6.6(vite@8.0.0(@types/node@24.11.0)(esbuild@0.27.3)(jiti@2.6.1)(terser@5.46.0)) transitivePeerDependencies: - vite @@ -4556,7 +4880,7 @@ snapshots: dependencies: punycode: 2.3.1 - vite@7.3.1(@types/node@24.11.0)(jiti@2.6.1)(terser@5.46.0): + vite@7.3.1(@types/node@24.11.0)(jiti@2.6.1)(lightningcss@1.32.0)(terser@5.46.0): dependencies: esbuild: 0.27.3 fdir: 6.5.0(picomatch@4.0.3) @@ -4568,16 +4892,32 @@ snapshots: '@types/node': 24.11.0 fsevents: 2.3.3 jiti: 2.6.1 + lightningcss: 1.32.0 + terser: 5.46.0 + + vite@8.0.0(@types/node@24.11.0)(esbuild@0.27.3)(jiti@2.6.1)(terser@5.46.0): + dependencies: + '@oxc-project/runtime': 0.115.0 + lightningcss: 1.32.0 + picomatch: 4.0.3 + postcss: 8.5.8 + rolldown: 1.0.0-rc.9 + tinyglobby: 0.2.15 + optionalDependencies: + '@types/node': 24.11.0 + esbuild: 0.27.3 + fsevents: 2.3.3 + jiti: 2.6.1 terser: 5.46.0 - vitefu@1.1.2(vite@7.3.1(@types/node@24.11.0)(jiti@2.6.1)(terser@5.46.0)): + vitefu@1.1.2(vite@8.0.0(@types/node@24.11.0)(esbuild@0.27.3)(jiti@2.6.1)(terser@5.46.0)): optionalDependencies: - vite: 7.3.1(@types/node@24.11.0)(jiti@2.6.1)(terser@5.46.0) + vite: 8.0.0(@types/node@24.11.0)(esbuild@0.27.3)(jiti@2.6.1)(terser@5.46.0) - vitest@4.0.18(@types/node@24.11.0)(jiti@2.6.1)(terser@5.46.0): + vitest@4.0.18(@types/node@24.11.0)(jiti@2.6.1)(lightningcss@1.32.0)(terser@5.46.0): dependencies: '@vitest/expect': 4.0.18 - '@vitest/mocker': 4.0.18(vite@7.3.1(@types/node@24.11.0)(jiti@2.6.1)(terser@5.46.0)) + '@vitest/mocker': 4.0.18(vite@7.3.1(@types/node@24.11.0)(jiti@2.6.1)(lightningcss@1.32.0)(terser@5.46.0)) '@vitest/pretty-format': 4.0.18 '@vitest/runner': 4.0.18 '@vitest/snapshot': 4.0.18 @@ -4594,7 +4934,7 @@ snapshots: tinyexec: 1.0.2 tinyglobby: 0.2.15 tinyrainbow: 3.0.3 - vite: 7.3.1(@types/node@24.11.0)(jiti@2.6.1)(terser@5.46.0) + vite: 7.3.1(@types/node@24.11.0)(jiti@2.6.1)(lightningcss@1.32.0)(terser@5.46.0) why-is-node-running: 2.3.0 optionalDependencies: '@types/node': 24.11.0 From 941ee44c5051cd2668c4df4d40924a1ec096546e Mon Sep 17 00:00:00 2001 From: William Justin <56458008+Xu-Justin@users.noreply.github.com> Date: Mon, 16 Mar 2026 19:09:02 +0700 Subject: [PATCH 42/95] fix(cli): ignore keystore.properties in Android templates (#14996) --- crates/tauri-cli/templates/mobile/android/.gitignore | 1 + 1 file changed, 1 insertion(+) diff --git a/crates/tauri-cli/templates/mobile/android/.gitignore b/crates/tauri-cli/templates/mobile/android/.gitignore index b24820317285..1c636c39a750 100644 --- a/crates/tauri-cli/templates/mobile/android/.gitignore +++ b/crates/tauri-cli/templates/mobile/android/.gitignore @@ -14,6 +14,7 @@ build .cxx local.properties key.properties +keystore.properties /.tauri /tauri.settings.gradle \ No newline at end of file From 63fb250d423ee67adf8a158a01ee6a34527ba905 Mon Sep 17 00:00:00 2001 From: llogiq Date: Tue, 17 Mar 2026 05:10:51 +0100 Subject: [PATCH 43/95] chore: reduce cloning in `EmbeddedAssets::get` (#15112) * reduce cloning in `EmbeddedAssets::get` * Apply suggestion from @Legend-Master * Fix github suggestion --------- Co-authored-by: Tony <68118705+Legend-Master@users.noreply.github.com> Co-authored-by: Tony --- crates/tauri-utils/src/assets.rs | 23 +++++++---------------- 1 file changed, 7 insertions(+), 16 deletions(-) diff --git a/crates/tauri-utils/src/assets.rs b/crates/tauri-utils/src/assets.rs index 3d904cd1f39f..486662d8dce8 100644 --- a/crates/tauri-utils/src/assets.rs +++ b/crates/tauri-utils/src/assets.rs @@ -168,27 +168,18 @@ impl EmbeddedAssets { /// Get an asset by key. #[cfg(feature = "compression")] pub fn get(&self, key: &AssetKey) -> Option> { - self - .assets - .get(key.as_ref()) - .map(|&(mut asdf)| { - // with the exception of extremely small files, output should usually be - // at least as large as the compressed version. - let mut buf = Vec::with_capacity(asdf.len()); - brotli::BrotliDecompress(&mut asdf, &mut buf).map(|()| buf) - }) - .and_then(Result::ok) - .map(Cow::Owned) + let &(mut asdf) = self.assets.get(key.as_ref())?; + // with the exception of extremely small files, output should usually be + // at least as large as the compressed version. + let mut buf = Vec::with_capacity(asdf.len()); + brotli::BrotliDecompress(&mut asdf, &mut buf).ok()?; + Some(Cow::Owned(buf)) } /// Get an asset by key. #[cfg(not(feature = "compression"))] pub fn get(&self, key: &AssetKey) -> Option> { - self - .assets - .get(key.as_ref()) - .copied() - .map(|a| Cow::Owned(a.to_vec())) + Some(Cow::Borrowed(self.assets.get(key.as_ref())?)) } /// Iterate on the assets. From 60922c092c42f59b5b4a9a38088b5ecab87f9eb8 Mon Sep 17 00:00:00 2001 From: Tony <68118705+Legend-Master@users.noreply.github.com> Date: Tue, 17 Mar 2026 18:38:42 +0800 Subject: [PATCH 44/95] refactor: reduce nesting in `AppManager::get_asset` (#15114) --- crates/tauri/src/manager/mod.rs | 68 +++++++++++++++------------------ 1 file changed, 31 insertions(+), 37 deletions(-) diff --git a/crates/tauri/src/manager/mod.rs b/crates/tauri/src/manager/mod.rs index 25ae8eaabe91..ca46ded96132 100644 --- a/crates/tauri/src/manager/mod.rs +++ b/crates/tauri/src/manager/mod.rs @@ -372,6 +372,7 @@ impl AppManager { } } + // TODO: Change to return `crate::Result` here in v3 pub fn get_asset( &self, mut path: String, @@ -417,49 +418,42 @@ impl AppManager { asset_path = fallback; asset }) - .ok_or_else(|| crate::Error::AssetNotFound(path.clone())) - .map(Cow::into_owned); + .ok_or_else(|| { + let error = crate::Error::AssetNotFound(path.clone()); + log::error!("{error}"); + Box::new(error) + })?; let mut csp_header = None; let is_html = asset_path.as_ref().ends_with(".html"); - match asset_response { - Ok(asset) => { - let final_data = if is_html { - let mut asset = String::from_utf8_lossy(&asset).into_owned(); - if let Some(csp) = self.csp() { - #[allow(unused_mut)] - let mut csp_map = set_csp(&mut asset, &self.assets, &asset_path, self, csp); - #[cfg(feature = "isolation")] - if let Pattern::Isolation { schema, .. } = &*self.pattern { - let default_src = csp_map - .entry("default-src".into()) - .or_insert_with(Default::default); - default_src.push(crate::pattern::format_real_schema( - schema, - _use_https_schema, - )); - } - - csp_header.replace(Csp::DirectiveMap(csp_map).to_string()); - } + let final_data = if is_html { + let mut asset = String::from_utf8_lossy(&asset_response).into_owned(); + if let Some(csp) = self.csp() { + #[allow(unused_mut)] + let mut csp_map = set_csp(&mut asset, &self.assets, &asset_path, self, csp); + #[cfg(feature = "isolation")] + if let Pattern::Isolation { schema, .. } = &*self.pattern { + let default_src = csp_map.entry("default-src".to_owned()).or_default(); + default_src.push(crate::pattern::format_real_schema( + schema, + _use_https_schema, + )); + } - asset.into_bytes() - } else { - asset - }; - let mime_type = tauri_utils::mime_type::MimeType::parse(&final_data, &path); - Ok(Asset { - bytes: final_data, - mime_type, - csp_header, - }) - } - Err(e) => { - log::error!("{:?}", e); - Err(Box::new(e)) + csp_header.replace(Csp::DirectiveMap(csp_map).to_string()); } - } + + asset.into_bytes() + } else { + asset_response.into_owned() + }; + let mime_type = tauri_utils::mime_type::MimeType::parse(&final_data, &path); + Ok(Asset { + bytes: final_data, + mime_type, + csp_header, + }) } pub(crate) fn listeners(&self) -> &Listeners { From ea597b53332b6cc4cca5d522de6ac5448b7e247c Mon Sep 17 00:00:00 2001 From: Sam Lidder Date: Tue, 17 Mar 2026 17:12:44 -0400 Subject: [PATCH 45/95] fix(cli): allow `build --bundles nsis` arg in linux+macOS (#14954) --- .changes/fix-build-bundles-arg.md | 7 ++++ crates/tauri-bundler/src/bundle.rs | 42 +++++++++++++-------- crates/tauri-bundler/src/bundle/kmp/mod.rs | 2 - crates/tauri-bundler/src/bundle/settings.rs | 2 +- crates/tauri-cli/src/bundle.rs | 2 +- 5 files changed, 36 insertions(+), 19 deletions(-) create mode 100644 .changes/fix-build-bundles-arg.md diff --git a/.changes/fix-build-bundles-arg.md b/.changes/fix-build-bundles-arg.md new file mode 100644 index 000000000000..de735d18c47d --- /dev/null +++ b/.changes/fix-build-bundles-arg.md @@ -0,0 +1,7 @@ +--- +"tauri-bundler": patch:bug +"tauri-cli": patch:bug +"@tauri-apps/cli": patch:bug +--- + +Fix `build --bundles` to allow `nsis` arg in linux+macOS diff --git a/crates/tauri-bundler/src/bundle.rs b/crates/tauri-bundler/src/bundle.rs index e20fb19c8e52..ab0a45032f93 100644 --- a/crates/tauri-bundler/src/bundle.rs +++ b/crates/tauri-bundler/src/bundle.rs @@ -4,7 +4,6 @@ // SPDX-License-Identifier: MIT mod category; -#[cfg(any(target_os = "linux", target_os = "windows"))] mod kmp; #[cfg(target_os = "linux")] mod linux; @@ -17,26 +16,16 @@ mod windows; use tauri_utils::{display_path, platform::Target as TargetPlatform}; -#[cfg(any(target_os = "linux", target_os = "windows"))] const BUNDLE_VAR_TOKEN: &[u8] = b"__TAURI_BUNDLE_TYPE_VAR_UNK"; /// Patch a binary with bundle type information -#[cfg(any(target_os = "linux", target_os = "windows"))] fn patch_binary(binary: &PathBuf, package_type: &PackageType) -> crate::Result<()> { - log::info!( - "Patching {} with bundle type information: {}", - display_path(binary), - package_type.short_name() - ); - - let mut file_data = std::fs::read(binary).expect("Could not read binary file."); - - let bundle_var_index = - kmp::index_of(BUNDLE_VAR_TOKEN, &file_data).ok_or(crate::Error::MissingBundleTypeVar)?; #[cfg(target_os = "linux")] let bundle_type = match package_type { crate::PackageType::Deb => b"__TAURI_BUNDLE_TYPE_VAR_DEB", crate::PackageType::Rpm => b"__TAURI_BUNDLE_TYPE_VAR_RPM", crate::PackageType::AppImage => b"__TAURI_BUNDLE_TYPE_VAR_APP", + // NSIS installers can be built in linux using cargo-xwin + crate::PackageType::Nsis => b"__TAURI_BUNDLE_TYPE_VAR_NSS", _ => { return Err(crate::Error::InvalidPackageType( package_type.short_name().to_owned(), @@ -55,7 +44,31 @@ fn patch_binary(binary: &PathBuf, package_type: &PackageType) -> crate::Result<( )) } }; + #[cfg(target_os = "macos")] + let bundle_type = match package_type { + // NSIS installers can be built in macOS using cargo-xwin + crate::PackageType::Nsis => b"__TAURI_BUNDLE_TYPE_VAR_NSS", + crate::PackageType::MacOsBundle | crate::PackageType::Dmg => { + // skip patching for macOS-native bundles + return Ok(()); + } + _ => { + return Err(crate::Error::InvalidPackageType( + package_type.short_name().to_owned(), + "macOS".to_owned(), + )) + } + }; + log::info!( + "Patching {} with bundle type information: {}", + display_path(binary), + package_type.short_name() + ); + + let mut file_data = std::fs::read(binary).expect("Could not read binary file."); + let bundle_var_index = + kmp::index_of(BUNDLE_VAR_TOKEN, &file_data).ok_or(crate::Error::MissingBundleTypeVar)?; file_data[bundle_var_index..bundle_var_index + BUNDLE_VAR_TOKEN.len()] .copy_from_slice(bundle_type); @@ -133,7 +146,6 @@ pub fn bundle_project(settings: &Settings) -> crate::Result> { continue; } - #[cfg(any(target_os = "linux", target_os = "windows"))] if let Err(e) = patch_binary(&main_binary_path, package_type) { log::warn!("Failed to add bundler type to the binary: {e}. Updater plugin may not be able to update this package. This shouldn't normally happen, please report it to https://github.com/tauri-apps/tauri/issues"); } @@ -163,7 +175,7 @@ pub fn bundle_project(settings: &Settings) -> crate::Result> { #[cfg(target_os = "windows")] PackageType::WindowsMsi => windows::msi::bundle_project(settings, false)?, - // note: don't restrict to windows as NSIS installers can be built in linux using cargo-xwin + // don't restrict to windows as NSIS installers can be built in linux+macOS using cargo-xwin PackageType::Nsis => windows::nsis::bundle_project(settings, false)?, #[cfg(target_os = "linux")] diff --git a/crates/tauri-bundler/src/bundle/kmp/mod.rs b/crates/tauri-bundler/src/bundle/kmp/mod.rs index 3e8489023044..863e4145c371 100644 --- a/crates/tauri-bundler/src/bundle/kmp/mod.rs +++ b/crates/tauri-bundler/src/bundle/kmp/mod.rs @@ -5,7 +5,6 @@ // Knuth–Morris–Pratt algorithm // based on https://github.com/howeih/rust_kmp -#[cfg(any(target_os = "linux", target_os = "windows"))] pub fn index_of(pattern: &[u8], target: &[u8]) -> Option { let failure_function = find_failure_function(pattern); @@ -38,7 +37,6 @@ pub fn index_of(pattern: &[u8], target: &[u8]) -> Option { None } -#[cfg(any(target_os = "linux", target_os = "windows"))] fn find_failure_function(pattern: &[u8]) -> Vec { let mut i = 1; let mut j = 0; diff --git a/crates/tauri-bundler/src/bundle/settings.rs b/crates/tauri-bundler/src/bundle/settings.rs index 71321b2937ba..5e2a81b38d4e 100644 --- a/crates/tauri-bundler/src/bundle/settings.rs +++ b/crates/tauri-bundler/src/bundle/settings.rs @@ -126,7 +126,7 @@ const ALL_PACKAGE_TYPES: &[PackageType] = &[ PackageType::IosBundle, #[cfg(target_os = "windows")] PackageType::WindowsMsi, - #[cfg(target_os = "windows")] + // NSIS installers can be built on all platforms but it's hidden in the --help output on macOS/Linux. PackageType::Nsis, #[cfg(target_os = "macos")] PackageType::MacOsBundle, diff --git a/crates/tauri-cli/src/bundle.rs b/crates/tauri-cli/src/bundle.rs index d40dba652bf8..4625eddc0b80 100644 --- a/crates/tauri-cli/src/bundle.rs +++ b/crates/tauri-cli/src/bundle.rs @@ -43,7 +43,7 @@ impl ValueEnum for BundleFormat { } fn to_possible_value(&self) -> Option { - let hide = self.0 == PackageType::Updater; + let hide = (!cfg!(windows) && self.0 == PackageType::Nsis) || self.0 == PackageType::Updater; Some(PossibleValue::new(self.0.short_name()).hide(hide)) } } From 5a05a3fe31c575c9be23049a108c3e97734b9fc3 Mon Sep 17 00:00:00 2001 From: Fabian-Lars <30730186+FabianLars@users.noreply.github.com> Date: Wed, 18 Mar 2026 09:11:44 +0100 Subject: [PATCH 46/95] chore(deps): update wrangler & flatted to fix audit (#15116) --- crates/tauri-schema-worker/package.json | 2 +- pnpm-lock.yaml | 98 ++++++++++++------------- 2 files changed, 50 insertions(+), 50 deletions(-) diff --git a/crates/tauri-schema-worker/package.json b/crates/tauri-schema-worker/package.json index 7e7326a0dfb3..c5cba019328e 100644 --- a/crates/tauri-schema-worker/package.json +++ b/crates/tauri-schema-worker/package.json @@ -8,6 +8,6 @@ "dev": "wrangler dev" }, "devDependencies": { - "wrangler": "^4.70.0" + "wrangler": "^4.75.0" } } diff --git a/pnpm-lock.yaml b/pnpm-lock.yaml index 92d25f0788b9..4df96ba054f6 100644 --- a/pnpm-lock.yaml +++ b/pnpm-lock.yaml @@ -15,8 +15,8 @@ importers: crates/tauri-schema-worker: devDependencies: wrangler: - specifier: ^4.70.0 - version: 4.70.0 + specifier: ^4.75.0 + version: 4.75.0 examples/api: dependencies: @@ -119,41 +119,41 @@ packages: resolution: {integrity: sha512-SIOD2DxrRRwQ+jgzlXCqoEFiKOFqaPjhnNTGKXSRLvp1HiOvapLaFG2kEr9dYQTYe8rKrd9uvDUzmAITeNyaHQ==} engines: {node: '>=18.0.0'} - '@cloudflare/unenv-preset@2.14.0': - resolution: {integrity: sha512-XKAkWhi1nBdNsSEoNG9nkcbyvfUrSjSf+VYVPfOto3gLTZVc3F4g6RASCMh6IixBKCG2yDgZKQIHGKtjcnLnKg==} + '@cloudflare/unenv-preset@2.15.0': + resolution: {integrity: sha512-EGYmJaGZKWl+X8tXxcnx4v2bOZSjQeNI5dWFeXivgX9+YCT69AkzHHwlNbVpqtEUTbew8eQurpyOpeN8fg00nw==} peerDependencies: unenv: 2.0.0-rc.24 - workerd: ^1.20260218.0 + workerd: 1.20260301.1 || ~1.20260302.1 || ~1.20260303.1 || ~1.20260304.1 || >1.20260305.0 <2.0.0-0 peerDependenciesMeta: workerd: optional: true - '@cloudflare/workerd-darwin-64@1.20260301.1': - resolution: {integrity: sha512-+kJvwociLrvy1JV9BAvoSVsMEIYD982CpFmo/yMEvBwxDIjltYsLTE8DLi0mCkGsQ8Ygidv2fD9wavzXeiY7OQ==} + '@cloudflare/workerd-darwin-64@1.20260317.1': + resolution: {integrity: sha512-8hjh3sPMwY8M/zedq3/sXoA2Q4BedlGufn3KOOleIG+5a4ReQKLlUah140D7J6zlKmYZAFMJ4tWC7hCuI/s79g==} engines: {node: '>=16'} cpu: [x64] os: [darwin] - '@cloudflare/workerd-darwin-arm64@1.20260301.1': - resolution: {integrity: sha512-PPIetY3e67YBr9O4UhILK8nbm5TqUDl14qx4rwFNrRSBOvlzuczzbd4BqgpAtbGVFxKp1PWpjAnBvGU/OI/tLQ==} + '@cloudflare/workerd-darwin-arm64@1.20260317.1': + resolution: {integrity: sha512-M/MnNyvO5HMgoIdr3QHjdCj2T1ki9gt0vIUnxYxBu9ISXS/jgtMl6chUVPJ7zHYBn9MyYr8ByeN6frjYxj0MGg==} engines: {node: '>=16'} cpu: [arm64] os: [darwin] - '@cloudflare/workerd-linux-64@1.20260301.1': - resolution: {integrity: sha512-Gu5vaVTZuYl3cHa+u5CDzSVDBvSkfNyuAHi6Mdfut7TTUdcb3V5CIcR/mXRSyMXzEy9YxEWIfdKMxOMBjupvYQ==} + '@cloudflare/workerd-linux-64@1.20260317.1': + resolution: {integrity: sha512-1ltuEjkRcS3fsVF7CxsKlWiRmzq2ZqMfqDN0qUOgbUwkpXsLVJsXmoblaLf5OP00ELlcgF0QsN0p2xPEua4Uug==} engines: {node: '>=16'} cpu: [x64] os: [linux] - '@cloudflare/workerd-linux-arm64@1.20260301.1': - resolution: {integrity: sha512-igL1pkyCXW6GiGpjdOAvqMi87UW0LMc/+yIQe/CSzuZJm5GzXoAMrwVTkCFnikk6JVGELrM5x0tGYlxa0sk5Iw==} + '@cloudflare/workerd-linux-arm64@1.20260317.1': + resolution: {integrity: sha512-3QrNnPF1xlaNwkHpasvRvAMidOvQs2NhXQmALJrEfpIJ/IDL2la8g499yXp3eqhG3hVMCB07XVY149GTs42Xtw==} engines: {node: '>=16'} cpu: [arm64] os: [linux] - '@cloudflare/workerd-windows-64@1.20260301.1': - resolution: {integrity: sha512-Q0wMJ4kcujXILwQKQFc1jaYamVsNvjuECzvRrTI8OxGFMx2yq9aOsswViE4X1gaS2YQQ5u0JGwuGi5WdT1Lt7A==} + '@cloudflare/workerd-windows-64@1.20260317.1': + resolution: {integrity: sha512-MfZTz+7LfuIpMGTa3RLXHX8Z/pnycZLItn94WRdHr8LPVet+C5/1Nzei399w/jr3+kzT4pDKk26JF/tlI5elpQ==} engines: {node: '>=16'} cpu: [x64] os: [win32] @@ -2031,8 +2031,8 @@ packages: resolution: {integrity: sha512-f7ccFPK3SXFHpx15UIGyRJ/FJQctuKZ0zVuN3frBo4HnK3cay9VEW0R6yPYFHC0AgqhukPzKjq22t5DmAyqGyw==} engines: {node: '>=16'} - flatted@3.3.4: - resolution: {integrity: sha512-3+mMldrTAPdta5kjX2G2J7iX4zxtnwpdA8Tr2ZSjkyPSanvbZAcy6flmtnXbEybHrDcU9641lxrMfFuUxVz9vA==} + flatted@3.4.2: + resolution: {integrity: sha512-PjDse7RzhcPkIJwy5t7KPWQSZ9cAbzQXcafsetQoD7sOJRQlGikNbx7yZp2OotDnJyrDcbyRq3Ttb18iYOqkxA==} fsevents@2.3.3: resolution: {integrity: sha512-5xoDfX+fL7faATnagmWPpbFtwh/R77WmMMqqHGS65C3vvB0YHrgF+B1YmZ3441tMj5n63k0212XNoJwzlhffQw==} @@ -2229,8 +2229,8 @@ packages: resolution: {integrity: sha512-PXwfBhYu0hBCPw8Dn0E+WDYb7af3dSLVWKi3HGv84IdF4TyFoC0ysxFd0Goxw7nSv4T/PzEJQxsYsEiFCKo2BA==} engines: {node: '>=8.6'} - miniflare@4.20260301.1: - resolution: {integrity: sha512-fqkHx0QMKswRH9uqQQQOU/RoaS3Wjckxy3CUX3YGJr0ZIMu7ObvI+NovdYi6RIsSPthNtq+3TPmRNxjeRiasog==} + miniflare@4.20260317.0: + resolution: {integrity: sha512-xuwk5Kjv+shi5iUBAdCrRl9IaWSGnTU8WuTQzsUS2GlSDIMCJuu8DiF/d9ExjMXYiQG5ml+k9SVKnMj8cRkq0w==} engines: {node: '>=18.0.0'} hasBin: true @@ -2522,8 +2522,8 @@ packages: undici-types@7.16.0: resolution: {integrity: sha512-Zz+aZWSj8LE6zoxD+xrjh4VfkIG8Ya6LvYkZqtUQGJPZjYl53ypCaUwWqo7eI0x66KBGeRo+mlBEkMSeSZ38Nw==} - undici@7.18.2: - resolution: {integrity: sha512-y+8YjDFzWdQlSE9N5nzKMT3g4a5UBX1HKowfdXh0uvAnTaqqwqB92Jt4UXBAeKekDs5IaDKyJFR4X1gYVCgXcw==} + undici@7.24.4: + resolution: {integrity: sha512-BM/JzwwaRXxrLdElV2Uo6cTLEjhSb3WXboncJamZ15NgUURmvlXvxa6xkwIOILIjPNo9i8ku136ZvWV0Uly8+w==} engines: {node: '>=20.18.1'} unenv@2.0.0-rc.24: @@ -2700,17 +2700,17 @@ packages: resolution: {integrity: sha512-BN22B5eaMMI9UMtjrGd5g5eCYPpCPDUy0FJXbYsaT5zYxjFOckS53SQDE3pWkVoWpHXVb3BrYcEN4Twa55B5cA==} engines: {node: '>=0.10.0'} - workerd@1.20260301.1: - resolution: {integrity: sha512-oterQ1IFd3h7PjCfT4znSFOkJCvNQ6YMOyZ40YsnO3nrSpgB4TbJVYWFOnyJAw71/RQuupfVqZZWKvsy8GO3fw==} + workerd@1.20260317.1: + resolution: {integrity: sha512-ZuEq1OdrJBS+NV+L5HMYPCzVn49a2O60slQiiLpG44jqtlOo+S167fWC76kEXteXLLLydeuRrluRel7WdOUa4g==} engines: {node: '>=16'} hasBin: true - wrangler@4.70.0: - resolution: {integrity: sha512-PNDZ9o4e+B5x+1bUbz62Hmwz6G9lw+I9pnYe/AguLddJFjfIyt2cmFOUOb3eOZSoXsrhcEPUg2YidYIbVwUkfw==} + wrangler@4.75.0: + resolution: {integrity: sha512-Efk1tcnm4eduBYpH1sSjMYydXMnIFPns/qABI3+fsbDrUk5GksNYX8nYGVP4sFygvGPO7kJc36YJKB5ooA7JAg==} engines: {node: '>=20.0.0'} hasBin: true peerDependencies: - '@cloudflare/workers-types': ^4.20260226.1 + '@cloudflare/workers-types': ^4.20260317.1 peerDependenciesMeta: '@cloudflare/workers-types': optional: true @@ -2749,25 +2749,25 @@ snapshots: '@cloudflare/kv-asset-handler@0.4.2': {} - '@cloudflare/unenv-preset@2.14.0(unenv@2.0.0-rc.24)(workerd@1.20260301.1)': + '@cloudflare/unenv-preset@2.15.0(unenv@2.0.0-rc.24)(workerd@1.20260317.1)': dependencies: unenv: 2.0.0-rc.24 optionalDependencies: - workerd: 1.20260301.1 + workerd: 1.20260317.1 - '@cloudflare/workerd-darwin-64@1.20260301.1': + '@cloudflare/workerd-darwin-64@1.20260317.1': optional: true - '@cloudflare/workerd-darwin-arm64@1.20260301.1': + '@cloudflare/workerd-darwin-arm64@1.20260317.1': optional: true - '@cloudflare/workerd-linux-64@1.20260301.1': + '@cloudflare/workerd-linux-64@1.20260317.1': optional: true - '@cloudflare/workerd-linux-arm64@1.20260301.1': + '@cloudflare/workerd-linux-arm64@1.20260317.1': optional: true - '@cloudflare/workerd-windows-64@1.20260301.1': + '@cloudflare/workerd-windows-64@1.20260317.1': optional: true '@cspotcode/source-map-support@0.8.1': @@ -4312,10 +4312,10 @@ snapshots: flat-cache@4.0.1: dependencies: - flatted: 3.3.4 + flatted: 3.4.2 keyv: 4.5.4 - flatted@3.3.4: {} + flatted@3.4.2: {} fsevents@2.3.3: optional: true @@ -4471,12 +4471,12 @@ snapshots: braces: 3.0.3 picomatch: 2.3.1 - miniflare@4.20260301.1: + miniflare@4.20260317.0: dependencies: '@cspotcode/source-map-support': 0.8.1 sharp: 0.34.5 - undici: 7.18.2 - workerd: 1.20260301.1 + undici: 7.24.4 + workerd: 1.20260317.1 ws: 8.18.0 youch: 4.1.0-beta.10 transitivePeerDependencies: @@ -4834,7 +4834,7 @@ snapshots: undici-types@7.16.0: {} - undici@7.18.2: {} + undici@7.24.4: {} unenv@2.0.0-rc.24: dependencies: @@ -4964,24 +4964,24 @@ snapshots: word-wrap@1.2.5: {} - workerd@1.20260301.1: + workerd@1.20260317.1: optionalDependencies: - '@cloudflare/workerd-darwin-64': 1.20260301.1 - '@cloudflare/workerd-darwin-arm64': 1.20260301.1 - '@cloudflare/workerd-linux-64': 1.20260301.1 - '@cloudflare/workerd-linux-arm64': 1.20260301.1 - '@cloudflare/workerd-windows-64': 1.20260301.1 + '@cloudflare/workerd-darwin-64': 1.20260317.1 + '@cloudflare/workerd-darwin-arm64': 1.20260317.1 + '@cloudflare/workerd-linux-64': 1.20260317.1 + '@cloudflare/workerd-linux-arm64': 1.20260317.1 + '@cloudflare/workerd-windows-64': 1.20260317.1 - wrangler@4.70.0: + wrangler@4.75.0: dependencies: '@cloudflare/kv-asset-handler': 0.4.2 - '@cloudflare/unenv-preset': 2.14.0(unenv@2.0.0-rc.24)(workerd@1.20260301.1) + '@cloudflare/unenv-preset': 2.15.0(unenv@2.0.0-rc.24)(workerd@1.20260317.1) blake3-wasm: 2.1.5 esbuild: 0.27.3 - miniflare: 4.20260301.1 + miniflare: 4.20260317.0 path-to-regexp: 6.3.0 unenv: 2.0.0-rc.24 - workerd: 1.20260301.1 + workerd: 1.20260317.1 optionalDependencies: fsevents: 2.3.3 transitivePeerDependencies: From a5d29f4a12e29db344fa9cd5975f7fff29ef61dd Mon Sep 17 00:00:00 2001 From: Fabian-Lars <30730186+FabianLars@users.noreply.github.com> Date: Wed, 18 Mar 2026 18:02:04 +0100 Subject: [PATCH 47/95] chore(deps): Update cargo-mobile2 and toml crates (#15115) * chore(deps): Update cargo-mobile2 and toml crates * remove toml from tauri-build cargotoml * 0.22.3 * try a range * json5 and changefile * Revert "json5 and changefile" This reverts commit eda416ba7923338e232cda452e63e97b65bcf7bf. * keep changefile --- .changes/toml-ver.md | 5 ++ Cargo.lock | 158 +++++++++++++++++++++------------ crates/tauri-build/Cargo.toml | 1 - crates/tauri-cli/Cargo.toml | 6 +- crates/tauri-plugin/Cargo.toml | 2 - crates/tauri-utils/Cargo.toml | 3 +- 6 files changed, 111 insertions(+), 64 deletions(-) create mode 100644 .changes/toml-ver.md diff --git a/.changes/toml-ver.md b/.changes/toml-ver.md new file mode 100644 index 000000000000..1732908c17a0 --- /dev/null +++ b/.changes/toml-ver.md @@ -0,0 +1,5 @@ +--- +tauri-utils: patch:deps +--- + +Changed `toml` crate version from `0.9` to `">=0.9, <=1"` diff --git a/Cargo.lock b/Cargo.lock index 8b9b0da50813..d9cbf78133ab 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -440,7 +440,7 @@ dependencies = [ "asn1-rs-derive", "asn1-rs-impl", "displaydoc", - "nom", + "nom 7.1.3", "num-traits", "rusticata-macros", "thiserror 1.0.69", @@ -539,7 +539,7 @@ dependencies = [ "anyhow", "arrayvec", "log", - "nom", + "nom 7.1.3", "num-rational", "v_frame", ] @@ -774,7 +774,7 @@ source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "d988fcc40055ceaa85edc55875a08f8abd29018582647fd82ad6128dba14a5f0" dependencies = [ "bitvec", - "nom", + "nom 7.1.3", ] [[package]] @@ -1055,9 +1055,9 @@ dependencies = [ [[package]] name = "cargo-mobile2" -version = "0.21.1" +version = "0.22.3" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "dcea7efeaac9f0fd9f886f43a13dde186a1e2266fe6b53a42659e4e0689570de" +checksum = "4409d8c4087e66ff08bae7497ef311dbdedcf9903049d66228056f99ebd2a19b" dependencies = [ "colored", "core-foundation 0.10.0", @@ -1074,16 +1074,17 @@ dependencies = [ "java-properties", "libc", "log", - "once-cell-regex", + "once_cell", "os_info", "os_pipe", "path_abs", "plist", + "regex", "serde", "serde_json", "textwrap", "thiserror 2.0.12", - "toml 0.9.10+spec-1.1.0", + "toml 1.0.6+spec-1.1.0", "ureq", "which", "windows 0.61.1", @@ -1120,7 +1121,7 @@ source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "374b7c592d9c00c1f4972ea58390ac6b18cbb6ab79011f3bdc90a0b82ca06b77" dependencies = [ "serde", - "toml 0.9.10+spec-1.1.0", + "toml 0.9.12+spec-1.1.0", ] [[package]] @@ -1320,7 +1321,7 @@ source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "117725a109d387c937a1533ce01b450cbde6b88abceea8473c4d7a85853cda3c" dependencies = [ "lazy_static", - "windows-sys 0.48.0", + "windows-sys 0.59.0", ] [[package]] @@ -2079,9 +2080,9 @@ checksum = "7454e41ff9012c00d53cf7f475c5e3afa3b91b7c90568495495e8d9bf47a1055" [[package]] name = "duct" -version = "1.0.0" +version = "1.1.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "b6ce170a0e8454fa0f9b0e5ca38a6ba17ed76a50916839d217eb5357e05cdfde" +checksum = "7e66e9c0c03d094e1a0ba1be130b849034aa80c3a2ab8ee94316bc809f3fa684" dependencies = [ "libc", "os_pipe", @@ -2214,7 +2215,7 @@ dependencies = [ "cc", "memchr", "rustc_version", - "toml 0.9.10+spec-1.1.0", + "toml 0.9.12+spec-1.1.0", "vswhom", "winreg 0.55.0", ] @@ -2590,12 +2591,12 @@ dependencies = [ [[package]] name = "freedesktop_entry_parser" -version = "1.3.0" +version = "2.0.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "db9c27b72f19a99a895f8ca89e2d26e4ef31013376e56fdafef697627306c3e4" +checksum = "2b368437186ec63ceb50d0832ee1ebcb5878037fe16ead1c68081d4aee0d140a" dependencies = [ - "nom", - "thiserror 1.0.69", + "indexmap 2.11.4", + "nom 8.0.0", ] [[package]] @@ -4319,7 +4320,7 @@ source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "fc2f4eb4bc735547cfed7c0a4922cbd04a4655978c09b54f1f7b228750664c34" dependencies = [ "cfg-if", - "windows-targets 0.48.5", + "windows-targets 0.52.6", ] [[package]] @@ -4821,6 +4822,15 @@ dependencies = [ "minimal-lexical", ] +[[package]] +name = "nom" +version = "8.0.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "df9761775871bdef83bee530e60050f7e54b1105350d6884eb0fb4f46c2f9405" +dependencies = [ + "memchr", +] + [[package]] name = "nonmax" version = "0.5.5" @@ -5222,21 +5232,11 @@ dependencies = [ "asn1-rs", ] -[[package]] -name = "once-cell-regex" -version = "0.2.1" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "b3de7e389a5043420c8f2b95ed03f3f104ad6f4c41f7d7e27298f033abc253e8" -dependencies = [ - "once_cell", - "regex", -] - [[package]] name = "once_cell" -version = "1.20.2" +version = "1.21.4" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "1261fe7e33c73b354eab43b1273a57c8f967d0391e80353e51f764ac02cf6775" +checksum = "9f7c3e4beb33f85d45ae3e3a1792185706c8e16d043238c593331cc7cd313b50" [[package]] name = "opaque-debug" @@ -5332,12 +5332,12 @@ dependencies = [ [[package]] name = "os_pipe" -version = "1.2.1" +version = "1.2.3" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "5ffd2b0a5634335b135d5728d84c5e0fd726954b87111f7506a61c502280d982" +checksum = "7d8fae84b431384b68627d0f9b3b1245fcf9f46f6c0e3dc902e9dce64edd1967" dependencies = [ "libc", - "windows-sys 0.59.0", + "windows-sys 0.60.2", ] [[package]] @@ -5787,7 +5787,7 @@ dependencies = [ "k256", "log", "md-5", - "nom", + "nom 7.1.3", "num-bigint-dig", "num-traits", "num_enum", @@ -6439,7 +6439,7 @@ dependencies = [ "either", "jzon", "konst", - "nom", + "nom 7.1.3", "num-bigint", "num-integer", "num-traits", @@ -6882,7 +6882,7 @@ dependencies = [ "itertools 0.13.0", "log", "md-5", - "nom", + "nom 7.1.3", "num", "num-derive", "num-traits", @@ -6967,7 +6967,7 @@ version = "4.1.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "faf0c4a6ece9950b9abdb62b1cfcf2a68b3b67a10ba445b3bb85be2a293d0632" dependencies = [ - "nom", + "nom 7.1.3", ] [[package]] @@ -7741,19 +7741,20 @@ dependencies = [ [[package]] name = "shared_child" -version = "1.0.1" +version = "1.1.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "09fa9338aed9a1df411814a5b2252f7cd206c55ae9bf2fa763f8de84603aa60c" +checksum = "1e362d9935bc50f019969e2f9ecd66786612daae13e8f277be7bfb66e8bed3f7" dependencies = [ "libc", - "windows-sys 0.59.0", + "sigchld", + "windows-sys 0.60.2", ] [[package]] name = "shared_thread" -version = "0.1.0" +version = "0.2.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "c7a6f98357c6bb0ebace19b22220e5543801d9de90ffe77f8abb27c056bac064" +checksum = "52b86057fcb5423f5018e331ac04623e32d6b5ce85e33300f92c79a1973928b0" [[package]] name = "shell-words" @@ -7767,6 +7768,27 @@ version = "1.3.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "0fda2ff0d084019ba4d7c6f371c95d8fd75ce3524c3cb8fb653a3023f6323e64" +[[package]] +name = "sigchld" +version = "0.2.4" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "47106eded3c154e70176fc83df9737335c94ce22f821c32d17ed1db1f83badb1" +dependencies = [ + "libc", + "os_pipe", + "signal-hook 0.3.18", +] + +[[package]] +name = "signal-hook" +version = "0.3.18" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "d881a16cf4426aa584979d30bd82cb33429027e42122b169753d6ef1085ed6e2" +dependencies = [ + "libc", + "signal-hook-registry", +] + [[package]] name = "signal-hook" version = "0.4.1" @@ -7794,7 +7816,7 @@ checksum = "e513e435a8898a0002270f29d0a708b7879708fb5c4d00e46983ca2d2d378cf0" dependencies = [ "futures-core", "libc", - "signal-hook", + "signal-hook 0.4.1", "tokio", ] @@ -8497,7 +8519,6 @@ dependencies = [ "tauri-codegen", "tauri-utils", "tauri-winres", - "toml 0.9.10+spec-1.1.0", "walkdir", ] @@ -8619,8 +8640,8 @@ dependencies = [ "tempfile", "thiserror 2.0.12", "tokio", - "toml 0.9.10+spec-1.1.0", - "toml_edit 0.24.0+spec-1.1.0", + "toml 1.0.6+spec-1.1.0", + "toml_edit 0.25.4+spec-1.1.0", "ureq", "url", "uuid", @@ -8679,7 +8700,7 @@ dependencies = [ "pico-args", "serde", "serde_json", - "signal-hook", + "signal-hook 0.4.1", "signal-hook-tokio", "tokio", "which", @@ -8752,7 +8773,6 @@ dependencies = [ "serde", "serde_json", "tauri-utils", - "toml 0.9.10+spec-1.1.0", "walkdir", ] @@ -8897,7 +8917,7 @@ dependencies = [ "swift-rs", "tauri", "thiserror 2.0.12", - "toml 0.9.10+spec-1.1.0", + "toml 1.0.6+spec-1.1.0", "url", "urlpattern", "uuid", @@ -8912,7 +8932,7 @@ checksum = "7c6d9028d41d4de835e3c482c677a8cb88137ac435d6ff9a71f392d4421576c9" dependencies = [ "embed-resource", "indexmap 2.11.4", - "toml 0.9.10+spec-1.1.0", + "toml 0.9.12+spec-1.1.0", ] [[package]] @@ -9241,9 +9261,9 @@ dependencies = [ [[package]] name = "toml" -version = "0.9.10+spec-1.1.0" +version = "0.9.12+spec-1.1.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "0825052159284a1a8b4d6c0c86cbc801f2da5afd2b225fa548c72f2e74002f48" +checksum = "cf92845e79fc2e2def6a5d828f0801e29a2f8acc037becc5ab08595c7d5e9863" dependencies = [ "indexmap 2.11.4", "serde_core", @@ -9254,6 +9274,21 @@ dependencies = [ "winnow 0.7.14", ] +[[package]] +name = "toml" +version = "1.0.6+spec-1.1.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "399b1124a3c9e16766831c6bba21e50192572cdd98706ea114f9502509686ffc" +dependencies = [ + "indexmap 2.11.4", + "serde_core", + "serde_spanned 1.0.4", + "toml_datetime 1.0.0+spec-1.1.0", + "toml_parser", + "toml_writer", + "winnow 0.7.14", +] + [[package]] name = "toml_datetime" version = "0.6.8" @@ -9272,6 +9307,15 @@ dependencies = [ "serde_core", ] +[[package]] +name = "toml_datetime" +version = "1.0.0+spec-1.1.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "32c2555c699578a4f59f0cc68e5116c8d7cabbd45e1409b989d4be085b53f13e" +dependencies = [ + "serde_core", +] + [[package]] name = "toml_edit" version = "0.19.15" @@ -9309,14 +9353,14 @@ dependencies = [ [[package]] name = "toml_edit" -version = "0.24.0+spec-1.1.0" +version = "0.25.4+spec-1.1.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "8c740b185920170a6d9191122cafef7010bd6270a3824594bff6784c04d7f09e" +checksum = "7193cbd0ce53dc966037f54351dbbcf0d5a642c7f0038c382ef9e677ce8c13f2" dependencies = [ "indexmap 2.11.4", "serde_core", "serde_spanned 1.0.4", - "toml_datetime 0.7.5+spec-1.1.0", + "toml_datetime 1.0.0+spec-1.1.0", "toml_parser", "toml_writer", "winnow 0.7.14", @@ -9324,9 +9368,9 @@ dependencies = [ [[package]] name = "toml_parser" -version = "1.0.6+spec-1.1.0" +version = "1.0.9+spec-1.1.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "a3198b4b0a8e11f09dd03e133c0280504d0801269e9afa46362ffde1cbeebf44" +checksum = "702d4415e08923e7e1ef96cd5727c0dfed80b4d2fa25db9647fe5eb6f7c5a4c4" dependencies = [ "winnow 0.7.14", ] @@ -10246,7 +10290,7 @@ version = "0.1.9" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "cf221c93e13a30d793f7645a0e7762c55d169dbb0a49671918a2319d289b10bb" dependencies = [ - "windows-sys 0.48.0", + "windows-sys 0.59.0", ] [[package]] diff --git a/crates/tauri-build/Cargo.toml b/crates/tauri-build/Cargo.toml index e12c041471b9..26a7f63d6d0b 100644 --- a/crates/tauri-build/Cargo.toml +++ b/crates/tauri-build/Cargo.toml @@ -41,7 +41,6 @@ tauri-winres = "0.3" semver = "1" dirs = "6" glob = "0.3" -toml = "0.9" # Our code requires at least 0.8.21 so don't simplify this to 0.8 schemars = { version = "0.8.21", features = ["preserve_order"] } diff --git a/crates/tauri-cli/Cargo.toml b/crates/tauri-cli/Cargo.toml index 370cdc623c7e..4f95db943b9a 100644 --- a/crates/tauri-cli/Cargo.toml +++ b/crates/tauri-cli/Cargo.toml @@ -36,7 +36,7 @@ name = "cargo-tauri" path = "src/main.rs" [target."cfg(any(target_os = \"linux\", target_os = \"dragonfly\", target_os = \"freebsd\", target_os = \"openbsd\", target_os = \"netbsd\", target_os = \"windows\", target_os = \"macos\"))".dependencies] -cargo-mobile2 = { version = "0.21.1", default-features = false } +cargo-mobile2 = { version = "0.22.3", default-features = false } [dependencies] jsonrpsee = { version = "0.24", features = ["server"] } @@ -56,7 +56,7 @@ notify = "8" notify-debouncer-full = "0.6" shared_child = "1" duct = "1.0" -toml_edit = { version = "0.24", features = ["serde"] } +toml_edit = { version = "0.25", features = ["serde"] } json-patch = "3" tauri-utils = { version = "2.8.3", path = "../tauri-utils", features = [ "isolation", @@ -65,7 +65,7 @@ tauri-utils = { version = "2.8.3", path = "../tauri-utils", features = [ "config-toml", "html-manipulation", ] } -toml = "0.9" +toml = "1" jsonschema = { version = "0.33", default-features = false } handlebars = "6" include_dir = "0.7" diff --git a/crates/tauri-plugin/Cargo.toml b/crates/tauri-plugin/Cargo.toml index c14998107a9e..1f89c33f01e7 100644 --- a/crates/tauri-plugin/Cargo.toml +++ b/crates/tauri-plugin/Cargo.toml @@ -19,7 +19,6 @@ build = [ "dep:serde", "dep:serde_json", "dep:glob", - "dep:toml", "dep:plist", "dep:walkdir", ] @@ -33,7 +32,6 @@ tauri-utils = { version = "2.8.3", default-features = false, features = [ ], path = "../tauri-utils" } serde_json = { version = "1", optional = true } glob = { version = "0.3", optional = true } -toml = { version = "0.9", optional = true } # Our code requires at least 0.8.21 so don't simplify this to 0.8 schemars = { version = "0.8.21", features = ["preserve_order"] } walkdir = { version = "2", optional = true } diff --git a/crates/tauri-utils/Cargo.toml b/crates/tauri-utils/Cargo.toml index 9a1d6637e558..37cd0dd6deb0 100644 --- a/crates/tauri-utils/Cargo.toml +++ b/crates/tauri-utils/Cargo.toml @@ -34,7 +34,8 @@ getrandom = { version = "0.3", optional = true, features = ["std"] } serialize-to-javascript = { version = "0.1.2", optional = true } ctor = "0.2" json5 = { version = "0.4", optional = true } -toml = { version = "0.9", features = ["parse"] } +# Part of public api in error type +toml = { version = ">=0.9, <=1", features = ["parse"] } json-patch = "3.0" # Our code requires at least 0.3.1 glob = "0.3.1" From 5cd42210e0998cbe98f365ba02576a432f656603 Mon Sep 17 00:00:00 2001 From: Seto Elkahfi Date: Fri, 20 Mar 2026 09:32:24 +0100 Subject: [PATCH 48/95] fix(cli): fix ios build when `Metal Toolchain` exist in the system (#14921) --- .changes/fix-ios-metal-toolchain.md | 6 ++++++ crates/tauri-cli/templates/mobile/ios/project.yml | 4 ++-- crates/tauri-cli/tests/fixtures/pbxproj/project.pbxproj | 8 ++++---- ...helpers__pbxproj__tests__project-modified.pbxproj.snap | 8 ++++---- ...uri_cli__helpers__pbxproj__tests__project.pbxproj.snap | 8 ++++---- 5 files changed, 20 insertions(+), 14 deletions(-) create mode 100644 .changes/fix-ios-metal-toolchain.md diff --git a/.changes/fix-ios-metal-toolchain.md b/.changes/fix-ios-metal-toolchain.md new file mode 100644 index 000000000000..ff08280304a2 --- /dev/null +++ b/.changes/fix-ios-metal-toolchain.md @@ -0,0 +1,6 @@ +--- +"tauri-cli": patch:bug +"@tauri-apps/cli": patch:bug +--- + +Fix iOS build failure when `Metal Toolchain` is installed by using explicit `$(DEVELOPER_DIR)/Toolchains/XcodeDefault.xctoolchain` path instead of `$(TOOLCHAIN_DIR)` for Swift library search paths. \ No newline at end of file diff --git a/crates/tauri-cli/templates/mobile/ios/project.yml b/crates/tauri-cli/templates/mobile/ios/project.yml index 1994d5e5aff7..c23c1949e33d 100644 --- a/crates/tauri-cli/templates/mobile/ios/project.yml +++ b/crates/tauri-cli/templates/mobile/ios/project.yml @@ -78,8 +78,8 @@ targets: ENABLE_BITCODE: false ARCHS: [{{join ios-valid-archs}}] VALID_ARCHS: {{~#each ios-valid-archs}} {{this}} {{/each}} - LIBRARY_SEARCH_PATHS[arch=x86_64]: $(inherited) $(PROJECT_DIR)/Externals/x86_64/$(CONFIGURATION) $(SDKROOT)/usr/lib/swift $(TOOLCHAIN_DIR)/usr/lib/swift/$(PLATFORM_NAME) $(TOOLCHAIN_DIR)/usr/lib/swift-5.0/$(PLATFORM_NAME) - LIBRARY_SEARCH_PATHS[arch=arm64]: $(inherited) $(PROJECT_DIR)/Externals/arm64/$(CONFIGURATION) $(SDKROOT)/usr/lib/swift $(TOOLCHAIN_DIR)/usr/lib/swift/$(PLATFORM_NAME) $(TOOLCHAIN_DIR)/usr/lib/swift-5.0/$(PLATFORM_NAME) + LIBRARY_SEARCH_PATHS[arch=x86_64]: $(inherited) $(PROJECT_DIR)/Externals/x86_64/$(CONFIGURATION) $(SDKROOT)/usr/lib/swift $(DEVELOPER_DIR)/Toolchains/XcodeDefault.xctoolchain/usr/lib/swift/$(PLATFORM_NAME) $(DEVELOPER_DIR)/Toolchains/XcodeDefault.xctoolchain/usr/lib/swift-5.0/$(PLATFORM_NAME) + LIBRARY_SEARCH_PATHS[arch=arm64]: $(inherited) $(PROJECT_DIR)/Externals/arm64/$(CONFIGURATION) $(SDKROOT)/usr/lib/swift $(DEVELOPER_DIR)/Toolchains/XcodeDefault.xctoolchain/usr/lib/swift/$(PLATFORM_NAME) $(DEVELOPER_DIR)/Toolchains/XcodeDefault.xctoolchain/usr/lib/swift-5.0/$(PLATFORM_NAME) ALWAYS_EMBED_SWIFT_STANDARD_LIBRARIES: true EXCLUDED_ARCHS[sdk=iphoneos*]: x86_64 groups: [app] diff --git a/crates/tauri-cli/tests/fixtures/pbxproj/project.pbxproj b/crates/tauri-cli/tests/fixtures/pbxproj/project.pbxproj index a3c74da6b00d..2604ffdc40a5 100644 --- a/crates/tauri-cli/tests/fixtures/pbxproj/project.pbxproj +++ b/crates/tauri-cli/tests/fixtures/pbxproj/project.pbxproj @@ -398,8 +398,8 @@ "$(inherited)", "@executable_path/Frameworks", ); - "LIBRARY_SEARCH_PATHS[arch=arm64]" = "$(inherited) $(PROJECT_DIR)/Externals/arm64/$(CONFIGURATION) $(SDKROOT)/usr/lib/swift $(TOOLCHAIN_DIR)/usr/lib/swift/$(PLATFORM_NAME) $(TOOLCHAIN_DIR)/usr/lib/swift-5.0/$(PLATFORM_NAME)"; - "LIBRARY_SEARCH_PATHS[arch=x86_64]" = "$(inherited) $(PROJECT_DIR)/Externals/x86_64/$(CONFIGURATION) $(SDKROOT)/usr/lib/swift $(TOOLCHAIN_DIR)/usr/lib/swift/$(PLATFORM_NAME) $(TOOLCHAIN_DIR)/usr/lib/swift-5.0/$(PLATFORM_NAME)"; + "LIBRARY_SEARCH_PATHS[arch=arm64]" = "$(inherited) $(PROJECT_DIR)/Externals/arm64/$(CONFIGURATION) $(SDKROOT)/usr/lib/swift $(DEVELOPER_DIR)/Toolchains/XcodeDefault.xctoolchain/usr/lib/swift/$(PLATFORM_NAME) $(DEVELOPER_DIR)/Toolchains/XcodeDefault.xctoolchain/usr/lib/swift-5.0/$(PLATFORM_NAME)"; + "LIBRARY_SEARCH_PATHS[arch=x86_64]" = "$(inherited) $(PROJECT_DIR)/Externals/x86_64/$(CONFIGURATION) $(SDKROOT)/usr/lib/swift $(DEVELOPER_DIR)/Toolchains/XcodeDefault.xctoolchain/usr/lib/swift/$(PLATFORM_NAME) $(DEVELOPER_DIR)/Toolchains/XcodeDefault.xctoolchain/usr/lib/swift-5.0/$(PLATFORM_NAME)"; PRODUCT_BUNDLE_IDENTIFIER = com.tauri.api; PRODUCT_NAME = "Tauri API"; SDKROOT = iphoneos; @@ -430,8 +430,8 @@ "$(inherited)", "@executable_path/Frameworks", ); - "LIBRARY_SEARCH_PATHS[arch=arm64]" = "$(inherited) $(PROJECT_DIR)/Externals/arm64/$(CONFIGURATION) $(SDKROOT)/usr/lib/swift $(TOOLCHAIN_DIR)/usr/lib/swift/$(PLATFORM_NAME) $(TOOLCHAIN_DIR)/usr/lib/swift-5.0/$(PLATFORM_NAME)"; - "LIBRARY_SEARCH_PATHS[arch=x86_64]" = "$(inherited) $(PROJECT_DIR)/Externals/x86_64/$(CONFIGURATION) $(SDKROOT)/usr/lib/swift $(TOOLCHAIN_DIR)/usr/lib/swift/$(PLATFORM_NAME) $(TOOLCHAIN_DIR)/usr/lib/swift-5.0/$(PLATFORM_NAME)"; + "LIBRARY_SEARCH_PATHS[arch=arm64]" = "$(inherited) $(PROJECT_DIR)/Externals/arm64/$(CONFIGURATION) $(SDKROOT)/usr/lib/swift $(DEVELOPER_DIR)/Toolchains/XcodeDefault.xctoolchain/usr/lib/swift/$(PLATFORM_NAME) $(DEVELOPER_DIR)/Toolchains/XcodeDefault.xctoolchain/usr/lib/swift-5.0/$(PLATFORM_NAME)"; + "LIBRARY_SEARCH_PATHS[arch=x86_64]" = "$(inherited) $(PROJECT_DIR)/Externals/x86_64/$(CONFIGURATION) $(SDKROOT)/usr/lib/swift $(DEVELOPER_DIR)/Toolchains/XcodeDefault.xctoolchain/usr/lib/swift/$(PLATFORM_NAME) $(DEVELOPER_DIR)/Toolchains/XcodeDefault.xctoolchain/usr/lib/swift-5.0/$(PLATFORM_NAME)"; PRODUCT_BUNDLE_IDENTIFIER = com.tauri.api; PRODUCT_NAME = "Tauri API"; SDKROOT = iphoneos; diff --git a/crates/tauri-cli/tests/fixtures/pbxproj/snapshots/tauri_cli__helpers__pbxproj__tests__project-modified.pbxproj.snap b/crates/tauri-cli/tests/fixtures/pbxproj/snapshots/tauri_cli__helpers__pbxproj__tests__project-modified.pbxproj.snap index a3dc6bf5ed43..97ba4c6235c9 100644 --- a/crates/tauri-cli/tests/fixtures/pbxproj/snapshots/tauri_cli__helpers__pbxproj__tests__project-modified.pbxproj.snap +++ b/crates/tauri-cli/tests/fixtures/pbxproj/snapshots/tauri_cli__helpers__pbxproj__tests__project-modified.pbxproj.snap @@ -402,8 +402,8 @@ expression: pbxproj.serialize() "$(inherited)", "@executable_path/Frameworks", ); - "LIBRARY_SEARCH_PATHS[arch=arm64]" = "$(inherited) $(PROJECT_DIR)/Externals/arm64/$(CONFIGURATION) $(SDKROOT)/usr/lib/swift $(TOOLCHAIN_DIR)/usr/lib/swift/$(PLATFORM_NAME) $(TOOLCHAIN_DIR)/usr/lib/swift-5.0/$(PLATFORM_NAME)"; - "LIBRARY_SEARCH_PATHS[arch=x86_64]" = "$(inherited) $(PROJECT_DIR)/Externals/x86_64/$(CONFIGURATION) $(SDKROOT)/usr/lib/swift $(TOOLCHAIN_DIR)/usr/lib/swift/$(PLATFORM_NAME) $(TOOLCHAIN_DIR)/usr/lib/swift-5.0/$(PLATFORM_NAME)"; + "LIBRARY_SEARCH_PATHS[arch=arm64]" = "$(inherited) $(PROJECT_DIR)/Externals/arm64/$(CONFIGURATION) $(SDKROOT)/usr/lib/swift $(DEVELOPER_DIR)/Toolchains/XcodeDefault.xctoolchain/usr/lib/swift/$(PLATFORM_NAME) $(DEVELOPER_DIR)/Toolchains/XcodeDefault.xctoolchain/usr/lib/swift-5.0/$(PLATFORM_NAME)"; + "LIBRARY_SEARCH_PATHS[arch=x86_64]" = "$(inherited) $(PROJECT_DIR)/Externals/x86_64/$(CONFIGURATION) $(SDKROOT)/usr/lib/swift $(DEVELOPER_DIR)/Toolchains/XcodeDefault.xctoolchain/usr/lib/swift/$(PLATFORM_NAME) $(DEVELOPER_DIR)/Toolchains/XcodeDefault.xctoolchain/usr/lib/swift-5.0/$(PLATFORM_NAME)"; PRODUCT_BUNDLE_IDENTIFIER = com.tauri.api; PRODUCT_NAME = "Tauri API"; SDKROOT = iphoneos; @@ -434,8 +434,8 @@ expression: pbxproj.serialize() "$(inherited)", "@executable_path/Frameworks", ); - "LIBRARY_SEARCH_PATHS[arch=arm64]" = "$(inherited) $(PROJECT_DIR)/Externals/arm64/$(CONFIGURATION) $(SDKROOT)/usr/lib/swift $(TOOLCHAIN_DIR)/usr/lib/swift/$(PLATFORM_NAME) $(TOOLCHAIN_DIR)/usr/lib/swift-5.0/$(PLATFORM_NAME)"; - "LIBRARY_SEARCH_PATHS[arch=x86_64]" = "$(inherited) $(PROJECT_DIR)/Externals/x86_64/$(CONFIGURATION) $(SDKROOT)/usr/lib/swift $(TOOLCHAIN_DIR)/usr/lib/swift/$(PLATFORM_NAME) $(TOOLCHAIN_DIR)/usr/lib/swift-5.0/$(PLATFORM_NAME)"; + "LIBRARY_SEARCH_PATHS[arch=arm64]" = "$(inherited) $(PROJECT_DIR)/Externals/arm64/$(CONFIGURATION) $(SDKROOT)/usr/lib/swift $(DEVELOPER_DIR)/Toolchains/XcodeDefault.xctoolchain/usr/lib/swift/$(PLATFORM_NAME) $(DEVELOPER_DIR)/Toolchains/XcodeDefault.xctoolchain/usr/lib/swift-5.0/$(PLATFORM_NAME)"; + "LIBRARY_SEARCH_PATHS[arch=x86_64]" = "$(inherited) $(PROJECT_DIR)/Externals/x86_64/$(CONFIGURATION) $(SDKROOT)/usr/lib/swift $(DEVELOPER_DIR)/Toolchains/XcodeDefault.xctoolchain/usr/lib/swift/$(PLATFORM_NAME) $(DEVELOPER_DIR)/Toolchains/XcodeDefault.xctoolchain/usr/lib/swift-5.0/$(PLATFORM_NAME)"; PRODUCT_BUNDLE_IDENTIFIER = com.tauri.api; PRODUCT_NAME = "Tauri Test"; SDKROOT = iphoneos; diff --git a/crates/tauri-cli/tests/fixtures/pbxproj/snapshots/tauri_cli__helpers__pbxproj__tests__project.pbxproj.snap b/crates/tauri-cli/tests/fixtures/pbxproj/snapshots/tauri_cli__helpers__pbxproj__tests__project.pbxproj.snap index d84a8c0e71ba..24c4db8b9f99 100644 --- a/crates/tauri-cli/tests/fixtures/pbxproj/snapshots/tauri_cli__helpers__pbxproj__tests__project.pbxproj.snap +++ b/crates/tauri-cli/tests/fixtures/pbxproj/snapshots/tauri_cli__helpers__pbxproj__tests__project.pbxproj.snap @@ -708,13 +708,13 @@ Pbxproj { identation: "\t\t\t\t", line_number: 400, key: "\"LIBRARY_SEARCH_PATHS[arch=arm64]\"", - value: "\"$(inherited) $(PROJECT_DIR)/Externals/arm64/$(CONFIGURATION) $(SDKROOT)/usr/lib/swift $(TOOLCHAIN_DIR)/usr/lib/swift/$(PLATFORM_NAME) $(TOOLCHAIN_DIR)/usr/lib/swift-5.0/$(PLATFORM_NAME)\"", + value: "\"$(inherited) $(PROJECT_DIR)/Externals/arm64/$(CONFIGURATION) $(SDKROOT)/usr/lib/swift $(DEVELOPER_DIR)/Toolchains/XcodeDefault.xctoolchain/usr/lib/swift/$(PLATFORM_NAME) $(DEVELOPER_DIR)/Toolchains/XcodeDefault.xctoolchain/usr/lib/swift-5.0/$(PLATFORM_NAME)\"", }, BuildSettings { identation: "\t\t\t\t", line_number: 401, key: "\"LIBRARY_SEARCH_PATHS[arch=x86_64]\"", - value: "\"$(inherited) $(PROJECT_DIR)/Externals/x86_64/$(CONFIGURATION) $(SDKROOT)/usr/lib/swift $(TOOLCHAIN_DIR)/usr/lib/swift/$(PLATFORM_NAME) $(TOOLCHAIN_DIR)/usr/lib/swift-5.0/$(PLATFORM_NAME)\"", + value: "\"$(inherited) $(PROJECT_DIR)/Externals/x86_64/$(CONFIGURATION) $(SDKROOT)/usr/lib/swift $(DEVELOPER_DIR)/Toolchains/XcodeDefault.xctoolchain/usr/lib/swift/$(PLATFORM_NAME) $(DEVELOPER_DIR)/Toolchains/XcodeDefault.xctoolchain/usr/lib/swift-5.0/$(PLATFORM_NAME)\"", }, BuildSettings { identation: "\t\t\t\t", @@ -820,13 +820,13 @@ Pbxproj { identation: "\t\t\t\t", line_number: 432, key: "\"LIBRARY_SEARCH_PATHS[arch=arm64]\"", - value: "\"$(inherited) $(PROJECT_DIR)/Externals/arm64/$(CONFIGURATION) $(SDKROOT)/usr/lib/swift $(TOOLCHAIN_DIR)/usr/lib/swift/$(PLATFORM_NAME) $(TOOLCHAIN_DIR)/usr/lib/swift-5.0/$(PLATFORM_NAME)\"", + value: "\"$(inherited) $(PROJECT_DIR)/Externals/arm64/$(CONFIGURATION) $(SDKROOT)/usr/lib/swift $(DEVELOPER_DIR)/Toolchains/XcodeDefault.xctoolchain/usr/lib/swift/$(PLATFORM_NAME) $(DEVELOPER_DIR)/Toolchains/XcodeDefault.xctoolchain/usr/lib/swift-5.0/$(PLATFORM_NAME)\"", }, BuildSettings { identation: "\t\t\t\t", line_number: 433, key: "\"LIBRARY_SEARCH_PATHS[arch=x86_64]\"", - value: "\"$(inherited) $(PROJECT_DIR)/Externals/x86_64/$(CONFIGURATION) $(SDKROOT)/usr/lib/swift $(TOOLCHAIN_DIR)/usr/lib/swift/$(PLATFORM_NAME) $(TOOLCHAIN_DIR)/usr/lib/swift-5.0/$(PLATFORM_NAME)\"", + value: "\"$(inherited) $(PROJECT_DIR)/Externals/x86_64/$(CONFIGURATION) $(SDKROOT)/usr/lib/swift $(DEVELOPER_DIR)/Toolchains/XcodeDefault.xctoolchain/usr/lib/swift/$(PLATFORM_NAME) $(DEVELOPER_DIR)/Toolchains/XcodeDefault.xctoolchain/usr/lib/swift-5.0/$(PLATFORM_NAME)\"", }, BuildSettings { identation: "\t\t\t\t", From 9fe7e27f73b8c446d65858773648d98e21d88137 Mon Sep 17 00:00:00 2001 From: sftse Date: Fri, 20 Mar 2026 11:18:29 +0100 Subject: [PATCH 49/95] Refactors (#15117) * refactor(tauri-build): make better use of OsString Co-authored-by: Tony <68118705+Legend-Master@users.noreply.github.com> * refactor(tauri-build): dont wrap const value in function * refactor(tauri-build): None codepath is never used, replace Option with Vec * refactor(tauri): use blocking apis where it makes sense * refactor(tauri): better use of std::fs API * refactor(tauri): rewind to start * refactor(tauri): fmt * add change file --- .changes/change-pr-15117.md | 6 +++ crates/tauri-build/src/lib.rs | 11 ++-- crates/tauri-build/src/manifest.rs | 38 +++++-------- crates/tauri/src/protocol/asset.rs | 86 ++++++++++++------------------ 4 files changed, 59 insertions(+), 82 deletions(-) create mode 100644 .changes/change-pr-15117.md diff --git a/.changes/change-pr-15117.md b/.changes/change-pr-15117.md new file mode 100644 index 000000000000..85eddd21f6ff --- /dev/null +++ b/.changes/change-pr-15117.md @@ -0,0 +1,6 @@ +--- +"tauri-build": patch:enhance +"tauri": patch:enhance +--- + +Simplify async-sync code boundaries, no externally visible changes diff --git a/crates/tauri-build/src/lib.rs b/crates/tauri-build/src/lib.rs index ddfac0cc5c7b..a6baf947665c 100644 --- a/crates/tauri-build/src/lib.rs +++ b/crates/tauri-build/src/lib.rs @@ -411,7 +411,8 @@ impl Attributes { } pub fn is_dev() -> bool { - env::var("DEP_TAURI_DEV").expect("missing `cargo:dev` instruction, please update tauri to latest") + env::var_os("DEP_TAURI_DEV") + .expect("missing `cargo:dev` instruction, please update tauri to latest") == "true" } @@ -458,7 +459,7 @@ pub fn try_build(attributes: Attributes) -> Result<()> { println!("cargo:rerun-if-env-changed=TAURI_CONFIG"); - let target_os = env::var("CARGO_CFG_TARGET_OS").unwrap(); + let target_os = env::var_os("CARGO_CFG_TARGET_OS").unwrap(); let mobile = target_os == "ios" || target_os == "android"; cfg_alias("desktop", !mobile); cfg_alias("mobile", mobile); @@ -503,7 +504,7 @@ pub fn try_build(attributes: Attributes) -> Result<()> { let cargo_toml_path = Path::new("Cargo.toml").canonicalize()?; let mut manifest = Manifest::::from_path_with_metadata(cargo_toml_path)?; - let out_dir = PathBuf::from(env::var("OUT_DIR").unwrap()); + let out_dir = PathBuf::from(env::var_os("OUT_DIR").unwrap()); manifest::check(&config, &mut manifest)?; @@ -538,7 +539,7 @@ pub fn try_build(attributes: Attributes) -> Result<()> { .bundle .resources .clone() - .unwrap_or_else(|| BundleResources::List(Vec::new())); + .unwrap_or(BundleResources::List(Vec::new())); if target_triple.contains("windows") { if let Some(fixed_webview2_runtime_path) = match &config.bundle.windows.webview_install_mode { WebviewInstallMode::FixedRuntime { path } => Some(path), @@ -682,7 +683,7 @@ pub fn try_build(attributes: Attributes) -> Result<()> { } } "msvc" => { - if env::var("STATIC_VCRUNTIME").is_ok_and(|v| v == "true") { + if env::var_os("STATIC_VCRUNTIME").is_some_and(|v| v == "true") { static_vcruntime::build(); } } diff --git a/crates/tauri-build/src/manifest.rs b/crates/tauri-build/src/manifest.rs index 30033e9bc2c3..5aa668eeae1c 100644 --- a/crates/tauri-build/src/manifest.rs +++ b/crates/tauri-build/src/manifest.rs @@ -23,7 +23,7 @@ struct AllowlistedDependency { name: String, alias: Option, kind: DependencyKind, - all_cli_managed_features: Option>, + all_cli_managed_features: Vec<&'static str>, expected_features: Vec, } @@ -33,7 +33,7 @@ pub fn check(config: &Config, manifest: &mut Manifest) -> Result<()> { name: "tauri-build".into(), alias: None, kind: DependencyKind::Build, - all_cli_managed_features: Some(vec!["isolation"]), + all_cli_managed_features: vec!["isolation"], expected_features: match config.app.security.pattern { PatternKind::Isolation { .. } => vec!["isolation".to_string()], _ => vec![], @@ -43,12 +43,10 @@ pub fn check(config: &Config, manifest: &mut Manifest) -> Result<()> { name: "tauri".into(), alias: None, kind: DependencyKind::Normal, - all_cli_managed_features: Some( - AppConfig::all_features() - .into_iter() - .filter(|f| f != &"tray-icon") - .collect(), - ), + all_cli_managed_features: AppConfig::all_features() + .into_iter() + .filter(|f| f != &"tray-icon") + .collect(), expected_features: config .app .features() @@ -129,23 +127,13 @@ fn check_features(dependency: Dependency, metadata: &AllowlistedDependency) -> R Dependency::Inherited(dep) => dep.features, }; - let diff = if let Some(all_cli_managed_features) = &metadata.all_cli_managed_features { - features_diff( - &features - .into_iter() - .filter(|f| all_cli_managed_features.contains(&f.as_str())) - .collect::>(), - &metadata.expected_features, - ) - } else { - features_diff( - &features - .into_iter() - .filter(|f| f.starts_with("allow-")) - .collect::>(), - &metadata.expected_features, - ) - }; + let diff = features_diff( + &features + .into_iter() + .filter(|f| metadata.all_cli_managed_features.contains(&f.as_str())) + .collect::>(), + &metadata.expected_features, + ); let mut error_message = String::new(); if !diff.remove.is_empty() { diff --git a/crates/tauri/src/protocol/asset.rs b/crates/tauri/src/protocol/asset.rs index 78ff0e38a44a..25f822059296 100644 --- a/crates/tauri/src/protocol/asset.rs +++ b/crates/tauri/src/protocol/asset.rs @@ -5,10 +5,10 @@ use crate::{path::SafePathBuf, scope, webview::UriSchemeProtocolHandler}; use http::{header::*, status::StatusCode, Request, Response}; use http_range::HttpRange; +use std::fs::File; +use std::io::{Read, Seek, Write}; use std::{borrow::Cow, io::SeekFrom}; use tauri_utils::mime_type::MimeType; -use tokio::fs::File; -use tokio::io::{AsyncReadExt, AsyncSeekExt, AsyncWriteExt}; pub fn get(scope: scope::fs::Scope, window_origin: String) -> UriSchemeProtocolHandler { Box::new( @@ -49,7 +49,7 @@ fn get_response( } // Separate block for easier error handling - let mut file = match crate::async_runtime::safe_block_on(File::open(path.clone())) { + let mut file = match File::open(path.clone()) { Ok(file) => file, Err(e) => { #[cfg(target_os = "android")] @@ -70,32 +70,20 @@ fn get_response( } }; - let (mut file, len, mime_type, read_bytes) = crate::async_runtime::safe_block_on(async move { - // get file length - let len = { - let old_pos = file.stream_position().await?; - let len = file.seek(SeekFrom::End(0)).await?; - file.seek(SeekFrom::Start(old_pos)).await?; - len - }; - + let len = file.metadata()?.len(); + let (mime_type, read_bytes) = { // get file mime type - let (mime_type, read_bytes) = { - let nbytes = len.min(8192); - let mut magic_buf = Vec::with_capacity(nbytes as usize); - let old_pos = file.stream_position().await?; - (&mut file).take(nbytes).read_to_end(&mut magic_buf).await?; - file.seek(SeekFrom::Start(old_pos)).await?; - ( - MimeType::parse(&magic_buf, &path), - // return the `magic_bytes` if we read the whole file - // to avoid reading it again later if this is not a range request - if len < 8192 { Some(magic_buf) } else { None }, - ) - }; - - Ok::<(File, u64, String, Option>), anyhow::Error>((file, len, mime_type, read_bytes)) - })?; + let nbytes = len.min(8192); + let mut magic_buf = Vec::with_capacity(nbytes as usize); + (&mut file).take(nbytes).read_to_end(&mut magic_buf)?; + file.rewind()?; + ( + MimeType::parse(&magic_buf, &path), + // return the `magic_bytes` if we read the whole file + // to avoid reading it again later if this is not a range request + if len < 8192 { Some(magic_buf) } else { None }, + ) + }; resp = resp.header(CONTENT_TYPE, &mime_type); @@ -148,12 +136,12 @@ fn get_response( // calculate number of bytes needed to be read let nbytes = end + 1 - start; - let buf = crate::async_runtime::safe_block_on(async move { + let buf = { let mut buf = Vec::with_capacity(nbytes as usize); - file.seek(SeekFrom::Start(start)).await?; - file.take(nbytes).read_to_end(&mut buf).await?; - Ok::, anyhow::Error>(buf) - })?; + file.seek(SeekFrom::Start(start))?; + file.take(nbytes).read_to_end(&mut buf)?; + buf + }; resp = resp.header(CONTENT_RANGE, format!("bytes {start}-{end}/{len}")); resp = resp.header(CONTENT_LENGTH, end + 1 - start); @@ -186,38 +174,34 @@ fn get_response( format!("multipart/byteranges; boundary={boundary}"), ); - let buf = crate::async_runtime::safe_block_on(async move { + let buf = { // multi-part range header let mut buf = Vec::new(); for (start, end) in ranges { // a new range is being written, write the range boundary - buf.write_all(boundary_sep.as_bytes()).await?; + buf.write_all(boundary_sep.as_bytes())?; // write the needed headers `Content-Type` and `Content-Range` - buf - .write_all(format!("{CONTENT_TYPE}: {mime_type}\r\n").as_bytes()) - .await?; - buf - .write_all(format!("{CONTENT_RANGE}: bytes {start}-{end}/{len}\r\n").as_bytes()) - .await?; + buf.write_all(format!("{CONTENT_TYPE}: {mime_type}\r\n").as_bytes())?; + buf.write_all(format!("{CONTENT_RANGE}: bytes {start}-{end}/{len}\r\n").as_bytes())?; // write the separator to indicate the start of the range body - buf.write_all("\r\n".as_bytes()).await?; + buf.write_all("\r\n".as_bytes())?; // calculate number of bytes needed to be read let nbytes = end + 1 - start; let mut local_buf = Vec::with_capacity(nbytes as usize); - file.seek(SeekFrom::Start(start)).await?; - (&mut file).take(nbytes).read_to_end(&mut local_buf).await?; + file.seek(SeekFrom::Start(start))?; + (&mut file).take(nbytes).read_to_end(&mut local_buf)?; buf.extend_from_slice(&local_buf); } // all ranges have been written, write the closing boundary - buf.write_all(boundary_closer.as_bytes()).await?; + buf.write_all(boundary_closer.as_bytes())?; - Ok::, anyhow::Error>(buf) - })?; + buf + }; resp.body(buf.into()) } } else if request.method() == http::Method::HEAD { @@ -230,11 +214,9 @@ fn get_response( let buf = if let Some(b) = read_bytes { b } else { - crate::async_runtime::safe_block_on(async move { - let mut local_buf = Vec::with_capacity(len as usize); - file.read_to_end(&mut local_buf).await?; - Ok::, anyhow::Error>(local_buf) - })? + let mut local_buf = Vec::with_capacity(len as usize); + file.read_to_end(&mut local_buf)?; + local_buf }; resp = resp.header(CONTENT_LENGTH, len); resp.body(buf.into()) From 7fea0755d0ae3f4720dc02cf7b769bb4ac7cbb69 Mon Sep 17 00:00:00 2001 From: "renovate[bot]" <29139614+renovate[bot]@users.noreply.github.com> Date: Sat, 21 Mar 2026 10:08:33 +0800 Subject: [PATCH 50/95] chore(deps): update rust crate tar to v0.4.45 [security] (#15129) Co-authored-by: renovate[bot] <29139614+renovate[bot]@users.noreply.github.com> --- Cargo.lock | 18 +++++++++--------- 1 file changed, 9 insertions(+), 9 deletions(-) diff --git a/Cargo.lock b/Cargo.lock index d9cbf78133ab..32ef61af53e3 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -1321,7 +1321,7 @@ source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "117725a109d387c937a1533ce01b450cbde6b88abceea8473c4d7a85853cda3c" dependencies = [ "lazy_static", - "windows-sys 0.59.0", + "windows-sys 0.48.0", ] [[package]] @@ -2345,7 +2345,7 @@ source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "33d852cb9b869c2a9b3df2f71a3074817f01e1844f839a144f5fcef059a4eb5d" dependencies = [ "libc", - "windows-sys 0.59.0", + "windows-sys 0.52.0", ] [[package]] @@ -4320,7 +4320,7 @@ source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "fc2f4eb4bc735547cfed7c0a4922cbd04a4655978c09b54f1f7b228750664c34" dependencies = [ "cfg-if", - "windows-targets 0.52.6", + "windows-targets 0.48.5", ] [[package]] @@ -6994,7 +6994,7 @@ dependencies = [ "errno", "libc", "linux-raw-sys 0.4.15", - "windows-sys 0.59.0", + "windows-sys 0.52.0", ] [[package]] @@ -7007,7 +7007,7 @@ dependencies = [ "errno", "libc", "linux-raw-sys 0.9.4", - "windows-sys 0.59.0", + "windows-sys 0.52.0", ] [[package]] @@ -8425,9 +8425,9 @@ checksum = "55937e1799185b12863d447f42597ed69d9928686b8d88a1df17376a097d8369" [[package]] name = "tar" -version = "0.4.43" +version = "0.4.45" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "c65998313f8e17d0d553d28f91a0df93e4dbbbf770279c7bc21ca0f09ea1a1f6" +checksum = "22692a6476a21fa75fdfc11d452fda482af402c008cdbaf3476414e122040973" dependencies = [ "filetime", "libc", @@ -8957,7 +8957,7 @@ dependencies = [ "getrandom 0.2.15", "once_cell", "rustix 0.38.43", - "windows-sys 0.59.0", + "windows-sys 0.52.0", ] [[package]] @@ -10290,7 +10290,7 @@ version = "0.1.9" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "cf221c93e13a30d793f7645a0e7762c55d169dbb0a49671918a2319d289b10bb" dependencies = [ - "windows-sys 0.59.0", + "windows-sys 0.48.0", ] [[package]] From 6b0bdf24650c26adb5c3bb4eb3e6a21321e15429 Mon Sep 17 00:00:00 2001 From: Lucas Fernandes Nogueira Date: Mon, 23 Mar 2026 13:32:02 -0300 Subject: [PATCH 51/95] feat(mobile): multi-window support (#14484) Co-authored-by: FabianLars <30730186+FabianLars@users.noreply.github.com> --- .changes/multi-window-mobile.md | 8 + .changes/tauri-dbus.md | 5 + Cargo.lock | 444 +++++++-- crates/tauri-build/src/mobile.rs | 3 +- crates/tauri-cli/config.schema.json | 21 + .../mobile/android/app/build.gradle.kts | 1 + crates/tauri-runtime-wry/Cargo.toml | 8 +- crates/tauri-runtime-wry/src/lib.rs | 185 ++-- crates/tauri-runtime/Cargo.toml | 2 + crates/tauri-runtime/src/lib.rs | 22 + crates/tauri-runtime/src/webview.rs | 4 +- crates/tauri-runtime/src/window.rs | 17 + .../schemas/config.schema.json | 21 + crates/tauri-utils/src/config.rs | 30 +- crates/tauri/Cargo.toml | 12 +- crates/tauri/build.rs | 3 + .../mobile/android-codegen/TauriActivity.kt | 48 +- .../src/main/java/app/tauri/plugin/Plugin.kt | 24 + .../java/app/tauri/plugin/PluginManager.kt | 61 +- .../app/autogenerated/reference.md | 27 + .../window/autogenerated/reference.md | 54 + crates/tauri/scripts/bundle.global.js | 2 +- crates/tauri/src/app.rs | 94 ++ crates/tauri/src/app/plugin.rs | 6 + crates/tauri/src/lib.rs | 14 +- crates/tauri/src/test/mock_runtime.rs | 25 + crates/tauri/src/webview/mod.rs | 10 + crates/tauri/src/webview/plugin.rs | 201 ++-- crates/tauri/src/webview/webview_window.rs | 460 +++++---- crates/tauri/src/window/mod.rs | 926 ++++++++++-------- crates/tauri/src/window/plugin.rs | 347 +++---- examples/api/src-tauri/src/lib.rs | 19 +- packages/api/src/app.ts | 7 +- packages/api/src/window.ts | 29 + 34 files changed, 2055 insertions(+), 1085 deletions(-) create mode 100644 .changes/multi-window-mobile.md create mode 100644 .changes/tauri-dbus.md diff --git a/.changes/multi-window-mobile.md b/.changes/multi-window-mobile.md new file mode 100644 index 000000000000..57af55470ac8 --- /dev/null +++ b/.changes/multi-window-mobile.md @@ -0,0 +1,8 @@ +--- +"tauri": minor:feat +"tauri-runtime-wry": minor:feat +"tauri-runtime": minor:feat +"tauri-utils": minor:feat +--- + +Support creating multiple windows on Android (activity embedding) and iOS (scenes). diff --git a/.changes/tauri-dbus.md b/.changes/tauri-dbus.md new file mode 100644 index 000000000000..cab4b325103c --- /dev/null +++ b/.changes/tauri-dbus.md @@ -0,0 +1,5 @@ +--- +tauri: minor:feat +--- + +Added `dbus` feature flag (enabled by default) which is required for theme detection on Linux. diff --git a/Cargo.lock b/Cargo.lock index 32ef61af53e3..3ee41ee22db5 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -815,11 +815,11 @@ dependencies = [ [[package]] name = "block2" -version = "0.6.0" +version = "0.6.2" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "1d59b4c170e16f0405a2e95aff44432a0d41aa97675f3d52623effe95792a037" +checksum = "cdeb9d870516001442e364c5220d3574d2da8dc765554b4a617230d33fa58ef5" dependencies = [ - "objc2 0.6.0", + "objc2 0.6.4", ] [[package]] @@ -1462,6 +1462,19 @@ dependencies = [ "libc", ] +[[package]] +name = "core-graphics" +version = "0.25.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "064badf302c3194842cf2c5d61f56cc88e54a759313879cdf03abdd27d0c3b97" +dependencies = [ + "bitflags 2.7.0", + "core-foundation 0.10.0", + "core-graphics-types", + "foreign-types 0.5.0", + "libc", +] + [[package]] name = "core-graphics-types" version = "0.2.0" @@ -1633,6 +1646,19 @@ dependencies = [ "syn 1.0.109", ] +[[package]] +name = "cssparser" +version = "0.36.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "dae61cf9c0abb83bd659dab65b7e4e38d8236824c85f0f804f173567bda257d2" +dependencies = [ + "cssparser-macros", + "dtoa-short", + "itoa", + "phf 0.13.1", + "smallvec", +] + [[package]] name = "cssparser-macros" version = "0.6.1" @@ -1786,6 +1812,17 @@ dependencies = [ "generic-array", ] +[[package]] +name = "dbus" +version = "0.9.10" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "21b3aa68d7e7abee336255bd7248ea965cc393f3e70411135a6f6a4b651345d4" +dependencies = [ + "libc", + "libdbus-sys", + "windows-sys 0.59.0", +] + [[package]] name = "der" version = "0.7.9" @@ -1868,7 +1905,16 @@ version = "1.0.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "4a9b99b9cbbe49445b21764dc0625032a89b145a2642e67603e1c936f5458d05" dependencies = [ - "derive_more-impl", + "derive_more-impl 1.0.0", +] + +[[package]] +name = "derive_more" +version = "2.0.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "093242cf7570c207c83073cf82f79706fe7b8317e98620a47d5be7c3d8497678" +dependencies = [ + "derive_more-impl 2.0.1", ] [[package]] @@ -1883,6 +1929,17 @@ dependencies = [ "unicode-xid", ] +[[package]] +name = "derive_more-impl" +version = "2.0.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "bda628edc44c4bb645fbe0f758797143e4e07926f7ebf4e9bdfbd3d2ce621df3" +dependencies = [ + "proc-macro2", + "quote", + "syn 2.0.117", +] + [[package]] name = "des" version = "0.8.1" @@ -1978,10 +2035,16 @@ dependencies = [ ] [[package]] -name = "dispatch" -version = "0.2.0" +name = "dispatch2" +version = "0.3.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "bd0c93bb4b0c6d9b77f4435b0ae98c24d17f1c45b2ff844c6151a07256ca923b" +checksum = "1e0e367e4e7da84520dedcac1901e4da967309406d1e51017ae1abfb97adbd38" +dependencies = [ + "bitflags 2.7.0", + "block2 0.6.2", + "libc", + "objc2 0.6.4", +] [[package]] name = "displaydoc" @@ -2023,6 +2086,21 @@ version = "0.3.3" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "fea41bba32d969b513997752735605054bc0dfa92b4c56bf1189f2e174be7a10" +[[package]] +name = "dom_query" +version = "0.27.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "521e380c0c8afb8d9a1e83a1822ee03556fc3e3e7dbc1fd30be14e37f9cb3f89" +dependencies = [ + "bit-set", + "cssparser 0.36.0", + "foldhash", + "html5ever 0.38.0", + "precomputed-hash", + "selectors 0.36.1", + "tendril 0.5.0", +] + [[package]] name = "dpi" version = "0.1.1" @@ -2505,6 +2583,12 @@ version = "1.0.7" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "3f9eec918d3f24069decb9af1554cad7c880e2da24a9afd88aca000531ab82c1" +[[package]] +name = "foldhash" +version = "0.2.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "77ce24cb58228fbb8aa041425bb1050850ac19177686ea6e0f41a70416f56fdb" + [[package]] name = "fontconfig-parser" version = "0.5.7" @@ -3245,10 +3329,20 @@ checksum = "3b7410cae13cbc75623c98ac4cbfd1f0bedddf3227afc24f370cf0f50a44a11c" dependencies = [ "log", "mac", - "markup5ever", + "markup5ever 0.14.1", "match_token", ] +[[package]] +name = "html5ever" +version = "0.38.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "1054432bae2f14e0061e33d23402fbaa67a921d319d56adc6bcf887ddad1cbc2" +dependencies = [ + "log", + "markup5ever 0.38.0", +] + [[package]] name = "http" version = "0.2.12" @@ -4232,10 +4326,10 @@ version = "0.8.8-speedreader" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "02cb977175687f33fa4afa0c95c112b987ea1443e5a51c8f8ff27dc618270cc2" dependencies = [ - "cssparser", - "html5ever", + "cssparser 0.29.6", + "html5ever 0.29.1", "indexmap 2.11.4", - "selectors", + "selectors 0.24.0", ] [[package]] @@ -4293,6 +4387,15 @@ version = "0.2.178" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "37c93d8daa9d8a012fd8ab92f088405fb202ea0b6ab73ee2482ae66af4f42091" +[[package]] +name = "libdbus-sys" +version = "0.2.7" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "328c4789d42200f1eeec05bd86c9c13c7f091d2ba9a6ea35acdf51f31bc0f043" +dependencies = [ + "pkg-config", +] + [[package]] name = "libfuzzer-sys" version = "0.4.8" @@ -4483,9 +4586,20 @@ dependencies = [ "log", "phf 0.11.3", "phf_codegen 0.11.3", - "string_cache", - "string_cache_codegen", - "tendril", + "string_cache 0.8.7", + "string_cache_codegen 0.5.2", + "tendril 0.4.3", +] + +[[package]] +name = "markup5ever" +version = "0.38.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "8983d30f2915feeaaab2d6babdd6bc7e9ed1a00b66b5e6d74df19aa9c0e91862" +dependencies = [ + "log", + "tendril 0.5.0", + "web_atoms", ] [[package]] @@ -4643,7 +4757,7 @@ dependencies = [ "gtk", "keyboard-types", "libxdo", - "objc2 0.6.0", + "objc2 0.6.4", "objc2-app-kit", "objc2-core-foundation", "objc2-foundation 0.3.0", @@ -4742,12 +4856,6 @@ dependencies = [ "thiserror 1.0.69", ] -[[package]] -name = "ndk-context" -version = "0.1.1" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "27b02d87554356db9e9a873add8782d4ea6e3e58ea071a9adb9a2e8ddb884a8b" - [[package]] name = "ndk-sys" version = "0.6.0+11769913" @@ -5057,9 +5165,9 @@ dependencies = [ [[package]] name = "objc2" -version = "0.6.0" +version = "0.6.4" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "3531f65190d9cff863b77a99857e74c314dd16bf56c538c4b57c7cbc3f3a6e59" +checksum = "3a12a8ed07aefc768292f076dc3ac8c48f3781c8f2d5851dd3d98950e8c5a89f" dependencies = [ "objc2-encode", "objc2-exception-helper", @@ -5072,12 +5180,33 @@ source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "5906f93257178e2f7ae069efb89fbd6ee94f0592740b5f8a1512ca498814d0fb" dependencies = [ "bitflags 2.7.0", - "block2 0.6.0", - "objc2 0.6.0", + "block2 0.6.2", + "objc2 0.6.4", "objc2-core-foundation", "objc2-foundation 0.3.0", ] +[[package]] +name = "objc2-cloud-kit" +version = "0.3.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "6c1948a9be5f469deadbd6bcb86ad7ff9e47b4f632380139722f7d9840c0d42c" +dependencies = [ + "bitflags 2.7.0", + "objc2 0.6.4", + "objc2-foundation 0.3.0", +] + +[[package]] +name = "objc2-core-data" +version = "0.3.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "1f860f8e841f6d32f754836f51e6bc7777cd7e7053cf18528233f6811d3eceb4" +dependencies = [ + "objc2 0.6.4", + "objc2-foundation 0.3.0", +] + [[package]] name = "objc2-core-foundation" version = "0.3.0" @@ -5085,7 +5214,7 @@ source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "daeaf60f25471d26948a1c2f840e3f7d86f4109e3af4e8e4b5cd70c39690d925" dependencies = [ "bitflags 2.7.0", - "objc2 0.6.0", + "objc2 0.6.4", ] [[package]] @@ -5095,7 +5224,29 @@ source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "f8dca602628b65356b6513290a21a6405b4d4027b8b250f0b98dddbb28b7de02" dependencies = [ "bitflags 2.7.0", + "objc2 0.6.4", "objc2-core-foundation", + "objc2-io-surface", +] + +[[package]] +name = "objc2-core-image" +version = "0.3.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "6ffa6bea72bf42c78b0b34e89c0bafac877d5f80bf91e159a5d96ea7f693ca56" +dependencies = [ + "objc2 0.6.4", + "objc2-foundation 0.3.0", +] + +[[package]] +name = "objc2-core-location" +version = "0.3.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "d31f4c5b5192304996badc466aeadffe1411d73a9bbd3b18b6b2ee9d048b07bd" +dependencies = [ + "objc2 0.6.4", + "objc2-foundation 0.3.0", ] [[package]] @@ -5132,8 +5283,19 @@ source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "3a21c6c9014b82c39515db5b396f91645182611c97d24637cf56ac01e5f8d998" dependencies = [ "bitflags 2.7.0", - "block2 0.6.0", - "objc2 0.6.0", + "block2 0.6.2", + "objc2 0.6.4", + "objc2-core-foundation", +] + +[[package]] +name = "objc2-io-surface" +version = "0.3.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "161a8b87e32610086e1a7a9e9ec39f84459db7b3a0881c1f16ca5a2605581c19" +dependencies = [ + "bitflags 2.7.0", + "objc2 0.6.4", "objc2-core-foundation", ] @@ -5162,6 +5324,18 @@ dependencies = [ "objc2-metal", ] +[[package]] +name = "objc2-quartz-core" +version = "0.3.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "6fb3794501bb1bee12f08dcad8c61f2a5875791ad1c6f47faa71a0f033f20071" +dependencies = [ + "bitflags 2.7.0", + "objc2 0.6.4", + "objc2-core-foundation", + "objc2-foundation 0.3.0", +] + [[package]] name = "objc2-ui-kit" version = "0.3.0" @@ -5169,8 +5343,26 @@ source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "777a571be14a42a3990d4ebedaeb8b54cd17377ec21b92e8200ac03797b3bee1" dependencies = [ "bitflags 2.7.0", - "objc2 0.6.0", + "block2 0.6.2", + "objc2 0.6.4", + "objc2-cloud-kit", + "objc2-core-data", "objc2-core-foundation", + "objc2-core-graphics", + "objc2-core-image", + "objc2-core-location", + "objc2-foundation 0.3.0", + "objc2-quartz-core 0.3.0", + "objc2-user-notifications", +] + +[[package]] +name = "objc2-user-notifications" +version = "0.3.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "670fe793adbf3b5e93686d48a05a7ed7ee53dfa65d106ced4805fae8969059b2" +dependencies = [ + "objc2 0.6.4", "objc2-foundation 0.3.0", ] @@ -5181,8 +5373,8 @@ source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "b717127e4014b0f9f3e8bba3d3f2acec81f1bde01f656823036e823ed2c94dce" dependencies = [ "bitflags 2.7.0", - "block2 0.6.0", - "objc2 0.6.0", + "block2 0.6.2", + "objc2 0.6.4", "objc2-app-kit", "objc2-core-foundation", "objc2-foundation 0.3.0", @@ -5337,7 +5529,7 @@ source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "7d8fae84b431384b68627d0f9b3b1245fcf9f46f6c0e3dc902e9dce64edd1967" dependencies = [ "libc", - "windows-sys 0.60.2", + "windows-sys 0.48.0", ] [[package]] @@ -5754,7 +5946,7 @@ dependencies = [ "aes-gcm", "aes-kw", "argon2", - "base64 0.22.1", + "base64 0.21.7", "bitfield", "block-padding", "blowfish", @@ -5841,6 +6033,17 @@ dependencies = [ "phf_shared 0.11.3", ] +[[package]] +name = "phf" +version = "0.13.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "c1562dc717473dbaa4c1f85a36410e03c047b2e7df7f45ee938fbef64ae7fadf" +dependencies = [ + "phf_macros 0.13.1", + "phf_shared 0.13.1", + "serde", +] + [[package]] name = "phf_codegen" version = "0.8.0" @@ -5861,6 +6064,16 @@ dependencies = [ "phf_shared 0.11.3", ] +[[package]] +name = "phf_codegen" +version = "0.13.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "49aa7f9d80421bca176ca8dbfebe668cc7a2684708594ec9f3c0db0805d5d6e1" +dependencies = [ + "phf_generator 0.13.1", + "phf_shared 0.13.1", +] + [[package]] name = "phf_generator" version = "0.8.0" @@ -5891,6 +6104,16 @@ dependencies = [ "rand 0.8.5", ] +[[package]] +name = "phf_generator" +version = "0.13.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "135ace3a761e564ec88c03a77317a7c6b80bb7f7135ef2544dbe054243b89737" +dependencies = [ + "fastrand", + "phf_shared 0.13.1", +] + [[package]] name = "phf_macros" version = "0.10.0" @@ -5918,6 +6141,19 @@ dependencies = [ "syn 2.0.117", ] +[[package]] +name = "phf_macros" +version = "0.13.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "812f032b54b1e759ccd5f8b6677695d5268c588701effba24601f6932f8269ef" +dependencies = [ + "phf_generator 0.13.1", + "phf_shared 0.13.1", + "proc-macro2", + "quote", + "syn 2.0.117", +] + [[package]] name = "phf_shared" version = "0.8.0" @@ -5945,6 +6181,15 @@ dependencies = [ "siphasher 1.0.1", ] +[[package]] +name = "phf_shared" +version = "0.13.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "e57fef6bc5981e38c2ce2d63bfa546861309f875b8a75f092d1d54ae2d64f266" +dependencies = [ + "siphasher 1.0.1", +] + [[package]] name = "pico-args" version = "0.5.0" @@ -6154,9 +6399,9 @@ checksum = "dc375e1527247fe1a97d8b7156678dfe7c1af2fc075c9a4db3690ecd2a148068" [[package]] name = "proc-macro2" -version = "1.0.92" +version = "1.0.106" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "37d3544b3f2748c54e147655edb5025752e2303145b5aefb3c3ea2c78b973bb0" +checksum = "8fd00f0bb2e90d81d1044c2b32617f68fcb9fa3bb7640c23e9c748e53fb30934" dependencies = [ "unicode-ident", ] @@ -7133,7 +7378,7 @@ dependencies = [ "security-framework 3.5.1", "security-framework-sys", "webpki-root-certs", - "windows-sys 0.60.2", + "windows-sys 0.52.0", ] [[package]] @@ -7405,14 +7650,33 @@ source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "0c37578180969d00692904465fb7f6b3d50b9a2b952b87c23d0e2e5cb5013416" dependencies = [ "bitflags 1.3.2", - "cssparser", + "cssparser 0.29.6", "derive_more 0.99.18", "fxhash", "log", "phf 0.8.0", "phf_codegen 0.8.0", "precomputed-hash", - "servo_arc", + "servo_arc 0.2.0", + "smallvec", +] + +[[package]] +name = "selectors" +version = "0.36.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "c5d9c0c92a92d33f08817311cf3f2c29a3538a8240e94a6a3c622ce652d7e00c" +dependencies = [ + "bitflags 2.7.0", + "cssparser 0.36.0", + "derive_more 2.0.1", + "log", + "new_debug_unreachable", + "phf 0.13.1", + "phf_codegen 0.13.1", + "precomputed-hash", + "rustc-hash", + "servo_arc 0.4.3", "smallvec", ] @@ -7690,6 +7954,15 @@ dependencies = [ "stable_deref_trait", ] +[[package]] +name = "servo_arc" +version = "0.4.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "170fb83ab34de17dc69aa7c67482b22218ddb85da56546f9bd6b929e32a05930" +dependencies = [ + "stable_deref_trait", +] + [[package]] name = "sha1" version = "0.10.6" @@ -7976,13 +8249,13 @@ checksum = "18051cdd562e792cad055119e0cdb2cfc137e44e3987532e0f9659a77931bb08" dependencies = [ "bytemuck", "cfg_aliases", - "core-graphics", + "core-graphics 0.24.0", "foreign-types 0.5.0", "js-sys", "log", "objc2 0.5.2", "objc2-foundation 0.2.2", - "objc2-quartz-core", + "objc2-quartz-core 0.2.2", "raw-window-handle", "redox_syscall", "wasm-bindgen", @@ -8130,6 +8403,18 @@ dependencies = [ "serde", ] +[[package]] +name = "string_cache" +version = "0.9.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "a18596f8c785a729f2819c0f6a7eae6ebeebdfffbfe4214ae6b087f690e31901" +dependencies = [ + "new_debug_unreachable", + "parking_lot", + "phf_shared 0.13.1", + "precomputed-hash", +] + [[package]] name = "string_cache_codegen" version = "0.5.2" @@ -8142,6 +8427,18 @@ dependencies = [ "quote", ] +[[package]] +name = "string_cache_codegen" +version = "0.6.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "585635e46db231059f76c5849798146164652513eb9e8ab2685939dd90f29b69" +dependencies = [ + "phf_generator 0.13.1", + "phf_shared 0.13.1", + "proc-macro2", + "quote", +] + [[package]] name = "strsim" version = "0.11.1" @@ -8368,35 +8665,35 @@ dependencies = [ [[package]] name = "tao" -version = "0.34.5" +version = "0.35.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "f3a753bdc39c07b192151523a3f77cd0394aa75413802c883a0f6f6a0e5ee2e7" +checksum = "1cf65722394c2ac443e80120064987f8914ee1d4e4e36e63cdf10f2990f01159" dependencies = [ "bitflags 2.7.0", - "block2 0.6.0", + "block2 0.6.2", "core-foundation 0.10.0", - "core-graphics", + "core-graphics 0.25.0", "crossbeam-channel", - "dispatch", + "dbus", + "dispatch2", "dlopen2", "dpi", "gdkwayland-sys", "gdkx11-sys", "gtk", "jni", - "lazy_static", "libc", "log", "ndk", - "ndk-context", "ndk-sys", - "objc2 0.6.0", + "objc2 0.6.4", "objc2-app-kit", "objc2-foundation 0.3.0", + "objc2-ui-kit", "once_cell", "parking_lot", + "percent-encoding", "raw-window-handle", - "scopeguard", "tao-macros", "unicode-segmentation", "url", @@ -8464,7 +8761,7 @@ dependencies = [ "log", "mime", "muda", - "objc2 0.6.0", + "objc2 0.6.4", "objc2-app-kit", "objc2-foundation 0.3.0", "objc2-ui-kit", @@ -8591,7 +8888,7 @@ dependencies = [ "glob", "handlebars", "heck 0.5.0", - "html5ever", + "html5ever 0.29.1", "ignore", "image", "include_dir", @@ -8786,7 +9083,7 @@ dependencies = [ "byte-unit", "fern", "log", - "objc2 0.6.0", + "objc2 0.6.4", "objc2-foundation 0.3.0", "serde", "serde_json", @@ -8818,7 +9115,7 @@ dependencies = [ "gtk", "http 1.3.1", "jni", - "objc2 0.6.0", + "objc2 0.6.4", "objc2-ui-kit", "objc2-web-kit", "raw-window-handle", @@ -8840,7 +9137,7 @@ dependencies = [ "http 1.3.1", "jni", "log", - "objc2 0.6.0", + "objc2 0.6.4", "objc2-app-kit", "once_cell", "percent-encoding", @@ -8894,7 +9191,7 @@ dependencies = [ "dunce", "getrandom 0.3.3", "glob", - "html5ever", + "html5ever 0.29.1", "http 1.3.1", "infer", "json-patch", @@ -8971,6 +9268,16 @@ dependencies = [ "utf-8", ] +[[package]] +name = "tendril" +version = "0.5.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "c4790fc369d5a530f4b544b094e31388b9b3a37c0f4652ade4505945f5660d24" +dependencies = [ + "new_debug_unreachable", + "utf-8", +] + [[package]] name = "termcolor" version = "1.4.1" @@ -9484,7 +9791,7 @@ dependencies = [ "dirs 6.0.0", "libappindicator", "muda", - "objc2 0.6.0", + "objc2 0.6.4", "objc2-app-kit", "objc2-core-foundation", "objc2-core-graphics", @@ -10131,6 +10438,18 @@ dependencies = [ "wasm-bindgen", ] +[[package]] +name = "web_atoms" +version = "0.2.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "57a9779e9f04d2ac1ce317aee707aa2f6b773afba7b931222bff6983843b1576" +dependencies = [ + "phf 0.13.1", + "phf_codegen 0.13.1", + "string_cache 0.9.0", + "string_cache_codegen 0.6.1", +] + [[package]] name = "webkit2gtk" version = "2.0.2" @@ -10305,7 +10624,7 @@ version = "0.6.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "d9bec5a31f3f9362f2258fd0e9c9dd61a9ca432e7306cc78c444258f0dce9a9c" dependencies = [ - "objc2 0.6.0", + "objc2 0.6.4", "objc2-app-kit", "objc2-core-foundation", "objc2-foundation 0.3.0", @@ -10876,27 +11195,26 @@ checksum = "1e9df38ee2d2c3c5948ea468a8406ff0db0b29ae1ffde1bcf20ef305bcc95c51" [[package]] name = "wry" -version = "0.54.0" +version = "0.55.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "e456eeaf7f09413fdc16799782879b2b9f1d264dfdbce4cf7e924df0ef36afb9" +checksum = "3013fd6116aac351dd2e18f349b28b2cfef3a5ff3253a9d0ce2d7193bb1b4429" dependencies = [ "base64 0.22.1", - "block2 0.6.0", + "block2 0.6.2", "cookie", "crossbeam-channel", "dirs 6.0.0", + "dom_query", "dpi", "dunce", "gdkx11", "gtk", - "html5ever", "http 1.3.1", "javascriptcore-rs", "jni", - "kuchikiki", "libc", "ndk", - "objc2 0.6.0", + "objc2 0.6.4", "objc2-app-kit", "objc2-core-foundation", "objc2-foundation 0.3.0", diff --git a/crates/tauri-build/src/mobile.rs b/crates/tauri-build/src/mobile.rs index 9acef2e917be..3dcd4136c8c4 100644 --- a/crates/tauri-build/src/mobile.rs +++ b/crates/tauri-build/src/mobile.rs @@ -15,7 +15,8 @@ pub fn generate_gradle_files(project_dir: PathBuf) -> Result<()> { "// THIS IS AN AUTOGENERATED FILE. DO NOT EDIT THIS FILE DIRECTLY.\n".to_string(); let mut app_build_gradle = "// THIS IS AN AUTOGENERATED FILE. DO NOT EDIT THIS FILE DIRECTLY. val implementation by configurations -dependencies {" +dependencies { + implementation(\"androidx.lifecycle:lifecycle-process:2.10.0\")" .to_string(); for (env, value) in std::env::vars_os() { diff --git a/crates/tauri-cli/config.schema.json b/crates/tauri-cli/config.schema.json index 664b695e186a..6b76427aabb4 100644 --- a/crates/tauri-cli/config.schema.json +++ b/crates/tauri-cli/config.schema.json @@ -603,6 +603,27 @@ "$ref": "#/definitions/ScrollBarStyle" } ] + }, + "activityName": { + "description": "The name of the Android activity to create for this window.", + "type": [ + "string", + "null" + ] + }, + "createdByActivityName": { + "description": "The name of the Android activity that is creating this webview window.\n\n This is important to determine which stack the activity will belong to.", + "type": [ + "string", + "null" + ] + }, + "requestedBySceneIdentifier": { + "description": "Sets the identifier of the scene that is requesting the new scene,\n establishing a relationship between the two scenes.\n\n By default the system uses the foreground scene.", + "type": [ + "string", + "null" + ] } }, "additionalProperties": false diff --git a/crates/tauri-cli/templates/mobile/android/app/build.gradle.kts b/crates/tauri-cli/templates/mobile/android/app/build.gradle.kts index 621f7bcaeabe..b1485863abf9 100644 --- a/crates/tauri-cli/templates/mobile/android/app/build.gradle.kts +++ b/crates/tauri-cli/templates/mobile/android/app/build.gradle.kts @@ -68,6 +68,7 @@ dependencies { implementation("androidx.appcompat:appcompat:1.7.1") implementation("androidx.activity:activity-ktx:1.10.1") implementation("com.google.android.material:material:1.12.0") + implementation("androidx.lifecycle:lifecycle-process:2.10.0") testImplementation("junit:junit:4.13.2") androidTestImplementation("androidx.test.ext:junit:1.1.4") androidTestImplementation("androidx.test.espresso:espresso-core:3.5.0") diff --git a/crates/tauri-runtime-wry/Cargo.toml b/crates/tauri-runtime-wry/Cargo.toml index 10ad16be189c..675f7fd8c876 100644 --- a/crates/tauri-runtime-wry/Cargo.toml +++ b/crates/tauri-runtime-wry/Cargo.toml @@ -13,13 +13,12 @@ edition.workspace = true rust-version.workspace = true [dependencies] -wry = { version = "0.54.0", default-features = false, features = [ - "drag-drop", +wry = { version = "0.55.0", default-features = false, features = [ "protocol", "os-webview", "linux-body", ] } -tao = { version = "0.34.5", default-features = false, features = ["rwh_06"] } +tao = { version = "0.35.0", default-features = false, features = ["rwh_06"] } tauri-runtime = { version = "2.10.1", path = "../tauri-runtime" } tauri-utils = { version = "2.8.3", path = "../tauri-utils" } raw-window-handle = "0.6" @@ -60,7 +59,7 @@ objc2-app-kit = { version = "0.3", default-features = false, features = [ jni = "0.21" [features] -default = ["x11"] +default = ["x11", "dbus"] devtools = ["wry/devtools", "tauri-runtime/devtools"] x11 = ["tao/x11", "wry/x11"] macos-private-api = [ @@ -74,3 +73,4 @@ tracing = ["dep:tracing", "wry/tracing"] macos-proxy = ["wry/mac-proxy"] unstable = [] common-controls-v6 = [] +dbus = ["tao/dbus"] diff --git a/crates/tauri-runtime-wry/src/lib.rs b/crates/tauri-runtime-wry/src/lib.rs index 61799d0394c9..e5b487800ec8 100644 --- a/crates/tauri-runtime-wry/src/lib.rs +++ b/crates/tauri-runtime-wry/src/lib.rs @@ -35,6 +35,8 @@ use tauri_runtime::{ #[cfg(target_vendor = "apple")] use objc2::rc::Retained; +#[cfg(target_os = "android")] +use tao::platform::android::{WindowBuilderExtAndroid, WindowExtAndroid}; #[cfg(target_os = "macos")] use tao::platform::macos::{EventLoopWindowTargetExtMacOS, WindowBuilderExtMacOS}; #[cfg(any( @@ -78,7 +80,6 @@ use tao::{ UserAttentionType as TaoUserAttentionType, }, }; -#[cfg(desktop)] use tauri_utils::config::PreventOverflowConfig; #[cfg(target_os = "macos")] use tauri_utils::TitleBarStyle; @@ -115,7 +116,7 @@ use wry::{ use wry::{WebViewBuilderExtUnix, WebViewExtUnix}; #[cfg(target_os = "ios")] -pub use tao::platform::ios::WindowExtIOS; +pub use tao::platform::ios::{WindowBuilderExtIOS, WindowExtIOS}; #[cfg(target_os = "macos")] pub use tao::platform::macos::{ ActivationPolicy as TaoActivationPolicy, EventLoopExtMacOS, WindowExtMacOS, @@ -880,68 +881,91 @@ impl WindowBuilder for WindowBuilderWrapper { window.inner = window.inner.with_cursor_moved_event(false); } - #[cfg(desktop)] + #[cfg(target_os = "android")] { - window = window - .title(config.title.to_string()) - .inner_size(config.width, config.height) - .focused(config.focus) - .focusable(config.focusable) - .visible(config.visible) - .resizable(config.resizable) - .fullscreen(config.fullscreen) - .decorations(config.decorations) - .maximized(config.maximized) - .always_on_bottom(config.always_on_bottom) - .always_on_top(config.always_on_top) - .visible_on_all_workspaces(config.visible_on_all_workspaces) - .content_protected(config.content_protected) - .skip_taskbar(config.skip_taskbar) - .theme(config.theme) - .closable(config.closable) - .maximizable(config.maximizable) - .minimizable(config.minimizable) - .shadow(config.shadow); - - let mut constraints = WindowSizeConstraints::default(); - - if let Some(min_width) = config.min_width { - constraints.min_width = Some(tao::dpi::LogicalUnit::new(min_width).into()); - } - if let Some(min_height) = config.min_height { - constraints.min_height = Some(tao::dpi::LogicalUnit::new(min_height).into()); + if let Some(activity_name) = &config.activity_name { + window.inner = window.inner.with_activity_name(activity_name.clone()); } - if let Some(max_width) = config.max_width { - constraints.max_width = Some(tao::dpi::LogicalUnit::new(max_width).into()); + if let Some(activity_name) = &config.created_by_activity_name { + window.inner = window + .inner + .with_created_by_activity_name(activity_name.clone()); } - if let Some(max_height) = config.max_height { - constraints.max_height = Some(tao::dpi::LogicalUnit::new(max_height).into()); - } - if let Some(color) = config.background_color { - window = window.background_color(color); - } - window = window.inner_size_constraints(constraints); + } - if let (Some(x), Some(y)) = (config.x, config.y) { - window = window.position(x, y); + #[cfg(target_os = "ios")] + { + if let Some(scene_identifier) = &config.requested_by_scene_identifier { + window.inner = window + .inner + .with_requesting_scene_identifier(scene_identifier.clone()); } + } - if config.center { - window = window.center(); - } + // ignore size from config for mobile for backward compatibility + #[cfg(not(any(target_os = "ios", target_os = "android")))] + { + window = window.inner_size(config.width, config.height); + } - if let Some(window_classname) = &config.window_classname { - window = window.window_classname(window_classname); - } + window = window + .title(config.title.to_string()) + .focused(config.focus) + .focusable(config.focusable) + .visible(config.visible) + .resizable(config.resizable) + .fullscreen(config.fullscreen) + .decorations(config.decorations) + .maximized(config.maximized) + .always_on_bottom(config.always_on_bottom) + .always_on_top(config.always_on_top) + .visible_on_all_workspaces(config.visible_on_all_workspaces) + .content_protected(config.content_protected) + .skip_taskbar(config.skip_taskbar) + .theme(config.theme) + .closable(config.closable) + .maximizable(config.maximizable) + .minimizable(config.minimizable) + .shadow(config.shadow); + + let mut constraints = WindowSizeConstraints::default(); + + if let Some(min_width) = config.min_width { + constraints.min_width = Some(tao::dpi::LogicalUnit::new(min_width).into()); + } + if let Some(min_height) = config.min_height { + constraints.min_height = Some(tao::dpi::LogicalUnit::new(min_height).into()); + } + if let Some(max_width) = config.max_width { + constraints.max_width = Some(tao::dpi::LogicalUnit::new(max_width).into()); + } + if let Some(max_height) = config.max_height { + constraints.max_height = Some(tao::dpi::LogicalUnit::new(max_height).into()); + } + if let Some(color) = config.background_color { + window = window.background_color(color); + } + window = window.inner_size_constraints(constraints); - if let Some(prevent_overflow) = &config.prevent_overflow { - window = match prevent_overflow { - PreventOverflowConfig::Enable(true) => window.prevent_overflow(), - PreventOverflowConfig::Margin(margin) => window - .prevent_overflow_with_margin(TaoPhysicalSize::new(margin.width, margin.height).into()), - _ => window, - }; - } + if let (Some(x), Some(y)) = (config.x, config.y) { + window = window.position(x, y); + } + + if config.center { + window = window.center(); + } + + if let Some(window_classname) = &config.window_classname { + window = window.window_classname(window_classname); + } + + if let Some(prevent_overflow) = &config.prevent_overflow { + window = match prevent_overflow { + PreventOverflowConfig::Enable(true) => window.prevent_overflow(), + PreventOverflowConfig::Margin(margin) => window + .prevent_overflow_with_margin(TaoPhysicalSize::new(margin.width, margin.height).into()), + _ => window, + }; } window @@ -1257,6 +1281,26 @@ impl WindowBuilder for WindowBuilderWrapper { fn window_classname>(self, _window_classname: S) -> Self { self } + + #[cfg(target_os = "android")] + fn activity_name>(mut self, class_name: S) -> Self { + self.inner = self.inner.with_activity_name(class_name.into()); + self + } + + #[cfg(target_os = "android")] + fn created_by_activity_name>(mut self, class_name: S) -> Self { + self.inner = self.inner.with_created_by_activity_name(class_name.into()); + self + } + + #[cfg(target_os = "ios")] + fn requested_by_scene_identifier>(mut self, identifier: S) -> Self { + self.inner = self + .inner + .with_requesting_scene_identifier(identifier.into()); + self + } } #[cfg(any( @@ -1348,6 +1392,10 @@ pub enum WindowMessage { target_os = "openbsd" ))] GtkBox(Sender), + #[cfg(target_os = "android")] + ActivityName(Sender), + #[cfg(target_os = "ios")] + SceneIdentifier(Sender), RawWindowHandle(Sender>), Theme(Sender), IsEnabled(Sender), @@ -2009,6 +2057,18 @@ impl WindowDispatch for WryWindowDispatcher { window_getter!(self, WindowMessage::GtkBox).map(|w| w.0) } + /// Returns the name of the Android activity associated with this window. + #[cfg(target_os = "android")] + fn activity_name(&self) -> Result { + window_getter!(self, WindowMessage::ActivityName) + } + + /// Returns the identifier of the UIScene tied to this UIWindow. + #[cfg(target_os = "ios")] + fn scene_identifier(&self) -> Result { + window_getter!(self, WindowMessage::SceneIdentifier) + } + fn window_handle( &self, ) -> std::result::Result, raw_window_handle::HandleError> { @@ -3317,6 +3377,14 @@ fn handle_user_message( WindowMessage::GtkBox(tx) => tx .send(GtkBox(window.default_vbox().unwrap().clone())) .unwrap(), + #[cfg(target_os = "android")] + WindowMessage::ActivityName(tx) => { + tx.send(window.activity_name()).unwrap(); + } + #[cfg(target_os = "ios")] + WindowMessage::SceneIdentifier(tx) => { + tx.send(window.scene_identifier()).unwrap(); + } WindowMessage::RawWindowHandle(tx) => tx .send( window @@ -4255,6 +4323,10 @@ fn handle_event_loop( } => callback(RunEvent::Reopen { has_visible_windows, }), + #[cfg(target_os = "ios")] + Event::SceneRequested { scene, options } => { + callback(RunEvent::SceneRequested { scene, options }); + } _ => (), } } @@ -4439,6 +4511,7 @@ fn create_window( let window = window_builder .inner .build(event_loop) + .inspect_err(|e| log::error!("Error creating window: {e:?}")) .map_err(|_| Error::CreateWindow)?; #[cfg(feature = "tracing")] diff --git a/crates/tauri-runtime/Cargo.toml b/crates/tauri-runtime/Cargo.toml index c25f743ff62e..4a3f3ea571b8 100644 --- a/crates/tauri-runtime/Cargo.toml +++ b/crates/tauri-runtime/Cargo.toml @@ -54,6 +54,8 @@ objc2 = "0.6" objc2-ui-kit = { version = "0.3.0", default-features = false, features = [ "UIView", "UIResponder", + "UIScene", + "UISceneOptions", ] } [target."cfg(target_os = \"macos\")".dependencies] diff --git a/crates/tauri-runtime/src/lib.rs b/crates/tauri-runtime/src/lib.rs index 5bf869dcde55..d0aefa010b2a 100644 --- a/crates/tauri-runtime/src/lib.rs +++ b/crates/tauri-runtime/src/lib.rs @@ -233,6 +233,20 @@ pub enum RunEvent { }, /// A custom event defined by the user. UserEvent(T), + /// Emitted when a scene is requested by the system. + /// + /// This event is emitted when a scene is requested by the system. + /// Scenes created by [`Window::new`] are not emitted with this event. + /// It is also not emitted for the main scene. + #[cfg(target_os = "ios")] + SceneRequested { + /// Scene that was requested by the system. + scene: objc2::rc::Retained, + /// Options that were used to request the scene. + /// + /// This lets you determine why the scene was requested. + options: objc2::rc::Retained, + }, } /// Action to take when the event loop is about to exit @@ -747,6 +761,14 @@ pub trait WindowDispatch: Debug + Clone + Send + Sync + Sized + 's ))] fn default_vbox(&self) -> Result; + /// Returns the name of the Android activity associated with this window. + #[cfg(target_os = "android")] + fn activity_name(&self) -> Result; + + /// Returns the identifier of the UIScene tied to this UIWindow. + #[cfg(target_os = "ios")] + fn scene_identifier(&self) -> Result; + /// Raw window handle. fn window_handle( &self, diff --git a/crates/tauri-runtime/src/webview.rs b/crates/tauri-runtime/src/webview.rs index 80f7edf0e94b..625a7703a437 100644 --- a/crates/tauri-runtime/src/webview.rs +++ b/crates/tauri-runtime/src/webview.rs @@ -218,7 +218,7 @@ pub struct PendingWebview> { #[cfg(target_os = "android")] #[allow(clippy::type_complexity)] pub on_webview_created: - Option) -> Result<(), jni::errors::Error> + Send>>, + Option) -> Result<(), jni::errors::Error> + Send + Sync>>, pub web_resource_request_handler: Option>, @@ -274,7 +274,7 @@ impl> PendingWebview { #[cfg(target_os = "android")] pub fn on_webview_created< - F: Fn(CreationContext<'_, '_>) -> Result<(), jni::errors::Error> + Send + 'static, + F: Fn(CreationContext<'_, '_>) -> Result<(), jni::errors::Error> + Send + Sync + 'static, >( mut self, f: F, diff --git a/crates/tauri-runtime/src/window.rs b/crates/tauri-runtime/src/window.rs index 652832c1ec49..35b84017cb7a 100644 --- a/crates/tauri-runtime/src/window.rs +++ b/crates/tauri-runtime/src/window.rs @@ -477,6 +477,23 @@ pub trait WindowBuilder: WindowBuilderBase { /// Sets custom name for Windows' window class. **Windows only**. #[must_use] fn window_classname>(self, window_classname: S) -> Self; + + /// The name of the activity to create for this webview window. + #[cfg(target_os = "android")] + fn activity_name>(self, class_name: S) -> Self; + + /// Sets the name of the activity that is creating this webview window. + /// + /// This is important to determine which stack the activity will belong to. + #[cfg(target_os = "android")] + fn created_by_activity_name>(self, class_name: S) -> Self; + + /// Sets the identifier of the UIScene that is requesting the creation of this new scene, + /// establishing a relationship between the two scenes. + /// + /// By default the system uses the foreground scene. + #[cfg(target_os = "ios")] + fn requested_by_scene_identifier>(self, identifier: S) -> Self; } /// A window that has yet to be built. diff --git a/crates/tauri-schema-generator/schemas/config.schema.json b/crates/tauri-schema-generator/schemas/config.schema.json index 664b695e186a..6b76427aabb4 100644 --- a/crates/tauri-schema-generator/schemas/config.schema.json +++ b/crates/tauri-schema-generator/schemas/config.schema.json @@ -603,6 +603,27 @@ "$ref": "#/definitions/ScrollBarStyle" } ] + }, + "activityName": { + "description": "The name of the Android activity to create for this window.", + "type": [ + "string", + "null" + ] + }, + "createdByActivityName": { + "description": "The name of the Android activity that is creating this webview window.\n\n This is important to determine which stack the activity will belong to.", + "type": [ + "string", + "null" + ] + }, + "requestedBySceneIdentifier": { + "description": "Sets the identifier of the scene that is requesting the new scene,\n establishing a relationship between the two scenes.\n\n By default the system uses the foreground scene.", + "type": [ + "string", + "null" + ] } }, "additionalProperties": false diff --git a/crates/tauri-utils/src/config.rs b/crates/tauri-utils/src/config.rs index 78f0ed3eceda..9ce5304969d6 100644 --- a/crates/tauri-utils/src/config.rs +++ b/crates/tauri-utils/src/config.rs @@ -1980,6 +1980,21 @@ pub struct WindowConfig { /// - **Linux / Android / iOS / macOS**: Unsupported. Only supports `Default` and performs no operation. #[serde(default, alias = "scroll-bar-style")] pub scroll_bar_style: ScrollBarStyle, + /// The name of the Android activity to create for this window. + #[serde(default, alias = "activity-name")] + pub activity_name: Option, + /// The name of the Android activity that is creating this webview window. + /// + /// This is important to determine which stack the activity will belong to. + #[serde(default, alias = "created-by-activity-name")] + pub created_by_activity_name: Option, + + /// Sets the identifier of the scene that is requesting the new scene, + /// establishing a relationship between the two scenes. + /// + /// By default the system uses the foreground scene. + #[serde(default, alias = "requested-by-scene-identifier")] + pub requested_by_scene_identifier: Option, } impl Default for WindowConfig { @@ -2042,6 +2057,9 @@ impl Default for WindowConfig { data_directory: None, data_store_identifier: None, scroll_bar_style: ScrollBarStyle::Default, + activity_name: None, + created_by_activity_name: None, + requested_by_scene_identifier: None, } } } @@ -2051,11 +2069,11 @@ fn default_window_label() -> String { } fn default_width() -> f64 { - 800f64 + 800. } fn default_height() -> f64 { - 600f64 + 600. } fn default_title() -> String { @@ -3576,6 +3594,9 @@ mod build { let data_directory = opt_lit(self.data_directory.as_ref().map(path_buf_lit).as_ref()); let data_store_identifier = opt_vec_lit(self.data_store_identifier, identity); let scroll_bar_style = &self.scroll_bar_style; + let activity_name = opt_lit(self.activity_name.as_ref()); + let created_by_activity_name = opt_lit(self.created_by_activity_name.as_ref()); + let requested_by_scene_identifier = opt_lit(self.requested_by_scene_identifier.as_ref()); literal_struct!( tokens, @@ -3636,7 +3657,10 @@ mod build { disable_input_accessory_view, data_directory, data_store_identifier, - scroll_bar_style + scroll_bar_style, + activity_name, + created_by_activity_name, + requested_by_scene_identifier ); } } diff --git a/crates/tauri/Cargo.toml b/crates/tauri/Cargo.toml index cdc4bc697197..9326713e5da1 100644 --- a/crates/tauri/Cargo.toml +++ b/crates/tauri/Cargo.toml @@ -159,6 +159,8 @@ jni = "0.21" libc = "0.2" swift-rs = "1" objc2-ui-kit = { version = "0.3.0", default-features = false, features = [ + "UIApplication", + "UIResponder", "UIView", ] } @@ -182,9 +184,17 @@ cargo_toml = "0.22" http-range = "0.1.5" [features] -default = ["wry", "compression", "common-controls-v6", "dynamic-acl", "x11"] +default = [ + "wry", + "compression", + "common-controls-v6", + "dynamic-acl", + "x11", + "dbus", +] unstable = ["tauri-runtime-wry?/unstable"] x11 = ["tauri-runtime-wry?/x11"] +dbus = ["tauri-runtime-wry?/dbus"] common-controls-v6 = [ "tray-icon?/common-controls-v6", "muda/common-controls-v6", diff --git a/crates/tauri/build.rs b/crates/tauri/build.rs index d63401ed099e..f2efb35cf1e2 100644 --- a/crates/tauri/build.rs +++ b/crates/tauri/build.rs @@ -69,6 +69,8 @@ const PLUGINS: &[(&str, &[(&str, bool)])] = &[ ("cursor_position", true), ("theme", true), ("is_always_on_top", true), + ("activity_name", true), + ("scene_identifier", true), // setters ("center", false), ("request_user_attention", false), @@ -166,6 +168,7 @@ const PLUGINS: &[(&str, &[(&str, bool)])] = &[ ("bundle_type", true), ("register_listener", true), ("remove_listener", true), + ("supports_multiple_windows", true), ], ), ( diff --git a/crates/tauri/mobile/android-codegen/TauriActivity.kt b/crates/tauri/mobile/android-codegen/TauriActivity.kt index 1c96394b89a7..d4c2cbaad95f 100644 --- a/crates/tauri/mobile/android-codegen/TauriActivity.kt +++ b/crates/tauri/mobile/android-codegen/TauriActivity.kt @@ -9,43 +9,51 @@ package {{package}} import android.content.Intent import android.content.res.Configuration import app.tauri.plugin.PluginManager +import androidx.lifecycle.DefaultLifecycleObserver +import androidx.lifecycle.LifecycleOwner +import androidx.lifecycle.ProcessLifecycleOwner + +object TauriLifecycleObserver : DefaultLifecycleObserver { + override fun onResume(owner: LifecycleOwner) { + super.onResume(owner) + PluginManager.onResume() + } + + override fun onPause(owner: LifecycleOwner) { + super.onPause(owner) + PluginManager.onPause() + } + + override fun onStop(owner: LifecycleOwner) { + super.onStop(owner) + PluginManager.onStop() + } +} abstract class TauriActivity : WryActivity() { - var pluginManager: PluginManager = PluginManager(this) override val handleBackNavigation: Boolean = false - override fun onNewIntent(intent: Intent) { - super.onNewIntent(intent) - pluginManager.onNewIntent(intent) - } - - override fun onResume() { - super.onResume() - pluginManager.onResume() + fun getPluginManager(): PluginManager { + return PluginManager } - override fun onPause() { - super.onPause() - pluginManager.onPause() + override fun onNewIntent(intent: Intent) { + super.onNewIntent(intent) + PluginManager.onNewIntent(intent) } override fun onRestart() { super.onRestart() - pluginManager.onRestart() - } - - override fun onStop() { - super.onStop() - pluginManager.onStop() + PluginManager.onRestart(this) } override fun onDestroy() { super.onDestroy() - pluginManager.onDestroy() + PluginManager.onDestroy(this) } override fun onConfigurationChanged(newConfig: Configuration) { super.onConfigurationChanged(newConfig) - pluginManager.onConfigurationChanged(newConfig) + PluginManager.onConfigurationChanged(newConfig) } } diff --git a/crates/tauri/mobile/android/src/main/java/app/tauri/plugin/Plugin.kt b/crates/tauri/mobile/android/src/main/java/app/tauri/plugin/Plugin.kt index d33fa8a4d15a..fda20dd03f07 100644 --- a/crates/tauri/mobile/android/src/main/java/app/tauri/plugin/Plugin.kt +++ b/crates/tauri/mobile/android/src/main/java/app/tauri/plugin/Plugin.kt @@ -11,6 +11,7 @@ import android.content.pm.PackageManager import android.net.Uri import android.webkit.WebView import androidx.activity.result.IntentSenderRequest +import androidx.appcompat.app.AppCompatActivity import androidx.core.app.ActivityCompat import app.tauri.FsUtils import app.tauri.Logger @@ -71,10 +72,18 @@ abstract class Plugin(private val activity: Activity) { */ open fun onResume() {} + + /** + * This event is called after onStop() when the current activity is being re-displayed to the user (the user has navigated back to it). + * It will be followed by onStart() and then onResume(). + */ + open fun onRestart(activity: AppCompatActivity) {} + /** * This event is called after onStop() when the current activity is being re-displayed to the user (the user has navigated back to it). * It will be followed by onStart() and then onResume(). */ + @Deprecated("use onRestart(activity: AppCompatActivity) instead") open fun onRestart() {} /** @@ -86,8 +95,23 @@ abstract class Plugin(private val activity: Activity) { /** * This event is called before the activity is destroyed. */ + open fun onDestroy(activity: AppCompatActivity) {} + /** + * This event is called before an activity is destroyed. + */ + @Deprecated("use onDestroy(activity: AppCompatActivity) instead") open fun onDestroy() {} + internal fun triggerOnDestroy(activity: AppCompatActivity) { + onDestroy(activity) + onDestroy() + } + + internal fun triggerOnRestart(activity: AppCompatActivity) { + onRestart(activity) + onRestart() + } + /** * This event is called when a configuration change occurs but the app does not recreate the activity. */ diff --git a/crates/tauri/mobile/android/src/main/java/app/tauri/plugin/PluginManager.kt b/crates/tauri/mobile/android/src/main/java/app/tauri/plugin/PluginManager.kt index 362896b706d0..0c64bb5f3411 100644 --- a/crates/tauri/mobile/android/src/main/java/app/tauri/plugin/PluginManager.kt +++ b/crates/tauri/mobile/android/src/main/java/app/tauri/plugin/PluginManager.kt @@ -4,7 +4,6 @@ package app.tauri.plugin -import android.app.PendingIntent import android.content.res.Configuration import android.content.Context import android.content.Intent @@ -26,7 +25,7 @@ import com.fasterxml.jackson.databind.ObjectMapper import com.fasterxml.jackson.databind.module.SimpleModule import java.lang.reflect.InvocationTargetException -class PluginManager(val activity: AppCompatActivity) { +object PluginManager { fun interface RequestPermissionsCallback { fun onResult(permissions: Map) } @@ -35,16 +34,33 @@ class PluginManager(val activity: AppCompatActivity) { fun onResult(result: ActivityResult) } + lateinit var activity: AppCompatActivity private val plugins: HashMap = HashMap() - private val startActivityForResultLauncher: ActivityResultLauncher - private val startIntentSenderForResultLauncher: ActivityResultLauncher - private val requestPermissionsLauncher: ActivityResultLauncher> + private lateinit var startActivityForResultLauncher: ActivityResultLauncher + private lateinit var startIntentSenderForResultLauncher: ActivityResultLauncher + private lateinit var requestPermissionsLauncher: ActivityResultLauncher> private var requestPermissionsCallback: RequestPermissionsCallback? = null private var startActivityForResultCallback: ActivityResultCallback? = null private var startIntentSenderForResultCallback: ActivityResultCallback? = null - private var jsonMapper: ObjectMapper + private var jsonMapper: ObjectMapper = ObjectMapper() + .disable(DeserializationFeature.FAIL_ON_UNKNOWN_PROPERTIES) + .enable(DeserializationFeature.FAIL_ON_NULL_FOR_PRIMITIVES) + .setVisibility(PropertyAccessor.FIELD, JsonAutoDetect.Visibility.ANY) init { + val channelDeserializer = ChannelDeserializer({ channelId, payload -> + sendChannelData(channelId, payload) + }, jsonMapper) + jsonMapper + .registerModule(SimpleModule().addDeserializer(Channel::class.java, channelDeserializer)) + } + + fun onActivityCreate(activity: AppCompatActivity) { + // TODO: on destroy, we should change to a different activity + if (::activity.isInitialized) { + return + } + this.activity = activity startActivityForResultLauncher = activity.registerForActivityResult(ActivityResultContracts.StartActivityForResult() ) { result -> @@ -68,17 +84,6 @@ class PluginManager(val activity: AppCompatActivity) { requestPermissionsCallback!!.onResult(result) } } - - jsonMapper = ObjectMapper() - .disable(DeserializationFeature.FAIL_ON_UNKNOWN_PROPERTIES) - .enable(DeserializationFeature.FAIL_ON_NULL_FOR_PRIMITIVES) - .setVisibility(PropertyAccessor.FIELD, JsonAutoDetect.Visibility.ANY) - - val channelDeserializer = ChannelDeserializer({ channelId, payload -> - sendChannelData(channelId, payload) - }, jsonMapper) - jsonMapper - .registerModule(SimpleModule().addDeserializer(Channel::class.java, channelDeserializer)) } fun onNewIntent(intent: Intent) { @@ -99,9 +104,9 @@ class PluginManager(val activity: AppCompatActivity) { } } - fun onRestart() { + fun onRestart(activity: AppCompatActivity) { for (plugin in plugins.values) { - plugin.instance.onRestart() + plugin.instance.triggerOnRestart(activity) } } @@ -111,9 +116,9 @@ class PluginManager(val activity: AppCompatActivity) { } } - fun onDestroy() { + fun onDestroy(activity: AppCompatActivity) { for (plugin in plugins.values) { - plugin.instance.onDestroy() + plugin.instance.triggerOnDestroy(activity) } } @@ -201,14 +206,12 @@ class PluginManager(val activity: AppCompatActivity) { } } - companion object { - fun loadConfig(context: Context, plugin: String, cls: Class): T { - val tauriConfigJson = FsUtils.readAsset(context.assets, "tauri.conf.json") - val mapper = ObjectMapper() - .configure(DeserializationFeature.FAIL_ON_UNKNOWN_PROPERTIES, false) - val config = mapper.readValue(tauriConfigJson, Config::class.java) - return mapper.readValue(config.plugins[plugin].toString(), cls) - } + fun loadConfig(context: Context, plugin: String, cls: Class): T { + val tauriConfigJson = FsUtils.readAsset(context.assets, "tauri.conf.json") + val mapper = ObjectMapper() + .configure(DeserializationFeature.FAIL_ON_UNKNOWN_PROPERTIES, false) + val config = mapper.readValue(tauriConfigJson, Config::class.java) + return mapper.readValue(config.plugins[plugin].toString(), cls) } private external fun handlePluginResponse(id: Int, success: String?, error: String?) diff --git a/crates/tauri/permissions/app/autogenerated/reference.md b/crates/tauri/permissions/app/autogenerated/reference.md index 178a632d93ab..581bd8da85e8 100644 --- a/crates/tauri/permissions/app/autogenerated/reference.md +++ b/crates/tauri/permissions/app/autogenerated/reference.md @@ -11,6 +11,7 @@ Default permissions for the plugin. - `allow-bundle-type` - `allow-register-listener` - `allow-remove-listener` +- `allow-supports-multiple-windows` ## Permission Table @@ -336,6 +337,32 @@ Denies the set_dock_visibility command without any pre-configured scope. +`core:app:allow-supports-multiple-windows` + + + + +Enables the supports_multiple_windows command without any pre-configured scope. + + + + + + + +`core:app:deny-supports-multiple-windows` + + + + +Denies the supports_multiple_windows command without any pre-configured scope. + + + + + + + `core:app:allow-tauri-version` diff --git a/crates/tauri/permissions/window/autogenerated/reference.md b/crates/tauri/permissions/window/autogenerated/reference.md index 00158661d0ed..9d591ba38e3d 100644 --- a/crates/tauri/permissions/window/autogenerated/reference.md +++ b/crates/tauri/permissions/window/autogenerated/reference.md @@ -29,6 +29,8 @@ Default permissions for the plugin. - `allow-cursor-position` - `allow-theme` - `allow-is-always-on-top` +- `allow-activity-name` +- `allow-scene-identifier` - `allow-internal-toggle-maximize` ## Permission Table @@ -40,6 +42,32 @@ Default permissions for the plugin. + + + +`core:window:allow-activity-name` + + + + +Enables the activity_name command without any pre-configured scope. + + + + + + + +`core:window:deny-activity-name` + + + + +Denies the activity_name command without any pre-configured scope. + + + + @@ -875,6 +903,32 @@ Denies the scale_factor command without any pre-configured scope. +`core:window:allow-scene-identifier` + + + + +Enables the scene_identifier command without any pre-configured scope. + + + + + + + +`core:window:deny-scene-identifier` + + + + +Denies the scene_identifier command without any pre-configured scope. + + + + + + + `core:window:allow-set-always-on-bottom` diff --git a/crates/tauri/scripts/bundle.global.js b/crates/tauri/scripts/bundle.global.js index 7f8eff34b263..33d685365b4d 100644 --- a/crates/tauri/scripts/bundle.global.js +++ b/crates/tauri/scripts/bundle.global.js @@ -1 +1 @@ -var __TAURI_IIFE__=function(e){"use strict";function n(e,n,t,i){if("a"===t&&!i)throw new TypeError("Private accessor was defined without a getter");if("function"==typeof n?e!==n||!i:!n.has(e))throw new TypeError("Cannot read private member from an object whose class did not declare it");return"m"===t?i:"a"===t?i.call(e):i?i.value:n.get(e)}function t(e,n,t,i,r){if("m"===i)throw new TypeError("Private method is not writable");if("a"===i&&!r)throw new TypeError("Private accessor was defined without a setter");if("function"==typeof n?e!==n||!r:!n.has(e))throw new TypeError("Cannot write private member to an object whose class did not declare it");return"a"===i?r.call(e,t):r?r.value=t:n.set(e,t),t}var i,r,s,a,l;"function"==typeof SuppressedError&&SuppressedError;const o="__TAURI_TO_IPC_KEY__";function u(e,n=!1){return window.__TAURI_INTERNALS__.transformCallback(e,n)}class c{constructor(e){i.set(this,void 0),r.set(this,0),s.set(this,[]),a.set(this,void 0),t(this,i,e||(()=>{}),"f"),this.id=u(e=>{const l=e.index;if("end"in e)return void(l==n(this,r,"f")?this.cleanupCallback():t(this,a,l,"f"));const o=e.message;if(l==n(this,r,"f")){for(n(this,i,"f").call(this,o),t(this,r,n(this,r,"f")+1,"f");n(this,r,"f")in n(this,s,"f");){const e=n(this,s,"f")[n(this,r,"f")];n(this,i,"f").call(this,e),delete n(this,s,"f")[n(this,r,"f")],t(this,r,n(this,r,"f")+1,"f")}n(this,r,"f")===n(this,a,"f")&&this.cleanupCallback()}else n(this,s,"f")[l]=o})}cleanupCallback(){window.__TAURI_INTERNALS__.unregisterCallback(this.id)}set onmessage(e){t(this,i,e,"f")}get onmessage(){return n(this,i,"f")}[(i=new WeakMap,r=new WeakMap,s=new WeakMap,a=new WeakMap,o)](){return`__CHANNEL__:${this.id}`}toJSON(){return this[o]()}}class d{constructor(e,n,t){this.plugin=e,this.event=n,this.channelId=t}async unregister(){return h(`plugin:${this.plugin}|remove_listener`,{event:this.event,channelId:this.channelId})}}async function p(e,n,t){const i=new c(t);try{return await h(`plugin:${e}|register_listener`,{event:n,handler:i}),new d(e,n,i.id)}catch{return await h(`plugin:${e}|registerListener`,{event:n,handler:i}),new d(e,n,i.id)}}async function h(e,n={},t){return window.__TAURI_INTERNALS__.invoke(e,n,t)}class w{get rid(){return n(this,l,"f")}constructor(e){l.set(this,void 0),t(this,l,e,"f")}async close(){return h("plugin:resources|close",{rid:this.rid})}}l=new WeakMap;var _=Object.freeze({__proto__:null,Channel:c,PluginListener:d,Resource:w,SERIALIZE_TO_IPC_FN:o,addPluginListener:p,checkPermissions:async function(e){return h(`plugin:${e}|check_permissions`)},convertFileSrc:function(e,n="asset"){return window.__TAURI_INTERNALS__.convertFileSrc(e,n)},invoke:h,isTauri:function(){return!!(globalThis||window).isTauri},requestPermissions:async function(e){return h(`plugin:${e}|request_permissions`)},transformCallback:u});class y extends w{constructor(e){super(e)}static async new(e,n,t){return h("plugin:image|new",{rgba:g(e),width:n,height:t}).then(e=>new y(e))}static async fromBytes(e){return h("plugin:image|from_bytes",{bytes:g(e)}).then(e=>new y(e))}static async fromPath(e){return h("plugin:image|from_path",{path:e}).then(e=>new y(e))}async rgba(){return h("plugin:image|rgba",{rid:this.rid}).then(e=>new Uint8Array(e))}async size(){return h("plugin:image|size",{rid:this.rid})}}function g(e){return null==e?null:"string"==typeof e?e:e instanceof y?e.rid:e}var b,m=Object.freeze({__proto__:null,Image:y,transformImage:g});!function(e){e.Nsis="nsis",e.Msi="msi",e.Deb="deb",e.Rpm="rpm",e.AppImage="appimage",e.App="app"}(b||(b={}));var f=Object.freeze({__proto__:null,get BundleType(){return b},defaultWindowIcon:async function(){return h("plugin:app|default_window_icon").then(e=>e?new y(e):null)},fetchDataStoreIdentifiers:async function(){return h("plugin:app|fetch_data_store_identifiers")},getBundleType:async function(){return h("plugin:app|bundle_type")},getIdentifier:async function(){return h("plugin:app|identifier")},getName:async function(){return h("plugin:app|name")},getTauriVersion:async function(){return h("plugin:app|tauri_version")},getVersion:async function(){return h("plugin:app|version")},hide:async function(){return h("plugin:app|app_hide")},onBackButtonPress:async function(e){return p("app","back-button",e)},removeDataStore:async function(e){return h("plugin:app|remove_data_store",{uuid:e})},setDockVisibility:async function(e){return h("plugin:app|set_dock_visibility",{visible:e})},setTheme:async function(e){return h("plugin:app|set_app_theme",{theme:e})},show:async function(){return h("plugin:app|app_show")}});class v{constructor(...e){this.type="Logical",1===e.length?"Logical"in e[0]?(this.width=e[0].Logical.width,this.height=e[0].Logical.height):(this.width=e[0].width,this.height=e[0].height):(this.width=e[0],this.height=e[1])}toPhysical(e){return new k(this.width*e,this.height*e)}[o](){return{width:this.width,height:this.height}}toJSON(){return this[o]()}}class k{constructor(...e){this.type="Physical",1===e.length?"Physical"in e[0]?(this.width=e[0].Physical.width,this.height=e[0].Physical.height):(this.width=e[0].width,this.height=e[0].height):(this.width=e[0],this.height=e[1])}toLogical(e){return new v(this.width/e,this.height/e)}[o](){return{width:this.width,height:this.height}}toJSON(){return this[o]()}}class A{constructor(e){this.size=e}toLogical(e){return this.size instanceof v?this.size:this.size.toLogical(e)}toPhysical(e){return this.size instanceof k?this.size:this.size.toPhysical(e)}[o](){return{[`${this.size.type}`]:{width:this.size.width,height:this.size.height}}}toJSON(){return this[o]()}}class T{constructor(...e){this.type="Logical",1===e.length?"Logical"in e[0]?(this.x=e[0].Logical.x,this.y=e[0].Logical.y):(this.x=e[0].x,this.y=e[0].y):(this.x=e[0],this.y=e[1])}toPhysical(e){return new I(this.x*e,this.y*e)}[o](){return{x:this.x,y:this.y}}toJSON(){return this[o]()}}class I{constructor(...e){this.type="Physical",1===e.length?"Physical"in e[0]?(this.x=e[0].Physical.x,this.y=e[0].Physical.y):(this.x=e[0].x,this.y=e[0].y):(this.x=e[0],this.y=e[1])}toLogical(e){return new T(this.x/e,this.y/e)}[o](){return{x:this.x,y:this.y}}toJSON(){return this[o]()}}class E{constructor(e){this.position=e}toLogical(e){return this.position instanceof T?this.position:this.position.toLogical(e)}toPhysical(e){return this.position instanceof I?this.position:this.position.toPhysical(e)}[o](){return{[`${this.position.type}`]:{x:this.position.x,y:this.position.y}}}toJSON(){return this[o]()}}var R,D=Object.freeze({__proto__:null,LogicalPosition:T,LogicalSize:v,PhysicalPosition:I,PhysicalSize:k,Position:E,Size:A});async function S(e,n){window.__TAURI_EVENT_PLUGIN_INTERNALS__.unregisterListener(e,n),await h("plugin:event|unlisten",{event:e,eventId:n})}async function N(e,n,t){var i;const r="string"==typeof(null==t?void 0:t.target)?{kind:"AnyLabel",label:t.target}:null!==(i=null==t?void 0:t.target)&&void 0!==i?i:{kind:"Any"};return h("plugin:event|listen",{event:e,target:r,handler:u(n)}).then(n=>async()=>S(e,n))}async function L(e,n,t){return N(e,t=>{S(e,t.id),n(t)},t)}async function C(e,n){await h("plugin:event|emit",{event:e,payload:n})}async function x(e,n,t){const i="string"==typeof e?{kind:"AnyLabel",label:e}:e;await h("plugin:event|emit_to",{target:i,event:n,payload:t})}!function(e){e.WINDOW_RESIZED="tauri://resize",e.WINDOW_MOVED="tauri://move",e.WINDOW_CLOSE_REQUESTED="tauri://close-requested",e.WINDOW_DESTROYED="tauri://destroyed",e.WINDOW_FOCUS="tauri://focus",e.WINDOW_BLUR="tauri://blur",e.WINDOW_SCALE_FACTOR_CHANGED="tauri://scale-change",e.WINDOW_THEME_CHANGED="tauri://theme-changed",e.WINDOW_CREATED="tauri://window-created",e.WEBVIEW_CREATED="tauri://webview-created",e.DRAG_ENTER="tauri://drag-enter",e.DRAG_OVER="tauri://drag-over",e.DRAG_DROP="tauri://drag-drop",e.DRAG_LEAVE="tauri://drag-leave"}(R||(R={}));var P,z,W,O=Object.freeze({__proto__:null,get TauriEvent(){return R},emit:C,emitTo:x,listen:N,once:L});function U(e){var n;if("items"in e)e.items=null===(n=e.items)||void 0===n?void 0:n.map(e=>"rid"in e?e:U(e));else if("action"in e&&e.action){const n=new c;return n.onmessage=e.action,delete e.action,{...e,handler:n}}return e}async function F(e,n){const t=new c;if(n&&"object"==typeof n&&("action"in n&&n.action&&(t.onmessage=n.action,delete n.action),"item"in n&&n.item&&"object"==typeof n.item&&"About"in n.item&&n.item.About&&"object"==typeof n.item.About&&"icon"in n.item.About&&n.item.About.icon&&(n.item.About.icon=g(n.item.About.icon)),"icon"in n&&n.icon&&(n.icon=g(n.icon)),"items"in n&&n.items)){function i(e){var n;return"rid"in e?[e.rid,e.kind]:("item"in e&&"object"==typeof e.item&&(null===(n=e.item.About)||void 0===n?void 0:n.icon)&&(e.item.About.icon=g(e.item.About.icon)),"icon"in e&&e.icon&&(e.icon=g(e.icon)),"items"in e&&e.items&&(e.items=e.items.map(i)),U(e))}n.items=n.items.map(i)}return h("plugin:menu|new",{kind:e,options:n,handler:t})}class M extends w{get id(){return n(this,P,"f")}get kind(){return n(this,z,"f")}constructor(e,n,i){super(e),P.set(this,void 0),z.set(this,void 0),t(this,P,n,"f"),t(this,z,i,"f")}}P=new WeakMap,z=new WeakMap;class B extends M{constructor(e,n){super(e,n,"MenuItem")}static async new(e){return F("MenuItem",e).then(([e,n])=>new B(e,n))}async text(){return h("plugin:menu|text",{rid:this.rid,kind:this.kind})}async setText(e){return h("plugin:menu|set_text",{rid:this.rid,kind:this.kind,text:e})}async isEnabled(){return h("plugin:menu|is_enabled",{rid:this.rid,kind:this.kind})}async setEnabled(e){return h("plugin:menu|set_enabled",{rid:this.rid,kind:this.kind,enabled:e})}async setAccelerator(e){return h("plugin:menu|set_accelerator",{rid:this.rid,kind:this.kind,accelerator:e})}}class V extends M{constructor(e,n){super(e,n,"Check")}static async new(e){return F("Check",e).then(([e,n])=>new V(e,n))}async text(){return h("plugin:menu|text",{rid:this.rid,kind:this.kind})}async setText(e){return h("plugin:menu|set_text",{rid:this.rid,kind:this.kind,text:e})}async isEnabled(){return h("plugin:menu|is_enabled",{rid:this.rid,kind:this.kind})}async setEnabled(e){return h("plugin:menu|set_enabled",{rid:this.rid,kind:this.kind,enabled:e})}async setAccelerator(e){return h("plugin:menu|set_accelerator",{rid:this.rid,kind:this.kind,accelerator:e})}async isChecked(){return h("plugin:menu|is_checked",{rid:this.rid})}async setChecked(e){return h("plugin:menu|set_checked",{rid:this.rid,checked:e})}}!function(e){e.Add="Add",e.Advanced="Advanced",e.Bluetooth="Bluetooth",e.Bookmarks="Bookmarks",e.Caution="Caution",e.ColorPanel="ColorPanel",e.ColumnView="ColumnView",e.Computer="Computer",e.EnterFullScreen="EnterFullScreen",e.Everyone="Everyone",e.ExitFullScreen="ExitFullScreen",e.FlowView="FlowView",e.Folder="Folder",e.FolderBurnable="FolderBurnable",e.FolderSmart="FolderSmart",e.FollowLinkFreestanding="FollowLinkFreestanding",e.FontPanel="FontPanel",e.GoLeft="GoLeft",e.GoRight="GoRight",e.Home="Home",e.IChatTheater="IChatTheater",e.IconView="IconView",e.Info="Info",e.InvalidDataFreestanding="InvalidDataFreestanding",e.LeftFacingTriangle="LeftFacingTriangle",e.ListView="ListView",e.LockLocked="LockLocked",e.LockUnlocked="LockUnlocked",e.MenuMixedState="MenuMixedState",e.MenuOnState="MenuOnState",e.MobileMe="MobileMe",e.MultipleDocuments="MultipleDocuments",e.Network="Network",e.Path="Path",e.PreferencesGeneral="PreferencesGeneral",e.QuickLook="QuickLook",e.RefreshFreestanding="RefreshFreestanding",e.Refresh="Refresh",e.Remove="Remove",e.RevealFreestanding="RevealFreestanding",e.RightFacingTriangle="RightFacingTriangle",e.Share="Share",e.Slideshow="Slideshow",e.SmartBadge="SmartBadge",e.StatusAvailable="StatusAvailable",e.StatusNone="StatusNone",e.StatusPartiallyAvailable="StatusPartiallyAvailable",e.StatusUnavailable="StatusUnavailable",e.StopProgressFreestanding="StopProgressFreestanding",e.StopProgress="StopProgress",e.TrashEmpty="TrashEmpty",e.TrashFull="TrashFull",e.User="User",e.UserAccounts="UserAccounts",e.UserGroup="UserGroup",e.UserGuest="UserGuest"}(W||(W={}));class G extends M{constructor(e,n){super(e,n,"Icon")}static async new(e){return F("Icon",e).then(([e,n])=>new G(e,n))}async text(){return h("plugin:menu|text",{rid:this.rid,kind:this.kind})}async setText(e){return h("plugin:menu|set_text",{rid:this.rid,kind:this.kind,text:e})}async isEnabled(){return h("plugin:menu|is_enabled",{rid:this.rid,kind:this.kind})}async setEnabled(e){return h("plugin:menu|set_enabled",{rid:this.rid,kind:this.kind,enabled:e})}async setAccelerator(e){return h("plugin:menu|set_accelerator",{rid:this.rid,kind:this.kind,accelerator:e})}async setIcon(e){return h("plugin:menu|set_icon",{rid:this.rid,kind:this.kind,icon:g(e)})}}class j extends M{constructor(e,n){super(e,n,"Predefined")}static async new(e){return F("Predefined",e).then(([e,n])=>new j(e,n))}async text(){return h("plugin:menu|text",{rid:this.rid,kind:this.kind})}async setText(e){return h("plugin:menu|set_text",{rid:this.rid,kind:this.kind,text:e})}}function H([e,n,t]){switch(t){case"Submenu":return new $(e,n);case"Predefined":return new j(e,n);case"Check":return new V(e,n);case"Icon":return new G(e,n);default:return new B(e,n)}}class $ extends M{constructor(e,n){super(e,n,"Submenu")}static async new(e){return F("Submenu",e).then(([e,n])=>new $(e,n))}async text(){return h("plugin:menu|text",{rid:this.rid,kind:this.kind})}async setText(e){return h("plugin:menu|set_text",{rid:this.rid,kind:this.kind,text:e})}async isEnabled(){return h("plugin:menu|is_enabled",{rid:this.rid,kind:this.kind})}async setEnabled(e){return h("plugin:menu|set_enabled",{rid:this.rid,kind:this.kind,enabled:e})}async append(e){return h("plugin:menu|append",{rid:this.rid,kind:this.kind,items:(Array.isArray(e)?e:[e]).map(e=>"rid"in e?[e.rid,e.kind]:e)})}async prepend(e){return h("plugin:menu|prepend",{rid:this.rid,kind:this.kind,items:(Array.isArray(e)?e:[e]).map(e=>"rid"in e?[e.rid,e.kind]:e)})}async insert(e,n){return h("plugin:menu|insert",{rid:this.rid,kind:this.kind,items:(Array.isArray(e)?e:[e]).map(e=>"rid"in e?[e.rid,e.kind]:e),position:n})}async remove(e){return h("plugin:menu|remove",{rid:this.rid,kind:this.kind,item:[e.rid,e.kind]})}async removeAt(e){return h("plugin:menu|remove_at",{rid:this.rid,kind:this.kind,position:e}).then(H)}async items(){return h("plugin:menu|items",{rid:this.rid,kind:this.kind}).then(e=>e.map(H))}async get(e){return h("plugin:menu|get",{rid:this.rid,kind:this.kind,id:e}).then(e=>e?H(e):null)}async popup(e,n){var t;return h("plugin:menu|popup",{rid:this.rid,kind:this.kind,window:null!==(t=null==n?void 0:n.label)&&void 0!==t?t:null,at:e instanceof E?e:e?new E(e):null})}async setAsWindowsMenuForNSApp(){return h("plugin:menu|set_as_windows_menu_for_nsapp",{rid:this.rid})}async setAsHelpMenuForNSApp(){return h("plugin:menu|set_as_help_menu_for_nsapp",{rid:this.rid})}async setIcon(e){return h("plugin:menu|set_icon",{rid:this.rid,kind:this.kind,icon:g(e)})}}class q extends M{constructor(e,n){super(e,n,"Menu")}static async new(e){return F("Menu",e).then(([e,n])=>new q(e,n))}static async default(){return h("plugin:menu|create_default").then(([e,n])=>new q(e,n))}async append(e){return h("plugin:menu|append",{rid:this.rid,kind:this.kind,items:(Array.isArray(e)?e:[e]).map(e=>"rid"in e?[e.rid,e.kind]:e)})}async prepend(e){return h("plugin:menu|prepend",{rid:this.rid,kind:this.kind,items:(Array.isArray(e)?e:[e]).map(e=>"rid"in e?[e.rid,e.kind]:e)})}async insert(e,n){return h("plugin:menu|insert",{rid:this.rid,kind:this.kind,items:(Array.isArray(e)?e:[e]).map(e=>"rid"in e?[e.rid,e.kind]:e),position:n})}async remove(e){return h("plugin:menu|remove",{rid:this.rid,kind:this.kind,item:[e.rid,e.kind]})}async removeAt(e){return h("plugin:menu|remove_at",{rid:this.rid,kind:this.kind,position:e}).then(H)}async items(){return h("plugin:menu|items",{rid:this.rid,kind:this.kind}).then(e=>e.map(H))}async get(e){return h("plugin:menu|get",{rid:this.rid,kind:this.kind,id:e}).then(e=>e?H(e):null)}async popup(e,n){var t;return h("plugin:menu|popup",{rid:this.rid,kind:this.kind,window:null!==(t=null==n?void 0:n.label)&&void 0!==t?t:null,at:e instanceof E?e:e?new E(e):null})}async setAsAppMenu(){return h("plugin:menu|set_as_app_menu",{rid:this.rid}).then(e=>e?new q(e[0],e[1]):null)}async setAsWindowMenu(e){var n;return h("plugin:menu|set_as_window_menu",{rid:this.rid,window:null!==(n=null==e?void 0:e.label)&&void 0!==n?n:null}).then(e=>e?new q(e[0],e[1]):null)}}var J=Object.freeze({__proto__:null,CheckMenuItem:V,IconMenuItem:G,Menu:q,MenuItem:B,get NativeIcon(){return W},PredefinedMenuItem:j,Submenu:$,itemFromKind:H});function Q(){var e,n;window.__TAURI_INTERNALS__=null!==(e=window.__TAURI_INTERNALS__)&&void 0!==e?e:{},window.__TAURI_EVENT_PLUGIN_INTERNALS__=null!==(n=window.__TAURI_EVENT_PLUGIN_INTERNALS__)&&void 0!==n?n:{}}var Z,K=Object.freeze({__proto__:null,clearMocks:function(){"object"==typeof window.__TAURI_INTERNALS__&&(delete window.__TAURI_INTERNALS__.invoke,delete window.__TAURI_INTERNALS__.transformCallback,delete window.__TAURI_INTERNALS__.unregisterCallback,delete window.__TAURI_INTERNALS__.runCallback,delete window.__TAURI_INTERNALS__.callbacks,delete window.__TAURI_INTERNALS__.convertFileSrc,delete window.__TAURI_INTERNALS__.metadata,"object"==typeof window.__TAURI_EVENT_PLUGIN_INTERNALS__&&delete window.__TAURI_EVENT_PLUGIN_INTERNALS__.unregisterListener)},mockConvertFileSrc:function(e){Q(),window.__TAURI_INTERNALS__.convertFileSrc=function(n,t="asset"){const i=encodeURIComponent(n);return"windows"===e?`http://${t}.localhost/${i}`:`${t}://localhost/${i}`}},mockIPC:function(e,n){function t(e,n){switch(e){case"plugin:event|listen":return function(e){i.has(e.event)||i.set(e.event,[]);return i.get(e.event).push(e.handler),e.handler}(n);case"plugin:event|emit":return function(e){const n=i.get(e.event)||[];for(const t of n)a(t,e);return null}(n);case"plugin:event|unlisten":return function(e){const n=i.get(e.event);if(n){const t=n.indexOf(e.id);-1!==t&&n.splice(t,1)}}(n)}}Q();const i=new Map,r=new Map;function s(e){r.delete(e)}function a(e,n){const t=r.get(e);t?t(n):console.warn(`[TAURI] Couldn't find callback id ${e}. This might happen when the app is reloaded while Rust is running an asynchronous operation.`)}window.__TAURI_INTERNALS__.invoke=async function(i,r,s){return(null==n?void 0:n.shouldMockEvents)&&function(e){return e.startsWith("plugin:event|")}(i)?t(i,r):e(i,r)},window.__TAURI_INTERNALS__.transformCallback=function(e,n=!1){const t=window.crypto.getRandomValues(new Uint32Array(1))[0];return r.set(t,i=>(n&&s(t),e&&e(i))),t},window.__TAURI_INTERNALS__.unregisterCallback=s,window.__TAURI_INTERNALS__.runCallback=a,window.__TAURI_INTERNALS__.callbacks=r,window.__TAURI_EVENT_PLUGIN_INTERNALS__.unregisterListener=function(e,n){s(n)}},mockWindows:function(e,...n){Q(),window.__TAURI_INTERNALS__.metadata={currentWindow:{label:e},currentWebview:{windowLabel:e,label:e}}}});!function(e){e[e.Audio=1]="Audio",e[e.Cache=2]="Cache",e[e.Config=3]="Config",e[e.Data=4]="Data",e[e.LocalData=5]="LocalData",e[e.Document=6]="Document",e[e.Download=7]="Download",e[e.Picture=8]="Picture",e[e.Public=9]="Public",e[e.Video=10]="Video",e[e.Resource=11]="Resource",e[e.Temp=12]="Temp",e[e.AppConfig=13]="AppConfig",e[e.AppData=14]="AppData",e[e.AppLocalData=15]="AppLocalData",e[e.AppCache=16]="AppCache",e[e.AppLog=17]="AppLog",e[e.Desktop=18]="Desktop",e[e.Executable=19]="Executable",e[e.Font=20]="Font",e[e.Home=21]="Home",e[e.Runtime=22]="Runtime",e[e.Template=23]="Template"}(Z||(Z={}));var Y=Object.freeze({__proto__:null,get BaseDirectory(){return Z},appCacheDir:async function(){return h("plugin:path|resolve_directory",{directory:Z.AppCache})},appConfigDir:async function(){return h("plugin:path|resolve_directory",{directory:Z.AppConfig})},appDataDir:async function(){return h("plugin:path|resolve_directory",{directory:Z.AppData})},appLocalDataDir:async function(){return h("plugin:path|resolve_directory",{directory:Z.AppLocalData})},appLogDir:async function(){return h("plugin:path|resolve_directory",{directory:Z.AppLog})},audioDir:async function(){return h("plugin:path|resolve_directory",{directory:Z.Audio})},basename:async function(e,n){return h("plugin:path|basename",{path:e,ext:n})},cacheDir:async function(){return h("plugin:path|resolve_directory",{directory:Z.Cache})},configDir:async function(){return h("plugin:path|resolve_directory",{directory:Z.Config})},dataDir:async function(){return h("plugin:path|resolve_directory",{directory:Z.Data})},delimiter:function(){return window.__TAURI_INTERNALS__.plugins.path.delimiter},desktopDir:async function(){return h("plugin:path|resolve_directory",{directory:Z.Desktop})},dirname:async function(e){return h("plugin:path|dirname",{path:e})},documentDir:async function(){return h("plugin:path|resolve_directory",{directory:Z.Document})},downloadDir:async function(){return h("plugin:path|resolve_directory",{directory:Z.Download})},executableDir:async function(){return h("plugin:path|resolve_directory",{directory:Z.Executable})},extname:async function(e){return h("plugin:path|extname",{path:e})},fontDir:async function(){return h("plugin:path|resolve_directory",{directory:Z.Font})},homeDir:async function(){return h("plugin:path|resolve_directory",{directory:Z.Home})},isAbsolute:async function(e){return h("plugin:path|is_absolute",{path:e})},join:async function(...e){return h("plugin:path|join",{paths:e})},localDataDir:async function(){return h("plugin:path|resolve_directory",{directory:Z.LocalData})},normalize:async function(e){return h("plugin:path|normalize",{path:e})},pictureDir:async function(){return h("plugin:path|resolve_directory",{directory:Z.Picture})},publicDir:async function(){return h("plugin:path|resolve_directory",{directory:Z.Public})},resolve:async function(...e){return h("plugin:path|resolve",{paths:e})},resolveResource:async function(e){return h("plugin:path|resolve_directory",{directory:Z.Resource,path:e})},resourceDir:async function(){return h("plugin:path|resolve_directory",{directory:Z.Resource})},runtimeDir:async function(){return h("plugin:path|resolve_directory",{directory:Z.Runtime})},sep:function(){return window.__TAURI_INTERNALS__.plugins.path.sep},tempDir:async function(){return h("plugin:path|resolve_directory",{directory:Z.Temp})},templateDir:async function(){return h("plugin:path|resolve_directory",{directory:Z.Template})},videoDir:async function(){return h("plugin:path|resolve_directory",{directory:Z.Video})}});class X extends w{constructor(e,n){super(e),this.id=n}static async getById(e){return h("plugin:tray|get_by_id",{id:e}).then(n=>n?new X(n,e):null)}static async removeById(e){return h("plugin:tray|remove_by_id",{id:e})}static async new(e){(null==e?void 0:e.menu)&&(e.menu=[e.menu.rid,e.menu.kind]),(null==e?void 0:e.icon)&&(e.icon=g(e.icon));const n=new c;if(null==e?void 0:e.action){const t=e.action;n.onmessage=e=>t(function(e){const n=e;return n.position=new I(e.position),n.rect.position=new I(e.rect.position),n.rect.size=new k(e.rect.size),n}(e)),delete e.action}return h("plugin:tray|new",{options:null!=e?e:{},handler:n}).then(([e,n])=>new X(e,n))}async setIcon(e){let n=null;return e&&(n=g(e)),h("plugin:tray|set_icon",{rid:this.rid,icon:n})}async setMenu(e){return e&&(e=[e.rid,e.kind]),h("plugin:tray|set_menu",{rid:this.rid,menu:e})}async setTooltip(e){return h("plugin:tray|set_tooltip",{rid:this.rid,tooltip:e})}async setTitle(e){return h("plugin:tray|set_title",{rid:this.rid,title:e})}async setVisible(e){return h("plugin:tray|set_visible",{rid:this.rid,visible:e})}async setTempDirPath(e){return h("plugin:tray|set_temp_dir_path",{rid:this.rid,path:e})}async setIconAsTemplate(e){return h("plugin:tray|set_icon_as_template",{rid:this.rid,asTemplate:e})}async setMenuOnLeftClick(e){return h("plugin:tray|set_show_menu_on_left_click",{rid:this.rid,onLeft:e})}async setShowMenuOnLeftClick(e){return h("plugin:tray|set_show_menu_on_left_click",{rid:this.rid,onLeft:e})}}var ee,ne,te=Object.freeze({__proto__:null,TrayIcon:X});!function(e){e[e.Critical=1]="Critical",e[e.Informational=2]="Informational"}(ee||(ee={}));class ie{constructor(e){this._preventDefault=!1,this.event=e.event,this.id=e.id}preventDefault(){this._preventDefault=!0}isPreventDefault(){return this._preventDefault}}function re(){return new le(window.__TAURI_INTERNALS__.metadata.currentWindow.label,{skip:!0})}async function se(){return h("plugin:window|get_all_windows").then(e=>e.map(e=>new le(e,{skip:!0})))}!function(e){e.None="none",e.Normal="normal",e.Indeterminate="indeterminate",e.Paused="paused",e.Error="error"}(ne||(ne={}));const ae=["tauri://created","tauri://error"];class le{constructor(e,n={}){var t;this.label=e,this.listeners=Object.create(null),(null==n?void 0:n.skip)||h("plugin:window|create",{options:{...n,parent:"string"==typeof n.parent?n.parent:null===(t=n.parent)||void 0===t?void 0:t.label,label:e}}).then(async()=>this.emit("tauri://created")).catch(async e=>this.emit("tauri://error",e))}static async getByLabel(e){var n;return null!==(n=(await se()).find(n=>n.label===e))&&void 0!==n?n:null}static getCurrent(){return re()}static async getAll(){return se()}static async getFocusedWindow(){for(const e of await se())if(await e.isFocused())return e;return null}async listen(e,n){return this._handleTauriEvent(e,n)?()=>{const t=this.listeners[e];t.splice(t.indexOf(n),1)}:N(e,n,{target:{kind:"Window",label:this.label}})}async once(e,n){return this._handleTauriEvent(e,n)?()=>{const t=this.listeners[e];t.splice(t.indexOf(n),1)}:L(e,n,{target:{kind:"Window",label:this.label}})}async emit(e,n){if(!ae.includes(e))return C(e,n);for(const t of this.listeners[e]||[])t({event:e,id:-1,payload:n})}async emitTo(e,n,t){if(!ae.includes(n))return x(e,n,t);for(const e of this.listeners[n]||[])e({event:n,id:-1,payload:t})}_handleTauriEvent(e,n){return!!ae.includes(e)&&(e in this.listeners?this.listeners[e].push(n):this.listeners[e]=[n],!0)}async scaleFactor(){return h("plugin:window|scale_factor",{label:this.label})}async innerPosition(){return h("plugin:window|inner_position",{label:this.label}).then(e=>new I(e))}async outerPosition(){return h("plugin:window|outer_position",{label:this.label}).then(e=>new I(e))}async innerSize(){return h("plugin:window|inner_size",{label:this.label}).then(e=>new k(e))}async outerSize(){return h("plugin:window|outer_size",{label:this.label}).then(e=>new k(e))}async isFullscreen(){return h("plugin:window|is_fullscreen",{label:this.label})}async isMinimized(){return h("plugin:window|is_minimized",{label:this.label})}async isMaximized(){return h("plugin:window|is_maximized",{label:this.label})}async isFocused(){return h("plugin:window|is_focused",{label:this.label})}async isDecorated(){return h("plugin:window|is_decorated",{label:this.label})}async isResizable(){return h("plugin:window|is_resizable",{label:this.label})}async isMaximizable(){return h("plugin:window|is_maximizable",{label:this.label})}async isMinimizable(){return h("plugin:window|is_minimizable",{label:this.label})}async isClosable(){return h("plugin:window|is_closable",{label:this.label})}async isVisible(){return h("plugin:window|is_visible",{label:this.label})}async title(){return h("plugin:window|title",{label:this.label})}async theme(){return h("plugin:window|theme",{label:this.label})}async isAlwaysOnTop(){return h("plugin:window|is_always_on_top",{label:this.label})}async center(){return h("plugin:window|center",{label:this.label})}async requestUserAttention(e){let n=null;return e&&(n=e===ee.Critical?{type:"Critical"}:{type:"Informational"}),h("plugin:window|request_user_attention",{label:this.label,value:n})}async setResizable(e){return h("plugin:window|set_resizable",{label:this.label,value:e})}async setEnabled(e){return h("plugin:window|set_enabled",{label:this.label,value:e})}async isEnabled(){return h("plugin:window|is_enabled",{label:this.label})}async setMaximizable(e){return h("plugin:window|set_maximizable",{label:this.label,value:e})}async setMinimizable(e){return h("plugin:window|set_minimizable",{label:this.label,value:e})}async setClosable(e){return h("plugin:window|set_closable",{label:this.label,value:e})}async setTitle(e){return h("plugin:window|set_title",{label:this.label,value:e})}async maximize(){return h("plugin:window|maximize",{label:this.label})}async unmaximize(){return h("plugin:window|unmaximize",{label:this.label})}async toggleMaximize(){return h("plugin:window|toggle_maximize",{label:this.label})}async minimize(){return h("plugin:window|minimize",{label:this.label})}async unminimize(){return h("plugin:window|unminimize",{label:this.label})}async show(){return h("plugin:window|show",{label:this.label})}async hide(){return h("plugin:window|hide",{label:this.label})}async close(){return h("plugin:window|close",{label:this.label})}async destroy(){return h("plugin:window|destroy",{label:this.label})}async setDecorations(e){return h("plugin:window|set_decorations",{label:this.label,value:e})}async setShadow(e){return h("plugin:window|set_shadow",{label:this.label,value:e})}async setEffects(e){return h("plugin:window|set_effects",{label:this.label,value:e})}async clearEffects(){return h("plugin:window|set_effects",{label:this.label,value:null})}async setAlwaysOnTop(e){return h("plugin:window|set_always_on_top",{label:this.label,value:e})}async setAlwaysOnBottom(e){return h("plugin:window|set_always_on_bottom",{label:this.label,value:e})}async setContentProtected(e){return h("plugin:window|set_content_protected",{label:this.label,value:e})}async setSize(e){return h("plugin:window|set_size",{label:this.label,value:e instanceof A?e:new A(e)})}async setMinSize(e){return h("plugin:window|set_min_size",{label:this.label,value:e instanceof A?e:e?new A(e):null})}async setMaxSize(e){return h("plugin:window|set_max_size",{label:this.label,value:e instanceof A?e:e?new A(e):null})}async setSizeConstraints(e){function n(e){return e?{Logical:e}:null}return h("plugin:window|set_size_constraints",{label:this.label,value:{minWidth:n(null==e?void 0:e.minWidth),minHeight:n(null==e?void 0:e.minHeight),maxWidth:n(null==e?void 0:e.maxWidth),maxHeight:n(null==e?void 0:e.maxHeight)}})}async setPosition(e){return h("plugin:window|set_position",{label:this.label,value:e instanceof E?e:new E(e)})}async setFullscreen(e){return h("plugin:window|set_fullscreen",{label:this.label,value:e})}async setSimpleFullscreen(e){return h("plugin:window|set_simple_fullscreen",{label:this.label,value:e})}async setFocus(){return h("plugin:window|set_focus",{label:this.label})}async setFocusable(e){return h("plugin:window|set_focusable",{label:this.label,value:e})}async setIcon(e){return h("plugin:window|set_icon",{label:this.label,value:g(e)})}async setSkipTaskbar(e){return h("plugin:window|set_skip_taskbar",{label:this.label,value:e})}async setCursorGrab(e){return h("plugin:window|set_cursor_grab",{label:this.label,value:e})}async setCursorVisible(e){return h("plugin:window|set_cursor_visible",{label:this.label,value:e})}async setCursorIcon(e){return h("plugin:window|set_cursor_icon",{label:this.label,value:e})}async setBackgroundColor(e){return h("plugin:window|set_background_color",{color:e})}async setCursorPosition(e){return h("plugin:window|set_cursor_position",{label:this.label,value:e instanceof E?e:new E(e)})}async setIgnoreCursorEvents(e){return h("plugin:window|set_ignore_cursor_events",{label:this.label,value:e})}async startDragging(){return h("plugin:window|start_dragging",{label:this.label})}async startResizeDragging(e){return h("plugin:window|start_resize_dragging",{label:this.label,value:e})}async setBadgeCount(e){return h("plugin:window|set_badge_count",{label:this.label,value:e})}async setBadgeLabel(e){return h("plugin:window|set_badge_label",{label:this.label,value:e})}async setOverlayIcon(e){return h("plugin:window|set_overlay_icon",{label:this.label,value:e?g(e):void 0})}async setProgressBar(e){return h("plugin:window|set_progress_bar",{label:this.label,value:e})}async setVisibleOnAllWorkspaces(e){return h("plugin:window|set_visible_on_all_workspaces",{label:this.label,value:e})}async setTitleBarStyle(e){return h("plugin:window|set_title_bar_style",{label:this.label,value:e})}async setTheme(e){return h("plugin:window|set_theme",{label:this.label,value:e})}async onResized(e){return this.listen(R.WINDOW_RESIZED,n=>{n.payload=new k(n.payload),e(n)})}async onMoved(e){return this.listen(R.WINDOW_MOVED,n=>{n.payload=new I(n.payload),e(n)})}async onCloseRequested(e){return this.listen(R.WINDOW_CLOSE_REQUESTED,async n=>{const t=new ie(n);await e(t),t.isPreventDefault()||await this.destroy()})}async onDragDropEvent(e){const n=await this.listen(R.DRAG_ENTER,n=>{e({...n,payload:{type:"enter",paths:n.payload.paths,position:new I(n.payload.position)}})}),t=await this.listen(R.DRAG_OVER,n=>{e({...n,payload:{type:"over",position:new I(n.payload.position)}})}),i=await this.listen(R.DRAG_DROP,n=>{e({...n,payload:{type:"drop",paths:n.payload.paths,position:new I(n.payload.position)}})}),r=await this.listen(R.DRAG_LEAVE,n=>{e({...n,payload:{type:"leave"}})});return()=>{n(),i(),t(),r()}}async onFocusChanged(e){const n=await this.listen(R.WINDOW_FOCUS,n=>{e({...n,payload:!0})}),t=await this.listen(R.WINDOW_BLUR,n=>{e({...n,payload:!1})});return()=>{n(),t()}}async onScaleChanged(e){return this.listen(R.WINDOW_SCALE_FACTOR_CHANGED,e)}async onThemeChanged(e){return this.listen(R.WINDOW_THEME_CHANGED,e)}}var oe,ue,ce,de;function pe(e){return null===e?null:{name:e.name,scaleFactor:e.scaleFactor,position:new I(e.position),size:new k(e.size),workArea:{position:new I(e.workArea.position),size:new k(e.workArea.size)}}}!function(e){e.Disabled="disabled",e.Throttle="throttle",e.Suspend="suspend"}(oe||(oe={})),function(e){e.Default="default",e.FluentOverlay="fluentOverlay"}(ue||(ue={})),function(e){e.AppearanceBased="appearanceBased",e.Light="light",e.Dark="dark",e.MediumLight="mediumLight",e.UltraDark="ultraDark",e.Titlebar="titlebar",e.Selection="selection",e.Menu="menu",e.Popover="popover",e.Sidebar="sidebar",e.HeaderView="headerView",e.Sheet="sheet",e.WindowBackground="windowBackground",e.HudWindow="hudWindow",e.FullScreenUI="fullScreenUI",e.Tooltip="tooltip",e.ContentBackground="contentBackground",e.UnderWindowBackground="underWindowBackground",e.UnderPageBackground="underPageBackground",e.Mica="mica",e.Blur="blur",e.Acrylic="acrylic",e.Tabbed="tabbed",e.TabbedDark="tabbedDark",e.TabbedLight="tabbedLight"}(ce||(ce={})),function(e){e.FollowsWindowActiveState="followsWindowActiveState",e.Active="active",e.Inactive="inactive"}(de||(de={}));var he=Object.freeze({__proto__:null,CloseRequestedEvent:ie,get Effect(){return ce},get EffectState(){return de},LogicalPosition:T,LogicalSize:v,PhysicalPosition:I,PhysicalSize:k,get ProgressBarStatus(){return ne},get UserAttentionType(){return ee},Window:le,availableMonitors:async function(){return h("plugin:window|available_monitors").then(e=>e.map(pe))},currentMonitor:async function(){return h("plugin:window|current_monitor").then(pe)},cursorPosition:async function(){return h("plugin:window|cursor_position").then(e=>new I(e))},getAllWindows:se,getCurrentWindow:re,monitorFromPoint:async function(e,n){return h("plugin:window|monitor_from_point",{x:e,y:n}).then(pe)},primaryMonitor:async function(){return h("plugin:window|primary_monitor").then(pe)}});function we(){return new ge(re(),window.__TAURI_INTERNALS__.metadata.currentWebview.label,{skip:!0})}async function _e(){return h("plugin:webview|get_all_webviews").then(e=>e.map(e=>new ge(new le(e.windowLabel,{skip:!0}),e.label,{skip:!0})))}const ye=["tauri://created","tauri://error"];class ge{constructor(e,n,t){this.window=e,this.label=n,this.listeners=Object.create(null),(null==t?void 0:t.skip)||h("plugin:webview|create_webview",{windowLabel:e.label,options:{...t,label:n}}).then(async()=>this.emit("tauri://created")).catch(async e=>this.emit("tauri://error",e))}static async getByLabel(e){var n;return null!==(n=(await _e()).find(n=>n.label===e))&&void 0!==n?n:null}static getCurrent(){return we()}static async getAll(){return _e()}async listen(e,n){return this._handleTauriEvent(e,n)?()=>{const t=this.listeners[e];t.splice(t.indexOf(n),1)}:N(e,n,{target:{kind:"Webview",label:this.label}})}async once(e,n){return this._handleTauriEvent(e,n)?()=>{const t=this.listeners[e];t.splice(t.indexOf(n),1)}:L(e,n,{target:{kind:"Webview",label:this.label}})}async emit(e,n){if(!ye.includes(e))return C(e,n);for(const t of this.listeners[e]||[])t({event:e,id:-1,payload:n})}async emitTo(e,n,t){if(!ye.includes(n))return x(e,n,t);for(const e of this.listeners[n]||[])e({event:n,id:-1,payload:t})}_handleTauriEvent(e,n){return!!ye.includes(e)&&(e in this.listeners?this.listeners[e].push(n):this.listeners[e]=[n],!0)}async position(){return h("plugin:webview|webview_position",{label:this.label}).then(e=>new I(e))}async size(){return h("plugin:webview|webview_size",{label:this.label}).then(e=>new k(e))}async close(){return h("plugin:webview|webview_close",{label:this.label})}async setSize(e){return h("plugin:webview|set_webview_size",{label:this.label,value:e instanceof A?e:new A(e)})}async setPosition(e){return h("plugin:webview|set_webview_position",{label:this.label,value:e instanceof E?e:new E(e)})}async setFocus(){return h("plugin:webview|set_webview_focus",{label:this.label})}async setAutoResize(e){return h("plugin:webview|set_webview_auto_resize",{label:this.label,value:e})}async hide(){return h("plugin:webview|webview_hide",{label:this.label})}async show(){return h("plugin:webview|webview_show",{label:this.label})}async setZoom(e){return h("plugin:webview|set_webview_zoom",{label:this.label,value:e})}async reparent(e){return h("plugin:webview|reparent",{label:this.label,window:"string"==typeof e?e:e.label})}async clearAllBrowsingData(){return h("plugin:webview|clear_all_browsing_data")}async setBackgroundColor(e){return h("plugin:webview|set_webview_background_color",{color:e})}async onDragDropEvent(e){const n=await this.listen(R.DRAG_ENTER,n=>{e({...n,payload:{type:"enter",paths:n.payload.paths,position:new I(n.payload.position)}})}),t=await this.listen(R.DRAG_OVER,n=>{e({...n,payload:{type:"over",position:new I(n.payload.position)}})}),i=await this.listen(R.DRAG_DROP,n=>{e({...n,payload:{type:"drop",paths:n.payload.paths,position:new I(n.payload.position)}})}),r=await this.listen(R.DRAG_LEAVE,n=>{e({...n,payload:{type:"leave"}})});return()=>{n(),i(),t(),r()}}}var be,me,fe=Object.freeze({__proto__:null,Webview:ge,getAllWebviews:_e,getCurrentWebview:we});function ve(){const e=we();return new Ae(e.label,{skip:!0})}async function ke(){return h("plugin:window|get_all_windows").then(e=>e.map(e=>new Ae(e,{skip:!0})))}class Ae{constructor(e,n={}){var t;this.label=e,this.listeners=Object.create(null),(null==n?void 0:n.skip)||h("plugin:webview|create_webview_window",{options:{...n,parent:"string"==typeof n.parent?n.parent:null===(t=n.parent)||void 0===t?void 0:t.label,label:e}}).then(async()=>this.emit("tauri://created")).catch(async e=>this.emit("tauri://error",e))}static async getByLabel(e){var n;const t=null!==(n=(await ke()).find(n=>n.label===e))&&void 0!==n?n:null;return t?new Ae(t.label,{skip:!0}):null}static getCurrent(){return ve()}static async getAll(){return ke()}async listen(e,n){return this._handleTauriEvent(e,n)?()=>{const t=this.listeners[e];t.splice(t.indexOf(n),1)}:N(e,n,{target:{kind:"WebviewWindow",label:this.label}})}async once(e,n){return this._handleTauriEvent(e,n)?()=>{const t=this.listeners[e];t.splice(t.indexOf(n),1)}:L(e,n,{target:{kind:"WebviewWindow",label:this.label}})}async setBackgroundColor(e){return h("plugin:window|set_background_color",{color:e}).then(()=>h("plugin:webview|set_webview_background_color",{color:e}))}}be=Ae,me=[le,ge],(Array.isArray(me)?me:[me]).forEach(e=>{Object.getOwnPropertyNames(e.prototype).forEach(n=>{var t;"object"==typeof be.prototype&&be.prototype&&n in be.prototype||Object.defineProperty(be.prototype,n,null!==(t=Object.getOwnPropertyDescriptor(e.prototype,n))&&void 0!==t?t:Object.create(null))})});var Te=Object.freeze({__proto__:null,WebviewWindow:Ae,getAllWebviewWindows:ke,getCurrentWebviewWindow:ve});return e.app=f,e.core=_,e.dpi=D,e.event=O,e.image=m,e.menu=J,e.mocks=K,e.path=Y,e.tray=te,e.webview=fe,e.webviewWindow=Te,e.window=he,e}({});window.__TAURI__=__TAURI_IIFE__; +var __TAURI_IIFE__=function(e){"use strict";function n(e,n,t,i){if("a"===t&&!i)throw new TypeError("Private accessor was defined without a getter");if("function"==typeof n?e!==n||!i:!n.has(e))throw new TypeError("Cannot read private member from an object whose class did not declare it");return"m"===t?i:"a"===t?i.call(e):i?i.value:n.get(e)}function t(e,n,t,i,r){if("m"===i)throw new TypeError("Private method is not writable");if("a"===i&&!r)throw new TypeError("Private accessor was defined without a setter");if("function"==typeof n?e!==n||!r:!n.has(e))throw new TypeError("Cannot write private member to an object whose class did not declare it");return"a"===i?r.call(e,t):r?r.value=t:n.set(e,t),t}var i,r,s,a,l;"function"==typeof SuppressedError&&SuppressedError;const o="__TAURI_TO_IPC_KEY__";function u(e,n=!1){return window.__TAURI_INTERNALS__.transformCallback(e,n)}class c{constructor(e){i.set(this,void 0),r.set(this,0),s.set(this,[]),a.set(this,void 0),t(this,i,e||(()=>{}),"f"),this.id=u(e=>{const l=e.index;if("end"in e)return void(l==n(this,r,"f")?this.cleanupCallback():t(this,a,l,"f"));const o=e.message;if(l==n(this,r,"f")){for(n(this,i,"f").call(this,o),t(this,r,n(this,r,"f")+1,"f");n(this,r,"f")in n(this,s,"f");){const e=n(this,s,"f")[n(this,r,"f")];n(this,i,"f").call(this,e),delete n(this,s,"f")[n(this,r,"f")],t(this,r,n(this,r,"f")+1,"f")}n(this,r,"f")===n(this,a,"f")&&this.cleanupCallback()}else n(this,s,"f")[l]=o})}cleanupCallback(){window.__TAURI_INTERNALS__.unregisterCallback(this.id)}set onmessage(e){t(this,i,e,"f")}get onmessage(){return n(this,i,"f")}[(i=new WeakMap,r=new WeakMap,s=new WeakMap,a=new WeakMap,o)](){return`__CHANNEL__:${this.id}`}toJSON(){return this[o]()}}class d{constructor(e,n,t){this.plugin=e,this.event=n,this.channelId=t}async unregister(){return h(`plugin:${this.plugin}|remove_listener`,{event:this.event,channelId:this.channelId})}}async function p(e,n,t){const i=new c(t);try{return await h(`plugin:${e}|register_listener`,{event:n,handler:i}),new d(e,n,i.id)}catch{return await h(`plugin:${e}|registerListener`,{event:n,handler:i}),new d(e,n,i.id)}}async function h(e,n={},t){return window.__TAURI_INTERNALS__.invoke(e,n,t)}class w{get rid(){return n(this,l,"f")}constructor(e){l.set(this,void 0),t(this,l,e,"f")}async close(){return h("plugin:resources|close",{rid:this.rid})}}l=new WeakMap;var _=Object.freeze({__proto__:null,Channel:c,PluginListener:d,Resource:w,SERIALIZE_TO_IPC_FN:o,addPluginListener:p,checkPermissions:async function(e){return h(`plugin:${e}|check_permissions`)},convertFileSrc:function(e,n="asset"){return window.__TAURI_INTERNALS__.convertFileSrc(e,n)},invoke:h,isTauri:function(){return!!(globalThis||window).isTauri},requestPermissions:async function(e){return h(`plugin:${e}|request_permissions`)},transformCallback:u});class y extends w{constructor(e){super(e)}static async new(e,n,t){return h("plugin:image|new",{rgba:g(e),width:n,height:t}).then(e=>new y(e))}static async fromBytes(e){return h("plugin:image|from_bytes",{bytes:g(e)}).then(e=>new y(e))}static async fromPath(e){return h("plugin:image|from_path",{path:e}).then(e=>new y(e))}async rgba(){return h("plugin:image|rgba",{rid:this.rid}).then(e=>new Uint8Array(e))}async size(){return h("plugin:image|size",{rid:this.rid})}}function g(e){return null==e?null:"string"==typeof e?e:e instanceof y?e.rid:e}var b,m=Object.freeze({__proto__:null,Image:y,transformImage:g});!function(e){e.Nsis="nsis",e.Msi="msi",e.Deb="deb",e.Rpm="rpm",e.AppImage="appimage",e.App="app"}(b||(b={}));var f=Object.freeze({__proto__:null,get BundleType(){return b},defaultWindowIcon:async function(){return h("plugin:app|default_window_icon").then(e=>e?new y(e):null)},fetchDataStoreIdentifiers:async function(){return h("plugin:app|fetch_data_store_identifiers")},getBundleType:async function(){return h("plugin:app|bundle_type")},getIdentifier:async function(){return h("plugin:app|identifier")},getName:async function(){return h("plugin:app|name")},getTauriVersion:async function(){return h("plugin:app|tauri_version")},getVersion:async function(){return h("plugin:app|version")},hide:async function(){return h("plugin:app|app_hide")},onBackButtonPress:async function(e){return p("app","back-button",e)},removeDataStore:async function(e){return h("plugin:app|remove_data_store",{uuid:e})},setDockVisibility:async function(e){return h("plugin:app|set_dock_visibility",{visible:e})},setTheme:async function(e){return h("plugin:app|set_app_theme",{theme:e})},show:async function(){return h("plugin:app|app_show")},supportsMultipleWindows:async function(){return h("plugin:app|supports_multiple_windows")}});class v{constructor(...e){this.type="Logical",1===e.length?"Logical"in e[0]?(this.width=e[0].Logical.width,this.height=e[0].Logical.height):(this.width=e[0].width,this.height=e[0].height):(this.width=e[0],this.height=e[1])}toPhysical(e){return new k(this.width*e,this.height*e)}[o](){return{width:this.width,height:this.height}}toJSON(){return this[o]()}}class k{constructor(...e){this.type="Physical",1===e.length?"Physical"in e[0]?(this.width=e[0].Physical.width,this.height=e[0].Physical.height):(this.width=e[0].width,this.height=e[0].height):(this.width=e[0],this.height=e[1])}toLogical(e){return new v(this.width/e,this.height/e)}[o](){return{width:this.width,height:this.height}}toJSON(){return this[o]()}}class A{constructor(e){this.size=e}toLogical(e){return this.size instanceof v?this.size:this.size.toLogical(e)}toPhysical(e){return this.size instanceof k?this.size:this.size.toPhysical(e)}[o](){return{[`${this.size.type}`]:{width:this.size.width,height:this.size.height}}}toJSON(){return this[o]()}}class T{constructor(...e){this.type="Logical",1===e.length?"Logical"in e[0]?(this.x=e[0].Logical.x,this.y=e[0].Logical.y):(this.x=e[0].x,this.y=e[0].y):(this.x=e[0],this.y=e[1])}toPhysical(e){return new I(this.x*e,this.y*e)}[o](){return{x:this.x,y:this.y}}toJSON(){return this[o]()}}class I{constructor(...e){this.type="Physical",1===e.length?"Physical"in e[0]?(this.x=e[0].Physical.x,this.y=e[0].Physical.y):(this.x=e[0].x,this.y=e[0].y):(this.x=e[0],this.y=e[1])}toLogical(e){return new T(this.x/e,this.y/e)}[o](){return{x:this.x,y:this.y}}toJSON(){return this[o]()}}class E{constructor(e){this.position=e}toLogical(e){return this.position instanceof T?this.position:this.position.toLogical(e)}toPhysical(e){return this.position instanceof I?this.position:this.position.toPhysical(e)}[o](){return{[`${this.position.type}`]:{x:this.position.x,y:this.position.y}}}toJSON(){return this[o]()}}var R,D=Object.freeze({__proto__:null,LogicalPosition:T,LogicalSize:v,PhysicalPosition:I,PhysicalSize:k,Position:E,Size:A});async function S(e,n){window.__TAURI_EVENT_PLUGIN_INTERNALS__.unregisterListener(e,n),await h("plugin:event|unlisten",{event:e,eventId:n})}async function N(e,n,t){var i;const r="string"==typeof(null==t?void 0:t.target)?{kind:"AnyLabel",label:t.target}:null!==(i=null==t?void 0:t.target)&&void 0!==i?i:{kind:"Any"};return h("plugin:event|listen",{event:e,target:r,handler:u(n)}).then(n=>async()=>S(e,n))}async function L(e,n,t){return N(e,t=>{S(e,t.id),n(t)},t)}async function C(e,n){await h("plugin:event|emit",{event:e,payload:n})}async function x(e,n,t){const i="string"==typeof e?{kind:"AnyLabel",label:e}:e;await h("plugin:event|emit_to",{target:i,event:n,payload:t})}!function(e){e.WINDOW_RESIZED="tauri://resize",e.WINDOW_MOVED="tauri://move",e.WINDOW_CLOSE_REQUESTED="tauri://close-requested",e.WINDOW_DESTROYED="tauri://destroyed",e.WINDOW_FOCUS="tauri://focus",e.WINDOW_BLUR="tauri://blur",e.WINDOW_SCALE_FACTOR_CHANGED="tauri://scale-change",e.WINDOW_THEME_CHANGED="tauri://theme-changed",e.WINDOW_CREATED="tauri://window-created",e.WEBVIEW_CREATED="tauri://webview-created",e.DRAG_ENTER="tauri://drag-enter",e.DRAG_OVER="tauri://drag-over",e.DRAG_DROP="tauri://drag-drop",e.DRAG_LEAVE="tauri://drag-leave"}(R||(R={}));var P,z,W,O=Object.freeze({__proto__:null,get TauriEvent(){return R},emit:C,emitTo:x,listen:N,once:L});function U(e){var n;if("items"in e)e.items=null===(n=e.items)||void 0===n?void 0:n.map(e=>"rid"in e?e:U(e));else if("action"in e&&e.action){const n=new c;return n.onmessage=e.action,delete e.action,{...e,handler:n}}return e}async function F(e,n){const t=new c;if(n&&"object"==typeof n&&("action"in n&&n.action&&(t.onmessage=n.action,delete n.action),"item"in n&&n.item&&"object"==typeof n.item&&"About"in n.item&&n.item.About&&"object"==typeof n.item.About&&"icon"in n.item.About&&n.item.About.icon&&(n.item.About.icon=g(n.item.About.icon)),"icon"in n&&n.icon&&(n.icon=g(n.icon)),"items"in n&&n.items)){function i(e){var n;return"rid"in e?[e.rid,e.kind]:("item"in e&&"object"==typeof e.item&&(null===(n=e.item.About)||void 0===n?void 0:n.icon)&&(e.item.About.icon=g(e.item.About.icon)),"icon"in e&&e.icon&&(e.icon=g(e.icon)),"items"in e&&e.items&&(e.items=e.items.map(i)),U(e))}n.items=n.items.map(i)}return h("plugin:menu|new",{kind:e,options:n,handler:t})}class M extends w{get id(){return n(this,P,"f")}get kind(){return n(this,z,"f")}constructor(e,n,i){super(e),P.set(this,void 0),z.set(this,void 0),t(this,P,n,"f"),t(this,z,i,"f")}}P=new WeakMap,z=new WeakMap;class B extends M{constructor(e,n){super(e,n,"MenuItem")}static async new(e){return F("MenuItem",e).then(([e,n])=>new B(e,n))}async text(){return h("plugin:menu|text",{rid:this.rid,kind:this.kind})}async setText(e){return h("plugin:menu|set_text",{rid:this.rid,kind:this.kind,text:e})}async isEnabled(){return h("plugin:menu|is_enabled",{rid:this.rid,kind:this.kind})}async setEnabled(e){return h("plugin:menu|set_enabled",{rid:this.rid,kind:this.kind,enabled:e})}async setAccelerator(e){return h("plugin:menu|set_accelerator",{rid:this.rid,kind:this.kind,accelerator:e})}}class V extends M{constructor(e,n){super(e,n,"Check")}static async new(e){return F("Check",e).then(([e,n])=>new V(e,n))}async text(){return h("plugin:menu|text",{rid:this.rid,kind:this.kind})}async setText(e){return h("plugin:menu|set_text",{rid:this.rid,kind:this.kind,text:e})}async isEnabled(){return h("plugin:menu|is_enabled",{rid:this.rid,kind:this.kind})}async setEnabled(e){return h("plugin:menu|set_enabled",{rid:this.rid,kind:this.kind,enabled:e})}async setAccelerator(e){return h("plugin:menu|set_accelerator",{rid:this.rid,kind:this.kind,accelerator:e})}async isChecked(){return h("plugin:menu|is_checked",{rid:this.rid})}async setChecked(e){return h("plugin:menu|set_checked",{rid:this.rid,checked:e})}}!function(e){e.Add="Add",e.Advanced="Advanced",e.Bluetooth="Bluetooth",e.Bookmarks="Bookmarks",e.Caution="Caution",e.ColorPanel="ColorPanel",e.ColumnView="ColumnView",e.Computer="Computer",e.EnterFullScreen="EnterFullScreen",e.Everyone="Everyone",e.ExitFullScreen="ExitFullScreen",e.FlowView="FlowView",e.Folder="Folder",e.FolderBurnable="FolderBurnable",e.FolderSmart="FolderSmart",e.FollowLinkFreestanding="FollowLinkFreestanding",e.FontPanel="FontPanel",e.GoLeft="GoLeft",e.GoRight="GoRight",e.Home="Home",e.IChatTheater="IChatTheater",e.IconView="IconView",e.Info="Info",e.InvalidDataFreestanding="InvalidDataFreestanding",e.LeftFacingTriangle="LeftFacingTriangle",e.ListView="ListView",e.LockLocked="LockLocked",e.LockUnlocked="LockUnlocked",e.MenuMixedState="MenuMixedState",e.MenuOnState="MenuOnState",e.MobileMe="MobileMe",e.MultipleDocuments="MultipleDocuments",e.Network="Network",e.Path="Path",e.PreferencesGeneral="PreferencesGeneral",e.QuickLook="QuickLook",e.RefreshFreestanding="RefreshFreestanding",e.Refresh="Refresh",e.Remove="Remove",e.RevealFreestanding="RevealFreestanding",e.RightFacingTriangle="RightFacingTriangle",e.Share="Share",e.Slideshow="Slideshow",e.SmartBadge="SmartBadge",e.StatusAvailable="StatusAvailable",e.StatusNone="StatusNone",e.StatusPartiallyAvailable="StatusPartiallyAvailable",e.StatusUnavailable="StatusUnavailable",e.StopProgressFreestanding="StopProgressFreestanding",e.StopProgress="StopProgress",e.TrashEmpty="TrashEmpty",e.TrashFull="TrashFull",e.User="User",e.UserAccounts="UserAccounts",e.UserGroup="UserGroup",e.UserGuest="UserGuest"}(W||(W={}));class G extends M{constructor(e,n){super(e,n,"Icon")}static async new(e){return F("Icon",e).then(([e,n])=>new G(e,n))}async text(){return h("plugin:menu|text",{rid:this.rid,kind:this.kind})}async setText(e){return h("plugin:menu|set_text",{rid:this.rid,kind:this.kind,text:e})}async isEnabled(){return h("plugin:menu|is_enabled",{rid:this.rid,kind:this.kind})}async setEnabled(e){return h("plugin:menu|set_enabled",{rid:this.rid,kind:this.kind,enabled:e})}async setAccelerator(e){return h("plugin:menu|set_accelerator",{rid:this.rid,kind:this.kind,accelerator:e})}async setIcon(e){return h("plugin:menu|set_icon",{rid:this.rid,kind:this.kind,icon:g(e)})}}class j extends M{constructor(e,n){super(e,n,"Predefined")}static async new(e){return F("Predefined",e).then(([e,n])=>new j(e,n))}async text(){return h("plugin:menu|text",{rid:this.rid,kind:this.kind})}async setText(e){return h("plugin:menu|set_text",{rid:this.rid,kind:this.kind,text:e})}}function H([e,n,t]){switch(t){case"Submenu":return new $(e,n);case"Predefined":return new j(e,n);case"Check":return new V(e,n);case"Icon":return new G(e,n);default:return new B(e,n)}}class $ extends M{constructor(e,n){super(e,n,"Submenu")}static async new(e){return F("Submenu",e).then(([e,n])=>new $(e,n))}async text(){return h("plugin:menu|text",{rid:this.rid,kind:this.kind})}async setText(e){return h("plugin:menu|set_text",{rid:this.rid,kind:this.kind,text:e})}async isEnabled(){return h("plugin:menu|is_enabled",{rid:this.rid,kind:this.kind})}async setEnabled(e){return h("plugin:menu|set_enabled",{rid:this.rid,kind:this.kind,enabled:e})}async append(e){return h("plugin:menu|append",{rid:this.rid,kind:this.kind,items:(Array.isArray(e)?e:[e]).map(e=>"rid"in e?[e.rid,e.kind]:e)})}async prepend(e){return h("plugin:menu|prepend",{rid:this.rid,kind:this.kind,items:(Array.isArray(e)?e:[e]).map(e=>"rid"in e?[e.rid,e.kind]:e)})}async insert(e,n){return h("plugin:menu|insert",{rid:this.rid,kind:this.kind,items:(Array.isArray(e)?e:[e]).map(e=>"rid"in e?[e.rid,e.kind]:e),position:n})}async remove(e){return h("plugin:menu|remove",{rid:this.rid,kind:this.kind,item:[e.rid,e.kind]})}async removeAt(e){return h("plugin:menu|remove_at",{rid:this.rid,kind:this.kind,position:e}).then(H)}async items(){return h("plugin:menu|items",{rid:this.rid,kind:this.kind}).then(e=>e.map(H))}async get(e){return h("plugin:menu|get",{rid:this.rid,kind:this.kind,id:e}).then(e=>e?H(e):null)}async popup(e,n){var t;return h("plugin:menu|popup",{rid:this.rid,kind:this.kind,window:null!==(t=null==n?void 0:n.label)&&void 0!==t?t:null,at:e instanceof E?e:e?new E(e):null})}async setAsWindowsMenuForNSApp(){return h("plugin:menu|set_as_windows_menu_for_nsapp",{rid:this.rid})}async setAsHelpMenuForNSApp(){return h("plugin:menu|set_as_help_menu_for_nsapp",{rid:this.rid})}async setIcon(e){return h("plugin:menu|set_icon",{rid:this.rid,kind:this.kind,icon:g(e)})}}class q extends M{constructor(e,n){super(e,n,"Menu")}static async new(e){return F("Menu",e).then(([e,n])=>new q(e,n))}static async default(){return h("plugin:menu|create_default").then(([e,n])=>new q(e,n))}async append(e){return h("plugin:menu|append",{rid:this.rid,kind:this.kind,items:(Array.isArray(e)?e:[e]).map(e=>"rid"in e?[e.rid,e.kind]:e)})}async prepend(e){return h("plugin:menu|prepend",{rid:this.rid,kind:this.kind,items:(Array.isArray(e)?e:[e]).map(e=>"rid"in e?[e.rid,e.kind]:e)})}async insert(e,n){return h("plugin:menu|insert",{rid:this.rid,kind:this.kind,items:(Array.isArray(e)?e:[e]).map(e=>"rid"in e?[e.rid,e.kind]:e),position:n})}async remove(e){return h("plugin:menu|remove",{rid:this.rid,kind:this.kind,item:[e.rid,e.kind]})}async removeAt(e){return h("plugin:menu|remove_at",{rid:this.rid,kind:this.kind,position:e}).then(H)}async items(){return h("plugin:menu|items",{rid:this.rid,kind:this.kind}).then(e=>e.map(H))}async get(e){return h("plugin:menu|get",{rid:this.rid,kind:this.kind,id:e}).then(e=>e?H(e):null)}async popup(e,n){var t;return h("plugin:menu|popup",{rid:this.rid,kind:this.kind,window:null!==(t=null==n?void 0:n.label)&&void 0!==t?t:null,at:e instanceof E?e:e?new E(e):null})}async setAsAppMenu(){return h("plugin:menu|set_as_app_menu",{rid:this.rid}).then(e=>e?new q(e[0],e[1]):null)}async setAsWindowMenu(e){var n;return h("plugin:menu|set_as_window_menu",{rid:this.rid,window:null!==(n=null==e?void 0:e.label)&&void 0!==n?n:null}).then(e=>e?new q(e[0],e[1]):null)}}var J=Object.freeze({__proto__:null,CheckMenuItem:V,IconMenuItem:G,Menu:q,MenuItem:B,get NativeIcon(){return W},PredefinedMenuItem:j,Submenu:$,itemFromKind:H});function Q(){var e,n;window.__TAURI_INTERNALS__=null!==(e=window.__TAURI_INTERNALS__)&&void 0!==e?e:{},window.__TAURI_EVENT_PLUGIN_INTERNALS__=null!==(n=window.__TAURI_EVENT_PLUGIN_INTERNALS__)&&void 0!==n?n:{}}var Z,K=Object.freeze({__proto__:null,clearMocks:function(){"object"==typeof window.__TAURI_INTERNALS__&&(delete window.__TAURI_INTERNALS__.invoke,delete window.__TAURI_INTERNALS__.transformCallback,delete window.__TAURI_INTERNALS__.unregisterCallback,delete window.__TAURI_INTERNALS__.runCallback,delete window.__TAURI_INTERNALS__.callbacks,delete window.__TAURI_INTERNALS__.convertFileSrc,delete window.__TAURI_INTERNALS__.metadata,"object"==typeof window.__TAURI_EVENT_PLUGIN_INTERNALS__&&delete window.__TAURI_EVENT_PLUGIN_INTERNALS__.unregisterListener)},mockConvertFileSrc:function(e){Q(),window.__TAURI_INTERNALS__.convertFileSrc=function(n,t="asset"){const i=encodeURIComponent(n);return"windows"===e?`http://${t}.localhost/${i}`:`${t}://localhost/${i}`}},mockIPC:function(e,n){function t(e,n){switch(e){case"plugin:event|listen":return function(e){i.has(e.event)||i.set(e.event,[]);return i.get(e.event).push(e.handler),e.handler}(n);case"plugin:event|emit":return function(e){const n=i.get(e.event)||[];for(const t of n)a(t,e);return null}(n);case"plugin:event|unlisten":return function(e){const n=i.get(e.event);if(n){const t=n.indexOf(e.id);-1!==t&&n.splice(t,1)}}(n)}}Q();const i=new Map,r=new Map;function s(e){r.delete(e)}function a(e,n){const t=r.get(e);t?t(n):console.warn(`[TAURI] Couldn't find callback id ${e}. This might happen when the app is reloaded while Rust is running an asynchronous operation.`)}window.__TAURI_INTERNALS__.invoke=async function(i,r,s){return(null==n?void 0:n.shouldMockEvents)&&function(e){return e.startsWith("plugin:event|")}(i)?t(i,r):e(i,r)},window.__TAURI_INTERNALS__.transformCallback=function(e,n=!1){const t=window.crypto.getRandomValues(new Uint32Array(1))[0];return r.set(t,i=>(n&&s(t),e&&e(i))),t},window.__TAURI_INTERNALS__.unregisterCallback=s,window.__TAURI_INTERNALS__.runCallback=a,window.__TAURI_INTERNALS__.callbacks=r,window.__TAURI_EVENT_PLUGIN_INTERNALS__.unregisterListener=function(e,n){s(n)}},mockWindows:function(e,...n){Q(),window.__TAURI_INTERNALS__.metadata={currentWindow:{label:e},currentWebview:{windowLabel:e,label:e}}}});!function(e){e[e.Audio=1]="Audio",e[e.Cache=2]="Cache",e[e.Config=3]="Config",e[e.Data=4]="Data",e[e.LocalData=5]="LocalData",e[e.Document=6]="Document",e[e.Download=7]="Download",e[e.Picture=8]="Picture",e[e.Public=9]="Public",e[e.Video=10]="Video",e[e.Resource=11]="Resource",e[e.Temp=12]="Temp",e[e.AppConfig=13]="AppConfig",e[e.AppData=14]="AppData",e[e.AppLocalData=15]="AppLocalData",e[e.AppCache=16]="AppCache",e[e.AppLog=17]="AppLog",e[e.Desktop=18]="Desktop",e[e.Executable=19]="Executable",e[e.Font=20]="Font",e[e.Home=21]="Home",e[e.Runtime=22]="Runtime",e[e.Template=23]="Template"}(Z||(Z={}));var Y=Object.freeze({__proto__:null,get BaseDirectory(){return Z},appCacheDir:async function(){return h("plugin:path|resolve_directory",{directory:Z.AppCache})},appConfigDir:async function(){return h("plugin:path|resolve_directory",{directory:Z.AppConfig})},appDataDir:async function(){return h("plugin:path|resolve_directory",{directory:Z.AppData})},appLocalDataDir:async function(){return h("plugin:path|resolve_directory",{directory:Z.AppLocalData})},appLogDir:async function(){return h("plugin:path|resolve_directory",{directory:Z.AppLog})},audioDir:async function(){return h("plugin:path|resolve_directory",{directory:Z.Audio})},basename:async function(e,n){return h("plugin:path|basename",{path:e,ext:n})},cacheDir:async function(){return h("plugin:path|resolve_directory",{directory:Z.Cache})},configDir:async function(){return h("plugin:path|resolve_directory",{directory:Z.Config})},dataDir:async function(){return h("plugin:path|resolve_directory",{directory:Z.Data})},delimiter:function(){return window.__TAURI_INTERNALS__.plugins.path.delimiter},desktopDir:async function(){return h("plugin:path|resolve_directory",{directory:Z.Desktop})},dirname:async function(e){return h("plugin:path|dirname",{path:e})},documentDir:async function(){return h("plugin:path|resolve_directory",{directory:Z.Document})},downloadDir:async function(){return h("plugin:path|resolve_directory",{directory:Z.Download})},executableDir:async function(){return h("plugin:path|resolve_directory",{directory:Z.Executable})},extname:async function(e){return h("plugin:path|extname",{path:e})},fontDir:async function(){return h("plugin:path|resolve_directory",{directory:Z.Font})},homeDir:async function(){return h("plugin:path|resolve_directory",{directory:Z.Home})},isAbsolute:async function(e){return h("plugin:path|is_absolute",{path:e})},join:async function(...e){return h("plugin:path|join",{paths:e})},localDataDir:async function(){return h("plugin:path|resolve_directory",{directory:Z.LocalData})},normalize:async function(e){return h("plugin:path|normalize",{path:e})},pictureDir:async function(){return h("plugin:path|resolve_directory",{directory:Z.Picture})},publicDir:async function(){return h("plugin:path|resolve_directory",{directory:Z.Public})},resolve:async function(...e){return h("plugin:path|resolve",{paths:e})},resolveResource:async function(e){return h("plugin:path|resolve_directory",{directory:Z.Resource,path:e})},resourceDir:async function(){return h("plugin:path|resolve_directory",{directory:Z.Resource})},runtimeDir:async function(){return h("plugin:path|resolve_directory",{directory:Z.Runtime})},sep:function(){return window.__TAURI_INTERNALS__.plugins.path.sep},tempDir:async function(){return h("plugin:path|resolve_directory",{directory:Z.Temp})},templateDir:async function(){return h("plugin:path|resolve_directory",{directory:Z.Template})},videoDir:async function(){return h("plugin:path|resolve_directory",{directory:Z.Video})}});class X extends w{constructor(e,n){super(e),this.id=n}static async getById(e){return h("plugin:tray|get_by_id",{id:e}).then(n=>n?new X(n,e):null)}static async removeById(e){return h("plugin:tray|remove_by_id",{id:e})}static async new(e){(null==e?void 0:e.menu)&&(e.menu=[e.menu.rid,e.menu.kind]),(null==e?void 0:e.icon)&&(e.icon=g(e.icon));const n=new c;if(null==e?void 0:e.action){const t=e.action;n.onmessage=e=>t(function(e){const n=e;return n.position=new I(e.position),n.rect.position=new I(e.rect.position),n.rect.size=new k(e.rect.size),n}(e)),delete e.action}return h("plugin:tray|new",{options:null!=e?e:{},handler:n}).then(([e,n])=>new X(e,n))}async setIcon(e){let n=null;return e&&(n=g(e)),h("plugin:tray|set_icon",{rid:this.rid,icon:n})}async setMenu(e){return e&&(e=[e.rid,e.kind]),h("plugin:tray|set_menu",{rid:this.rid,menu:e})}async setTooltip(e){return h("plugin:tray|set_tooltip",{rid:this.rid,tooltip:e})}async setTitle(e){return h("plugin:tray|set_title",{rid:this.rid,title:e})}async setVisible(e){return h("plugin:tray|set_visible",{rid:this.rid,visible:e})}async setTempDirPath(e){return h("plugin:tray|set_temp_dir_path",{rid:this.rid,path:e})}async setIconAsTemplate(e){return h("plugin:tray|set_icon_as_template",{rid:this.rid,asTemplate:e})}async setMenuOnLeftClick(e){return h("plugin:tray|set_show_menu_on_left_click",{rid:this.rid,onLeft:e})}async setShowMenuOnLeftClick(e){return h("plugin:tray|set_show_menu_on_left_click",{rid:this.rid,onLeft:e})}}var ee,ne,te=Object.freeze({__proto__:null,TrayIcon:X});!function(e){e[e.Critical=1]="Critical",e[e.Informational=2]="Informational"}(ee||(ee={}));class ie{constructor(e){this._preventDefault=!1,this.event=e.event,this.id=e.id}preventDefault(){this._preventDefault=!0}isPreventDefault(){return this._preventDefault}}function re(){return new le(window.__TAURI_INTERNALS__.metadata.currentWindow.label,{skip:!0})}async function se(){return h("plugin:window|get_all_windows").then(e=>e.map(e=>new le(e,{skip:!0})))}!function(e){e.None="none",e.Normal="normal",e.Indeterminate="indeterminate",e.Paused="paused",e.Error="error"}(ne||(ne={}));const ae=["tauri://created","tauri://error"];class le{constructor(e,n={}){var t;this.label=e,this.listeners=Object.create(null),(null==n?void 0:n.skip)||h("plugin:window|create",{options:{...n,parent:"string"==typeof n.parent?n.parent:null===(t=n.parent)||void 0===t?void 0:t.label,label:e}}).then(async()=>this.emit("tauri://created")).catch(async e=>this.emit("tauri://error",e))}static async getByLabel(e){var n;return null!==(n=(await se()).find(n=>n.label===e))&&void 0!==n?n:null}static getCurrent(){return re()}static async getAll(){return se()}static async getFocusedWindow(){for(const e of await se())if(await e.isFocused())return e;return null}async listen(e,n){return this._handleTauriEvent(e,n)?()=>{const t=this.listeners[e];t.splice(t.indexOf(n),1)}:N(e,n,{target:{kind:"Window",label:this.label}})}async once(e,n){return this._handleTauriEvent(e,n)?()=>{const t=this.listeners[e];t.splice(t.indexOf(n),1)}:L(e,n,{target:{kind:"Window",label:this.label}})}async emit(e,n){if(!ae.includes(e))return C(e,n);for(const t of this.listeners[e]||[])t({event:e,id:-1,payload:n})}async emitTo(e,n,t){if(!ae.includes(n))return x(e,n,t);for(const e of this.listeners[n]||[])e({event:n,id:-1,payload:t})}_handleTauriEvent(e,n){return!!ae.includes(e)&&(e in this.listeners?this.listeners[e].push(n):this.listeners[e]=[n],!0)}async scaleFactor(){return h("plugin:window|scale_factor",{label:this.label})}async innerPosition(){return h("plugin:window|inner_position",{label:this.label}).then(e=>new I(e))}async outerPosition(){return h("plugin:window|outer_position",{label:this.label}).then(e=>new I(e))}async innerSize(){return h("plugin:window|inner_size",{label:this.label}).then(e=>new k(e))}async outerSize(){return h("plugin:window|outer_size",{label:this.label}).then(e=>new k(e))}async isFullscreen(){return h("plugin:window|is_fullscreen",{label:this.label})}async isMinimized(){return h("plugin:window|is_minimized",{label:this.label})}async isMaximized(){return h("plugin:window|is_maximized",{label:this.label})}async isFocused(){return h("plugin:window|is_focused",{label:this.label})}async isDecorated(){return h("plugin:window|is_decorated",{label:this.label})}async isResizable(){return h("plugin:window|is_resizable",{label:this.label})}async isMaximizable(){return h("plugin:window|is_maximizable",{label:this.label})}async isMinimizable(){return h("plugin:window|is_minimizable",{label:this.label})}async isClosable(){return h("plugin:window|is_closable",{label:this.label})}async isVisible(){return h("plugin:window|is_visible",{label:this.label})}async title(){return h("plugin:window|title",{label:this.label})}async theme(){return h("plugin:window|theme",{label:this.label})}async isAlwaysOnTop(){return h("plugin:window|is_always_on_top",{label:this.label})}async activityName(){return h("plugin:window|activity_name",{label:this.label})}async sceneIdentifier(){return h("plugin:window|scene_identifier",{label:this.label})}async center(){return h("plugin:window|center",{label:this.label})}async requestUserAttention(e){let n=null;return e&&(n=e===ee.Critical?{type:"Critical"}:{type:"Informational"}),h("plugin:window|request_user_attention",{label:this.label,value:n})}async setResizable(e){return h("plugin:window|set_resizable",{label:this.label,value:e})}async setEnabled(e){return h("plugin:window|set_enabled",{label:this.label,value:e})}async isEnabled(){return h("plugin:window|is_enabled",{label:this.label})}async setMaximizable(e){return h("plugin:window|set_maximizable",{label:this.label,value:e})}async setMinimizable(e){return h("plugin:window|set_minimizable",{label:this.label,value:e})}async setClosable(e){return h("plugin:window|set_closable",{label:this.label,value:e})}async setTitle(e){return h("plugin:window|set_title",{label:this.label,value:e})}async maximize(){return h("plugin:window|maximize",{label:this.label})}async unmaximize(){return h("plugin:window|unmaximize",{label:this.label})}async toggleMaximize(){return h("plugin:window|toggle_maximize",{label:this.label})}async minimize(){return h("plugin:window|minimize",{label:this.label})}async unminimize(){return h("plugin:window|unminimize",{label:this.label})}async show(){return h("plugin:window|show",{label:this.label})}async hide(){return h("plugin:window|hide",{label:this.label})}async close(){return h("plugin:window|close",{label:this.label})}async destroy(){return h("plugin:window|destroy",{label:this.label})}async setDecorations(e){return h("plugin:window|set_decorations",{label:this.label,value:e})}async setShadow(e){return h("plugin:window|set_shadow",{label:this.label,value:e})}async setEffects(e){return h("plugin:window|set_effects",{label:this.label,value:e})}async clearEffects(){return h("plugin:window|set_effects",{label:this.label,value:null})}async setAlwaysOnTop(e){return h("plugin:window|set_always_on_top",{label:this.label,value:e})}async setAlwaysOnBottom(e){return h("plugin:window|set_always_on_bottom",{label:this.label,value:e})}async setContentProtected(e){return h("plugin:window|set_content_protected",{label:this.label,value:e})}async setSize(e){return h("plugin:window|set_size",{label:this.label,value:e instanceof A?e:new A(e)})}async setMinSize(e){return h("plugin:window|set_min_size",{label:this.label,value:e instanceof A?e:e?new A(e):null})}async setMaxSize(e){return h("plugin:window|set_max_size",{label:this.label,value:e instanceof A?e:e?new A(e):null})}async setSizeConstraints(e){function n(e){return e?{Logical:e}:null}return h("plugin:window|set_size_constraints",{label:this.label,value:{minWidth:n(null==e?void 0:e.minWidth),minHeight:n(null==e?void 0:e.minHeight),maxWidth:n(null==e?void 0:e.maxWidth),maxHeight:n(null==e?void 0:e.maxHeight)}})}async setPosition(e){return h("plugin:window|set_position",{label:this.label,value:e instanceof E?e:new E(e)})}async setFullscreen(e){return h("plugin:window|set_fullscreen",{label:this.label,value:e})}async setSimpleFullscreen(e){return h("plugin:window|set_simple_fullscreen",{label:this.label,value:e})}async setFocus(){return h("plugin:window|set_focus",{label:this.label})}async setFocusable(e){return h("plugin:window|set_focusable",{label:this.label,value:e})}async setIcon(e){return h("plugin:window|set_icon",{label:this.label,value:g(e)})}async setSkipTaskbar(e){return h("plugin:window|set_skip_taskbar",{label:this.label,value:e})}async setCursorGrab(e){return h("plugin:window|set_cursor_grab",{label:this.label,value:e})}async setCursorVisible(e){return h("plugin:window|set_cursor_visible",{label:this.label,value:e})}async setCursorIcon(e){return h("plugin:window|set_cursor_icon",{label:this.label,value:e})}async setBackgroundColor(e){return h("plugin:window|set_background_color",{color:e})}async setCursorPosition(e){return h("plugin:window|set_cursor_position",{label:this.label,value:e instanceof E?e:new E(e)})}async setIgnoreCursorEvents(e){return h("plugin:window|set_ignore_cursor_events",{label:this.label,value:e})}async startDragging(){return h("plugin:window|start_dragging",{label:this.label})}async startResizeDragging(e){return h("plugin:window|start_resize_dragging",{label:this.label,value:e})}async setBadgeCount(e){return h("plugin:window|set_badge_count",{label:this.label,value:e})}async setBadgeLabel(e){return h("plugin:window|set_badge_label",{label:this.label,value:e})}async setOverlayIcon(e){return h("plugin:window|set_overlay_icon",{label:this.label,value:e?g(e):void 0})}async setProgressBar(e){return h("plugin:window|set_progress_bar",{label:this.label,value:e})}async setVisibleOnAllWorkspaces(e){return h("plugin:window|set_visible_on_all_workspaces",{label:this.label,value:e})}async setTitleBarStyle(e){return h("plugin:window|set_title_bar_style",{label:this.label,value:e})}async setTheme(e){return h("plugin:window|set_theme",{label:this.label,value:e})}async onResized(e){return this.listen(R.WINDOW_RESIZED,n=>{n.payload=new k(n.payload),e(n)})}async onMoved(e){return this.listen(R.WINDOW_MOVED,n=>{n.payload=new I(n.payload),e(n)})}async onCloseRequested(e){return this.listen(R.WINDOW_CLOSE_REQUESTED,async n=>{const t=new ie(n);await e(t),t.isPreventDefault()||await this.destroy()})}async onDragDropEvent(e){const n=await this.listen(R.DRAG_ENTER,n=>{e({...n,payload:{type:"enter",paths:n.payload.paths,position:new I(n.payload.position)}})}),t=await this.listen(R.DRAG_OVER,n=>{e({...n,payload:{type:"over",position:new I(n.payload.position)}})}),i=await this.listen(R.DRAG_DROP,n=>{e({...n,payload:{type:"drop",paths:n.payload.paths,position:new I(n.payload.position)}})}),r=await this.listen(R.DRAG_LEAVE,n=>{e({...n,payload:{type:"leave"}})});return()=>{n(),i(),t(),r()}}async onFocusChanged(e){const n=await this.listen(R.WINDOW_FOCUS,n=>{e({...n,payload:!0})}),t=await this.listen(R.WINDOW_BLUR,n=>{e({...n,payload:!1})});return()=>{n(),t()}}async onScaleChanged(e){return this.listen(R.WINDOW_SCALE_FACTOR_CHANGED,e)}async onThemeChanged(e){return this.listen(R.WINDOW_THEME_CHANGED,e)}}var oe,ue,ce,de;function pe(e){return null===e?null:{name:e.name,scaleFactor:e.scaleFactor,position:new I(e.position),size:new k(e.size),workArea:{position:new I(e.workArea.position),size:new k(e.workArea.size)}}}!function(e){e.Disabled="disabled",e.Throttle="throttle",e.Suspend="suspend"}(oe||(oe={})),function(e){e.Default="default",e.FluentOverlay="fluentOverlay"}(ue||(ue={})),function(e){e.AppearanceBased="appearanceBased",e.Light="light",e.Dark="dark",e.MediumLight="mediumLight",e.UltraDark="ultraDark",e.Titlebar="titlebar",e.Selection="selection",e.Menu="menu",e.Popover="popover",e.Sidebar="sidebar",e.HeaderView="headerView",e.Sheet="sheet",e.WindowBackground="windowBackground",e.HudWindow="hudWindow",e.FullScreenUI="fullScreenUI",e.Tooltip="tooltip",e.ContentBackground="contentBackground",e.UnderWindowBackground="underWindowBackground",e.UnderPageBackground="underPageBackground",e.Mica="mica",e.Blur="blur",e.Acrylic="acrylic",e.Tabbed="tabbed",e.TabbedDark="tabbedDark",e.TabbedLight="tabbedLight"}(ce||(ce={})),function(e){e.FollowsWindowActiveState="followsWindowActiveState",e.Active="active",e.Inactive="inactive"}(de||(de={}));var he=Object.freeze({__proto__:null,CloseRequestedEvent:ie,get Effect(){return ce},get EffectState(){return de},LogicalPosition:T,LogicalSize:v,PhysicalPosition:I,PhysicalSize:k,get ProgressBarStatus(){return ne},get UserAttentionType(){return ee},Window:le,availableMonitors:async function(){return h("plugin:window|available_monitors").then(e=>e.map(pe))},currentMonitor:async function(){return h("plugin:window|current_monitor").then(pe)},cursorPosition:async function(){return h("plugin:window|cursor_position").then(e=>new I(e))},getAllWindows:se,getCurrentWindow:re,monitorFromPoint:async function(e,n){return h("plugin:window|monitor_from_point",{x:e,y:n}).then(pe)},primaryMonitor:async function(){return h("plugin:window|primary_monitor").then(pe)}});function we(){return new ge(re(),window.__TAURI_INTERNALS__.metadata.currentWebview.label,{skip:!0})}async function _e(){return h("plugin:webview|get_all_webviews").then(e=>e.map(e=>new ge(new le(e.windowLabel,{skip:!0}),e.label,{skip:!0})))}const ye=["tauri://created","tauri://error"];class ge{constructor(e,n,t){this.window=e,this.label=n,this.listeners=Object.create(null),(null==t?void 0:t.skip)||h("plugin:webview|create_webview",{windowLabel:e.label,options:{...t,label:n}}).then(async()=>this.emit("tauri://created")).catch(async e=>this.emit("tauri://error",e))}static async getByLabel(e){var n;return null!==(n=(await _e()).find(n=>n.label===e))&&void 0!==n?n:null}static getCurrent(){return we()}static async getAll(){return _e()}async listen(e,n){return this._handleTauriEvent(e,n)?()=>{const t=this.listeners[e];t.splice(t.indexOf(n),1)}:N(e,n,{target:{kind:"Webview",label:this.label}})}async once(e,n){return this._handleTauriEvent(e,n)?()=>{const t=this.listeners[e];t.splice(t.indexOf(n),1)}:L(e,n,{target:{kind:"Webview",label:this.label}})}async emit(e,n){if(!ye.includes(e))return C(e,n);for(const t of this.listeners[e]||[])t({event:e,id:-1,payload:n})}async emitTo(e,n,t){if(!ye.includes(n))return x(e,n,t);for(const e of this.listeners[n]||[])e({event:n,id:-1,payload:t})}_handleTauriEvent(e,n){return!!ye.includes(e)&&(e in this.listeners?this.listeners[e].push(n):this.listeners[e]=[n],!0)}async position(){return h("plugin:webview|webview_position",{label:this.label}).then(e=>new I(e))}async size(){return h("plugin:webview|webview_size",{label:this.label}).then(e=>new k(e))}async close(){return h("plugin:webview|webview_close",{label:this.label})}async setSize(e){return h("plugin:webview|set_webview_size",{label:this.label,value:e instanceof A?e:new A(e)})}async setPosition(e){return h("plugin:webview|set_webview_position",{label:this.label,value:e instanceof E?e:new E(e)})}async setFocus(){return h("plugin:webview|set_webview_focus",{label:this.label})}async setAutoResize(e){return h("plugin:webview|set_webview_auto_resize",{label:this.label,value:e})}async hide(){return h("plugin:webview|webview_hide",{label:this.label})}async show(){return h("plugin:webview|webview_show",{label:this.label})}async setZoom(e){return h("plugin:webview|set_webview_zoom",{label:this.label,value:e})}async reparent(e){return h("plugin:webview|reparent",{label:this.label,window:"string"==typeof e?e:e.label})}async clearAllBrowsingData(){return h("plugin:webview|clear_all_browsing_data")}async setBackgroundColor(e){return h("plugin:webview|set_webview_background_color",{color:e})}async onDragDropEvent(e){const n=await this.listen(R.DRAG_ENTER,n=>{e({...n,payload:{type:"enter",paths:n.payload.paths,position:new I(n.payload.position)}})}),t=await this.listen(R.DRAG_OVER,n=>{e({...n,payload:{type:"over",position:new I(n.payload.position)}})}),i=await this.listen(R.DRAG_DROP,n=>{e({...n,payload:{type:"drop",paths:n.payload.paths,position:new I(n.payload.position)}})}),r=await this.listen(R.DRAG_LEAVE,n=>{e({...n,payload:{type:"leave"}})});return()=>{n(),i(),t(),r()}}}var be,me,fe=Object.freeze({__proto__:null,Webview:ge,getAllWebviews:_e,getCurrentWebview:we});function ve(){const e=we();return new Ae(e.label,{skip:!0})}async function ke(){return h("plugin:window|get_all_windows").then(e=>e.map(e=>new Ae(e,{skip:!0})))}class Ae{constructor(e,n={}){var t;this.label=e,this.listeners=Object.create(null),(null==n?void 0:n.skip)||h("plugin:webview|create_webview_window",{options:{...n,parent:"string"==typeof n.parent?n.parent:null===(t=n.parent)||void 0===t?void 0:t.label,label:e}}).then(async()=>this.emit("tauri://created")).catch(async e=>this.emit("tauri://error",e))}static async getByLabel(e){var n;const t=null!==(n=(await ke()).find(n=>n.label===e))&&void 0!==n?n:null;return t?new Ae(t.label,{skip:!0}):null}static getCurrent(){return ve()}static async getAll(){return ke()}async listen(e,n){return this._handleTauriEvent(e,n)?()=>{const t=this.listeners[e];t.splice(t.indexOf(n),1)}:N(e,n,{target:{kind:"WebviewWindow",label:this.label}})}async once(e,n){return this._handleTauriEvent(e,n)?()=>{const t=this.listeners[e];t.splice(t.indexOf(n),1)}:L(e,n,{target:{kind:"WebviewWindow",label:this.label}})}async setBackgroundColor(e){return h("plugin:window|set_background_color",{color:e}).then(()=>h("plugin:webview|set_webview_background_color",{color:e}))}}be=Ae,me=[le,ge],(Array.isArray(me)?me:[me]).forEach(e=>{Object.getOwnPropertyNames(e.prototype).forEach(n=>{var t;"object"==typeof be.prototype&&be.prototype&&n in be.prototype||Object.defineProperty(be.prototype,n,null!==(t=Object.getOwnPropertyDescriptor(e.prototype,n))&&void 0!==t?t:Object.create(null))})});var Te=Object.freeze({__proto__:null,WebviewWindow:Ae,getAllWebviewWindows:ke,getCurrentWebviewWindow:ve});return e.app=f,e.core=_,e.dpi=D,e.event=O,e.image=m,e.menu=J,e.mocks=K,e.path=Y,e.tray=te,e.webview=fe,e.webviewWindow=Te,e.window=he,e}({});window.__TAURI__=__TAURI_IIFE__; diff --git a/crates/tauri/src/app.rs b/crates/tauri/src/app.rs index e8e5343d9abf..6550b76f1cbe 100644 --- a/crates/tauri/src/app.rs +++ b/crates/tauri/src/app.rs @@ -252,6 +252,20 @@ pub enum RunEvent { /// Indicates whether the NSApplication object found any visible windows in your application. has_visible_windows: bool, }, + /// Emitted when a scene is requested by the system. + /// + /// This event is emitted when a scene is requested by the system. + /// Scenes created by [`Window::new`] are not emitted with this event. + /// It is also not emitted for the main scene. + #[cfg(target_os = "ios")] + SceneRequested { + /// Scene that was requested by the system. + scene: objc2::rc::Retained, + /// Options that were used to request the scene. + /// + /// This lets you determine why the scene was requested. + options: objc2::rc::Retained, + }, } impl From for RunEvent { @@ -632,6 +646,18 @@ impl AppHandle { pub fn set_device_event_filter(&self, filter: DeviceEventFilter) { self.runtime_handle.set_device_event_filter(filter); } + + /// Whether the application supports multiple windows. + #[cfg(target_os = "ios")] + pub fn supports_multiple_windows(&self) -> bool { + let (tx, rx) = std::sync::mpsc::channel(); + self.run_on_main_thread(move || unsafe { + let mtm = objc2::MainThreadMarker::new().unwrap(); + let ui_application = objc2_ui_kit::UIApplication::sharedApplication(mtm); + tx.send(ui_application.supportsMultipleScenes()).unwrap(); + }); + rx.recv().unwrap() + } } impl Manager for AppHandle { @@ -656,6 +682,16 @@ impl ManagerBase for AppHandle { fn managed_app_handle(&self) -> &AppHandle { self } + + #[cfg(target_os = "android")] + fn activity_name(&self) -> Option> { + None + } + + #[cfg(target_os = "ios")] + fn scene_identifier(&self) -> Option> { + None + } } /// The instance of the currently running application. @@ -706,6 +742,16 @@ impl ManagerBase for App { fn managed_app_handle(&self) -> &AppHandle { self.handle() } + + #[cfg(target_os = "android")] + fn activity_name(&self) -> Option> { + None + } + + #[cfg(target_os = "ios")] + fn scene_identifier(&self) -> Option> { + None + } } /// APIs specific to the wry runtime. @@ -1045,6 +1091,40 @@ macro_rules! shared_app_impl { pub fn invoke_key(&self) -> &str { self.manager.invoke_key() } + + /// Whether the application supports multiple windows. + #[cfg(desktop)] + pub fn supports_multiple_windows(&self) -> bool { + true + } + + /// Whether the application supports multiple windows. + #[cfg(target_os = "android")] + pub fn supports_multiple_windows(&self) -> bool { + let runtime_handle = match self.runtime() { + RuntimeOrDispatch::Runtime(runtime) => runtime.handle(), + RuntimeOrDispatch::RuntimeHandle(handle) => handle, + _ => unreachable!(), + }; + + let (tx, rx) = std::sync::mpsc::channel(); + + runtime_handle.run_on_android_context(move |env, _activity, _webview| { + let supports = (|| { + let version_class = env.find_class("android/os/Build$VERSION")?; + let sdk = env + .get_static_field(version_class, "SDK_INT", "I")? + .i() + .unwrap_or_default(); + crate::Result::Ok(sdk >= 32) + })() + .unwrap_or(false); + + let _ = tx.send(supports); + }); + + rx.recv().unwrap_or(false) + } } impl Listener for $app { @@ -1144,6 +1224,16 @@ impl App { &self.handle } + /// Whether the application supports multiple windows. + #[cfg(target_os = "ios")] + pub fn supports_multiple_windows(&self) -> bool { + unsafe { + let mtm = objc2::MainThreadMarker::new().unwrap(); + let ui_application = objc2_ui_kit::UIApplication::sharedApplication(mtm); + ui_application.supportsMultipleScenes() + } + } + /// Sets the activation policy for the application. It is set to `NSApplicationActivationPolicyRegular` by default. /// /// # Examples @@ -2483,6 +2573,10 @@ fn on_event_loop_event( } => RunEvent::Reopen { has_visible_windows, }, + #[cfg(target_os = "ios")] + RuntimeRunEvent::SceneRequested { scene, options } => { + RunEvent::SceneRequested { scene, options } + } _ => unimplemented!(), }; diff --git a/crates/tauri/src/app/plugin.rs b/crates/tauri/src/app/plugin.rs index 8b9d3f358daf..20d07fc67736 100644 --- a/crates/tauri/src/app/plugin.rs +++ b/crates/tauri/src/app/plugin.rs @@ -115,6 +115,11 @@ pub fn bundle_type() -> Option { tauri_utils::platform::bundle_type() } +#[command(root = "crate")] +pub fn supports_multiple_windows(app: AppHandle) -> bool { + app.supports_multiple_windows() +} + pub fn init() -> TauriPlugin { Builder::new("app") .invoke_handler(crate::generate_handler![ @@ -131,6 +136,7 @@ pub fn init() -> TauriPlugin { set_app_theme, set_dock_visibility, bundle_type, + supports_multiple_windows, ]) .setup(|_app, _api| { #[cfg(target_os = "android")] diff --git a/crates/tauri/src/lib.rs b/crates/tauri/src/lib.rs index d56ba8736ea5..38cbbc3a58ec 100644 --- a/crates/tauri/src/lib.rs +++ b/crates/tauri/src/lib.rs @@ -13,6 +13,7 @@ //! - **wry** *(enabled by default)*: Enables the [wry](https://github.com/tauri-apps/wry) runtime. Only disable it if you want a custom runtime. //! - **common-controls-v6** *(enabled by default)*: Enables [Common Controls v6](https://learn.microsoft.com/en-us/windows/win32/controls/common-control-versions) support on Windows, mainly for the predefined `about` menu item. //! - **x11** *(enabled by default)*: Enables X11 support. Disable this if you only target Wayland. +//! - **dbus** *(enabled by default)*: Enables dbus dependency for theme support on Linux. Disable this if you do not need theme support or don't want to build the dbus rust crate. The WebView dependencies use dbus either way. //! - **unstable**: Enables unstable features. Be careful, it might introduce breaking changes in future minor releases. //! - **tracing**: Enables [`tracing`](https://docs.rs/tracing/latest/tracing) for window startup, plugins, `Window::eval`, events, IPC, updater and custom protocol request handlers. //! - **test**: Enables the [`mod@test`] module exposing unit test helpers. @@ -137,14 +138,7 @@ macro_rules! android_binding { ::tauri::wry::android_binding!($domain, $app_name, $wry); - ::tauri::tao::android_binding!( - $domain, - $app_name, - WryActivity, - android_setup, - $main, - ::tauri::tao - ); + ::tauri::tao::android_binding!($domain, $app_name, Rust, android_setup, $main, ::tauri::tao); // be careful when renaming this, the `Java_app_tauri_plugin_PluginManager_handlePluginResponse` symbol is checked by the CLI ::tauri::tao::platform::android::prelude::android_fn!( @@ -1067,6 +1061,10 @@ pub(crate) mod sealed { fn manager_owned(&self) -> Arc>; fn runtime(&self) -> RuntimeOrDispatch<'_, R>; fn managed_app_handle(&self) -> &AppHandle; + #[cfg(target_os = "android")] + fn activity_name(&self) -> Option>; + #[cfg(target_os = "ios")] + fn scene_identifier(&self) -> Option>; } } diff --git a/crates/tauri/src/test/mock_runtime.rs b/crates/tauri/src/test/mock_runtime.rs index 5fbedd013fb4..7913e9ac014c 100644 --- a/crates/tauri/src/test/mock_runtime.rs +++ b/crates/tauri/src/test/mock_runtime.rs @@ -534,6 +534,21 @@ impl WindowBuilder for MockWindowBuilder { fn background_color(self, _color: tauri_utils::config::Color) -> Self { self } + + #[cfg(target_os = "android")] + fn activity_name>(self, _class_name: S) -> Self { + self + } + + #[cfg(target_os = "android")] + fn created_by_activity_name>(self, _class_name: S) -> Self { + self + } + + #[cfg(target_os = "ios")] + fn requested_by_scene_identifier>(self, _identifier: S) -> Self { + self + } } impl WebviewDispatch for MockWebviewDispatcher { @@ -796,6 +811,16 @@ impl WindowDispatch for MockWindowDispatcher { unimplemented!() } + #[cfg(target_os = "android")] + fn activity_name(&self) -> Result { + unimplemented!() + } + + #[cfg(target_os = "ios")] + fn scene_identifier(&self) -> Result { + unimplemented!() + } + fn window_handle( &self, ) -> std::result::Result, raw_window_handle::HandleError> { diff --git a/crates/tauri/src/webview/mod.rs b/crates/tauri/src/webview/mod.rs index 8842382bf15a..75aceb44999c 100644 --- a/crates/tauri/src/webview/mod.rs +++ b/crates/tauri/src/webview/mod.rs @@ -2278,6 +2278,16 @@ impl ManagerBase for Webview { fn managed_app_handle(&self) -> &AppHandle { &self.app_handle } + + #[cfg(target_os = "android")] + fn activity_name(&self) -> Option> { + Some(self.window().activity_name()) + } + + #[cfg(target_os = "ios")] + fn scene_identifier(&self) -> Option> { + Some(self.window().scene_identifier()) + } } impl<'de, R: Runtime> CommandArg<'de, R> for Webview { diff --git a/crates/tauri/src/webview/plugin.rs b/crates/tauri/src/webview/plugin.rs index 78bfd80210e2..5999112eb894 100644 --- a/crates/tauri/src/webview/plugin.rs +++ b/crates/tauri/src/webview/plugin.rs @@ -5,86 +5,51 @@ //! The tauri plugin to create and manipulate windows from JS. use crate::{ + command, plugin::{Builder, TauriPlugin}, - Runtime, + sealed::ManagerBase, + utils::config::WindowConfig, + AppHandle, Runtime, WebviewWindowBuilder, }; -#[cfg(desktop)] -mod desktop_commands { +#[derive(serde::Serialize)] +struct WebviewRef { + window_label: String, + label: String, +} - use serde::Serialize; - use tauri_runtime::dpi::{Position, Size}; - use tauri_utils::config::WindowConfig; +#[command(root = "crate")] +async fn get_all_webviews(app: AppHandle) -> Vec { + app + .manager() + .webviews() + .values() + .map(|webview| WebviewRef { + window_label: webview.window_ref().label().into(), + label: webview.label().into(), + }) + .collect() +} + +#[command(root = "crate")] +async fn create_webview_window( + app: AppHandle, + options: WindowConfig, +) -> crate::Result<()> { + WebviewWindowBuilder::from_config(&app, &options)?.build()?; + Ok(()) +} +#[cfg(desktop)] +mod desktop_commands { use super::*; use crate::{ - command, sealed::ManagerBase, webview::Color, AppHandle, Webview, WebviewWindowBuilder, + command, + runtime::dpi::{Position, Size}, + utils::config::Color, + Webview, }; - #[derive(Serialize)] - pub struct WebviewRef { - window_label: String, - label: String, - } - - #[command(root = "crate")] - pub async fn get_all_webviews(app: AppHandle) -> Vec { - app - .manager() - .webviews() - .values() - .map(|webview| WebviewRef { - window_label: webview.window_ref().label().into(), - label: webview.label().into(), - }) - .collect() - } - - #[command(root = "crate")] - pub async fn create_webview_window( - app: AppHandle, - options: WindowConfig, - ) -> crate::Result<()> { - WebviewWindowBuilder::from_config(&app, &options)?.build()?; - Ok(()) - } - - #[cfg(not(feature = "unstable"))] - #[command(root = "crate")] - pub async fn create_webview() -> crate::Result<()> { - Err(crate::Error::UnstableFeatureNotSupported) - } - - #[cfg(feature = "unstable")] - #[command(root = "crate")] - pub async fn create_webview( - app: AppHandle, - window_label: String, - options: WindowConfig, - ) -> crate::Result<()> { - use anyhow::Context; - - let window = app - .manager() - .get_window(&window_label) - .ok_or(crate::Error::WindowNotFound)?; - - let x = options.x.context("missing parameter `options.x`")?; - let y = options.y.context("missing parameter `options.y`")?; - let width = options.width; - let height = options.height; - - let builder = crate::webview::WebviewBuilder::from_config(&options); - - window.add_child( - builder, - tauri_runtime::dpi::LogicalPosition::new(x, y), - tauri_runtime::dpi::LogicalSize::new(width, height), - )?; - - Ok(()) - } - fn get_webview( webview: Webview, label: Option, @@ -163,6 +128,42 @@ mod desktop_commands { ); setter!(clear_all_browsing_data, clear_all_browsing_data); + #[cfg(not(feature = "unstable"))] + #[command(root = "crate")] + pub async fn create_webview() -> crate::Result<()> { + Err(crate::Error::UnstableFeatureNotSupported) + } + + #[cfg(feature = "unstable")] + #[command(root = "crate")] + pub async fn create_webview( + app: crate::AppHandle, + window_label: String, + options: WindowConfig, + ) -> crate::Result<()> { + use anyhow::Context; + + let window = app + .manager() + .get_window(&window_label) + .ok_or(crate::Error::WindowNotFound)?; + + let x = options.x.context("missing parameter `options.x`")?; + let y = options.y.context("missing parameter `options.y`")?; + let width = options.width; + let height = options.height; + + let builder = crate::webview::WebviewBuilder::from_config(&options); + + window.add_child( + builder, + tauri_runtime::dpi::LogicalPosition::new(x, y), + tauri_runtime::dpi::LogicalSize::new(width, height), + )?; + + Ok(()) + } + #[command(root = "crate")] pub async fn reparent( webview: crate::Webview, @@ -228,39 +229,29 @@ pub fn init() -> TauriPlugin { } builder - .invoke_handler( - #[cfg(desktop)] - crate::generate_handler![ - #![plugin(webview)] - desktop_commands::create_webview, - desktop_commands::create_webview_window, - // getters - desktop_commands::get_all_webviews, - desktop_commands::webview_position, - desktop_commands::webview_size, - // setters - desktop_commands::webview_close, - desktop_commands::set_webview_size, - desktop_commands::set_webview_position, - desktop_commands::set_webview_focus, - desktop_commands::set_webview_auto_resize, - desktop_commands::set_webview_background_color, - desktop_commands::set_webview_zoom, - desktop_commands::webview_hide, - desktop_commands::webview_show, - desktop_commands::print, - desktop_commands::reparent, - desktop_commands::clear_all_browsing_data, - #[cfg(any(debug_assertions, feature = "devtools"))] - desktop_commands::internal_toggle_devtools, - ], - #[cfg(mobile)] - |invoke| { - invoke - .resolver - .reject("Webview API not available on mobile"); - true - }, - ) + .invoke_handler(crate::generate_handler![ + #![plugin(webview)] + create_webview_window, + get_all_webviews, + #[cfg(desktop)] desktop_commands::create_webview, + // getters + #[cfg(desktop)] desktop_commands::webview_position, + #[cfg(desktop)] desktop_commands::webview_size, + // setters + #[cfg(desktop)] desktop_commands::webview_close, + #[cfg(desktop)] desktop_commands::set_webview_size, + #[cfg(desktop)] desktop_commands::set_webview_position, + #[cfg(desktop)] desktop_commands::set_webview_focus, + #[cfg(desktop)] desktop_commands::set_webview_auto_resize, + #[cfg(desktop)] desktop_commands::set_webview_background_color, + #[cfg(desktop)] desktop_commands::set_webview_zoom, + #[cfg(desktop)] desktop_commands::webview_hide, + #[cfg(desktop)] desktop_commands::webview_show, + #[cfg(desktop)] desktop_commands::print, + #[cfg(desktop)] desktop_commands::clear_all_browsing_data, + #[cfg(desktop)] desktop_commands::reparent, + #[cfg(all(desktop, any(debug_assertions, feature = "devtools")))] + desktop_commands::internal_toggle_devtools, + ]) .build() } diff --git a/crates/tauri/src/webview/webview_window.rs b/crates/tauri/src/webview/webview_window.rs index ca84e83b2426..86ad050b582b 100644 --- a/crates/tauri/src/webview/webview_window.rs +++ b/crates/tauri/src/webview/webview_window.rs @@ -13,7 +13,7 @@ use std::{ use crate::{ event::EventTarget, ipc::ScopeObject, - runtime::dpi::{PhysicalPosition, PhysicalSize}, + runtime::dpi::{PhysicalPosition, PhysicalSize, Position, Size}, webview::{NewWindowResponse, ScrollBarStyle}, window::Monitor, Emitter, EventName, Listener, ResourceTable, Window, @@ -22,11 +22,7 @@ use crate::{ use crate::{ image::Image, menu::{ContextMenu, Menu}, - runtime::{ - dpi::{Position, Size}, - window::CursorIcon, - UserAttentionType, - }, + runtime::{window::CursorIcon, UserAttentionType}, }; use tauri_runtime::webview::NewWindowFeatures; use tauri_utils::config::{BackgroundThrottlingPolicy, Color, WebviewUrl, WindowConfig}; @@ -465,44 +461,6 @@ impl<'a, R: Runtime, M: Manager> WebviewWindowBuilder<'a, R, M> { self } - /// The initial position of the window in logical pixels. - #[must_use] - pub fn position(mut self, x: f64, y: f64) -> Self { - self.window_builder = self.window_builder.position(x, y); - self - } - - /// Window size in logical pixels. - #[must_use] - pub fn inner_size(mut self, width: f64, height: f64) -> Self { - self.window_builder = self.window_builder.inner_size(width, height); - self - } - - /// Window min inner size in logical pixels. - #[must_use] - pub fn min_inner_size(mut self, min_width: f64, min_height: f64) -> Self { - self.window_builder = self.window_builder.min_inner_size(min_width, min_height); - self - } - - /// Window max inner size in logical pixels. - #[must_use] - pub fn max_inner_size(mut self, max_width: f64, max_height: f64) -> Self { - self.window_builder = self.window_builder.max_inner_size(max_width, max_height); - self - } - - /// Window inner size constraints. - #[must_use] - pub fn inner_size_constraints( - mut self, - constraints: tauri_runtime::window::WindowSizeConstraints, - ) -> Self { - self.window_builder = self.window_builder.inner_size_constraints(constraints); - self - } - /// Prevent the window from overflowing the working area (e.g. monitor size - taskbar size) /// on creation, which means the window size will be limited to `monitor size - taskbar size` /// @@ -531,14 +489,6 @@ impl<'a, R: Runtime, M: Manager> WebviewWindowBuilder<'a, R, M> { self } - /// Whether the window is resizable or not. - /// When resizable is set to false, native window's maximize button is automatically disabled. - #[must_use] - pub fn resizable(mut self, resizable: bool) -> Self { - self.window_builder = self.window_builder.resizable(resizable); - self - } - /// Whether the window's native maximize button is enabled or not. /// If resizable is set to false, this setting is ignored. /// @@ -576,13 +526,6 @@ impl<'a, R: Runtime, M: Manager> WebviewWindowBuilder<'a, R, M> { self } - /// The title of the window in the title bar. - #[must_use] - pub fn title>(mut self, title: S) -> Self { - self.window_builder = self.window_builder.title(title); - self - } - /// Whether to start the window in fullscreen or not. #[must_use] pub fn fullscreen(mut self, fullscreen: bool) -> Self { @@ -590,25 +533,6 @@ impl<'a, R: Runtime, M: Manager> WebviewWindowBuilder<'a, R, M> { self } - /// Sets the window to be initially focused. - #[must_use] - #[deprecated( - since = "1.2.0", - note = "The window is automatically focused by default. This function Will be removed in 3.0.0. Use `focused` instead." - )] - pub fn focus(mut self) -> Self { - self.window_builder = self.window_builder.focused(true); - self.webview_builder = self.webview_builder.focused(true); - self - } - - /// Whether the window will be focusable or not. - #[must_use] - pub fn focusable(mut self, focusable: bool) -> Self { - self.window_builder = self.window_builder.focusable(focusable); - self - } - /// Whether the window will be initially focused or not. #[must_use] pub fn focused(mut self, focused: bool) -> Self { @@ -624,24 +548,6 @@ impl<'a, R: Runtime, M: Manager> WebviewWindowBuilder<'a, R, M> { self } - /// Whether the window should be immediately visible upon creation. - #[must_use] - pub fn visible(mut self, visible: bool) -> Self { - self.window_builder = self.window_builder.visible(visible); - self - } - - /// Forces a theme or uses the system settings if None was provided. - /// - /// ## Platform-specific - /// - /// - **macOS**: Only supported on macOS 10.14+. - #[must_use] - pub fn theme(mut self, theme: Option) -> Self { - self.window_builder = self.window_builder.theme(theme); - self - } - /// Whether the window should have borders and bars. #[must_use] pub fn decorations(mut self, decorations: bool) -> Self { @@ -672,13 +578,6 @@ impl<'a, R: Runtime, M: Manager> WebviewWindowBuilder<'a, R, M> { self } - /// Prevents the window contents from being captured by other apps. - #[must_use] - pub fn content_protected(mut self, protected: bool) -> Self { - self.window_builder = self.window_builder.content_protected(protected); - self - } - /// Sets the window icon. pub fn icon(mut self, icon: Image<'a>) -> crate::Result { self.window_builder = self.window_builder.icon(icon)?; @@ -896,6 +795,106 @@ impl<'a, R: Runtime, M: Manager> WebviewWindowBuilder<'a, R, M> { } } +/// Window APIs. +impl<'a, R: Runtime, M: Manager> WebviewWindowBuilder<'a, R, M> { + /// The initial position of the window in logical pixels. + #[must_use] + pub fn position(mut self, x: f64, y: f64) -> Self { + self.window_builder = self.window_builder.position(x, y); + self + } + + /// Window size in logical pixels. + #[must_use] + pub fn inner_size(mut self, width: f64, height: f64) -> Self { + self.window_builder = self.window_builder.inner_size(width, height); + self + } + + /// Window min inner size in logical pixels. + #[must_use] + pub fn min_inner_size(mut self, min_width: f64, min_height: f64) -> Self { + self.window_builder = self.window_builder.min_inner_size(min_width, min_height); + self + } + + /// Window max inner size in logical pixels. + #[must_use] + pub fn max_inner_size(mut self, max_width: f64, max_height: f64) -> Self { + self.window_builder = self.window_builder.max_inner_size(max_width, max_height); + self + } + + /// Window inner size constraints. + #[must_use] + pub fn inner_size_constraints( + mut self, + constraints: tauri_runtime::window::WindowSizeConstraints, + ) -> Self { + self.window_builder = self.window_builder.inner_size_constraints(constraints); + self + } + + /// Whether the window is resizable or not. + /// When resizable is set to false, native window's maximize button is automatically disabled. + #[must_use] + pub fn resizable(mut self, resizable: bool) -> Self { + self.window_builder = self.window_builder.resizable(resizable); + self + } + + /// The title of the window in the title bar. + #[must_use] + pub fn title>(mut self, title: S) -> Self { + self.window_builder = self.window_builder.title(title); + self + } + + /// Sets the window to be initially focused. + #[must_use] + #[deprecated( + since = "1.2.0", + note = "The window is automatically focused by default. This function Will be removed in 3.0.0. Use `focused` instead." + )] + pub fn focus(mut self) -> Self { + self.window_builder = self.window_builder.focused(true); + self.webview_builder = self.webview_builder.focused(true); + self + } + + /// Whether the window will be focusable or not. + #[must_use] + pub fn focusable(mut self, focusable: bool) -> Self { + self.window_builder = self.window_builder.focusable(focusable); + self + } + + /// Whether the window should be immediately visible upon creation. + #[must_use] + pub fn visible(mut self, visible: bool) -> Self { + self.window_builder = self.window_builder.visible(visible); + self + } + + /// Forces a theme or uses the system settings if None was provided. + /// + /// ## Platform-specific + /// + /// - **macOS**: Only supported on macOS 10.14+. + #[must_use] + pub fn theme(mut self, theme: Option) -> Self { + self.window_builder = self.window_builder.theme(theme); + self + } + + /// Prevents the window contents from being captured by other apps. + #[must_use] + pub fn content_protected(mut self, protected: bool) -> Self { + self.window_builder = self.window_builder.content_protected(protected); + self + } +} + /// Webview attributes. impl> WebviewWindowBuilder<'_, R, M> { /// Sets whether clicking an inactive window also clicks through to the webview. @@ -1376,6 +1375,40 @@ impl> WebviewWindowBuilder<'_, R, M> { } } +// Android specific APIs +#[cfg(target_os = "android")] +impl> WebviewWindowBuilder<'_, R, M> { + /// The name of the activity to create for this webview window. + pub fn activity_name>(mut self, class_name: S) -> Self { + self.window_builder = self.window_builder.activity_name(class_name); + self + } + + /// Sets the name of the activity that is creating this webview window. + /// + /// This is important to determine which stack the activity will belong to. + pub fn created_by_activity_name>(mut self, class_name: S) -> Self { + self.window_builder = self.window_builder.created_by_activity_name(class_name); + self + } +} + +/// iOS specific APIs +#[cfg(target_os = "ios")] +impl> WebviewWindowBuilder<'_, R, M> { + /// Sets the identifier of the scene that is requesting the new scene, + /// establishing a relationship between the two scenes. + /// + /// By default the system uses the foreground scene. + #[cfg(target_os = "ios")] + pub fn requested_by_scene_identifier(mut self, identifier: String) -> Self { + self.window_builder = self + .window_builder + .requested_by_scene_identifier(identifier); + self + } +} + /// A type that wraps a [`Window`] together with a [`Webview`]. #[default_runtime(crate::Wry, wry)] #[derive(Debug)] @@ -1805,6 +1838,12 @@ impl WebviewWindow { self.window.default_vbox() } + /// Returns the name of the Android activity associated with this window. + #[cfg(target_os = "android")] + pub fn activity_name(&self) -> crate::Result { + self.window.activity_name() + } + /// Returns the current window theme. /// /// ## Platform-specific @@ -1857,17 +1896,6 @@ impl WebviewWindow { self.window.request_user_attention(request_type) } - /// Determines if this window should be resizable. - /// When resizable is set to false, native window's maximize button is automatically disabled. - pub fn set_resizable(&self, resizable: bool) -> crate::Result<()> { - self.window.set_resizable(resizable) - } - - /// Enable or disable the window. - pub fn set_enabled(&self, enabled: bool) -> crate::Result<()> { - self.webview.window().set_enabled(enabled) - } - /// Determines if this window's native maximize button should be enabled. /// If resizable is set to false, this setting is ignored. /// @@ -1899,11 +1927,6 @@ impl WebviewWindow { self.window.set_closable(closable) } - /// Set this window's title. - pub fn set_title(&self, title: &str) -> crate::Result<()> { - self.window.set_title(title) - } - /// Maximizes this window. pub fn maximize(&self) -> crate::Result<()> { self.window.maximize() @@ -1924,26 +1947,6 @@ impl WebviewWindow { self.window.unminimize() } - /// Show this window. - pub fn show(&self) -> crate::Result<()> { - self.window.show() - } - - /// Hide this window. - pub fn hide(&self) -> crate::Result<()> { - self.window.hide() - } - - /// Closes this window. It emits [`crate::RunEvent::CloseRequested`] first like a user-initiated close request so you can intercept it. - pub fn close(&self) -> crate::Result<()> { - self.window.close() - } - - /// Destroys this window. Similar to [`Self::close`] but does not emit any events and force close the window instead. - pub fn destroy(&self) -> crate::Result<()> { - self.window.destroy() - } - /// Determines if this window should be [decorated]. /// /// [decorated]: https://en.wikipedia.org/wiki/Window_(computing)#Window_decoration @@ -2019,39 +2022,6 @@ impl WebviewWindow { .set_visible_on_all_workspaces(visible_on_all_workspaces) } - /// Prevents the window contents from being captured by other apps. - pub fn set_content_protected(&self, protected: bool) -> crate::Result<()> { - self.window.set_content_protected(protected) - } - - /// Resizes this window. - pub fn set_size>(&self, size: S) -> crate::Result<()> { - self.window.set_size(size.into()) - } - - /// Sets this window's minimum inner size. - pub fn set_min_size>(&self, size: Option) -> crate::Result<()> { - self.window.set_min_size(size.map(|s| s.into())) - } - - /// Sets this window's maximum inner size. - pub fn set_max_size>(&self, size: Option) -> crate::Result<()> { - self.window.set_max_size(size.map(|s| s.into())) - } - - /// Sets this window's minimum inner width. - pub fn set_size_constraints( - &self, - constraints: tauri_runtime::window::WindowSizeConstraints, - ) -> crate::Result<()> { - self.window.set_size_constraints(constraints) - } - - /// Sets this window's position. - pub fn set_position>(&self, position: Pos) -> crate::Result<()> { - self.window.set_position(position) - } - /// Determines if this window should be fullscreen. pub fn set_fullscreen(&self, fullscreen: bool) -> crate::Result<()> { self.window.set_fullscreen(fullscreen) @@ -2071,41 +2041,11 @@ impl WebviewWindow { self.window.set_simple_fullscreen(enable) } - /// Bring the window to front and focus. - pub fn set_focus(&self) -> crate::Result<()> { - self.window.set_focus() - } - - /// Sets whether the window can be focused. - /// - /// ## Platform-specific - /// - /// - **macOS**: If the window is already focused, it is not possible to unfocus it after calling `set_focusable(false)`. - /// In this case, you might consider calling [`Window::set_focus`] but it will move the window to the back i.e. at the bottom in terms of z-order. - pub fn set_focusable(&self, focusable: bool) -> crate::Result<()> { - self.window.set_focusable(focusable) - } - /// Sets this window' icon. pub fn set_icon(&self, icon: Image<'_>) -> crate::Result<()> { self.window.set_icon(icon) } - /// Sets the window background color. - /// - /// ## Platform-specific: - /// - /// - **iOS / Android:** Unsupported. - /// - **macOS**: Not implemented for the webview layer.. - /// - **Windows**: - /// - alpha channel is ignored for the window layer. - /// - On Windows 7, transparency is not supported and the alpha value will be ignored for the webview layer.. - /// - On Windows 8 and newer: translucent colors are not supported so any alpha value other than `0` will be replaced by `255` for the webview layer. - pub fn set_background_color(&self, color: Option) -> crate::Result<()> { - self.window.set_background_color(color)?; - self.webview.set_background_color(color) - } - /// Whether to hide the window icon from the taskbar or not. /// /// ## Platform-specific @@ -2205,6 +2145,108 @@ impl WebviewWindow { pub fn set_title_bar_style(&self, style: tauri_utils::TitleBarStyle) -> crate::Result<()> { self.window.set_title_bar_style(style) } +} + +/// Desktop window setters and actions. +impl WebviewWindow { + /// Determines if this window should be resizable. + /// When resizable is set to false, native window's maximize button is automatically disabled. + pub fn set_resizable(&self, resizable: bool) -> crate::Result<()> { + self.window.set_resizable(resizable) + } + + /// Enable or disable the window. + pub fn set_enabled(&self, enabled: bool) -> crate::Result<()> { + self.webview.window().set_enabled(enabled) + } + + /// Set this window's title. + pub fn set_title(&self, title: &str) -> crate::Result<()> { + self.window.set_title(title) + } + + /// Show this window. + pub fn show(&self) -> crate::Result<()> { + self.window.show() + } + + /// Hide this window. + pub fn hide(&self) -> crate::Result<()> { + self.window.hide() + } + + /// Closes this window. It emits [`crate::RunEvent::CloseRequested`] first like a user-initiated close request so you can intercept it. + pub fn close(&self) -> crate::Result<()> { + self.window.close() + } + + /// Destroys this window. Similar to [`Self::close`] but does not emit any events and force close the window instead. + pub fn destroy(&self) -> crate::Result<()> { + self.window.destroy() + } + + /// Prevents the window contents from being captured by other apps. + pub fn set_content_protected(&self, protected: bool) -> crate::Result<()> { + self.window.set_content_protected(protected) + } + + /// Resizes this window. + pub fn set_size>(&self, size: S) -> crate::Result<()> { + self.window.set_size(size.into()) + } + + /// Sets this window's minimum inner size. + pub fn set_min_size>(&self, size: Option) -> crate::Result<()> { + self.window.set_min_size(size.map(|s| s.into())) + } + + /// Sets this window's maximum inner size. + pub fn set_max_size>(&self, size: Option) -> crate::Result<()> { + self.window.set_max_size(size.map(|s| s.into())) + } + + /// Sets this window's minimum inner width. + pub fn set_size_constraints( + &self, + constraints: tauri_runtime::window::WindowSizeConstraints, + ) -> crate::Result<()> { + self.window.set_size_constraints(constraints) + } + + /// Sets this window's position. + pub fn set_position>(&self, position: Pos) -> crate::Result<()> { + self.window.set_position(position) + } + + /// Bring the window to front and focus. + pub fn set_focus(&self) -> crate::Result<()> { + self.window.set_focus() + } + + /// Sets whether the window can be focused. + /// + /// ## Platform-specific + /// + /// - **macOS**: If the window is already focused, it is not possible to unfocus it after calling `set_focusable(false)`. + /// In this case, you might consider calling [`Window::set_focus`] but it will move the window to the back i.e. at the bottom in terms of z-order. + pub fn set_focusable(&self, focusable: bool) -> crate::Result<()> { + self.window.set_focusable(focusable) + } + + /// Sets the window background color. + /// + /// ## Platform-specific: + /// + /// - **iOS / Android:** Unsupported. + /// - **macOS**: Not implemented for the webview layer.. + /// - **Windows**: + /// - alpha channel is ignored for the window layer. + /// - On Windows 7, transparency is not supported and the alpha value will be ignored for the webview layer.. + /// - On Windows 8 and newer: translucent colors are not supported so any alpha value other than `0` will be replaced by `255` for the webview layer. + pub fn set_background_color(&self, color: Option) -> crate::Result<()> { + self.window.set_background_color(color)?; + self.webview.set_background_color(color) + } /// Sets the theme for this window. /// @@ -2217,7 +2259,7 @@ impl WebviewWindow { } } -/// Desktop webview setters and actions. +/// Desktop webview APIs. #[cfg(desktop)] impl WebviewWindow { /// Opens the dialog to prints the contents of the webview. @@ -2590,10 +2632,20 @@ impl ManagerBase for WebviewWindow { } fn runtime(&self) -> RuntimeOrDispatch<'_, R> { - self.webview.runtime() + self.window.runtime() } fn managed_app_handle(&self) -> &AppHandle { self.webview.managed_app_handle() } + + #[cfg(target_os = "android")] + fn activity_name(&self) -> Option> { + Some(self.window.activity_name()) + } + + #[cfg(target_os = "ios")] + fn scene_identifier(&self) -> Option> { + Some(self.window.scene_identifier()) + } } diff --git a/crates/tauri/src/window/mod.rs b/crates/tauri/src/window/mod.rs index 47c95628bcc4..faaaca48b006 100644 --- a/crates/tauri/src/window/mod.rs +++ b/crates/tauri/src/window/mod.rs @@ -21,6 +21,7 @@ use crate::{ ipc::{CommandArg, CommandItem, InvokeError}, manager::{AppManager, EmitPayload}, runtime::{ + dpi::{Position, Size}, monitor::Monitor as RuntimeMonitor, window::{DetachedWindow, PendingWindow, WindowBuilder as _}, RuntimeHandle, WindowDispatch, @@ -35,10 +36,7 @@ use crate::{ use crate::{ image::Image, menu::{ContextMenu, Menu, MenuId}, - runtime::{ - dpi::{Position, Size}, - UserAttentionType, - }, + runtime::UserAttentionType, CursorIcon, }; @@ -129,6 +127,10 @@ unstable_struct!( #[cfg(desktop)] on_menu_event: Option>>, window_effects: Option, + #[cfg(target_os = "android")] + created_by_activity_name_set: bool, + #[cfg(target_os = "ios")] + requested_by_scene_identifier_set: bool, } ); @@ -215,6 +217,10 @@ async fn create_window(app: tauri::AppHandle) { #[cfg(desktop)] on_menu_event: None, window_effects: None, + #[cfg(target_os = "android")] + created_by_activity_name_set: false, + #[cfg(target_os = "ios")] + requested_by_scene_identifier_set: false, } } @@ -250,6 +256,10 @@ async fn reopen_window(app: tauri::AppHandle) { pub fn from_config(manager: &'a M, config: &WindowConfig) -> crate::Result { #[cfg_attr(not(windows), allow(unused_mut))] let mut builder = Self { + #[cfg(target_os = "android")] + created_by_activity_name_set: config.created_by_activity_name.is_some(), + #[cfg(target_os = "ios")] + requested_by_scene_identifier_set: config.requested_by_scene_identifier.is_some(), manager, label: config.label.clone(), window_effects: config.window_effects.clone(), @@ -345,12 +355,31 @@ tauri::Builder::default() /// Creates a new window with an optional webview. fn build_internal( - self, + // mutable on Android + #[allow(unused_mut)] mut self, webview: Option>, ) -> crate::Result> { #[cfg(desktop)] let theme = self.window_builder.get_theme(); + #[cfg(target_os = "android")] + if !self.created_by_activity_name_set { + if let Some(manager_window_activity_name) = self.manager.activity_name() { + self.window_builder = self + .window_builder + .created_by_activity_name(manager_window_activity_name?); + } + } + + #[cfg(target_os = "ios")] + if !self.requested_by_scene_identifier_set { + if let Some(manager_window_scene_identifier) = self.manager.scene_identifier() { + self.window_builder = self + .window_builder + .requested_by_scene_identifier(manager_window_scene_identifier?); + } + } + let mut pending = PendingWindow::new(self.window_builder, self.label)?; if let Some(webview) = webview { pending.set_webview(webview); @@ -425,7 +454,7 @@ tauri::Builder::default() } } -/// Desktop APIs. +/// Desktop APIs #[cfg(desktop)] #[cfg_attr(not(feature = "unstable"), allow(dead_code))] impl<'a, R: Runtime, M: Manager> WindowBuilder<'a, R, M> { @@ -443,44 +472,6 @@ impl<'a, R: Runtime, M: Manager> WindowBuilder<'a, R, M> { self } - /// The initial position of the window in logical pixels. - #[must_use] - pub fn position(mut self, x: f64, y: f64) -> Self { - self.window_builder = self.window_builder.position(x, y); - self - } - - /// Window size in logical pixels. - #[must_use] - pub fn inner_size(mut self, width: f64, height: f64) -> Self { - self.window_builder = self.window_builder.inner_size(width, height); - self - } - - /// Window min inner size in logical pixels. - #[must_use] - pub fn min_inner_size(mut self, min_width: f64, min_height: f64) -> Self { - self.window_builder = self.window_builder.min_inner_size(min_width, min_height); - self - } - - /// Window max inner size in logical pixels. - #[must_use] - pub fn max_inner_size(mut self, max_width: f64, max_height: f64) -> Self { - self.window_builder = self.window_builder.max_inner_size(max_width, max_height); - self - } - - /// Window inner size constraints. - #[must_use] - pub fn inner_size_constraints( - mut self, - constraints: tauri_runtime::window::WindowSizeConstraints, - ) -> Self { - self.window_builder = self.window_builder.inner_size_constraints(constraints); - self - } - /// Prevent the window from overflowing the working area (e.g. monitor size - taskbar size) /// on creation, which means the window size will be limited to `monitor size - taskbar size` /// @@ -511,14 +502,6 @@ impl<'a, R: Runtime, M: Manager> WindowBuilder<'a, R, M> { self } - /// Whether the window is resizable or not. - /// When resizable is set to false, native window's maximize button is automatically disabled. - #[must_use] - pub fn resizable(mut self, resizable: bool) -> Self { - self.window_builder = self.window_builder.resizable(resizable); - self - } - /// Whether the window's native maximize button is enabled or not. /// If resizable is set to false, this setting is ignored. /// @@ -556,13 +539,6 @@ impl<'a, R: Runtime, M: Manager> WindowBuilder<'a, R, M> { self } - /// The title of the window in the title bar. - #[must_use] - pub fn title>(mut self, title: S) -> Self { - self.window_builder = self.window_builder.title(title); - self - } - /// Whether to start the window in fullscreen or not. #[must_use] pub fn fullscreen(mut self, fullscreen: bool) -> Self { @@ -570,31 +546,6 @@ impl<'a, R: Runtime, M: Manager> WindowBuilder<'a, R, M> { self } - /// Sets the window to be initially focused. - #[must_use] - #[deprecated( - since = "1.2.0", - note = "The window is automatically focused by default. This function Will be removed in 3.0.0. Use `focused` instead." - )] - pub fn focus(mut self) -> Self { - self.window_builder = self.window_builder.focused(true); - self - } - - /// Whether the window will be initially focused or not. - #[must_use] - pub fn focused(mut self, focused: bool) -> Self { - self.window_builder = self.window_builder.focused(focused); - self - } - - /// Whether the window will be focusable or not. - #[must_use] - pub fn focusable(mut self, focusable: bool) -> Self { - self.window_builder = self.window_builder.focusable(focusable); - self - } - /// Whether the window should be maximized upon creation. #[must_use] pub fn maximized(mut self, maximized: bool) -> Self { @@ -602,37 +553,6 @@ impl<'a, R: Runtime, M: Manager> WindowBuilder<'a, R, M> { self } - /// Whether the window should be immediately visible upon creation. - #[must_use] - pub fn visible(mut self, visible: bool) -> Self { - self.window_builder = self.window_builder.visible(visible); - self - } - - /// Forces a theme or uses the system settings if None was provided. - /// - /// ## Platform-specific - /// - /// - **macOS**: Only supported on macOS 10.14+. - #[must_use] - pub fn theme(mut self, theme: Option) -> Self { - self.window_builder = self.window_builder.theme(theme); - self - } - - /// Whether the window should be transparent. If this is true, writing colors - /// with alpha values different than `1.0` will produce a transparent window. - #[cfg(any(not(target_os = "macos"), feature = "macos-private-api"))] - #[cfg_attr( - docsrs, - doc(cfg(any(not(target_os = "macos"), feature = "macos-private-api"))) - )] - #[must_use] - pub fn transparent(mut self, transparent: bool) -> Self { - self.window_builder = self.window_builder.transparent(transparent); - self - } - /// Whether the window should have borders and bars. #[must_use] pub fn decorations(mut self, decorations: bool) -> Self { @@ -667,13 +587,6 @@ impl<'a, R: Runtime, M: Manager> WindowBuilder<'a, R, M> { self } - /// Prevents the window contents from being captured by other apps. - #[must_use] - pub fn content_protected(mut self, protected: bool) -> Self { - self.window_builder = self.window_builder.content_protected(protected); - self - } - /// Sets the window icon. pub fn icon(mut self, icon: Image<'a>) -> crate::Result { self.window_builder = self.window_builder.icon(icon.into())?; @@ -892,106 +805,260 @@ impl<'a, R: Runtime, M: Manager> WindowBuilder<'a, R, M> { } } -impl> WindowBuilder<'_, R, M> { - /// Set the window and webview background color. - /// - /// ## Platform-specific: - /// - /// - **Windows**: alpha channel is ignored. +/// Window APIs. +#[cfg_attr(not(feature = "unstable"), allow(dead_code))] +impl<'a, R: Runtime, M: Manager> WindowBuilder<'a, R, M> { + /// The initial position of the window in logical pixels. #[must_use] - pub fn background_color(mut self, color: Color) -> Self { - self.window_builder = self.window_builder.background_color(color); + pub fn position(mut self, x: f64, y: f64) -> Self { + self.window_builder = self.window_builder.position(x, y); self } -} -/// A wrapper struct to hold the window menu state -/// and whether it is global per-app or specific to this window. -#[cfg(desktop)] -pub(crate) struct WindowMenu { - pub(crate) is_app_wide: bool, - pub(crate) menu: Menu, -} - -// TODO: expand these docs since this is a pretty important type -/// A window managed by Tauri. -/// -/// This type also implements [`Manager`] which allows you to manage other windows attached to -/// the same application. -#[default_runtime(crate::Wry, wry)] -pub struct Window { - /// The window created by the runtime. - pub(crate) window: DetachedWindow, - /// The manager to associate this window with. - pub(crate) manager: Arc>, - pub(crate) app_handle: AppHandle, - // The menu set for this window - #[cfg(desktop)] - pub(crate) menu: Arc>>>, - pub(crate) resources_table: Arc>, -} -impl std::fmt::Debug for Window { - fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { - f.debug_struct("Window") - .field("window", &self.window) - .field("manager", &self.manager) - .field("app_handle", &self.app_handle) - .finish() + /// Window size in logical pixels. + #[must_use] + pub fn inner_size(mut self, width: f64, height: f64) -> Self { + self.window_builder = self.window_builder.inner_size(width, height); + self } -} -impl raw_window_handle::HasWindowHandle for Window { - fn window_handle( - &self, - ) -> std::result::Result, raw_window_handle::HandleError> { - self.window.dispatcher.window_handle() + /// Window min inner size in logical pixels. + #[must_use] + pub fn min_inner_size(mut self, min_width: f64, min_height: f64) -> Self { + self.window_builder = self.window_builder.min_inner_size(min_width, min_height); + self } -} -impl raw_window_handle::HasDisplayHandle for Window { - fn display_handle( - &self, - ) -> std::result::Result, raw_window_handle::HandleError> { - self.app_handle.display_handle() + /// Window max inner size in logical pixels. + #[must_use] + pub fn max_inner_size(mut self, max_width: f64, max_height: f64) -> Self { + self.window_builder = self.window_builder.max_inner_size(max_width, max_height); + self } -} -impl Clone for Window { - fn clone(&self) -> Self { - Self { - window: self.window.clone(), - manager: self.manager.clone(), - app_handle: self.app_handle.clone(), - #[cfg(desktop)] - menu: self.menu.clone(), - resources_table: self.resources_table.clone(), - } + /// Window inner size constraints. + #[must_use] + pub fn inner_size_constraints( + mut self, + constraints: tauri_runtime::window::WindowSizeConstraints, + ) -> Self { + self.window_builder = self.window_builder.inner_size_constraints(constraints); + self } -} -impl Hash for Window { - /// Only use the [`Window`]'s label to represent its hash. - fn hash(&self, state: &mut H) { - self.window.label.hash(state) + /// Whether the window is resizable or not. + /// When resizable is set to false, native window's maximize button is automatically disabled. + #[must_use] + pub fn resizable(mut self, resizable: bool) -> Self { + self.window_builder = self.window_builder.resizable(resizable); + self } -} -impl Eq for Window {} -impl PartialEq for Window { - /// Only use the [`Window`]'s label to compare equality. - fn eq(&self, other: &Self) -> bool { - self.window.label.eq(&other.window.label) + /// The title of the window in the title bar. + #[must_use] + pub fn title>(mut self, title: S) -> Self { + self.window_builder = self.window_builder.title(title); + self } -} -impl Manager for Window { - fn resources_table(&self) -> MutexGuard<'_, ResourceTable> { + /// Sets the window to be initially focused. + #[must_use] + #[deprecated( + since = "1.2.0", + note = "The window is automatically focused by default. This function Will be removed in 3.0.0. Use `focused` instead." + )] + pub fn focus(mut self) -> Self { + self.window_builder = self.window_builder.focused(true); self - .resources_table - .lock() - .expect("poisoned window resources table") } -} + + /// Whether the window will be initially focused or not. + #[must_use] + pub fn focused(mut self, focused: bool) -> Self { + self.window_builder = self.window_builder.focused(focused); + self + } + + /// Whether the window will be focusable or not. + #[must_use] + pub fn focusable(mut self, focusable: bool) -> Self { + self.window_builder = self.window_builder.focusable(focusable); + self + } + + /// Whether the window should be immediately visible upon creation. + #[must_use] + pub fn visible(mut self, visible: bool) -> Self { + self.window_builder = self.window_builder.visible(visible); + self + } + + /// Forces a theme or uses the system settings if None was provided. + /// + /// ## Platform-specific + /// + /// - **macOS**: Only supported on macOS 10.14+. + #[must_use] + pub fn theme(mut self, theme: Option) -> Self { + self.window_builder = self.window_builder.theme(theme); + self + } + + /// Whether the window should be transparent. If this is true, writing colors + /// with alpha values different than `1.0` will produce a transparent window. + #[cfg(any(not(target_os = "macos"), feature = "macos-private-api"))] + #[cfg_attr( + docsrs, + doc(cfg(any(not(target_os = "macos"), feature = "macos-private-api"))) + )] + #[must_use] + pub fn transparent(mut self, transparent: bool) -> Self { + self.window_builder = self.window_builder.transparent(transparent); + self + } + + /// Prevents the window contents from being captured by other apps. + #[must_use] + pub fn content_protected(mut self, protected: bool) -> Self { + self.window_builder = self.window_builder.content_protected(protected); + self + } + + /// Set the window and webview background color. + /// + /// ## Platform-specific: + /// + /// - **Windows**: alpha channel is ignored. + #[must_use] + pub fn background_color(mut self, color: Color) -> Self { + self.window_builder = self.window_builder.background_color(color); + self + } +} + +#[cfg(target_os = "android")] +impl> WindowBuilder<'_, R, M> { + /// The name of the activity to create for this webview window. + pub fn activity_name>(mut self, class_name: S) -> Self { + self.window_builder = self.window_builder.activity_name(class_name); + self + } + + /// Sets the name of the activity that is creating this webview window. + /// + /// This is important to determine which stack the activity will belong to. + pub fn created_by_activity_name>(mut self, class_name: S) -> Self { + self.created_by_activity_name_set = true; + self.window_builder = self.window_builder.created_by_activity_name(class_name); + self + } +} + +/// iOS specific APIs +#[cfg(target_os = "ios")] +impl> WindowBuilder<'_, R, M> { + /// Sets the identifier of the scene that is requesting the new scene, + /// establishing a relationship between the two scenes. + /// + /// By default the system uses the foreground scene. + #[cfg(target_os = "ios")] + pub fn requested_by_scene_identifier(mut self, identifier: String) -> Self { + self.requested_by_scene_identifier_set = true; + self.window_builder = self + .window_builder + .requested_by_scene_identifier(identifier); + self + } +} + +/// A wrapper struct to hold the window menu state +/// and whether it is global per-app or specific to this window. +#[cfg(desktop)] +pub(crate) struct WindowMenu { + pub(crate) is_app_wide: bool, + pub(crate) menu: Menu, +} + +// TODO: expand these docs since this is a pretty important type +/// A window managed by Tauri. +/// +/// This type also implements [`Manager`] which allows you to manage other windows attached to +/// the same application. +#[default_runtime(crate::Wry, wry)] +pub struct Window { + /// The window created by the runtime. + pub(crate) window: DetachedWindow, + /// The manager to associate this window with. + pub(crate) manager: Arc>, + pub(crate) app_handle: AppHandle, + // The menu set for this window + #[cfg(desktop)] + pub(crate) menu: Arc>>>, + pub(crate) resources_table: Arc>, +} + +impl std::fmt::Debug for Window { + fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { + f.debug_struct("Window") + .field("window", &self.window) + .field("manager", &self.manager) + .field("app_handle", &self.app_handle) + .finish() + } +} + +impl raw_window_handle::HasWindowHandle for Window { + fn window_handle( + &self, + ) -> std::result::Result, raw_window_handle::HandleError> { + self.window.dispatcher.window_handle() + } +} + +impl raw_window_handle::HasDisplayHandle for Window { + fn display_handle( + &self, + ) -> std::result::Result, raw_window_handle::HandleError> { + self.app_handle.display_handle() + } +} + +impl Clone for Window { + fn clone(&self) -> Self { + Self { + window: self.window.clone(), + manager: self.manager.clone(), + app_handle: self.app_handle.clone(), + #[cfg(desktop)] + menu: self.menu.clone(), + resources_table: self.resources_table.clone(), + } + } +} + +impl Hash for Window { + /// Only use the [`Window`]'s label to represent its hash. + fn hash(&self, state: &mut H) { + self.window.label.hash(state) + } +} + +impl Eq for Window {} +impl PartialEq for Window { + /// Only use the [`Window`]'s label to compare equality. + fn eq(&self, other: &Self) -> bool { + self.window.label.eq(&other.window.label) + } +} + +impl Manager for Window { + fn resources_table(&self) -> MutexGuard<'_, ResourceTable> { + self + .resources_table + .lock() + .expect("poisoned window resources table") + } +} impl ManagerBase for Window { fn manager(&self) -> &AppManager { @@ -1009,6 +1076,16 @@ impl ManagerBase for Window { fn managed_app_handle(&self) -> &AppHandle { &self.app_handle } + + #[cfg(target_os = "android")] + fn activity_name(&self) -> Option> { + Some(self.activity_name()) + } + + #[cfg(target_os = "ios")] + fn scene_identifier(&self) -> Option> { + Some(self.scene_identifier()) + } } impl<'de, R: Runtime> CommandArg<'de, R> for Window { @@ -1619,6 +1696,22 @@ impl Window { self.window.dispatcher.default_vbox().map_err(Into::into) } + /// Returns the name of the Android activity associated with this window. + #[cfg(target_os = "android")] + pub fn activity_name(&self) -> crate::Result { + self.window.dispatcher.activity_name().map_err(Into::into) + } + + /// Returns the identifier of the UIScene tied to this window. + #[cfg(target_os = "ios")] + pub fn scene_identifier(&self) -> crate::Result { + self + .window + .dispatcher + .scene_identifier() + .map_err(Into::into) + } + /// Returns the current window theme. /// /// ## Platform-specific @@ -1645,36 +1738,8 @@ impl Window { } } -/// Desktop window setters and actions. -#[cfg(desktop)] +/// Window setters and actions. impl Window { - /// Centers the window. - pub fn center(&self) -> crate::Result<()> { - self.window.dispatcher.center().map_err(Into::into) - } - - /// Requests user attention to the window, this has no effect if the application - /// is already focused. How requesting for user attention manifests is platform dependent, - /// see `UserAttentionType` for details. - /// - /// Providing `None` will unset the request for user attention. Unsetting the request for - /// user attention might not be done automatically by the WM when the window receives input. - /// - /// ## Platform-specific - /// - /// - **macOS:** `None` has no effect. - /// - **Linux:** Urgency levels have the same effect. - pub fn request_user_attention( - &self, - request_type: Option, - ) -> crate::Result<()> { - self - .window - .dispatcher - .request_user_attention(request_type) - .map_err(Into::into) - } - /// Determines if this window should be resizable. /// When resizable is set to false, native window's maximize button is automatically disabled. pub fn set_resizable(&self, resizable: bool) -> crate::Result<()> { @@ -1685,49 +1750,6 @@ impl Window { .map_err(Into::into) } - /// Determines if this window's native maximize button should be enabled. - /// If resizable is set to false, this setting is ignored. - /// - /// ## Platform-specific - /// - /// - **macOS:** Disables the "zoom" button in the window titlebar, which is also used to enter fullscreen mode. - /// - **Linux / iOS / Android:** Unsupported. - pub fn set_maximizable(&self, maximizable: bool) -> crate::Result<()> { - self - .window - .dispatcher - .set_maximizable(maximizable) - .map_err(Into::into) - } - - /// Determines if this window's native minimize button should be enabled. - /// - /// ## Platform-specific - /// - /// - **Linux / iOS / Android:** Unsupported. - pub fn set_minimizable(&self, minimizable: bool) -> crate::Result<()> { - self - .window - .dispatcher - .set_minimizable(minimizable) - .map_err(Into::into) - } - - /// Determines if this window's native close button should be enabled. - /// - /// ## Platform-specific - /// - /// - **Linux:** "GTK+ will do its best to convince the window manager not to show a close button. - /// Depending on the system, this function may not have any effect when called on a window that is already visible" - /// - **iOS / Android:** Unsupported. - pub fn set_closable(&self, closable: bool) -> crate::Result<()> { - self - .window - .dispatcher - .set_closable(closable) - .map_err(Into::into) - } - /// Set this window's title. pub fn set_title(&self, title: &str) -> crate::Result<()> { self @@ -1746,26 +1768,6 @@ impl Window { .map_err(Into::into) } - /// Maximizes this window. - pub fn maximize(&self) -> crate::Result<()> { - self.window.dispatcher.maximize().map_err(Into::into) - } - - /// Un-maximizes this window. - pub fn unmaximize(&self) -> crate::Result<()> { - self.window.dispatcher.unmaximize().map_err(Into::into) - } - - /// Minimizes this window. - pub fn minimize(&self) -> crate::Result<()> { - self.window.dispatcher.minimize().map_err(Into::into) - } - - /// Un-minimizes this window. - pub fn unminimize(&self) -> crate::Result<()> { - self.window.dispatcher.unminimize().map_err(Into::into) - } - /// Show this window. pub fn show(&self) -> crate::Result<()> { self.window.dispatcher.show().map_err(Into::into) @@ -1786,6 +1788,219 @@ impl Window { self.window.dispatcher.destroy().map_err(Into::into) } + /// Sets the window background color. + /// + /// ## Platform-specific: + /// + /// - **Windows:** alpha channel is ignored. + /// - **iOS / Android:** Unsupported. + pub fn set_background_color(&self, color: Option) -> crate::Result<()> { + self + .window + .dispatcher + .set_background_color(color) + .map_err(Into::into) + } + + /// Prevents the window contents from being captured by other apps. + pub fn set_content_protected(&self, protected: bool) -> crate::Result<()> { + self + .window + .dispatcher + .set_content_protected(protected) + .map_err(Into::into) + } + + /// Resizes this window. + pub fn set_size>(&self, size: S) -> crate::Result<()> { + self + .window + .dispatcher + .set_size(size.into()) + .map_err(Into::into) + } + + /// Sets this window's minimum inner size. + pub fn set_min_size>(&self, size: Option) -> crate::Result<()> { + self + .window + .dispatcher + .set_min_size(size.map(|s| s.into())) + .map_err(Into::into) + } + + /// Sets this window's maximum inner size. + pub fn set_max_size>(&self, size: Option) -> crate::Result<()> { + self + .window + .dispatcher + .set_max_size(size.map(|s| s.into())) + .map_err(Into::into) + } + + /// Sets this window's minimum inner width. + pub fn set_size_constraints( + &self, + constraints: tauri_runtime::window::WindowSizeConstraints, + ) -> crate::Result<()> { + self + .window + .dispatcher + .set_size_constraints(constraints) + .map_err(Into::into) + } + + /// Sets this window's position. + pub fn set_position>(&self, position: Pos) -> crate::Result<()> { + self + .window + .dispatcher + .set_position(position.into()) + .map_err(Into::into) + } + + /// Bring the window to front and focus. + pub fn set_focus(&self) -> crate::Result<()> { + self.window.dispatcher.set_focus().map_err(Into::into) + } + + /// Sets whether the window can be focused. + /// + /// ## Platform-specific + /// + /// - **macOS**: If the window is already focused, it is not possible to unfocus it after calling `set_focusable(false)`. + /// In this case, you might consider calling [`Window::set_focus`] but it will move the window to the back i.e. at the bottom in terms of z-order. + pub fn set_focusable(&self, focusable: bool) -> crate::Result<()> { + self + .window + .dispatcher + .set_focusable(focusable) + .map_err(Into::into) + } + + /// Sets the theme for this window. + /// + /// ## Platform-specific + /// + /// - **Linux / macOS**: Theme is app-wide and not specific to this window. + /// - **iOS / Android:** Unsupported. + pub fn set_theme(&self, theme: Option) -> crate::Result<()> { + self + .window + .dispatcher + .set_theme(theme) + .map_err(Into::::into)?; + #[cfg(windows)] + if let (Some(menu), Ok(hwnd)) = (self.menu(), self.hwnd()) { + let raw_hwnd = hwnd.0 as isize; + self.run_on_main_thread(move || { + let _ = unsafe { + menu.inner().set_theme_for_hwnd( + raw_hwnd, + theme + .map(crate::menu::map_to_menu_theme) + .unwrap_or(muda::MenuTheme::Auto), + ) + }; + })?; + }; + Ok(()) + } +} + +/// Desktop window setters and actions. +#[cfg(desktop)] +impl Window { + /// Centers the window. + pub fn center(&self) -> crate::Result<()> { + self.window.dispatcher.center().map_err(Into::into) + } + + /// Requests user attention to the window, this has no effect if the application + /// is already focused. How requesting for user attention manifests is platform dependent, + /// see `UserAttentionType` for details. + /// + /// Providing `None` will unset the request for user attention. Unsetting the request for + /// user attention might not be done automatically by the WM when the window receives input. + /// + /// ## Platform-specific + /// + /// - **macOS:** `None` has no effect. + /// - **Linux:** Urgency levels have the same effect. + pub fn request_user_attention( + &self, + request_type: Option, + ) -> crate::Result<()> { + self + .window + .dispatcher + .request_user_attention(request_type) + .map_err(Into::into) + } + + /// Determines if this window's native maximize button should be enabled. + /// If resizable is set to false, this setting is ignored. + /// + /// ## Platform-specific + /// + /// - **macOS:** Disables the "zoom" button in the window titlebar, which is also used to enter fullscreen mode. + /// - **Linux / iOS / Android:** Unsupported. + pub fn set_maximizable(&self, maximizable: bool) -> crate::Result<()> { + self + .window + .dispatcher + .set_maximizable(maximizable) + .map_err(Into::into) + } + + /// Determines if this window's native minimize button should be enabled. + /// + /// ## Platform-specific + /// + /// - **Linux / iOS / Android:** Unsupported. + pub fn set_minimizable(&self, minimizable: bool) -> crate::Result<()> { + self + .window + .dispatcher + .set_minimizable(minimizable) + .map_err(Into::into) + } + + /// Determines if this window's native close button should be enabled. + /// + /// ## Platform-specific + /// + /// - **Linux:** "GTK+ will do its best to convince the window manager not to show a close button. + /// Depending on the system, this function may not have any effect when called on a window that is already visible" + /// - **iOS / Android:** Unsupported. + pub fn set_closable(&self, closable: bool) -> crate::Result<()> { + self + .window + .dispatcher + .set_closable(closable) + .map_err(Into::into) + } + + /// Maximizes this window. + pub fn maximize(&self) -> crate::Result<()> { + self.window.dispatcher.maximize().map_err(Into::into) + } + + /// Un-maximizes this window. + pub fn unmaximize(&self) -> crate::Result<()> { + self.window.dispatcher.unmaximize().map_err(Into::into) + } + + /// Minimizes this window. + pub fn minimize(&self) -> crate::Result<()> { + self.window.dispatcher.minimize().map_err(Into::into) + } + + /// Un-minimizes this window. + pub fn unminimize(&self) -> crate::Result<()> { + self.window.dispatcher.unminimize().map_err(Into::into) + } + /// Determines if this window should be [decorated]. /// /// [decorated]: https://en.wikipedia.org/wiki/Window_(computing)#Window_decoration @@ -1888,77 +2103,6 @@ tauri::Builder::default() .map_err(Into::into) } - /// Sets the window background color. - /// - /// ## Platform-specific: - /// - /// - **Windows:** alpha channel is ignored. - /// - **iOS / Android:** Unsupported. - pub fn set_background_color(&self, color: Option) -> crate::Result<()> { - self - .window - .dispatcher - .set_background_color(color) - .map_err(Into::into) - } - - /// Prevents the window contents from being captured by other apps. - pub fn set_content_protected(&self, protected: bool) -> crate::Result<()> { - self - .window - .dispatcher - .set_content_protected(protected) - .map_err(Into::into) - } - - /// Resizes this window. - pub fn set_size>(&self, size: S) -> crate::Result<()> { - self - .window - .dispatcher - .set_size(size.into()) - .map_err(Into::into) - } - - /// Sets this window's minimum inner size. - pub fn set_min_size>(&self, size: Option) -> crate::Result<()> { - self - .window - .dispatcher - .set_min_size(size.map(|s| s.into())) - .map_err(Into::into) - } - - /// Sets this window's maximum inner size. - pub fn set_max_size>(&self, size: Option) -> crate::Result<()> { - self - .window - .dispatcher - .set_max_size(size.map(|s| s.into())) - .map_err(Into::into) - } - - /// Sets this window's minimum inner width. - pub fn set_size_constraints( - &self, - constraints: tauri_runtime::window::WindowSizeConstraints, - ) -> crate::Result<()> { - self - .window - .dispatcher - .set_size_constraints(constraints) - .map_err(Into::into) - } - - /// Sets this window's position. - pub fn set_position>(&self, position: Pos) -> crate::Result<()> { - self - .window - .dispatcher - .set_position(position.into()) - .map_err(Into::into) - } - /// Determines if this window should be fullscreen. pub fn set_fullscreen(&self, fullscreen: bool) -> crate::Result<()> { self @@ -1991,25 +2135,6 @@ tauri::Builder::default() self.set_fullscreen(enable) } - /// Bring the window to front and focus. - pub fn set_focus(&self) -> crate::Result<()> { - self.window.dispatcher.set_focus().map_err(Into::into) - } - - /// Sets whether the window can be focused. - /// - /// ## Platform-specific - /// - /// - **macOS**: If the window is already focused, it is not possible to unfocus it after calling `set_focusable(false)`. - /// In this case, you might consider calling [`Window::set_focus`] but it will move the window to the back i.e. at the bottom in terms of z-order. - pub fn set_focusable(&self, focusable: bool) -> crate::Result<()> { - self - .window - .dispatcher - .set_focusable(focusable) - .map_err(Into::into) - } - /// Sets this window' icon. pub fn set_icon(&self, icon: Image<'_>) -> crate::Result<()> { self @@ -2175,35 +2300,6 @@ tauri::Builder::default() .set_title_bar_style(style) .map_err(Into::into) } - - /// Sets the theme for this window. - /// - /// ## Platform-specific - /// - /// - **Linux / macOS**: Theme is app-wide and not specific to this window. - /// - **iOS / Android:** Unsupported. - pub fn set_theme(&self, theme: Option) -> crate::Result<()> { - self - .window - .dispatcher - .set_theme(theme) - .map_err(Into::::into)?; - #[cfg(windows)] - if let (Some(menu), Ok(hwnd)) = (self.menu(), self.hwnd()) { - let raw_hwnd = hwnd.0 as isize; - self.run_on_main_thread(move || { - let _ = unsafe { - menu.inner().set_theme_for_hwnd( - raw_hwnd, - theme - .map(crate::menu::map_to_menu_theme) - .unwrap_or(muda::MenuTheme::Auto), - ) - }; - })?; - }; - Ok(()) - } } /// Progress bar state. diff --git a/crates/tauri/src/window/plugin.rs b/crates/tauri/src/window/plugin.rs index e1fecd9b732d..4fba9e72e9cd 100644 --- a/crates/tauri/src/window/plugin.rs +++ b/crates/tauri/src/window/plugin.rs @@ -6,23 +6,56 @@ use crate::{ plugin::{Builder, TauriPlugin}, - Runtime, + sealed::ManagerBase, + Runtime, Window, }; -#[cfg(desktop)] -mod desktop_commands { - use tauri_runtime::{window::WindowSizeConstraints, ResizeDirection}; - use tauri_utils::TitleBarStyle; +fn get_window(window: Window, label: Option) -> crate::Result> { + match label { + Some(l) if !l.is_empty() => window + .manager() + .get_window(&l) + .ok_or(crate::Error::WindowNotFound), + _ => Ok(window), + } +} +macro_rules! getter { + ($cmd: ident, $ret: ty) => { + #[command(root = "crate")] + pub async fn $cmd(window: Window, label: Option) -> crate::Result<$ret> { + get_window(window, label)?.$cmd().map_err(Into::into) + } + }; +} + +macro_rules! setter { + ($cmd: ident) => { + #[command(root = "crate")] + pub async fn $cmd(window: Window, label: Option) -> crate::Result<()> { + get_window(window, label)?.$cmd().map_err(Into::into) + } + }; + + ($cmd: ident, $input: ty) => { + #[command(root = "crate")] + pub async fn $cmd( + window: Window, + label: Option, + value: $input, + ) -> crate::Result<()> { + get_window(window, label)?.$cmd(value).map_err(Into::into) + } + }; +} + +mod commands { + use tauri_runtime::window::WindowSizeConstraints; use super::*; use crate::{ - command, - sealed::ManagerBase, - utils::config::{WindowConfig, WindowEffectsConfig}, - window::Color, - window::{ProgressBarState, WindowBuilder}, - AppHandle, CursorIcon, Manager, Monitor, PhysicalPosition, PhysicalSize, Position, Size, Theme, - UserAttentionType, Webview, Window, + command, sealed::ManagerBase, utils::config::WindowConfig, window::Color, + window::WindowBuilder, AppHandle, PhysicalPosition, PhysicalSize, Position, Size, Theme, + Window, }; #[command(root = "crate")] @@ -31,110 +64,89 @@ mod desktop_commands { } #[command(root = "crate")] - pub async fn create(app: AppHandle, options: WindowConfig) -> crate::Result<()> { - WindowBuilder::from_config(&app, &options)?.build()?; + pub async fn create(window: Window, options: WindowConfig) -> crate::Result<()> { + WindowBuilder::from_config(&window, &options)?.build()?; Ok(()) } - fn get_window(window: Window, label: Option) -> crate::Result> { - match label { - Some(l) if !l.is_empty() => window - .manager() - .get_window(&l) - .ok_or(crate::Error::WindowNotFound), - _ => Ok(window), - } - } - - macro_rules! getter { - ($cmd: ident, $ret: ty) => { - #[command(root = "crate")] - pub async fn $cmd( - window: Window, - label: Option, - ) -> crate::Result<$ret> { - get_window(window, label)?.$cmd().map_err(Into::into) - } - }; - } - - macro_rules! setter { - ($cmd: ident) => { - #[command(root = "crate")] - pub async fn $cmd(window: Window, label: Option) -> crate::Result<()> { - get_window(window, label)?.$cmd().map_err(Into::into) - } - }; - - ($cmd: ident, $input: ty) => { - #[command(root = "crate")] - pub async fn $cmd( - window: Window, - label: Option, - value: $input, - ) -> crate::Result<()> { - get_window(window, label)?.$cmd(value).map_err(Into::into) - } - }; - } - getter!(scale_factor, f64); getter!(inner_position, PhysicalPosition); getter!(outer_position, PhysicalPosition); getter!(inner_size, PhysicalSize); getter!(outer_size, PhysicalSize); + getter!(is_focused, bool); + getter!(is_resizable, bool); + getter!(is_visible, bool); + getter!(is_enabled, bool); + getter!(title, String); + getter!(theme, Theme); + #[cfg(target_os = "android")] + getter!(activity_name, String); + #[cfg(target_os = "ios")] + getter!(scene_identifier, String); + + setter!(set_resizable, bool); + setter!(set_title, &str); + setter!(show); + setter!(hide); + setter!(close); + setter!(destroy); + setter!(set_content_protected, bool); + setter!(set_size, Size); + setter!(set_min_size, Option); + setter!(set_max_size, Option); + setter!(set_position, Position); + setter!(set_focus); + setter!(set_focusable, bool); + setter!(set_background_color, Option); + setter!(set_size_constraints, WindowSizeConstraints); + setter!(set_theme, Option); + setter!(set_enabled, bool); +} + +#[cfg(desktop)] +mod desktop_commands { + use tauri_runtime::ResizeDirection; + use tauri_utils::TitleBarStyle; + + use super::*; + use crate::{ + command, utils::config::WindowEffectsConfig, window::ProgressBarState, CursorIcon, Manager, + Monitor, PhysicalPosition, Position, UserAttentionType, Webview, + }; + getter!(is_fullscreen, bool); getter!(is_minimized, bool); getter!(is_maximized, bool); - getter!(is_focused, bool); getter!(is_decorated, bool); - getter!(is_resizable, bool); getter!(is_maximizable, bool); getter!(is_minimizable, bool); getter!(is_closable, bool); - getter!(is_visible, bool); - getter!(is_enabled, bool); - getter!(title, String); getter!(current_monitor, Option); getter!(primary_monitor, Option); getter!(available_monitors, Vec); getter!(cursor_position, PhysicalPosition); - getter!(theme, Theme); getter!(is_always_on_top, bool); setter!(center); setter!(request_user_attention, Option); - setter!(set_resizable, bool); setter!(set_maximizable, bool); setter!(set_minimizable, bool); setter!(set_closable, bool); - setter!(set_title, &str); setter!(maximize); setter!(unmaximize); setter!(minimize); setter!(unminimize); - setter!(show); - setter!(hide); - setter!(close); - setter!(destroy); setter!(set_decorations, bool); setter!(set_shadow, bool); setter!(set_effects, Option); setter!(set_always_on_top, bool); setter!(set_always_on_bottom, bool); - setter!(set_content_protected, bool); - setter!(set_size, Size); - setter!(set_min_size, Option); - setter!(set_max_size, Option); - setter!(set_position, Position); setter!(set_fullscreen, bool); setter!(set_simple_fullscreen, bool); - setter!(set_focus); - setter!(set_focusable, bool); setter!(set_skip_taskbar, bool); setter!(set_cursor_grab, bool); setter!(set_cursor_visible, bool); - setter!(set_background_color, Option); setter!(set_cursor_icon, CursorIcon); setter!(set_cursor_position, Position); setter!(set_ignore_cursor_events, bool); @@ -146,9 +158,6 @@ mod desktop_commands { setter!(set_badge_label, Option); setter!(set_visible_on_all_workspaces, bool); setter!(set_title_bar_style, TitleBarStyle); - setter!(set_size_constraints, WindowSizeConstraints); - setter!(set_theme, Option); - setter!(set_enabled, bool); #[command(root = "crate")] #[cfg(target_os = "windows")] @@ -244,96 +253,94 @@ pub fn init() -> TauriPlugin { Builder::new("window") .js_init_script(init_script) - .invoke_handler( - #[cfg(desktop)] - crate::generate_handler![ - #![plugin(window)] - desktop_commands::create, - // getters - desktop_commands::get_all_windows, - desktop_commands::scale_factor, - desktop_commands::inner_position, - desktop_commands::outer_position, - desktop_commands::inner_size, - desktop_commands::outer_size, - desktop_commands::is_fullscreen, - desktop_commands::is_minimized, - desktop_commands::is_maximized, - desktop_commands::is_focused, - desktop_commands::is_decorated, - desktop_commands::is_resizable, - desktop_commands::is_maximizable, - desktop_commands::is_minimizable, - desktop_commands::is_closable, - desktop_commands::is_visible, - desktop_commands::is_enabled, - desktop_commands::title, - desktop_commands::current_monitor, - desktop_commands::primary_monitor, - desktop_commands::monitor_from_point, - desktop_commands::available_monitors, - desktop_commands::cursor_position, - desktop_commands::theme, - desktop_commands::is_always_on_top, - // setters - desktop_commands::center, - desktop_commands::request_user_attention, - desktop_commands::set_resizable, - desktop_commands::set_maximizable, - desktop_commands::set_minimizable, - desktop_commands::set_closable, - desktop_commands::set_title, - desktop_commands::maximize, - desktop_commands::unmaximize, - desktop_commands::minimize, - desktop_commands::unminimize, - desktop_commands::show, - desktop_commands::hide, - desktop_commands::close, - desktop_commands::destroy, - desktop_commands::set_decorations, - desktop_commands::set_shadow, - desktop_commands::set_effects, - desktop_commands::set_always_on_top, - desktop_commands::set_always_on_bottom, - desktop_commands::set_content_protected, - desktop_commands::set_size, - desktop_commands::set_min_size, - desktop_commands::set_max_size, - desktop_commands::set_size_constraints, - desktop_commands::set_position, - desktop_commands::set_fullscreen, - desktop_commands::set_simple_fullscreen, - desktop_commands::set_focus, - desktop_commands::set_focusable, - desktop_commands::set_enabled, - desktop_commands::set_skip_taskbar, - desktop_commands::set_cursor_grab, - desktop_commands::set_cursor_visible, - desktop_commands::set_cursor_icon, - desktop_commands::set_cursor_position, - desktop_commands::set_ignore_cursor_events, - desktop_commands::start_dragging, - desktop_commands::start_resize_dragging, - desktop_commands::set_badge_count, - #[cfg(target_os = "macos")] - desktop_commands::set_badge_label, - desktop_commands::set_progress_bar, - #[cfg(target_os = "windows")] - desktop_commands::set_overlay_icon, - desktop_commands::set_icon, - desktop_commands::set_visible_on_all_workspaces, - desktop_commands::set_background_color, - desktop_commands::set_title_bar_style, - desktop_commands::set_theme, - desktop_commands::toggle_maximize, - desktop_commands::internal_toggle_maximize, - ], - #[cfg(mobile)] - |invoke| { - invoke.resolver.reject("Window API not available on mobile"); - true - }, - ) + .invoke_handler(crate::generate_handler![ + #![plugin(window)] + commands::create, + // getters + commands::get_all_windows, + commands::scale_factor, + commands::inner_position, + commands::outer_position, + commands::inner_size, + commands::outer_size, + commands::is_focused, + commands::is_resizable, + commands::is_visible, + commands::is_enabled, + commands::title, + commands::theme, + #[cfg(target_os = "android")] + commands::activity_name, + #[cfg(target_os = "ios")] + commands::scene_identifier, + + commands::set_resizable, + commands::set_title, + commands::show, + commands::hide, + commands::close, + commands::destroy, + commands::set_content_protected, + commands::set_size, + commands::set_min_size, + commands::set_max_size, + commands::set_position, + commands::set_size_constraints, + commands::set_focus, + commands::set_focusable, + commands::set_enabled, + commands::set_background_color, + commands::set_theme, + + #[cfg(desktop)] desktop_commands::is_fullscreen, + #[cfg(desktop)] desktop_commands::is_minimized, + #[cfg(desktop)] desktop_commands::is_maximized, + #[cfg(desktop)] desktop_commands::is_decorated, + #[cfg(desktop)] desktop_commands::is_maximizable, + #[cfg(desktop)] desktop_commands::is_minimizable, + #[cfg(desktop)] desktop_commands::is_closable, + #[cfg(desktop)] desktop_commands::current_monitor, + #[cfg(desktop)] desktop_commands::primary_monitor, + #[cfg(desktop)] desktop_commands::monitor_from_point, + #[cfg(desktop)] desktop_commands::available_monitors, + #[cfg(desktop)] desktop_commands::cursor_position, + #[cfg(desktop)] desktop_commands::is_always_on_top, + // setters + #[cfg(desktop)] desktop_commands::center, + #[cfg(desktop)] desktop_commands::request_user_attention, + #[cfg(desktop)] desktop_commands::set_maximizable, + #[cfg(desktop)] desktop_commands::set_minimizable, + #[cfg(desktop)] desktop_commands::set_closable, + #[cfg(desktop)] desktop_commands::maximize, + #[cfg(desktop)] desktop_commands::unmaximize, + #[cfg(desktop)] desktop_commands::minimize, + #[cfg(desktop)] desktop_commands::unminimize, + #[cfg(desktop)] desktop_commands::set_decorations, + #[cfg(desktop)] desktop_commands::set_shadow, + #[cfg(desktop)] desktop_commands::set_effects, + #[cfg(desktop)] desktop_commands::set_always_on_top, + #[cfg(desktop)] desktop_commands::set_always_on_bottom, + #[cfg(desktop)] desktop_commands::set_fullscreen, + #[cfg(desktop)] desktop_commands::set_simple_fullscreen, + #[cfg(desktop)] desktop_commands::set_skip_taskbar, + #[cfg(desktop)] desktop_commands::set_cursor_grab, + #[cfg(desktop)] desktop_commands::set_cursor_visible, + #[cfg(desktop)] desktop_commands::set_cursor_icon, + #[cfg(desktop)] desktop_commands::set_cursor_position, + #[cfg(desktop)] desktop_commands::set_ignore_cursor_events, + #[cfg(desktop)] desktop_commands::start_dragging, + #[cfg(desktop)] desktop_commands::start_resize_dragging, + #[cfg(desktop)] desktop_commands::set_badge_count, + #[cfg(target_os = "macos")] + #[cfg(desktop)] desktop_commands::set_badge_label, + #[cfg(desktop)] desktop_commands::set_progress_bar, + #[cfg(target_os = "windows")] + #[cfg(desktop)] desktop_commands::set_overlay_icon, + #[cfg(desktop)] desktop_commands::set_icon, + #[cfg(desktop)] desktop_commands::set_visible_on_all_workspaces, + #[cfg(desktop)] desktop_commands::set_title_bar_style, + #[cfg(desktop)] desktop_commands::toggle_maximize, + #[cfg(desktop)] desktop_commands::internal_toggle_maximize, + ]) .build() } diff --git a/examples/api/src-tauri/src/lib.rs b/examples/api/src-tauri/src/lib.rs index 73a573672fab..47cc753f4c8b 100644 --- a/examples/api/src-tauri/src/lib.rs +++ b/examples/api/src-tauri/src/lib.rs @@ -86,7 +86,7 @@ pub fn run_app) + Send + 'static>( let number = created_window_count.fetch_add(1, std::sync::atomic::Ordering::Relaxed); - let builder = tauri::WebviewWindowBuilder::new( + let builder = WebviewWindowBuilder::new( &app_, format!("new-{number}"), tauri::WebviewUrl::External("about:blank".parse().unwrap()), @@ -181,9 +181,12 @@ pub fn run_app) + Send + 'static>( #[cfg(target_os = "macos")] app.set_activation_policy(tauri::ActivationPolicy::Regular); + #[cfg(target_os = "ios")] + let mut counter = 0; app.run(move |_app_handle, _event| { - #[cfg(all(desktop, not(test)))] + #[cfg(not(test))] match &_event { + #[cfg(desktop)] RunEvent::ExitRequested { api, code, .. } => { // Keep the event loop running even if all windows are closed // This allow us to catch tray icon events when there is no window @@ -192,6 +195,7 @@ pub fn run_app) + Send + 'static>( api.prevent_exit(); } } + #[cfg(desktop)] RunEvent::WindowEvent { event: tauri::WindowEvent::CloseRequested { api, .. }, label, @@ -207,6 +211,17 @@ pub fn run_app) + Send + 'static>( .destroy() .unwrap(); } + #[cfg(target_os = "ios")] + RunEvent::SceneRequested { .. } => { + counter += 1; + WebviewWindowBuilder::new( + _app_handle, + format!("main-from-scene-{counter}"), + WebviewUrl::default(), + ) + .build() + .unwrap(); + } _ => (), } }) diff --git a/packages/api/src/app.ts b/packages/api/src/app.ts index 55b28043631f..82cc51859224 100644 --- a/packages/api/src/app.ts +++ b/packages/api/src/app.ts @@ -274,6 +274,10 @@ async function onBackButtonPress( ) } +async function supportsMultipleWindows(): Promise { + return invoke('plugin:app|supports_multiple_windows') +} + export { getName, getVersion, @@ -288,5 +292,6 @@ export { setDockVisibility, getBundleType, type OnBackButtonPressPayload, - onBackButtonPress + onBackButtonPress, + supportsMultipleWindows } diff --git a/packages/api/src/window.ts b/packages/api/src/window.ts index 8a11d2cc3cb6..a6b157ad84d3 100644 --- a/packages/api/src/window.ts +++ b/packages/api/src/window.ts @@ -820,6 +820,18 @@ class Window { }) } + async activityName(): Promise { + return invoke('plugin:window|activity_name', { + label: this.label + }) + } + + async sceneIdentifier(): Promise { + return invoke('plugin:window|scene_identifier', { + label: this.label + }) + } + // Setters /** @@ -2511,6 +2523,23 @@ interface WindowOptions { * - **Linux / Android / iOS / macOS**: Unsupported. Only supports `Default` and performs no operation. */ scrollBarStyle?: ScrollBarStyle + /** + * The name of the Android activity to create for this window. + */ + activityName?: string + /** + * The name of the Android activity that is creating this webview window. + * + * This is important to determine which stack the activity will belong to. + */ + createdByActivityName?: string + /** + * Sets the identifier of the UIScene that is requesting the creation of this new scene, + * establishing a relationship between the two scenes. + * + * By default the system uses the foreground scene. + */ + requestedBySceneIdentifier?: string } function mapMonitor(m: Monitor | null): Monitor | null { From 840b4c01ca04ed3fb38349772007c2025d949314 Mon Sep 17 00:00:00 2001 From: Joshua Megnauth <48846352+joshuamegnauth54@users.noreply.github.com> Date: Tue, 24 Mar 2026 04:35:05 -0400 Subject: [PATCH 52/95] feat: Allow getting inner PathBuf from SafePathBuf (#14908) * Allow getting inner PathBuf from SafePathBuf SafePathBuf implements AsRef which is ergonomic and useful. However, some APIs take owned PathBufs. This leads to clunky code where the caller has to get a &Path from the SafePathBuf then take ownership of that path. Ideally, if a user has a SafePathBuf and needs a PathBuf, they won't need to allocate again just to get the inner PathBuf back. * Apply suggestion from @Legend-Master --- .changes/safepathbuf_into_pathbuf.md | 5 +++++ crates/tauri/src/path/mod.rs | 6 ++++++ 2 files changed, 11 insertions(+) create mode 100644 .changes/safepathbuf_into_pathbuf.md diff --git a/.changes/safepathbuf_into_pathbuf.md b/.changes/safepathbuf_into_pathbuf.md new file mode 100644 index 000000000000..1a72fa205040 --- /dev/null +++ b/.changes/safepathbuf_into_pathbuf.md @@ -0,0 +1,5 @@ +--- +"tauri": patch:enhance +--- + +Implement retrieving inner PathBuf from SafePathBuf to ease using APIs that require an owned PathBuf diff --git a/crates/tauri/src/path/mod.rs b/crates/tauri/src/path/mod.rs index f504435c5692..c00af5d8da28 100644 --- a/crates/tauri/src/path/mod.rs +++ b/crates/tauri/src/path/mod.rs @@ -73,6 +73,12 @@ impl FromStr for SafePathBuf { } } +impl From for PathBuf { + fn from(path: SafePathBuf) -> Self { + path.0 + } +} + impl<'de> Deserialize<'de> for SafePathBuf { fn deserialize(deserializer: D) -> std::result::Result where From 2f0e0f6b77d74de91baeffaddcc61e3ac359cfa5 Mon Sep 17 00:00:00 2001 From: Tony <68118705+Legend-Master@users.noreply.github.com> Date: Tue, 24 Mar 2026 23:39:50 +0800 Subject: [PATCH 53/95] refactor(runtime-wry): remove RefCell hack (#14862) * refactor(runtime-wry): remove RefCell hack * Remove `Sync` requirement on `on_new_window` * Merge branch 'dev' into remove-ref-cell-hack * Add change file --- .changes/new-window-main-thread.md | 6 ++ crates/tauri-runtime-wry/src/lib.rs | 113 ++++++++++----------- crates/tauri-runtime/src/webview.rs | 2 +- crates/tauri/src/webview/mod.rs | 9 +- crates/tauri/src/webview/webview_window.rs | 5 +- 5 files changed, 61 insertions(+), 74 deletions(-) create mode 100644 .changes/new-window-main-thread.md diff --git a/.changes/new-window-main-thread.md b/.changes/new-window-main-thread.md new file mode 100644 index 000000000000..e4911da87246 --- /dev/null +++ b/.changes/new-window-main-thread.md @@ -0,0 +1,6 @@ +--- +"tauri": minor:changes +"tauri-runtime-wry": minor:changes +--- + +The new window handler passed to `on_new_window` no longer requires `Sync`, and runs on main thread on Windows, aligning with other platforms diff --git a/crates/tauri-runtime-wry/src/lib.rs b/crates/tauri-runtime-wry/src/lib.rs index e5b487800ec8..f196a08de544 100644 --- a/crates/tauri-runtime-wry/src/lib.rs +++ b/crates/tauri-runtime-wry/src/lib.rs @@ -4000,13 +4000,9 @@ fn handle_user_message( } } Message::CreateWindow(window_id, handler) => match handler(event_loop) { - // wait for borrow_mut to be available - on Windows we might poll for the window to be inserted - Ok(webview) => loop { - if let Ok(mut windows) = windows.0.try_borrow_mut() { - windows.insert(window_id, webview); - break; - } - }, + Ok(webview) => { + windows.0.borrow_mut().insert(window_id, webview); + } Err(e) => { log::error!("{e}"); } @@ -4789,63 +4785,56 @@ You may have it installed on another user account, but it is not available for t #[cfg(desktop)] let context = context.clone(); webview_builder = webview_builder.with_new_window_req_handler(move |url, features| { - url - .parse() - .map(|url| { - let response = new_window_handler( - url, - tauri_runtime::webview::NewWindowFeatures::new( - features.size, - features.position, - tauri_runtime::webview::NewWindowOpener { - #[cfg(desktop)] - webview: features.opener.webview, - #[cfg(windows)] - environment: features.opener.environment, - #[cfg(target_os = "macos")] - target_configuration: features.opener.target_configuration, - }, - ), - ); - match response { - tauri_runtime::webview::NewWindowResponse::Allow => wry::NewWindowResponse::Allow, + let Ok(url) = url.parse() else { + return wry::NewWindowResponse::Deny; + }; + let response = new_window_handler( + url, + tauri_runtime::webview::NewWindowFeatures::new( + features.size, + features.position, + tauri_runtime::webview::NewWindowOpener { #[cfg(desktop)] - tauri_runtime::webview::NewWindowResponse::Create { window_id } => { - let windows = &context.main_thread.windows.0; - let webview = loop { - if let Some(webview) = windows.try_borrow().ok().and_then(|windows| { - windows - .get(&window_id) - .map(|window| window.webviews.first().unwrap().clone()) - }) { - break webview; - } else { - // on Windows the window is created async so we should wait for it to be available - std::thread::sleep(std::time::Duration::from_millis(50)); - continue; - }; - }; - - #[cfg(desktop)] - wry::NewWindowResponse::Create { - #[cfg(target_os = "macos")] - webview: wry::WebViewExtMacOS::webview(&*webview).as_super().into(), - #[cfg(any( - target_os = "linux", - target_os = "dragonfly", - target_os = "freebsd", - target_os = "netbsd", - target_os = "openbsd", - ))] - webview: webview.webview(), - #[cfg(windows)] - webview: webview.webview(), - } - } - tauri_runtime::webview::NewWindowResponse::Deny => wry::NewWindowResponse::Deny, + webview: features.opener.webview, + #[cfg(windows)] + environment: features.opener.environment, + #[cfg(target_os = "macos")] + target_configuration: features.opener.target_configuration, + }, + ), + ); + match response { + tauri_runtime::webview::NewWindowResponse::Allow => wry::NewWindowResponse::Allow, + #[cfg(desktop)] + tauri_runtime::webview::NewWindowResponse::Create { window_id } => { + let windows = &context.main_thread.windows.0; + let webview = windows + .borrow() + .get(&window_id) + .unwrap() + .webviews + .first() + .unwrap() + .clone(); + + #[cfg(desktop)] + wry::NewWindowResponse::Create { + #[cfg(target_os = "macos")] + webview: wry::WebViewExtMacOS::webview(&*webview).as_super().into(), + #[cfg(any( + target_os = "linux", + target_os = "dragonfly", + target_os = "freebsd", + target_os = "netbsd", + target_os = "openbsd", + ))] + webview: webview.webview(), + #[cfg(windows)] + webview: webview.webview(), } - }) - .unwrap_or(wry::NewWindowResponse::Deny) + } + tauri_runtime::webview::NewWindowResponse::Deny => wry::NewWindowResponse::Deny, + } }); } diff --git a/crates/tauri-runtime/src/webview.rs b/crates/tauri-runtime/src/webview.rs index 625a7703a437..49707858dcb9 100644 --- a/crates/tauri-runtime/src/webview.rs +++ b/crates/tauri-runtime/src/webview.rs @@ -33,7 +33,7 @@ type WebResourceRequestHandler = type NavigationHandler = dyn Fn(&Url) -> bool + Send; -type NewWindowHandler = dyn Fn(Url, NewWindowFeatures) -> NewWindowResponse + Send + Sync; +type NewWindowHandler = dyn Fn(Url, NewWindowFeatures) -> NewWindowResponse + Send; type OnPageLoadHandler = dyn Fn(Url, PageLoadEvent) + Send; diff --git a/crates/tauri/src/webview/mod.rs b/crates/tauri/src/webview/mod.rs index 75aceb44999c..8b66459dc12d 100644 --- a/crates/tauri/src/webview/mod.rs +++ b/crates/tauri/src/webview/mod.rs @@ -58,8 +58,7 @@ use std::{ pub(crate) type WebResourceRequestHandler = dyn Fn(http::Request>, &mut http::Response>) + Send + Sync; pub(crate) type NavigationHandler = dyn Fn(&Url) -> bool + Send; -pub(crate) type NewWindowHandler = - dyn Fn(Url, NewWindowFeatures) -> NewWindowResponse + Send + Sync; +pub(crate) type NewWindowHandler = dyn Fn(Url, NewWindowFeatures) -> NewWindowResponse + Send; pub(crate) type UriSchemeProtocolHandler = Box>, UriSchemeResponder) + Send + Sync>; pub(crate) type OnPageLoad = dyn Fn(Webview, PageLoadPayload<'_>) + Send + Sync + 'static; @@ -581,12 +580,9 @@ tauri::Builder::default() /// # Platform-specific /// /// - **Android / iOS**: Not supported. - /// - **Windows**: The closure is executed on a separate thread to prevent a deadlock. /// /// [window.open]: https://developer.mozilla.org/en-US/docs/Web/API/Window/open - pub fn on_new_window< - F: Fn(Url, NewWindowFeatures) -> NewWindowResponse + Send + Sync + 'static, - >( + pub fn on_new_window NewWindowResponse + Send + 'static>( mut self, f: F, ) -> Self { @@ -724,7 +720,6 @@ tauri::Builder::default() as Box< dyn Fn(Url, NewWindowFeatures) -> tauri_runtime::webview::NewWindowResponse + Send - + Sync + 'static, > }); diff --git a/crates/tauri/src/webview/webview_window.rs b/crates/tauri/src/webview/webview_window.rs index 86ad050b582b..dc6098014d4a 100644 --- a/crates/tauri/src/webview/webview_window.rs +++ b/crates/tauri/src/webview/webview_window.rs @@ -310,12 +310,9 @@ impl<'a, R: Runtime, M: Manager> WebviewWindowBuilder<'a, R, M> { /// # Platform-specific /// /// - **Android / iOS**: Not supported. - /// - **Windows**: The closure is executed on a separate thread to prevent a deadlock. /// /// [window.open]: https://developer.mozilla.org/en-US/docs/Web/API/Window/open - pub fn on_new_window< - F: Fn(Url, NewWindowFeatures) -> NewWindowResponse + Send + Sync + 'static, - >( + pub fn on_new_window NewWindowResponse + Send + 'static>( mut self, f: F, ) -> Self { From aebcf9641a88748dfb1e16408ca033f095aa3b1b Mon Sep 17 00:00:00 2001 From: "renovate[bot]" <29139614+renovate[bot]@users.noreply.github.com> Date: Tue, 24 Mar 2026 17:54:31 +0100 Subject: [PATCH 54/95] chore(deps): update dependency rollup to v4.59.1 (#15150) Co-authored-by: renovate[bot] <29139614+renovate[bot]@users.noreply.github.com> --- packages/api/package.json | 2 +- pnpm-lock.yaml | 230 +++++++++++++++++++------------------- 2 files changed, 116 insertions(+), 116 deletions(-) diff --git a/packages/api/package.json b/packages/api/package.json index db3744fc2446..f4e27d121c33 100644 --- a/packages/api/package.json +++ b/packages/api/package.json @@ -55,7 +55,7 @@ "eslint-plugin-security": "4.0.0", "fast-glob": "3.3.3", "globals": "^17.4.0", - "rollup": "4.59.0", + "rollup": "4.59.1", "tslib": "^2.8.1", "typescript": "^5.9.3", "typescript-eslint": "^8.56.1" diff --git a/pnpm-lock.yaml b/pnpm-lock.yaml index 4df96ba054f6..72af631ffd8f 100644 --- a/pnpm-lock.yaml +++ b/pnpm-lock.yaml @@ -57,10 +57,10 @@ importers: version: 10.0.1(eslint@10.0.2(jiti@2.6.1)) '@rollup/plugin-terser': specifier: 1.0.0 - version: 1.0.0(rollup@4.59.0) + version: 1.0.0(rollup@4.59.1) '@rollup/plugin-typescript': specifier: 12.3.0 - version: 12.3.0(rollup@4.59.0)(tslib@2.8.1)(typescript@5.9.3) + version: 12.3.0(rollup@4.59.1)(tslib@2.8.1)(typescript@5.9.3) '@types/eslint': specifier: ^9.6.1 version: 9.6.1 @@ -83,8 +83,8 @@ importers: specifier: ^17.4.0 version: 17.4.0 rollup: - specifier: 4.59.0 - version: 4.59.0 + specifier: 4.59.1 + version: 4.59.1 tslib: specifier: ^2.8.1 version: 2.8.1 @@ -1398,141 +1398,141 @@ packages: rollup: optional: true - '@rollup/rollup-android-arm-eabi@4.59.0': - resolution: {integrity: sha512-upnNBkA6ZH2VKGcBj9Fyl9IGNPULcjXRlg0LLeaioQWueH30p6IXtJEbKAgvyv+mJaMxSm1l6xwDXYjpEMiLMg==} + '@rollup/rollup-android-arm-eabi@4.59.1': + resolution: {integrity: sha512-xB0b51TB7IfDEzAojXahmr+gfA00uYVInJGgNNkeQG6RPnCPGr7udsylFLTubuIUSRE6FkcI1NElyRt83PP5oQ==} cpu: [arm] os: [android] - '@rollup/rollup-android-arm64@4.59.0': - resolution: {integrity: sha512-hZ+Zxj3SySm4A/DylsDKZAeVg0mvi++0PYVceVyX7hemkw7OreKdCvW2oQ3T1FMZvCaQXqOTHb8qmBShoqk69Q==} + '@rollup/rollup-android-arm64@4.59.1': + resolution: {integrity: sha512-XOjPId0qwSDKHaIsdzHJtKCxX0+nH8MhBwvrNsT7tVyKmdTx1jJ4XzN5RZXCdTzMpufLb+B8llTC0D8uCrLhcw==} cpu: [arm64] os: [android] - '@rollup/rollup-darwin-arm64@4.59.0': - resolution: {integrity: sha512-W2Psnbh1J8ZJw0xKAd8zdNgF9HRLkdWwwdWqubSVk0pUuQkoHnv7rx4GiF9rT4t5DIZGAsConRE3AxCdJ4m8rg==} + '@rollup/rollup-darwin-arm64@4.59.1': + resolution: {integrity: sha512-vQuRd28p0gQpPrS6kppd8IrWmFo42U8Pz1XLRjSZXq5zCqyMDYFABT7/sywL11mO1EL10Qhh7MVPEwkG8GiBeg==} cpu: [arm64] os: [darwin] - '@rollup/rollup-darwin-x64@4.59.0': - resolution: {integrity: sha512-ZW2KkwlS4lwTv7ZVsYDiARfFCnSGhzYPdiOU4IM2fDbL+QGlyAbjgSFuqNRbSthybLbIJ915UtZBtmuLrQAT/w==} + '@rollup/rollup-darwin-x64@4.59.1': + resolution: {integrity: sha512-x6VG6U29+Ivlnajrg1IHdzXeAwSoEHBFVO+CtC9Brugx6de712CUJobRUxsIA0KYrQvCmzNrMPFTT1A4CCqNTg==} cpu: [x64] os: [darwin] - '@rollup/rollup-freebsd-arm64@4.59.0': - resolution: {integrity: sha512-EsKaJ5ytAu9jI3lonzn3BgG8iRBjV4LxZexygcQbpiU0wU0ATxhNVEpXKfUa0pS05gTcSDMKpn3Sx+QB9RlTTA==} + '@rollup/rollup-freebsd-arm64@4.59.1': + resolution: {integrity: sha512-Sgi0Uo6t1YCHJMNO3Y8+bm+SvOanUGkoZKn/VJPwYUe2kp31X5KnXmzKd/NjW8iA3gFcfNZ64zh14uOGrIllCQ==} cpu: [arm64] os: [freebsd] - '@rollup/rollup-freebsd-x64@4.59.0': - resolution: {integrity: sha512-d3DuZi2KzTMjImrxoHIAODUZYoUUMsuUiY4SRRcJy6NJoZ6iIqWnJu9IScV9jXysyGMVuW+KNzZvBLOcpdl3Vg==} + '@rollup/rollup-freebsd-x64@4.59.1': + resolution: {integrity: sha512-AM4xnwEZwukdhk7laMWfzWu9JGSVnJd+Fowt6Fd7QW1nrf3h0Hp7Qx5881M4aqrUlKBCybOxz0jofvIIfl7C5g==} cpu: [x64] os: [freebsd] - '@rollup/rollup-linux-arm-gnueabihf@4.59.0': - resolution: {integrity: sha512-t4ONHboXi/3E0rT6OZl1pKbl2Vgxf9vJfWgmUoCEVQVxhW6Cw/c8I6hbbu7DAvgp82RKiH7TpLwxnJeKv2pbsw==} + '@rollup/rollup-linux-arm-gnueabihf@4.59.1': + resolution: {integrity: sha512-KUizqxpwaR2AZdAUsMWfL/C94pUu7TKpoPd88c8yFVixJ+l9hejkrwoK5Zj3wiNh65UeyryKnJyxL1b7yNqFQA==} cpu: [arm] os: [linux] libc: [glibc] - '@rollup/rollup-linux-arm-musleabihf@4.59.0': - resolution: {integrity: sha512-CikFT7aYPA2ufMD086cVORBYGHffBo4K8MQ4uPS/ZnY54GKj36i196u8U+aDVT2LX4eSMbyHtyOh7D7Zvk2VvA==} + '@rollup/rollup-linux-arm-musleabihf@4.59.1': + resolution: {integrity: sha512-MZoQ/am77ckJtZGFAtPucgUuJWiop3m2R3lw7tC0QCcbfl4DRhQUBUkHWCkcrT3pqy5Mzv5QQgY6Dmlba6iTWg==} cpu: [arm] os: [linux] libc: [musl] - '@rollup/rollup-linux-arm64-gnu@4.59.0': - resolution: {integrity: sha512-jYgUGk5aLd1nUb1CtQ8E+t5JhLc9x5WdBKew9ZgAXg7DBk0ZHErLHdXM24rfX+bKrFe+Xp5YuJo54I5HFjGDAA==} + '@rollup/rollup-linux-arm64-gnu@4.59.1': + resolution: {integrity: sha512-Sez95TP6xGjkWB1608EfhCX1gdGrO5wzyN99VqzRtC17x/1bhw5VU1V0GfKUwbW/Xr1J8mSasoFoJa6Y7aGGSA==} cpu: [arm64] os: [linux] libc: [glibc] - '@rollup/rollup-linux-arm64-musl@4.59.0': - resolution: {integrity: sha512-peZRVEdnFWZ5Bh2KeumKG9ty7aCXzzEsHShOZEFiCQlDEepP1dpUl/SrUNXNg13UmZl+gzVDPsiCwnV1uI0RUA==} + '@rollup/rollup-linux-arm64-musl@4.59.1': + resolution: {integrity: sha512-9Cs2Seq98LWNOJzR89EGTZoiP8EkZ9UbQhBlDgfAkM6asVna1xJ04W2CLYWDN/RpUgOjtQvcv8wQVi1t5oQazA==} cpu: [arm64] os: [linux] libc: [musl] - '@rollup/rollup-linux-loong64-gnu@4.59.0': - resolution: {integrity: sha512-gbUSW/97f7+r4gHy3Jlup8zDG190AuodsWnNiXErp9mT90iCy9NKKU0Xwx5k8VlRAIV2uU9CsMnEFg/xXaOfXg==} + '@rollup/rollup-linux-loong64-gnu@4.59.1': + resolution: {integrity: sha512-n9yqttftgFy7IrNEnHy1bOp6B4OSe8mJDiPkT7EqlM9FnKOwUMnCK62ixW0Kd9Clw0/wgvh8+SqaDXMFvw3KqQ==} cpu: [loong64] os: [linux] libc: [glibc] - '@rollup/rollup-linux-loong64-musl@4.59.0': - resolution: {integrity: sha512-yTRONe79E+o0FWFijasoTjtzG9EBedFXJMl888NBEDCDV9I2wGbFFfJQQe63OijbFCUZqxpHz1GzpbtSFikJ4Q==} + '@rollup/rollup-linux-loong64-musl@4.59.1': + resolution: {integrity: sha512-SfpNXDzVTqs/riak4xXcLpq5gIQWsqGWMhN1AGRQKB4qGSs4r0sEs3ervXPcE1O9RsQ5bm8Muz6zmQpQnPss1g==} cpu: [loong64] os: [linux] libc: [musl] - '@rollup/rollup-linux-ppc64-gnu@4.59.0': - resolution: {integrity: sha512-sw1o3tfyk12k3OEpRddF68a1unZ5VCN7zoTNtSn2KndUE+ea3m3ROOKRCZxEpmT9nsGnogpFP9x6mnLTCaoLkA==} + '@rollup/rollup-linux-ppc64-gnu@4.59.1': + resolution: {integrity: sha512-LjaChED0wQnjKZU+tsmGbN+9nN1XhaWUkAlSbTdhpEseCS4a15f/Q8xC2BN4GDKRzhhLZpYtJBZr2NZhR0jvNw==} cpu: [ppc64] os: [linux] libc: [glibc] - '@rollup/rollup-linux-ppc64-musl@4.59.0': - resolution: {integrity: sha512-+2kLtQ4xT3AiIxkzFVFXfsmlZiG5FXYW7ZyIIvGA7Bdeuh9Z0aN4hVyXS/G1E9bTP/vqszNIN/pUKCk/BTHsKA==} + '@rollup/rollup-linux-ppc64-musl@4.59.1': + resolution: {integrity: sha512-ojW7iTJSIs4pwB2xV6QXGwNyDctvXOivYllttuPbXguuKDX5vwpqYJsHc6D2LZzjDGHML414Tuj3LvVPe1CT1A==} cpu: [ppc64] os: [linux] libc: [musl] - '@rollup/rollup-linux-riscv64-gnu@4.59.0': - resolution: {integrity: sha512-NDYMpsXYJJaj+I7UdwIuHHNxXZ/b/N2hR15NyH3m2qAtb/hHPA4g4SuuvrdxetTdndfj9b1WOmy73kcPRoERUg==} + '@rollup/rollup-linux-riscv64-gnu@4.59.1': + resolution: {integrity: sha512-FP+Q6WTcxxvsr0wQczhSE+tOZvFPV8A/mUE6mhZYFW9/eea/y/XqAgRoLLMuE9Cz0hfX5bi7p116IWoB+P237A==} cpu: [riscv64] os: [linux] libc: [glibc] - '@rollup/rollup-linux-riscv64-musl@4.59.0': - resolution: {integrity: sha512-nLckB8WOqHIf1bhymk+oHxvM9D3tyPndZH8i8+35p/1YiVoVswPid2yLzgX7ZJP0KQvnkhM4H6QZ5m0LzbyIAg==} + '@rollup/rollup-linux-riscv64-musl@4.59.1': + resolution: {integrity: sha512-L1uD9b/Ig8Z+rn1KttCJjwhN1FgjRMBKsPaBsDKkfUl7GfFq71pU4vWCnpOsGljycFEbkHWARZLf4lMYg3WOLw==} cpu: [riscv64] os: [linux] libc: [musl] - '@rollup/rollup-linux-s390x-gnu@4.59.0': - resolution: {integrity: sha512-oF87Ie3uAIvORFBpwnCvUzdeYUqi2wY6jRFWJAy1qus/udHFYIkplYRW+wo+GRUP4sKzYdmE1Y3+rY5Gc4ZO+w==} + '@rollup/rollup-linux-s390x-gnu@4.59.1': + resolution: {integrity: sha512-EZc9NGTk/oSUzzOD4nYY4gIjteo2M3CiozX6t1IXGCOdgxJTlVu/7EdPeiqeHPSIrxkLhavqpBAUCfvC6vBOug==} cpu: [s390x] os: [linux] libc: [glibc] - '@rollup/rollup-linux-x64-gnu@4.59.0': - resolution: {integrity: sha512-3AHmtQq/ppNuUspKAlvA8HtLybkDflkMuLK4DPo77DfthRb71V84/c4MlWJXixZz4uruIH4uaa07IqoAkG64fg==} + '@rollup/rollup-linux-x64-gnu@4.59.1': + resolution: {integrity: sha512-NQ9KyU1Anuy59L8+HHOKM++CoUxrQWrZWXRik4BJFm+7i5NP6q/SW43xIBr80zzt+PDBJ7LeNmloQGfa0JGk0w==} cpu: [x64] os: [linux] libc: [glibc] - '@rollup/rollup-linux-x64-musl@4.59.0': - resolution: {integrity: sha512-2UdiwS/9cTAx7qIUZB/fWtToJwvt0Vbo0zmnYt7ED35KPg13Q0ym1g442THLC7VyI6JfYTP4PiSOWyoMdV2/xg==} + '@rollup/rollup-linux-x64-musl@4.59.1': + resolution: {integrity: sha512-GZkLk2t6naywsveSFBsEb0PLU+JC9ggVjbndsbG20VPhar6D1gkMfCx4NfP9owpovBXTN+eRdqGSkDGIxPHhmQ==} cpu: [x64] os: [linux] libc: [musl] - '@rollup/rollup-openbsd-x64@4.59.0': - resolution: {integrity: sha512-M3bLRAVk6GOwFlPTIxVBSYKUaqfLrn8l0psKinkCFxl4lQvOSz8ZrKDz2gxcBwHFpci0B6rttydI4IpS4IS/jQ==} + '@rollup/rollup-openbsd-x64@4.59.1': + resolution: {integrity: sha512-1hjG9Jpl2KDOetr64iQd8AZAEjkDUUK5RbDkYWsViYLC1op1oNzdjMJeFiofcGhqbNTaY2kfgqowE7DILifsrA==} cpu: [x64] os: [openbsd] - '@rollup/rollup-openharmony-arm64@4.59.0': - resolution: {integrity: sha512-tt9KBJqaqp5i5HUZzoafHZX8b5Q2Fe7UjYERADll83O4fGqJ49O1FsL6LpdzVFQcpwvnyd0i+K/VSwu/o/nWlA==} + '@rollup/rollup-openharmony-arm64@4.59.1': + resolution: {integrity: sha512-ARoKfflk0SiiYm3r1fmF73K/yB+PThmOwfWCk1sr7x/k9dc3uGLWuEE9if+Pw21el8MSpp3TMnG5vLNsJ/MMGQ==} cpu: [arm64] os: [openharmony] - '@rollup/rollup-win32-arm64-msvc@4.59.0': - resolution: {integrity: sha512-V5B6mG7OrGTwnxaNUzZTDTjDS7F75PO1ae6MJYdiMu60sq0CqN5CVeVsbhPxalupvTX8gXVSU9gq+Rx1/hvu6A==} + '@rollup/rollup-win32-arm64-msvc@4.59.1': + resolution: {integrity: sha512-oOST61G6VM45Mz2vdzWMr1s2slI7y9LqxEV5fCoWi2MDONmMvgsJVHSXxce/I2xOSZPTZ47nDPOl1tkwKWSHcw==} cpu: [arm64] os: [win32] - '@rollup/rollup-win32-ia32-msvc@4.59.0': - resolution: {integrity: sha512-UKFMHPuM9R0iBegwzKF4y0C4J9u8C6MEJgFuXTBerMk7EJ92GFVFYBfOZaSGLu6COf7FxpQNqhNS4c4icUPqxA==} + '@rollup/rollup-win32-ia32-msvc@4.59.1': + resolution: {integrity: sha512-x5WgLi5dWpRz7WclKBGEF15LcWTh0ewrHM6Cq4A+WUbkysUMZNeqt05bwPonOQ3ihPS/WMhAZV5zB1DfnI4Sxg==} cpu: [ia32] os: [win32] - '@rollup/rollup-win32-x64-gnu@4.59.0': - resolution: {integrity: sha512-laBkYlSS1n2L8fSo1thDNGrCTQMmxjYY5G0WFWjFFYZkKPjsMBsgJfGf4TLxXrF6RyhI60L8TMOjBMvXiTcxeA==} + '@rollup/rollup-win32-x64-gnu@4.59.1': + resolution: {integrity: sha512-wS+zHAJRVP5zOL0e+a3V3E/NTEwM2HEvvNKoDy5Xcfs0o8lljxn+EAFPkUsxihBdmDq1JWzXmmB9cbssCPdxxw==} cpu: [x64] os: [win32] - '@rollup/rollup-win32-x64-msvc@4.59.0': - resolution: {integrity: sha512-2HRCml6OztYXyJXAvdDXPKcawukWY2GpR5/nxKp4iBgiO3wcoEGkAaqctIbZcNB6KlUQBIqt8VYkNSj2397EfA==} + '@rollup/rollup-win32-x64-msvc@4.59.1': + resolution: {integrity: sha512-rhHyrMeLpErT/C7BxcEsU4COHQUzHyrPYW5tOZUeUhziNtRuYxmDWvqQqzpuUt8xpOgmbKa1btGXfnA/ANVO+g==} cpu: [x64] os: [win32] @@ -2372,8 +2372,8 @@ packages: engines: {node: ^20.19.0 || >=22.12.0} hasBin: true - rollup@4.59.0: - resolution: {integrity: sha512-2oMpl67a3zCH9H79LeMcbDhXW/UmWG/y2zuqnF2jQq5uq9TbM9TVyXvA4+t+ne2IIkBdrLpAaRQAvo7YI/Yyeg==} + rollup@4.59.1: + resolution: {integrity: sha512-iZKH8BeoCwTCBTZBZWQQMreekd4mdomwdjIQ40GC1oZm6o+8PnNMIxFOiCsGMWeS8iDJ7KZcl7KwmKk/0HOQpA==} engines: {node: '>=18.0.0', npm: '>=8.0.0'} hasBin: true @@ -3628,104 +3628,104 @@ snapshots: '@rolldown/pluginutils@1.0.0-rc.9': {} - '@rollup/plugin-terser@1.0.0(rollup@4.59.0)': + '@rollup/plugin-terser@1.0.0(rollup@4.59.1)': dependencies: serialize-javascript: 7.0.4 smob: 1.6.1 terser: 5.46.0 optionalDependencies: - rollup: 4.59.0 + rollup: 4.59.1 - '@rollup/plugin-typescript@12.3.0(rollup@4.59.0)(tslib@2.8.1)(typescript@5.9.3)': + '@rollup/plugin-typescript@12.3.0(rollup@4.59.1)(tslib@2.8.1)(typescript@5.9.3)': dependencies: - '@rollup/pluginutils': 5.3.0(rollup@4.59.0) + '@rollup/pluginutils': 5.3.0(rollup@4.59.1) resolve: 1.22.11 typescript: 5.9.3 optionalDependencies: - rollup: 4.59.0 + rollup: 4.59.1 tslib: 2.8.1 - '@rollup/pluginutils@5.3.0(rollup@4.59.0)': + '@rollup/pluginutils@5.3.0(rollup@4.59.1)': dependencies: '@types/estree': 1.0.8 estree-walker: 2.0.2 picomatch: 4.0.3 optionalDependencies: - rollup: 4.59.0 + rollup: 4.59.1 - '@rollup/rollup-android-arm-eabi@4.59.0': + '@rollup/rollup-android-arm-eabi@4.59.1': optional: true - '@rollup/rollup-android-arm64@4.59.0': + '@rollup/rollup-android-arm64@4.59.1': optional: true - '@rollup/rollup-darwin-arm64@4.59.0': + '@rollup/rollup-darwin-arm64@4.59.1': optional: true - '@rollup/rollup-darwin-x64@4.59.0': + '@rollup/rollup-darwin-x64@4.59.1': optional: true - '@rollup/rollup-freebsd-arm64@4.59.0': + '@rollup/rollup-freebsd-arm64@4.59.1': optional: true - '@rollup/rollup-freebsd-x64@4.59.0': + '@rollup/rollup-freebsd-x64@4.59.1': optional: true - '@rollup/rollup-linux-arm-gnueabihf@4.59.0': + '@rollup/rollup-linux-arm-gnueabihf@4.59.1': optional: true - '@rollup/rollup-linux-arm-musleabihf@4.59.0': + '@rollup/rollup-linux-arm-musleabihf@4.59.1': optional: true - '@rollup/rollup-linux-arm64-gnu@4.59.0': + '@rollup/rollup-linux-arm64-gnu@4.59.1': optional: true - '@rollup/rollup-linux-arm64-musl@4.59.0': + '@rollup/rollup-linux-arm64-musl@4.59.1': optional: true - '@rollup/rollup-linux-loong64-gnu@4.59.0': + '@rollup/rollup-linux-loong64-gnu@4.59.1': optional: true - '@rollup/rollup-linux-loong64-musl@4.59.0': + '@rollup/rollup-linux-loong64-musl@4.59.1': optional: true - '@rollup/rollup-linux-ppc64-gnu@4.59.0': + '@rollup/rollup-linux-ppc64-gnu@4.59.1': optional: true - '@rollup/rollup-linux-ppc64-musl@4.59.0': + '@rollup/rollup-linux-ppc64-musl@4.59.1': optional: true - '@rollup/rollup-linux-riscv64-gnu@4.59.0': + '@rollup/rollup-linux-riscv64-gnu@4.59.1': optional: true - '@rollup/rollup-linux-riscv64-musl@4.59.0': + '@rollup/rollup-linux-riscv64-musl@4.59.1': optional: true - '@rollup/rollup-linux-s390x-gnu@4.59.0': + '@rollup/rollup-linux-s390x-gnu@4.59.1': optional: true - '@rollup/rollup-linux-x64-gnu@4.59.0': + '@rollup/rollup-linux-x64-gnu@4.59.1': optional: true - '@rollup/rollup-linux-x64-musl@4.59.0': + '@rollup/rollup-linux-x64-musl@4.59.1': optional: true - '@rollup/rollup-openbsd-x64@4.59.0': + '@rollup/rollup-openbsd-x64@4.59.1': optional: true - '@rollup/rollup-openharmony-arm64@4.59.0': + '@rollup/rollup-openharmony-arm64@4.59.1': optional: true - '@rollup/rollup-win32-arm64-msvc@4.59.0': + '@rollup/rollup-win32-arm64-msvc@4.59.1': optional: true - '@rollup/rollup-win32-ia32-msvc@4.59.0': + '@rollup/rollup-win32-ia32-msvc@4.59.1': optional: true - '@rollup/rollup-win32-x64-gnu@4.59.0': + '@rollup/rollup-win32-x64-gnu@4.59.1': optional: true - '@rollup/rollup-win32-x64-msvc@4.59.0': + '@rollup/rollup-win32-x64-msvc@4.59.1': optional: true '@sindresorhus/is@7.2.0': {} @@ -4636,35 +4636,35 @@ snapshots: '@rolldown/binding-win32-arm64-msvc': 1.0.0-rc.9 '@rolldown/binding-win32-x64-msvc': 1.0.0-rc.9 - rollup@4.59.0: + rollup@4.59.1: dependencies: '@types/estree': 1.0.8 optionalDependencies: - '@rollup/rollup-android-arm-eabi': 4.59.0 - '@rollup/rollup-android-arm64': 4.59.0 - '@rollup/rollup-darwin-arm64': 4.59.0 - '@rollup/rollup-darwin-x64': 4.59.0 - '@rollup/rollup-freebsd-arm64': 4.59.0 - '@rollup/rollup-freebsd-x64': 4.59.0 - '@rollup/rollup-linux-arm-gnueabihf': 4.59.0 - '@rollup/rollup-linux-arm-musleabihf': 4.59.0 - '@rollup/rollup-linux-arm64-gnu': 4.59.0 - '@rollup/rollup-linux-arm64-musl': 4.59.0 - '@rollup/rollup-linux-loong64-gnu': 4.59.0 - '@rollup/rollup-linux-loong64-musl': 4.59.0 - '@rollup/rollup-linux-ppc64-gnu': 4.59.0 - '@rollup/rollup-linux-ppc64-musl': 4.59.0 - '@rollup/rollup-linux-riscv64-gnu': 4.59.0 - '@rollup/rollup-linux-riscv64-musl': 4.59.0 - '@rollup/rollup-linux-s390x-gnu': 4.59.0 - '@rollup/rollup-linux-x64-gnu': 4.59.0 - '@rollup/rollup-linux-x64-musl': 4.59.0 - '@rollup/rollup-openbsd-x64': 4.59.0 - '@rollup/rollup-openharmony-arm64': 4.59.0 - '@rollup/rollup-win32-arm64-msvc': 4.59.0 - '@rollup/rollup-win32-ia32-msvc': 4.59.0 - '@rollup/rollup-win32-x64-gnu': 4.59.0 - '@rollup/rollup-win32-x64-msvc': 4.59.0 + '@rollup/rollup-android-arm-eabi': 4.59.1 + '@rollup/rollup-android-arm64': 4.59.1 + '@rollup/rollup-darwin-arm64': 4.59.1 + '@rollup/rollup-darwin-x64': 4.59.1 + '@rollup/rollup-freebsd-arm64': 4.59.1 + '@rollup/rollup-freebsd-x64': 4.59.1 + '@rollup/rollup-linux-arm-gnueabihf': 4.59.1 + '@rollup/rollup-linux-arm-musleabihf': 4.59.1 + '@rollup/rollup-linux-arm64-gnu': 4.59.1 + '@rollup/rollup-linux-arm64-musl': 4.59.1 + '@rollup/rollup-linux-loong64-gnu': 4.59.1 + '@rollup/rollup-linux-loong64-musl': 4.59.1 + '@rollup/rollup-linux-ppc64-gnu': 4.59.1 + '@rollup/rollup-linux-ppc64-musl': 4.59.1 + '@rollup/rollup-linux-riscv64-gnu': 4.59.1 + '@rollup/rollup-linux-riscv64-musl': 4.59.1 + '@rollup/rollup-linux-s390x-gnu': 4.59.1 + '@rollup/rollup-linux-x64-gnu': 4.59.1 + '@rollup/rollup-linux-x64-musl': 4.59.1 + '@rollup/rollup-openbsd-x64': 4.59.1 + '@rollup/rollup-openharmony-arm64': 4.59.1 + '@rollup/rollup-win32-arm64-msvc': 4.59.1 + '@rollup/rollup-win32-ia32-msvc': 4.59.1 + '@rollup/rollup-win32-x64-gnu': 4.59.1 + '@rollup/rollup-win32-x64-msvc': 4.59.1 fsevents: 2.3.3 run-parallel@1.2.0: @@ -4886,7 +4886,7 @@ snapshots: fdir: 6.5.0(picomatch@4.0.3) picomatch: 4.0.3 postcss: 8.5.8 - rollup: 4.59.0 + rollup: 4.59.1 tinyglobby: 0.2.15 optionalDependencies: '@types/node': 24.11.0 From a2fc5e9e7fc433eb1ccbc11f346d4f9e6da7ed62 Mon Sep 17 00:00:00 2001 From: Thomas Eizinger Date: Wed, 25 Mar 2026 23:58:51 +1100 Subject: [PATCH 55/95] refactor: replace `kuchikiki` with `dom_query` (#14959) * test: add more unit-tests for `html` module * refactor: remove html dependencies from `tauri-cli` * feat: introduce `html-manipulation-2` feature * Remove deprecation * Use new feature flag * Unroll `build` feature * Introduce `build-2` feature * Reduce diff * Use `build-2` in more places * Add docs * Refactor `inject_script_hashes` * Refactor `with_head` * Rename serialize and parse functions * Add changes file * Remove unused function * Update changelog * Remove test * Update wry * Add todo comments we don't have the git blame data in html2, better do it now or never find it again * refactor `with_head` to `ensure_head` * Remove unused casts * Avoid using format to construct html elements which has the potential to get injected * Feature gate `inline_isolation` * Keep old prepends appends * Fix `inline_isolation_replaces_src_with_content` test * End meta tag * Mirror test to old html module * Use back to `append_html` for csp and link issue * Try out dom query main branch * Use nodes instead to avoid an extra clone * Use wry 0.54.4 and dom_query 0.27 * Mark stability * Remove `PatternObject` --------- Co-authored-by: Tony Co-authored-by: Tony <68118705+Legend-Master@users.noreply.github.com> --- .changes/supersede-kuchikiki.md | 6 + Cargo.lock | 24 +- crates/tauri-build/Cargo.toml | 2 +- crates/tauri-cli/Cargo.toml | 4 +- .../tauri-cli/src/dev/builtin_dev_server.rs | 30 +- crates/tauri-codegen/Cargo.toml | 2 +- crates/tauri-codegen/src/context.rs | 54 ++- crates/tauri-codegen/src/embedded_assets.rs | 2 +- crates/tauri-plugin/Cargo.toml | 2 +- crates/tauri-utils/Cargo.toml | 12 + crates/tauri-utils/src/acl/capability.rs | 2 +- crates/tauri-utils/src/acl/identifier.rs | 2 +- crates/tauri-utils/src/acl/manifest.rs | 2 +- crates/tauri-utils/src/acl/mod.rs | 6 +- crates/tauri-utils/src/acl/resolved.rs | 2 +- crates/tauri-utils/src/acl/value.rs | 2 +- crates/tauri-utils/src/config.rs | 2 +- crates/tauri-utils/src/html.rs | 109 +++++- crates/tauri-utils/src/html2.rs | 335 ++++++++++++++++++ crates/tauri-utils/src/lib.rs | 6 +- crates/tauri-utils/src/platform.rs | 2 +- crates/tauri-utils/src/plugin.rs | 4 +- crates/tauri/Cargo.toml | 4 +- crates/tauri/src/manager/webview.rs | 6 +- crates/tests/acl/Cargo.toml | 2 +- 25 files changed, 526 insertions(+), 98 deletions(-) create mode 100644 .changes/supersede-kuchikiki.md create mode 100644 crates/tauri-utils/src/html2.rs diff --git a/.changes/supersede-kuchikiki.md b/.changes/supersede-kuchikiki.md new file mode 100644 index 000000000000..18974ff48ab8 --- /dev/null +++ b/.changes/supersede-kuchikiki.md @@ -0,0 +1,6 @@ +--- +"tauri-utils": minor:deps +--- + +Add new `html-manipulation-2` and `build-2` feature flags that use `dom_query` instead of `kuchikiki` for HTML parsing / manipulation. +This allows downstream users to remove `kuchikiki` and its dependencies from their dependency tree. diff --git a/Cargo.lock b/Cargo.lock index 3ee41ee22db5..f0b7ea703886 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -1321,7 +1321,7 @@ source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "117725a109d387c937a1533ce01b450cbde6b88abceea8473c4d7a85853cda3c" dependencies = [ "lazy_static", - "windows-sys 0.48.0", + "windows-sys 0.59.0", ] [[package]] @@ -2423,7 +2423,7 @@ source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "33d852cb9b869c2a9b3df2f71a3074817f01e1844f839a144f5fcef059a4eb5d" dependencies = [ "libc", - "windows-sys 0.52.0", + "windows-sys 0.59.0", ] [[package]] @@ -4423,7 +4423,7 @@ source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "fc2f4eb4bc735547cfed7c0a4922cbd04a4655978c09b54f1f7b228750664c34" dependencies = [ "cfg-if", - "windows-targets 0.48.5", + "windows-targets 0.52.6", ] [[package]] @@ -5529,7 +5529,7 @@ source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "7d8fae84b431384b68627d0f9b3b1245fcf9f46f6c0e3dc902e9dce64edd1967" dependencies = [ "libc", - "windows-sys 0.48.0", + "windows-sys 0.60.2", ] [[package]] @@ -5946,7 +5946,7 @@ dependencies = [ "aes-gcm", "aes-kw", "argon2", - "base64 0.21.7", + "base64 0.22.1", "bitfield", "block-padding", "blowfish", @@ -7239,7 +7239,7 @@ dependencies = [ "errno", "libc", "linux-raw-sys 0.4.15", - "windows-sys 0.52.0", + "windows-sys 0.59.0", ] [[package]] @@ -7252,7 +7252,7 @@ dependencies = [ "errno", "libc", "linux-raw-sys 0.9.4", - "windows-sys 0.52.0", + "windows-sys 0.59.0", ] [[package]] @@ -7378,7 +7378,7 @@ dependencies = [ "security-framework 3.5.1", "security-framework-sys", "webpki-root-certs", - "windows-sys 0.52.0", + "windows-sys 0.60.2", ] [[package]] @@ -8888,7 +8888,6 @@ dependencies = [ "glob", "handlebars", "heck 0.5.0", - "html5ever 0.29.1", "ignore", "image", "include_dir", @@ -8901,7 +8900,6 @@ dependencies = [ "jsonrpsee-core", "jsonrpsee-ws-client", "jsonschema", - "kuchikiki", "libc", "local-ip-address", "log", @@ -9188,6 +9186,7 @@ dependencies = [ "brotli", "cargo_metadata", "ctor 0.2.9", + "dom_query", "dunce", "getrandom 0.3.3", "glob", @@ -9213,6 +9212,7 @@ dependencies = [ "serialize-to-javascript", "swift-rs", "tauri", + "tempfile", "thiserror 2.0.12", "toml 1.0.6+spec-1.1.0", "url", @@ -9254,7 +9254,7 @@ dependencies = [ "getrandom 0.2.15", "once_cell", "rustix 0.38.43", - "windows-sys 0.52.0", + "windows-sys 0.59.0", ] [[package]] @@ -10609,7 +10609,7 @@ version = "0.1.9" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "cf221c93e13a30d793f7645a0e7762c55d169dbb0a49671918a2319d289b10bb" dependencies = [ - "windows-sys 0.48.0", + "windows-sys 0.59.0", ] [[package]] diff --git a/crates/tauri-build/Cargo.toml b/crates/tauri-build/Cargo.toml index 26a7f63d6d0b..aa72428572b1 100644 --- a/crates/tauri-build/Cargo.toml +++ b/crates/tauri-build/Cargo.toml @@ -28,7 +28,7 @@ anyhow = "1" quote = { version = "1", optional = true } tauri-codegen = { version = "2.5.5", path = "../tauri-codegen", optional = true } tauri-utils = { version = "2.8.3", path = "../tauri-utils", features = [ - "build", + "build-2", "resources", ] } cargo_toml = "0.22" diff --git a/crates/tauri-cli/Cargo.toml b/crates/tauri-cli/Cargo.toml index 4f95db943b9a..9e216f6c55a3 100644 --- a/crates/tauri-cli/Cargo.toml +++ b/crates/tauri-cli/Cargo.toml @@ -63,7 +63,7 @@ tauri-utils = { version = "2.8.3", path = "../tauri-utils", features = [ "schema", "config-json5", "config-toml", - "html-manipulation", + "html-manipulation-2", ] } toml = "1" jsonschema = { version = "0.33", default-features = false } @@ -89,8 +89,6 @@ env_logger = "0.11" icns = { package = "tauri-icns", version = "0.1" } image = { version = "0.25", default-features = false, features = ["ico"] } axum = { version = "0.8", features = ["ws"] } -html5ever = "0.29" -kuchiki = { package = "kuchikiki", version = "=0.8.8-speedreader" } tokio = { version = "1", features = ["macros", "sync"] } common-path = "1" serde-value = "0.7" diff --git a/crates/tauri-cli/src/dev/builtin_dev_server.rs b/crates/tauri-cli/src/dev/builtin_dev_server.rs index 1b49058ed224..292b7459dd10 100644 --- a/crates/tauri-cli/src/dev/builtin_dev_server.rs +++ b/crates/tauri-cli/src/dev/builtin_dev_server.rs @@ -7,8 +7,6 @@ use axum::{ http::{header, StatusCode, Uri}, response::{IntoResponse, Response}, }; -use html5ever::{namespace_url, ns, LocalName, QualName}; -use kuchiki::{traits::TendrilSink, NodeRef}; use std::{ net::{IpAddr, SocketAddr}, path::{Path, PathBuf}, @@ -128,30 +126,14 @@ async fn ws_handler(ws: WebSocketUpgrade, state: State) -> Response } fn inject_address(html_bytes: Vec, address: &SocketAddr) -> Vec { - fn with_html_head(document: &mut NodeRef, f: F) { - if let Ok(ref node) = document.select_first("head") { - f(node.as_node()) - } else { - let node = NodeRef::new_element( - QualName::new(None, ns!(html), LocalName::from("head")), - None, - ); - f(&node); - document.prepend(node) - } - } + let document = tauri_utils::html2::parse_doc(String::from_utf8_lossy(&html_bytes).into_owned()); - let mut document = kuchiki::parse_html() - .one(String::from_utf8_lossy(&html_bytes).into_owned()) - .document_node; - with_html_head(&mut document, |head| { - let script = RELOAD_SCRIPT.replace("{{reload_url}}", &format!("ws://{address}/__tauri_cli")); - let script_el = NodeRef::new_element(QualName::new(None, ns!(html), "script".into()), None); - script_el.append(NodeRef::new_text(script)); - head.prepend(script_el); - }); + tauri_utils::html2::append_script_to_head( + &document, + &RELOAD_SCRIPT.replace("{{reload_url}}", &format!("ws://{address}/__tauri_cli")), + ); - tauri_utils::html::serialize_node(&document) + tauri_utils::html2::serialize_doc(&document) } fn fs_read_scoped(path: PathBuf, scope: &Path) -> crate::Result> { diff --git a/crates/tauri-codegen/Cargo.toml b/crates/tauri-codegen/Cargo.toml index e1154e67687c..78de83cf0791 100644 --- a/crates/tauri-codegen/Cargo.toml +++ b/crates/tauri-codegen/Cargo.toml @@ -21,7 +21,7 @@ syn = "2" serde = { version = "1", features = ["derive"] } serde_json = "1" tauri-utils = { version = "2.8.3", path = "../tauri-utils", features = [ - "build", + "build-2", ] } thiserror = "2" walkdir = "2" diff --git a/crates/tauri-codegen/src/context.rs b/crates/tauri-codegen/src/context.rs index bc889bd8d4fc..415b7413fcf3 100644 --- a/crates/tauri-codegen/src/context.rs +++ b/crates/tauri-codegen/src/context.rs @@ -25,7 +25,7 @@ use tauri_utils::{ }, assets::AssetKey, config::{Config, FrontendDist, PatternKind}, - html::{inject_nonce_token, parse as parse_html, serialize_node as serialize_html_node, NodeRef}, + html2::{inject_nonce_token, parse_doc, serialize_doc, Document}, platform::Target, tokens::{map_lit, str_lit}, }; @@ -44,27 +44,25 @@ pub struct ContextData { pub test: bool, } -fn inject_script_hashes(document: &NodeRef, key: &AssetKey, csp_hashes: &mut CspHashes) { - if let Ok(inline_script_elements) = document.select("script:not(:empty)") { - let mut scripts = Vec::new(); - for inline_script_el in inline_script_elements { - let script = inline_script_el.as_node().text_contents(); - let mut hasher = Sha256::new(); - hasher.update(tauri_utils::html::normalize_script_for_csp( - script.as_bytes(), - )); - let hash = hasher.finalize(); - scripts.push(format!( - "'sha256-{}'", - base64::engine::general_purpose::STANDARD.encode(hash) - )); - } - csp_hashes - .inline_scripts - .entry(key.clone().into()) - .or_default() - .append(&mut scripts); - } +fn inject_script_hashes(document: &Document, key: &AssetKey, csp_hashes: &mut CspHashes) { + let script_elements = document.select("script:not(:empty)"); + + let scripts = script_elements + .iter() + .map(|element| { + let script = tauri_utils::html2::normalize_script_for_csp(element.text().as_bytes()); + let script_hash = Sha256::digest(script); + let hash_base64 = base64::engine::general_purpose::STANDARD.encode(script_hash); + + format!("'sha256-{hash_base64}'") + }) + .collect::>(); + + csp_hashes + .inline_scripts + .entry(key.clone().into()) + .or_default() + .extend(scripts); } fn map_core_assets( @@ -77,7 +75,7 @@ fn map_core_assets( if path.extension() == Some(OsStr::new("html")) { #[allow(clippy::collapsible_if)] if csp { - let document = parse_html(String::from_utf8_lossy(input).into_owned()); + let document = parse_doc(String::from_utf8_lossy(input).into_owned()); inject_nonce_token(&document, &dangerous_disable_asset_csp_modification); @@ -85,7 +83,7 @@ fn map_core_assets( inject_script_hashes(&document, key, csp_hashes); } - *input = serialize_html_node(&document); + *input = serialize_doc(&document); } } Ok(()) @@ -108,13 +106,13 @@ fn map_isolation( move |key, path, input, csp_hashes| { if path.extension() == Some(OsStr::new("html")) { - let isolation_html = parse_html(String::from_utf8_lossy(input).into_owned()); + let isolation_html = parse_doc(String::from_utf8_lossy(input).into_owned()); // this is appended, so no need to reverse order it - tauri_utils::html::inject_codegen_isolation_script(&isolation_html); + tauri_utils::html2::inject_codegen_isolation_script(&isolation_html); // temporary workaround for windows not loading assets - tauri_utils::html::inline_isolation(&isolation_html, &dir); + tauri_utils::html2::inline_isolation(&isolation_html, &dir); inject_nonce_token( &isolation_html, @@ -125,7 +123,7 @@ fn map_isolation( csp_hashes.styles.push(iframe_style_csp_hash.clone()); - *input = isolation_html.to_string().as_bytes().to_vec() + *input = serialize_doc(&isolation_html) } Ok(()) diff --git a/crates/tauri-codegen/src/embedded_assets.rs b/crates/tauri-codegen/src/embedded_assets.rs index ede7ee6d9310..f3d1bd2757cb 100644 --- a/crates/tauri-codegen/src/embedded_assets.rs +++ b/crates/tauri-codegen/src/embedded_assets.rs @@ -181,7 +181,7 @@ impl CspHashes { let mut hasher = Sha256::new(); hasher.update( &std::fs::read(path) - .map(|b| tauri_utils::html::normalize_script_for_csp(&b)) + .map(|b| tauri_utils::html2::normalize_script_for_csp(&b)) .map_err(|error| EmbeddedAssetsError::AssetRead { path: path.to_path_buf(), error, diff --git a/crates/tauri-plugin/Cargo.toml b/crates/tauri-plugin/Cargo.toml index 1f89c33f01e7..022492dceed0 100644 --- a/crates/tauri-plugin/Cargo.toml +++ b/crates/tauri-plugin/Cargo.toml @@ -28,7 +28,7 @@ runtime = [] anyhow = { version = "1", optional = true } serde = { version = "1", optional = true } tauri-utils = { version = "2.8.3", default-features = false, features = [ - "build", + "build-2", ], path = "../tauri-utils" } serde_json = { version = "1", optional = true } glob = { version = "0.3", optional = true } diff --git a/crates/tauri-utils/Cargo.toml b/crates/tauri-utils/Cargo.toml index 37cd0dd6deb0..0c4feb51ff11 100644 --- a/crates/tauri-utils/Cargo.toml +++ b/crates/tauri-utils/Cargo.toml @@ -24,6 +24,7 @@ brotli = { version = "8", optional = true, default-features = false, features = url = { version = "2", features = ["serde"] } html5ever = { version = "0.29", optional = true } kuchiki = { package = "kuchikiki", version = "0.8.8-speedreader", optional = true } +dom_query = { version = "0.27", optional = true, default-features = false } proc-macro2 = { version = "1", optional = true } quote = { version = "1", optional = true } # Our code requires at least 0.8.21 so don't change this to 0.8 @@ -59,6 +60,7 @@ swift-rs = { version = "1", optional = true, features = ["build"] } getrandom = { version = "0.3", features = ["std"] } serial_test = "3" tauri = { path = "../tauri" } +tempfile = "3.15.0" [features] build = [ @@ -69,6 +71,15 @@ build = [ "swift-rs", "html-manipulation", ] +# Same as `build` but uses `html-manipulation-2` to avoid the `kuchikiki` dependency. +build-2 = [ + "proc-macro2", + "quote", + "cargo_metadata", + "schema", + "swift-rs", + "html-manipulation-2", +] compression = ["brotli"] schema = ["schemars"] isolation = ["aes-gcm", "getrandom", "serialize-to-javascript"] @@ -77,3 +88,4 @@ config-json5 = ["json5"] config-toml = [] resources = ["walkdir"] html-manipulation = ["dep:html5ever", "dep:kuchiki"] +html-manipulation-2 = ["dep:dom_query"] diff --git a/crates/tauri-utils/src/acl/capability.rs b/crates/tauri-utils/src/acl/capability.rs index 4e7417d11c4e..33a2c60c78ac 100644 --- a/crates/tauri-utils/src/acl/capability.rs +++ b/crates/tauri-utils/src/acl/capability.rs @@ -322,7 +322,7 @@ impl FromStr for CapabilityFile { } } -#[cfg(feature = "build")] +#[cfg(any(feature = "build", feature = "build-2"))] mod build { use std::convert::identity; diff --git a/crates/tauri-utils/src/acl/identifier.rs b/crates/tauri-utils/src/acl/identifier.rs index bb571c9fd326..26c7326d2c6d 100644 --- a/crates/tauri-utils/src/acl/identifier.rs +++ b/crates/tauri-utils/src/acl/identifier.rs @@ -283,7 +283,7 @@ mod tests { } } -#[cfg(feature = "build")] +#[cfg(any(feature = "build", feature = "build-2"))] mod build { use proc_macro2::TokenStream; use quote::{quote, ToTokens, TokenStreamExt}; diff --git a/crates/tauri-utils/src/acl/manifest.rs b/crates/tauri-utils/src/acl/manifest.rs index 8c4eed0fda92..ff18df825d3a 100644 --- a/crates/tauri-utils/src/acl/manifest.rs +++ b/crates/tauri-utils/src/acl/manifest.rs @@ -126,7 +126,7 @@ impl Manifest { } } -#[cfg(feature = "build")] +#[cfg(any(feature = "build", feature = "build-2"))] mod build { use proc_macro2::TokenStream; use quote::{quote, ToTokens, TokenStreamExt}; diff --git a/crates/tauri-utils/src/acl/mod.rs b/crates/tauri-utils/src/acl/mod.rs index 03c33d4fdc4c..b9bb6a2d0ebc 100644 --- a/crates/tauri-utils/src/acl/mod.rs +++ b/crates/tauri-utils/src/acl/mod.rs @@ -58,7 +58,7 @@ pub const ALLOWED_COMMANDS_FILE_NAME: &str = "allowed-commands.json"; /// the value is set to the config's directory pub const REMOVE_UNUSED_COMMANDS_ENV_VAR: &str = "REMOVE_UNUSED_COMMANDS"; -#[cfg(feature = "build")] +#[cfg(any(feature = "build", feature = "build-2"))] pub mod build; pub mod capability; pub mod identifier; @@ -104,7 +104,7 @@ pub enum Error { CreateDir(std::io::Error, PathBuf), /// [`cargo_metadata`] was not able to complete successfully - #[cfg(feature = "build")] + #[cfg(any(feature = "build", feature = "build-2"))] #[error("failed to execute: {0}")] Metadata(#[from] ::cargo_metadata::Error), @@ -460,7 +460,7 @@ mod tests { } } -#[cfg(feature = "build")] +#[cfg(any(feature = "build", feature = "build-2"))] mod build_ { use std::convert::identity; diff --git a/crates/tauri-utils/src/acl/resolved.rs b/crates/tauri-utils/src/acl/resolved.rs index 941019822a00..8aa4322f5640 100644 --- a/crates/tauri-utils/src/acl/resolved.rs +++ b/crates/tauri-utils/src/acl/resolved.rs @@ -438,7 +438,7 @@ fn display_perm_key(prefix: &str) -> &str { } } -#[cfg(feature = "build")] +#[cfg(any(feature = "build", feature = "build-2"))] mod build { use proc_macro2::TokenStream; use quote::{quote, ToTokens, TokenStreamExt}; diff --git a/crates/tauri-utils/src/acl/value.rs b/crates/tauri-utils/src/acl/value.rs index 34c7efc488a6..24ac91eb7382 100644 --- a/crates/tauri-utils/src/acl/value.rs +++ b/crates/tauri-utils/src/acl/value.rs @@ -145,7 +145,7 @@ impl From for Value { } } -#[cfg(feature = "build")] +#[cfg(any(feature = "build", feature = "build-2"))] mod build { use std::convert::identity; diff --git a/crates/tauri-utils/src/config.rs b/crates/tauri-utils/src/config.rs index 9ce5304969d6..19035d11af58 100644 --- a/crates/tauri-utils/src/config.rs +++ b/crates/tauri-utils/src/config.rs @@ -3354,7 +3354,7 @@ pub struct PluginConfig(pub HashMap); /// This allows for a build script to output the values in a `Config` to a `TokenStream`, which can /// then be consumed by another crate. Useful for passing a config to both the build script and the /// application using tauri while only parsing it once (in the build script). -#[cfg(feature = "build")] +#[cfg(any(feature = "build", feature = "build-2"))] mod build { use super::*; use crate::{literal_struct, tokens::*}; diff --git a/crates/tauri-utils/src/html.rs b/crates/tauri-utils/src/html.rs index 958ce597832f..bc2aaf373c10 100644 --- a/crates/tauri-utils/src/html.rs +++ b/crates/tauri-utils/src/html.rs @@ -281,6 +281,7 @@ pub fn inline_isolation(document: &NodeRef, dir: &Path) { } } +// TODO: Verify this, this is not found in the HTML spec, see https://github.com/tauri-apps/tauri/pull/14265#discussion_r2415396842 /// Normalize line endings in script content to match what the browser uses for CSP hashing. /// /// According to the HTML spec, browsers normalize: @@ -315,6 +316,13 @@ pub fn normalize_script_for_csp(input: &[u8]) -> Vec { #[cfg(test)] mod tests { + use std::io::Write; + + use super::*; + use crate::{ + assets::{SCRIPT_NONCE_TOKEN, STYLE_NONCE_TOKEN}, + config, + }; #[test] fn csp() { @@ -322,12 +330,14 @@ mod tests { "".to_string(), "".to_string(), ]; + for html in htmls { - let document = super::parse(html); + let document = parse(html); let csp = "csp-string"; - super::inject_csp(&document, csp); + inject_csp(&document, csp); + assert_eq!( - document.to_string(), + String::from_utf8(serialize_node(&document)).unwrap(), format!( r#""#, ) @@ -336,12 +346,97 @@ mod tests { } #[test] - fn normalize_script_for_csp() { + fn normalize_script_for_csp_test() { let js = "// Copyright 2019-2024 Tauri Programme within The Commons Conservancy\r// SPDX-License-Identifier: Apache-2.0\n// SPDX-License-Identifier: MIT\r\n\r\nwindow.__TAURI_ISOLATION_HOOK__ = (payload, options) => {\r\n return payload\r\n}\r\n"; let expected = "// Copyright 2019-2024 Tauri Programme within The Commons Conservancy\n// SPDX-License-Identifier: Apache-2.0\n// SPDX-License-Identifier: MIT\n\nwindow.__TAURI_ISOLATION_HOOK__ = (payload, options) => {\n return payload\n}\n"; + + assert_eq!(normalize_script_for_csp(js.as_bytes()), expected.as_bytes()) + } + + #[test] + fn parse_and_serialize_roundtrips() { + let htmls = [ + "Test

Hello

", + "", + ]; + + for html in htmls { + let parsed = parse(html.to_string()); + let serialized = serialize_node(&parsed); + let result = String::from_utf8(serialized).unwrap(); + + assert_eq!(result, html); + } + } + + #[test] + fn inject_nonce_to_scripts() { + let html = r#""#; + + let document = parse(html.to_string()); + inject_nonce_token(&document, &config::DisabledCspModificationKind::Flag(false)); + + assert_eq!( + String::from_utf8(serialize_node(&document)).unwrap(), + format!( + r#""# + ) + ); + } + + #[test] + fn inject_nonce_to_styles() { + let html = r#""#; + + let document = parse(html.to_string()); + inject_nonce_token(&document, &config::DisabledCspModificationKind::Flag(false)); + + assert_eq!( + String::from_utf8(serialize_node(&document)).unwrap(), + format!( + r#""# + ) + ); + } + + #[test] + fn inject_nonce_skips_existing() { + let html = r#""#; + + let document = parse(html.to_string()); + inject_nonce_token(&document, &config::DisabledCspModificationKind::Flag(false)); + + assert_eq!(String::from_utf8(serialize_node(&document)).unwrap(), html); + } + + #[test] + fn inject_nonce_respects_disabled_modification() { + let html = r#""#; + + let document = parse(html.to_string()); + inject_nonce_token(&document, &config::DisabledCspModificationKind::Flag(true)); + assert_eq!( - super::normalize_script_for_csp(js.as_bytes()), - expected.as_bytes() - ) + String::from_utf8(serialize_node(&document)).unwrap(), + r#""# + ); + } + + #[test] + fn inline_isolation_replaces_src_with_content() { + let temp_dir = tempfile::tempdir().unwrap(); + let mut file = tempfile::NamedTempFile::with_suffix_in(".js", &temp_dir).unwrap(); + file.write_all(b"console.log('test');").unwrap(); + let file_name = file.path().file_name().unwrap().to_str().unwrap(); + + let html = + format!(r#""#); + let document = parse(html); + inline_isolation(&document, temp_dir.path()); + + assert_eq!( + String::from_utf8(serialize_node(&document)).unwrap(), + r#""# + ); } } diff --git a/crates/tauri-utils/src/html2.rs b/crates/tauri-utils/src/html2.rs new file mode 100644 index 000000000000..7f591dc2788d --- /dev/null +++ b/crates/tauri-utils/src/html2.rs @@ -0,0 +1,335 @@ +// Copyright 2019-2024 Tauri Programme within The Commons Conservancy +// SPDX-License-Identifier: Apache-2.0 +// SPDX-License-Identifier: MIT + +//! The module to process HTML in Tauri. +//! +//! # Stability +//! +//! This is utility used in Tauri internally and not considered part of the stable API. +//! If you use it, note that it may include breaking changes in the future. + +use dom_query::NodeRef; + +use crate::{ + assets::{SCRIPT_NONCE_TOKEN, STYLE_NONCE_TOKEN}, + config::DisabledCspModificationKind, +}; + +/// # Stability +/// +/// This dependency might receive updates in minor releases. +pub use dom_query::Document; + +/// Serializes the document to HTML. +/// +/// # Stability +/// +/// This dependency [`dom_query`] for [`Document`] might receive updates in minor releases. +pub fn serialize_doc(document: &Document) -> Vec { + document.html().as_bytes().to_vec() +} + +/// Parses the given HTML string. +/// +/// # Stability +/// +/// This dependency [`dom_query`] for [`Document`] might receive updates in minor releases. +pub fn parse_doc(html: String) -> Document { + Document::from(html) +} + +fn ensure_head(document: &Document) -> NodeRef<'_> { + document.head().unwrap_or_else(|| { + let html = document.html_root(); + let head = document.tree.new_element("head"); + html.prepend_child(&head); + head + }) +} + +fn inject_nonce(document: &Document, selector: &str, token: &str) { + let elements = document.select(selector); + for elem in elements.nodes() { + // if the node already has the `nonce` attribute, skip it + if elem.attr("nonce").is_some() { + continue; + } + elem.set_attr("nonce", token); + } +} + +/// Inject nonce tokens to all scripts and styles. +/// +/// # Stability +/// +/// This dependency [`dom_query`] for [`Document`] might receive updates in minor releases. +pub fn inject_nonce_token( + document: &Document, + dangerous_disable_asset_csp_modification: &DisabledCspModificationKind, +) { + if dangerous_disable_asset_csp_modification.can_modify("script-src") { + inject_nonce(document, "script[src^='http']", SCRIPT_NONCE_TOKEN); + } + if dangerous_disable_asset_csp_modification.can_modify("style-src") { + inject_nonce(document, "style", STYLE_NONCE_TOKEN); + } +} + +/// Injects a content security policy to the HTML. +/// +/// # Stability +/// +/// This dependency [`dom_query`] for [`Document`] might receive updates in minor releases. +pub fn inject_csp(document: &Document, csp: &str) { + let head = ensure_head(document); + let meta_tag = document.tree.new_element("meta"); + meta_tag.set_attr("http-equiv", "Content-Security-Policy"); + meta_tag.set_attr("content", csp); + head.append_child(&meta_tag); +} + +/// Injects a content security policy to the HTML. +/// +/// # Stability +/// +/// This dependency [`dom_query`] for [`Document`] might receive updates in minor releases. +pub fn append_script_to_head(document: &Document, script: &str) { + let head = ensure_head(document); + let script_tag = document.tree.new_element("script"); + script_tag.set_text(script); + head.prepend_child(&script_tag); +} + +/// Injects the Isolation JavaScript to a codegen time document. +/// +/// Note: This function is not considered part of the stable API. +/// +/// # Stability +/// +/// This dependency [`dom_query`] for [`Document`] might receive updates in minor releases. +#[cfg(feature = "isolation")] +pub fn inject_codegen_isolation_script(document: &Document) { + use crate::pattern::isolation::IsolationJavascriptCodegen; + use serialize_to_javascript::DefaultTemplate; + + let head = ensure_head(document); + + let script_content = IsolationJavascriptCodegen {} + .render_default(&Default::default()) + .expect("unable to render codegen isolation script template") + .into_string(); + + let script_tag = document.tree.new_element("script"); + script_tag.set_attr("nonce", SCRIPT_NONCE_TOKEN); + script_tag.set_text(script_content); + + head.prepend_child(&script_tag); +} + +/// Temporary workaround for Windows not allowing requests +/// +/// Note: this does not prevent path traversal due to the isolation application expectation that it +/// is secure. +/// +/// # Stability +/// +/// This dependency [`dom_query`] for [`Document`] might receive updates in minor releases. +#[cfg(feature = "isolation")] +pub fn inline_isolation(document: &Document, dir: &std::path::Path) { + let scripts = document.select("script[src]"); + + for script in scripts.nodes() { + let src = match script.attr("src") { + Some(s) => s.to_string(), + None => continue, + }; + + let mut path = std::path::PathBuf::from(src); + if path.has_root() { + path = path + .strip_prefix("/") + .expect("Tauri \"Isolation\" Pattern only supports relative or absolute (`/`) paths.") + .into(); + } + + let file = std::fs::read_to_string(dir.join(path)).expect("unable to find isolation file"); + + script.set_text(file); + script.remove_attr("src"); + } +} + +// TODO: Verify this, this is not found in the HTML spec, see https://github.com/tauri-apps/tauri/pull/14265#discussion_r2415396842 +/// Normalize line endings in script content to match what the browser uses for CSP hashing. +/// +/// According to the HTML spec, browsers normalize: +/// - `\r\n` → `\n` +/// - `\r` → `\n` +pub fn normalize_script_for_csp(input: &[u8]) -> Vec { + let mut output = Vec::with_capacity(input.len()); + + let mut i = 0; + while i < input.len() { + match input[i] { + b'\r' => { + if i + 1 < input.len() && input[i + 1] == b'\n' { + // CRLF → LF + output.push(b'\n'); + i += 2; + } else { + // Lone CR → LF + output.push(b'\n'); + i += 1; + } + } + _ => { + output.push(input[i]); + i += 1; + } + } + } + + output +} + +#[cfg(test)] +mod tests { + use super::*; + use crate::{ + assets::{SCRIPT_NONCE_TOKEN, STYLE_NONCE_TOKEN}, + config, + }; + + #[test] + fn csp() { + let htmls = vec![ + "".to_string(), + "".to_string(), + ]; + + for html in htmls { + let document = parse_doc(html); + let csp = "csp-string"; + inject_csp(&document, csp); + + assert_eq!( + String::from_utf8(serialize_doc(&document)).unwrap(), + format!( + r#""# + ) + ); + } + } + + #[test] + fn normalize_script_for_csp_test() { + let js = "// Copyright 2019-2024 Tauri Programme within The Commons Conservancy\r// SPDX-License-Identifier: Apache-2.0\n// SPDX-License-Identifier: MIT\r\n\r\nwindow.__TAURI_ISOLATION_HOOK__ = (payload, options) => {\r\n return payload\r\n}\r\n"; + let expected = "// Copyright 2019-2024 Tauri Programme within The Commons Conservancy\n// SPDX-License-Identifier: Apache-2.0\n// SPDX-License-Identifier: MIT\n\nwindow.__TAURI_ISOLATION_HOOK__ = (payload, options) => {\n return payload\n}\n"; + + assert_eq!(normalize_script_for_csp(js.as_bytes()), expected.as_bytes()) + } + + #[test] + fn parse_and_serialize_roundtrips() { + let htmls = [ + "Test

Hello

", + "", + ]; + + for html in htmls { + let parsed = parse_doc(html.to_string()); + let serialized = serialize_doc(&parsed); + let result = String::from_utf8(serialized).unwrap(); + + assert_eq!(result, html); + } + } + + #[test] + fn inject_nonce_to_scripts() { + let html = r#""#; + + let document = parse_doc(html.to_string()); + inject_nonce_token(&document, &config::DisabledCspModificationKind::Flag(false)); + + assert_eq!( + String::from_utf8(serialize_doc(&document)).unwrap(), + format!( + r#""# + ) + ); + } + + #[test] + fn inject_nonce_to_styles() { + let html = r#""#; + + let document = parse_doc(html.to_string()); + inject_nonce_token(&document, &config::DisabledCspModificationKind::Flag(false)); + + assert_eq!( + String::from_utf8(serialize_doc(&document)).unwrap(), + format!( + r#""# + ) + ); + } + + #[test] + fn append_script_to_head_test() { + let html = r#""#; + + let document = parse_doc(html.to_string()); + append_script_to_head(&document, r#"console.log('Test')"#); + + assert_eq!( + String::from_utf8(serialize_doc(&document)).unwrap(), + format!(r#""#) + ); + } + + #[test] + fn inject_nonce_skips_existing() { + let html = r#""#; + + let document = parse_doc(html.to_string()); + inject_nonce_token(&document, &config::DisabledCspModificationKind::Flag(false)); + + assert_eq!(String::from_utf8(serialize_doc(&document)).unwrap(), html); + } + + #[test] + fn inject_nonce_respects_disabled_modification() { + let html = r#""#; + + let document = parse_doc(html.to_string()); + inject_nonce_token(&document, &config::DisabledCspModificationKind::Flag(true)); + + assert_eq!( + String::from_utf8(serialize_doc(&document)).unwrap(), + r#""# + ); + } + + #[test] + #[cfg(feature = "isolation")] + fn inline_isolation_replaces_src_with_content() { + use std::io::Write; + + let temp_dir = tempfile::tempdir().unwrap(); + let mut file = tempfile::NamedTempFile::with_suffix_in(".js", &temp_dir).unwrap(); + file.write_all(b"console.log('test');").unwrap(); + let file_name = file.path().file_name().unwrap().to_str().unwrap(); + + let html = + format!(r#""#); + let document = parse_doc(html); + inline_isolation(&document, temp_dir.path()); + + assert_eq!( + String::from_utf8(serialize_doc(&document)).unwrap(), + r#""# + ); + } +} diff --git a/crates/tauri-utils/src/lib.rs b/crates/tauri-utils/src/lib.rs index 25e5a4f97db7..3b2a31ef59ac 100644 --- a/crates/tauri-utils/src/lib.rs +++ b/crates/tauri-utils/src/lib.rs @@ -26,6 +26,8 @@ pub mod config; pub mod config_v1; #[cfg(feature = "html-manipulation")] pub mod html; +#[cfg(feature = "html-manipulation-2")] +pub mod html2; pub mod io; pub mod mime_type; pub mod platform; @@ -33,10 +35,10 @@ pub mod plugin; /// Prepare application resources and sidecars. #[cfg(feature = "resources")] pub mod resources; -#[cfg(feature = "build")] +#[cfg(any(feature = "build", feature = "build-2"))] pub mod tokens; -#[cfg(feature = "build")] +#[cfg(any(feature = "build", feature = "build-2"))] pub mod build; /// Application pattern. diff --git a/crates/tauri-utils/src/platform.rs b/crates/tauri-utils/src/platform.rs index 4ce3d2fac403..a83201bdc4a5 100644 --- a/crates/tauri-utils/src/platform.rs +++ b/crates/tauri-utils/src/platform.rs @@ -369,7 +369,7 @@ pub fn bundle_type() -> Option { } } -#[cfg(feature = "build")] +#[cfg(any(feature = "build", feature = "build-2"))] mod build { use proc_macro2::TokenStream; use quote::{quote, ToTokens, TokenStreamExt}; diff --git a/crates/tauri-utils/src/plugin.rs b/crates/tauri-utils/src/plugin.rs index 8f178ca4163a..9fe35be2dfc4 100644 --- a/crates/tauri-utils/src/plugin.rs +++ b/crates/tauri-utils/src/plugin.rs @@ -3,10 +3,10 @@ // SPDX-License-Identifier: MIT //! Compile-time and runtime types for Tauri plugins. -#[cfg(feature = "build")] +#[cfg(any(feature = "build", feature = "build-2"))] pub use build::*; -#[cfg(feature = "build")] +#[cfg(any(feature = "build", feature = "build-2"))] mod build { use std::{ env::vars_os, diff --git a/crates/tauri/Cargo.toml b/crates/tauri/Cargo.toml index 9326713e5da1..071076fa442b 100644 --- a/crates/tauri/Cargo.toml +++ b/crates/tauri/Cargo.toml @@ -169,7 +169,7 @@ glob = "0.3" heck = "0.5" tauri-build = { path = "../tauri-build/", default-features = false, version = "2.5.6" } tauri-utils = { path = "../tauri-utils/", version = "2.8.3", features = [ - "build", + "build-2", ] } [dev-dependencies] @@ -222,7 +222,7 @@ macos-private-api = [ "tauri-runtime/macos-private-api", "tauri-runtime-wry?/macos-private-api", ] -webview-data-url = ["data-url", "tauri-utils/html-manipulation"] +webview-data-url = ["data-url", "tauri-utils/html-manipulation-2"] protocol-asset = ["http-range"] config-json5 = ["tauri-macros/config-json5"] config-toml = ["tauri-macros/config-toml"] diff --git a/crates/tauri/src/manager/webview.rs b/crates/tauri/src/manager/webview.rs index 98c470b76e60..4845f4fa6e99 100644 --- a/crates/tauri/src/manager/webview.rs +++ b/crates/tauri/src/manager/webview.rs @@ -460,9 +460,9 @@ impl WebviewManager { let html = String::from_utf8_lossy(&body).into_owned(); // naive way to check if it's an html if html.contains('<') && html.contains('>') { - let document = tauri_utils::html::parse(html); - tauri_utils::html::inject_csp(&document, &csp.to_string()); - url.set_path(&format!("{},{document}", mime::TEXT_HTML)); + let document = tauri_utils::html2::parse_doc(html); + tauri_utils::html2::inject_csp(&document, &csp.to_string()); + url.set_path(&format!("{},{}", mime::TEXT_HTML, document.html())); } } } diff --git a/crates/tests/acl/Cargo.toml b/crates/tests/acl/Cargo.toml index 0fe970b9990d..9e4f45b903b7 100644 --- a/crates/tests/acl/Cargo.toml +++ b/crates/tests/acl/Cargo.toml @@ -11,6 +11,6 @@ rust-version.workspace = true publish = false [dev-dependencies] -tauri-utils = { path = "../../tauri-utils/", features = ["build"] } +tauri-utils = { path = "../../tauri-utils/", features = ["build-2"] } serde_json = "1" insta = "1" From ea4af050aaf25288651a74f043ef543e1e5a3b6f Mon Sep 17 00:00:00 2001 From: "renovate[bot]" <29139614+renovate[bot]@users.noreply.github.com> Date: Wed, 25 Mar 2026 22:12:22 +0800 Subject: [PATCH 56/95] chore(deps): update dependency rollup to v4.60.0 (#15154) --- packages/api/package.json | 2 +- pnpm-lock.yaml | 230 +++++++++++++++++++------------------- 2 files changed, 116 insertions(+), 116 deletions(-) diff --git a/packages/api/package.json b/packages/api/package.json index f4e27d121c33..3f4c5a1ecd42 100644 --- a/packages/api/package.json +++ b/packages/api/package.json @@ -55,7 +55,7 @@ "eslint-plugin-security": "4.0.0", "fast-glob": "3.3.3", "globals": "^17.4.0", - "rollup": "4.59.1", + "rollup": "4.60.0", "tslib": "^2.8.1", "typescript": "^5.9.3", "typescript-eslint": "^8.56.1" diff --git a/pnpm-lock.yaml b/pnpm-lock.yaml index 72af631ffd8f..07556356ac4b 100644 --- a/pnpm-lock.yaml +++ b/pnpm-lock.yaml @@ -57,10 +57,10 @@ importers: version: 10.0.1(eslint@10.0.2(jiti@2.6.1)) '@rollup/plugin-terser': specifier: 1.0.0 - version: 1.0.0(rollup@4.59.1) + version: 1.0.0(rollup@4.60.0) '@rollup/plugin-typescript': specifier: 12.3.0 - version: 12.3.0(rollup@4.59.1)(tslib@2.8.1)(typescript@5.9.3) + version: 12.3.0(rollup@4.60.0)(tslib@2.8.1)(typescript@5.9.3) '@types/eslint': specifier: ^9.6.1 version: 9.6.1 @@ -83,8 +83,8 @@ importers: specifier: ^17.4.0 version: 17.4.0 rollup: - specifier: 4.59.1 - version: 4.59.1 + specifier: 4.60.0 + version: 4.60.0 tslib: specifier: ^2.8.1 version: 2.8.1 @@ -1398,141 +1398,141 @@ packages: rollup: optional: true - '@rollup/rollup-android-arm-eabi@4.59.1': - resolution: {integrity: sha512-xB0b51TB7IfDEzAojXahmr+gfA00uYVInJGgNNkeQG6RPnCPGr7udsylFLTubuIUSRE6FkcI1NElyRt83PP5oQ==} + '@rollup/rollup-android-arm-eabi@4.60.0': + resolution: {integrity: sha512-WOhNW9K8bR3kf4zLxbfg6Pxu2ybOUbB2AjMDHSQx86LIF4rH4Ft7vmMwNt0loO0eonglSNy4cpD3MKXXKQu0/A==} cpu: [arm] os: [android] - '@rollup/rollup-android-arm64@4.59.1': - resolution: {integrity: sha512-XOjPId0qwSDKHaIsdzHJtKCxX0+nH8MhBwvrNsT7tVyKmdTx1jJ4XzN5RZXCdTzMpufLb+B8llTC0D8uCrLhcw==} + '@rollup/rollup-android-arm64@4.60.0': + resolution: {integrity: sha512-u6JHLll5QKRvjciE78bQXDmqRqNs5M/3GVqZeMwvmjaNODJih/WIrJlFVEihvV0MiYFmd+ZyPr9wxOVbPAG2Iw==} cpu: [arm64] os: [android] - '@rollup/rollup-darwin-arm64@4.59.1': - resolution: {integrity: sha512-vQuRd28p0gQpPrS6kppd8IrWmFo42U8Pz1XLRjSZXq5zCqyMDYFABT7/sywL11mO1EL10Qhh7MVPEwkG8GiBeg==} + '@rollup/rollup-darwin-arm64@4.60.0': + resolution: {integrity: sha512-qEF7CsKKzSRc20Ciu2Zw1wRrBz4g56F7r/vRwY430UPp/nt1x21Q/fpJ9N5l47WWvJlkNCPJz3QRVw008fi7yA==} cpu: [arm64] os: [darwin] - '@rollup/rollup-darwin-x64@4.59.1': - resolution: {integrity: sha512-x6VG6U29+Ivlnajrg1IHdzXeAwSoEHBFVO+CtC9Brugx6de712CUJobRUxsIA0KYrQvCmzNrMPFTT1A4CCqNTg==} + '@rollup/rollup-darwin-x64@4.60.0': + resolution: {integrity: sha512-WADYozJ4QCnXCH4wPB+3FuGmDPoFseVCUrANmA5LWwGmC6FL14BWC7pcq+FstOZv3baGX65tZ378uT6WG8ynTw==} cpu: [x64] os: [darwin] - '@rollup/rollup-freebsd-arm64@4.59.1': - resolution: {integrity: sha512-Sgi0Uo6t1YCHJMNO3Y8+bm+SvOanUGkoZKn/VJPwYUe2kp31X5KnXmzKd/NjW8iA3gFcfNZ64zh14uOGrIllCQ==} + '@rollup/rollup-freebsd-arm64@4.60.0': + resolution: {integrity: sha512-6b8wGHJlDrGeSE3aH5mGNHBjA0TTkxdoNHik5EkvPHCt351XnigA4pS7Wsj/Eo9Y8RBU6f35cjN9SYmCFBtzxw==} cpu: [arm64] os: [freebsd] - '@rollup/rollup-freebsd-x64@4.59.1': - resolution: {integrity: sha512-AM4xnwEZwukdhk7laMWfzWu9JGSVnJd+Fowt6Fd7QW1nrf3h0Hp7Qx5881M4aqrUlKBCybOxz0jofvIIfl7C5g==} + '@rollup/rollup-freebsd-x64@4.60.0': + resolution: {integrity: sha512-h25Ga0t4jaylMB8M/JKAyrvvfxGRjnPQIR8lnCayyzEjEOx2EJIlIiMbhpWxDRKGKF8jbNH01NnN663dH638mA==} cpu: [x64] os: [freebsd] - '@rollup/rollup-linux-arm-gnueabihf@4.59.1': - resolution: {integrity: sha512-KUizqxpwaR2AZdAUsMWfL/C94pUu7TKpoPd88c8yFVixJ+l9hejkrwoK5Zj3wiNh65UeyryKnJyxL1b7yNqFQA==} + '@rollup/rollup-linux-arm-gnueabihf@4.60.0': + resolution: {integrity: sha512-RzeBwv0B3qtVBWtcuABtSuCzToo2IEAIQrcyB/b2zMvBWVbjo8bZDjACUpnaafaxhTw2W+imQbP2BD1usasK4g==} cpu: [arm] os: [linux] libc: [glibc] - '@rollup/rollup-linux-arm-musleabihf@4.59.1': - resolution: {integrity: sha512-MZoQ/am77ckJtZGFAtPucgUuJWiop3m2R3lw7tC0QCcbfl4DRhQUBUkHWCkcrT3pqy5Mzv5QQgY6Dmlba6iTWg==} + '@rollup/rollup-linux-arm-musleabihf@4.60.0': + resolution: {integrity: sha512-Sf7zusNI2CIU1HLzuu9Tc5YGAHEZs5Lu7N1ssJG4Tkw6e0MEsN7NdjUDDfGNHy2IU+ENyWT+L2obgWiguWibWQ==} cpu: [arm] os: [linux] libc: [musl] - '@rollup/rollup-linux-arm64-gnu@4.59.1': - resolution: {integrity: sha512-Sez95TP6xGjkWB1608EfhCX1gdGrO5wzyN99VqzRtC17x/1bhw5VU1V0GfKUwbW/Xr1J8mSasoFoJa6Y7aGGSA==} + '@rollup/rollup-linux-arm64-gnu@4.60.0': + resolution: {integrity: sha512-DX2x7CMcrJzsE91q7/O02IJQ5/aLkVtYFryqCjduJhUfGKG6yJV8hxaw8pZa93lLEpPTP/ohdN4wFz7yp/ry9A==} cpu: [arm64] os: [linux] libc: [glibc] - '@rollup/rollup-linux-arm64-musl@4.59.1': - resolution: {integrity: sha512-9Cs2Seq98LWNOJzR89EGTZoiP8EkZ9UbQhBlDgfAkM6asVna1xJ04W2CLYWDN/RpUgOjtQvcv8wQVi1t5oQazA==} + '@rollup/rollup-linux-arm64-musl@4.60.0': + resolution: {integrity: sha512-09EL+yFVbJZlhcQfShpswwRZ0Rg+z/CsSELFCnPt3iK+iqwGsI4zht3secj5vLEs957QvFFXnzAT0FFPIxSrkQ==} cpu: [arm64] os: [linux] libc: [musl] - '@rollup/rollup-linux-loong64-gnu@4.59.1': - resolution: {integrity: sha512-n9yqttftgFy7IrNEnHy1bOp6B4OSe8mJDiPkT7EqlM9FnKOwUMnCK62ixW0Kd9Clw0/wgvh8+SqaDXMFvw3KqQ==} + '@rollup/rollup-linux-loong64-gnu@4.60.0': + resolution: {integrity: sha512-i9IcCMPr3EXm8EQg5jnja0Zyc1iFxJjZWlb4wr7U2Wx/GrddOuEafxRdMPRYVaXjgbhvqalp6np07hN1w9kAKw==} cpu: [loong64] os: [linux] libc: [glibc] - '@rollup/rollup-linux-loong64-musl@4.59.1': - resolution: {integrity: sha512-SfpNXDzVTqs/riak4xXcLpq5gIQWsqGWMhN1AGRQKB4qGSs4r0sEs3ervXPcE1O9RsQ5bm8Muz6zmQpQnPss1g==} + '@rollup/rollup-linux-loong64-musl@4.60.0': + resolution: {integrity: sha512-DGzdJK9kyJ+B78MCkWeGnpXJ91tK/iKA6HwHxF4TAlPIY7GXEvMe8hBFRgdrR9Ly4qebR/7gfUs9y2IoaVEyog==} cpu: [loong64] os: [linux] libc: [musl] - '@rollup/rollup-linux-ppc64-gnu@4.59.1': - resolution: {integrity: sha512-LjaChED0wQnjKZU+tsmGbN+9nN1XhaWUkAlSbTdhpEseCS4a15f/Q8xC2BN4GDKRzhhLZpYtJBZr2NZhR0jvNw==} + '@rollup/rollup-linux-ppc64-gnu@4.60.0': + resolution: {integrity: sha512-RwpnLsqC8qbS8z1H1AxBA1H6qknR4YpPR9w2XX0vo2Sz10miu57PkNcnHVaZkbqyw/kUWfKMI73jhmfi9BRMUQ==} cpu: [ppc64] os: [linux] libc: [glibc] - '@rollup/rollup-linux-ppc64-musl@4.59.1': - resolution: {integrity: sha512-ojW7iTJSIs4pwB2xV6QXGwNyDctvXOivYllttuPbXguuKDX5vwpqYJsHc6D2LZzjDGHML414Tuj3LvVPe1CT1A==} + '@rollup/rollup-linux-ppc64-musl@4.60.0': + resolution: {integrity: sha512-Z8pPf54Ly3aqtdWC3G4rFigZgNvd+qJlOE52fmko3KST9SoGfAdSRCwyoyG05q1HrrAblLbk1/PSIV+80/pxLg==} cpu: [ppc64] os: [linux] libc: [musl] - '@rollup/rollup-linux-riscv64-gnu@4.59.1': - resolution: {integrity: sha512-FP+Q6WTcxxvsr0wQczhSE+tOZvFPV8A/mUE6mhZYFW9/eea/y/XqAgRoLLMuE9Cz0hfX5bi7p116IWoB+P237A==} + '@rollup/rollup-linux-riscv64-gnu@4.60.0': + resolution: {integrity: sha512-3a3qQustp3COCGvnP4SvrMHnPQ9d1vzCakQVRTliaz8cIp/wULGjiGpbcqrkv0WrHTEp8bQD/B3HBjzujVWLOA==} cpu: [riscv64] os: [linux] libc: [glibc] - '@rollup/rollup-linux-riscv64-musl@4.59.1': - resolution: {integrity: sha512-L1uD9b/Ig8Z+rn1KttCJjwhN1FgjRMBKsPaBsDKkfUl7GfFq71pU4vWCnpOsGljycFEbkHWARZLf4lMYg3WOLw==} + '@rollup/rollup-linux-riscv64-musl@4.60.0': + resolution: {integrity: sha512-pjZDsVH/1VsghMJ2/kAaxt6dL0psT6ZexQVrijczOf+PeP2BUqTHYejk3l6TlPRydggINOeNRhvpLa0AYpCWSQ==} cpu: [riscv64] os: [linux] libc: [musl] - '@rollup/rollup-linux-s390x-gnu@4.59.1': - resolution: {integrity: sha512-EZc9NGTk/oSUzzOD4nYY4gIjteo2M3CiozX6t1IXGCOdgxJTlVu/7EdPeiqeHPSIrxkLhavqpBAUCfvC6vBOug==} + '@rollup/rollup-linux-s390x-gnu@4.60.0': + resolution: {integrity: sha512-3ObQs0BhvPgiUVZrN7gqCSvmFuMWvWvsjG5ayJ3Lraqv+2KhOsp+pUbigqbeWqueGIsnn+09HBw27rJ+gYK4VQ==} cpu: [s390x] os: [linux] libc: [glibc] - '@rollup/rollup-linux-x64-gnu@4.59.1': - resolution: {integrity: sha512-NQ9KyU1Anuy59L8+HHOKM++CoUxrQWrZWXRik4BJFm+7i5NP6q/SW43xIBr80zzt+PDBJ7LeNmloQGfa0JGk0w==} + '@rollup/rollup-linux-x64-gnu@4.60.0': + resolution: {integrity: sha512-EtylprDtQPdS5rXvAayrNDYoJhIz1/vzN2fEubo3yLE7tfAw+948dO0g4M0vkTVFhKojnF+n6C8bDNe+gDRdTg==} cpu: [x64] os: [linux] libc: [glibc] - '@rollup/rollup-linux-x64-musl@4.59.1': - resolution: {integrity: sha512-GZkLk2t6naywsveSFBsEb0PLU+JC9ggVjbndsbG20VPhar6D1gkMfCx4NfP9owpovBXTN+eRdqGSkDGIxPHhmQ==} + '@rollup/rollup-linux-x64-musl@4.60.0': + resolution: {integrity: sha512-k09oiRCi/bHU9UVFqD17r3eJR9bn03TyKraCrlz5ULFJGdJGi7VOmm9jl44vOJvRJ6P7WuBi/s2A97LxxHGIdw==} cpu: [x64] os: [linux] libc: [musl] - '@rollup/rollup-openbsd-x64@4.59.1': - resolution: {integrity: sha512-1hjG9Jpl2KDOetr64iQd8AZAEjkDUUK5RbDkYWsViYLC1op1oNzdjMJeFiofcGhqbNTaY2kfgqowE7DILifsrA==} + '@rollup/rollup-openbsd-x64@4.60.0': + resolution: {integrity: sha512-1o/0/pIhozoSaDJoDcec+IVLbnRtQmHwPV730+AOD29lHEEo4F5BEUB24H0OBdhbBBDwIOSuf7vgg0Ywxdfiiw==} cpu: [x64] os: [openbsd] - '@rollup/rollup-openharmony-arm64@4.59.1': - resolution: {integrity: sha512-ARoKfflk0SiiYm3r1fmF73K/yB+PThmOwfWCk1sr7x/k9dc3uGLWuEE9if+Pw21el8MSpp3TMnG5vLNsJ/MMGQ==} + '@rollup/rollup-openharmony-arm64@4.60.0': + resolution: {integrity: sha512-pESDkos/PDzYwtyzB5p/UoNU/8fJo68vcXM9ZW2V0kjYayj1KaaUfi1NmTUTUpMn4UhU4gTuK8gIaFO4UGuMbA==} cpu: [arm64] os: [openharmony] - '@rollup/rollup-win32-arm64-msvc@4.59.1': - resolution: {integrity: sha512-oOST61G6VM45Mz2vdzWMr1s2slI7y9LqxEV5fCoWi2MDONmMvgsJVHSXxce/I2xOSZPTZ47nDPOl1tkwKWSHcw==} + '@rollup/rollup-win32-arm64-msvc@4.60.0': + resolution: {integrity: sha512-hj1wFStD7B1YBeYmvY+lWXZ7ey73YGPcViMShYikqKT1GtstIKQAtfUI6yrzPjAy/O7pO0VLXGmUVWXQMaYgTQ==} cpu: [arm64] os: [win32] - '@rollup/rollup-win32-ia32-msvc@4.59.1': - resolution: {integrity: sha512-x5WgLi5dWpRz7WclKBGEF15LcWTh0ewrHM6Cq4A+WUbkysUMZNeqt05bwPonOQ3ihPS/WMhAZV5zB1DfnI4Sxg==} + '@rollup/rollup-win32-ia32-msvc@4.60.0': + resolution: {integrity: sha512-SyaIPFoxmUPlNDq5EHkTbiKzmSEmq/gOYFI/3HHJ8iS/v1mbugVa7dXUzcJGQfoytp9DJFLhHH4U3/eTy2Bq4w==} cpu: [ia32] os: [win32] - '@rollup/rollup-win32-x64-gnu@4.59.1': - resolution: {integrity: sha512-wS+zHAJRVP5zOL0e+a3V3E/NTEwM2HEvvNKoDy5Xcfs0o8lljxn+EAFPkUsxihBdmDq1JWzXmmB9cbssCPdxxw==} + '@rollup/rollup-win32-x64-gnu@4.60.0': + resolution: {integrity: sha512-RdcryEfzZr+lAr5kRm2ucN9aVlCCa2QNq4hXelZxb8GG0NJSazq44Z3PCCc8wISRuCVnGs0lQJVX5Vp6fKA+IA==} cpu: [x64] os: [win32] - '@rollup/rollup-win32-x64-msvc@4.59.1': - resolution: {integrity: sha512-rhHyrMeLpErT/C7BxcEsU4COHQUzHyrPYW5tOZUeUhziNtRuYxmDWvqQqzpuUt8xpOgmbKa1btGXfnA/ANVO+g==} + '@rollup/rollup-win32-x64-msvc@4.60.0': + resolution: {integrity: sha512-PrsWNQ8BuE00O3Xsx3ALh2Df8fAj9+cvvX9AIA6o4KpATR98c9mud4XtDWVvsEuyia5U4tVSTKygawyJkjm60w==} cpu: [x64] os: [win32] @@ -2372,8 +2372,8 @@ packages: engines: {node: ^20.19.0 || >=22.12.0} hasBin: true - rollup@4.59.1: - resolution: {integrity: sha512-iZKH8BeoCwTCBTZBZWQQMreekd4mdomwdjIQ40GC1oZm6o+8PnNMIxFOiCsGMWeS8iDJ7KZcl7KwmKk/0HOQpA==} + rollup@4.60.0: + resolution: {integrity: sha512-yqjxruMGBQJ2gG4HtjZtAfXArHomazDHoFwFFmZZl0r7Pdo7qCIXKqKHZc8yeoMgzJJ+pO6pEEHa+V7uzWlrAQ==} engines: {node: '>=18.0.0', npm: '>=8.0.0'} hasBin: true @@ -3628,104 +3628,104 @@ snapshots: '@rolldown/pluginutils@1.0.0-rc.9': {} - '@rollup/plugin-terser@1.0.0(rollup@4.59.1)': + '@rollup/plugin-terser@1.0.0(rollup@4.60.0)': dependencies: serialize-javascript: 7.0.4 smob: 1.6.1 terser: 5.46.0 optionalDependencies: - rollup: 4.59.1 + rollup: 4.60.0 - '@rollup/plugin-typescript@12.3.0(rollup@4.59.1)(tslib@2.8.1)(typescript@5.9.3)': + '@rollup/plugin-typescript@12.3.0(rollup@4.60.0)(tslib@2.8.1)(typescript@5.9.3)': dependencies: - '@rollup/pluginutils': 5.3.0(rollup@4.59.1) + '@rollup/pluginutils': 5.3.0(rollup@4.60.0) resolve: 1.22.11 typescript: 5.9.3 optionalDependencies: - rollup: 4.59.1 + rollup: 4.60.0 tslib: 2.8.1 - '@rollup/pluginutils@5.3.0(rollup@4.59.1)': + '@rollup/pluginutils@5.3.0(rollup@4.60.0)': dependencies: '@types/estree': 1.0.8 estree-walker: 2.0.2 picomatch: 4.0.3 optionalDependencies: - rollup: 4.59.1 + rollup: 4.60.0 - '@rollup/rollup-android-arm-eabi@4.59.1': + '@rollup/rollup-android-arm-eabi@4.60.0': optional: true - '@rollup/rollup-android-arm64@4.59.1': + '@rollup/rollup-android-arm64@4.60.0': optional: true - '@rollup/rollup-darwin-arm64@4.59.1': + '@rollup/rollup-darwin-arm64@4.60.0': optional: true - '@rollup/rollup-darwin-x64@4.59.1': + '@rollup/rollup-darwin-x64@4.60.0': optional: true - '@rollup/rollup-freebsd-arm64@4.59.1': + '@rollup/rollup-freebsd-arm64@4.60.0': optional: true - '@rollup/rollup-freebsd-x64@4.59.1': + '@rollup/rollup-freebsd-x64@4.60.0': optional: true - '@rollup/rollup-linux-arm-gnueabihf@4.59.1': + '@rollup/rollup-linux-arm-gnueabihf@4.60.0': optional: true - '@rollup/rollup-linux-arm-musleabihf@4.59.1': + '@rollup/rollup-linux-arm-musleabihf@4.60.0': optional: true - '@rollup/rollup-linux-arm64-gnu@4.59.1': + '@rollup/rollup-linux-arm64-gnu@4.60.0': optional: true - '@rollup/rollup-linux-arm64-musl@4.59.1': + '@rollup/rollup-linux-arm64-musl@4.60.0': optional: true - '@rollup/rollup-linux-loong64-gnu@4.59.1': + '@rollup/rollup-linux-loong64-gnu@4.60.0': optional: true - '@rollup/rollup-linux-loong64-musl@4.59.1': + '@rollup/rollup-linux-loong64-musl@4.60.0': optional: true - '@rollup/rollup-linux-ppc64-gnu@4.59.1': + '@rollup/rollup-linux-ppc64-gnu@4.60.0': optional: true - '@rollup/rollup-linux-ppc64-musl@4.59.1': + '@rollup/rollup-linux-ppc64-musl@4.60.0': optional: true - '@rollup/rollup-linux-riscv64-gnu@4.59.1': + '@rollup/rollup-linux-riscv64-gnu@4.60.0': optional: true - '@rollup/rollup-linux-riscv64-musl@4.59.1': + '@rollup/rollup-linux-riscv64-musl@4.60.0': optional: true - '@rollup/rollup-linux-s390x-gnu@4.59.1': + '@rollup/rollup-linux-s390x-gnu@4.60.0': optional: true - '@rollup/rollup-linux-x64-gnu@4.59.1': + '@rollup/rollup-linux-x64-gnu@4.60.0': optional: true - '@rollup/rollup-linux-x64-musl@4.59.1': + '@rollup/rollup-linux-x64-musl@4.60.0': optional: true - '@rollup/rollup-openbsd-x64@4.59.1': + '@rollup/rollup-openbsd-x64@4.60.0': optional: true - '@rollup/rollup-openharmony-arm64@4.59.1': + '@rollup/rollup-openharmony-arm64@4.60.0': optional: true - '@rollup/rollup-win32-arm64-msvc@4.59.1': + '@rollup/rollup-win32-arm64-msvc@4.60.0': optional: true - '@rollup/rollup-win32-ia32-msvc@4.59.1': + '@rollup/rollup-win32-ia32-msvc@4.60.0': optional: true - '@rollup/rollup-win32-x64-gnu@4.59.1': + '@rollup/rollup-win32-x64-gnu@4.60.0': optional: true - '@rollup/rollup-win32-x64-msvc@4.59.1': + '@rollup/rollup-win32-x64-msvc@4.60.0': optional: true '@sindresorhus/is@7.2.0': {} @@ -4636,35 +4636,35 @@ snapshots: '@rolldown/binding-win32-arm64-msvc': 1.0.0-rc.9 '@rolldown/binding-win32-x64-msvc': 1.0.0-rc.9 - rollup@4.59.1: + rollup@4.60.0: dependencies: '@types/estree': 1.0.8 optionalDependencies: - '@rollup/rollup-android-arm-eabi': 4.59.1 - '@rollup/rollup-android-arm64': 4.59.1 - '@rollup/rollup-darwin-arm64': 4.59.1 - '@rollup/rollup-darwin-x64': 4.59.1 - '@rollup/rollup-freebsd-arm64': 4.59.1 - '@rollup/rollup-freebsd-x64': 4.59.1 - '@rollup/rollup-linux-arm-gnueabihf': 4.59.1 - '@rollup/rollup-linux-arm-musleabihf': 4.59.1 - '@rollup/rollup-linux-arm64-gnu': 4.59.1 - '@rollup/rollup-linux-arm64-musl': 4.59.1 - '@rollup/rollup-linux-loong64-gnu': 4.59.1 - '@rollup/rollup-linux-loong64-musl': 4.59.1 - '@rollup/rollup-linux-ppc64-gnu': 4.59.1 - '@rollup/rollup-linux-ppc64-musl': 4.59.1 - '@rollup/rollup-linux-riscv64-gnu': 4.59.1 - '@rollup/rollup-linux-riscv64-musl': 4.59.1 - '@rollup/rollup-linux-s390x-gnu': 4.59.1 - '@rollup/rollup-linux-x64-gnu': 4.59.1 - '@rollup/rollup-linux-x64-musl': 4.59.1 - '@rollup/rollup-openbsd-x64': 4.59.1 - '@rollup/rollup-openharmony-arm64': 4.59.1 - '@rollup/rollup-win32-arm64-msvc': 4.59.1 - '@rollup/rollup-win32-ia32-msvc': 4.59.1 - '@rollup/rollup-win32-x64-gnu': 4.59.1 - '@rollup/rollup-win32-x64-msvc': 4.59.1 + '@rollup/rollup-android-arm-eabi': 4.60.0 + '@rollup/rollup-android-arm64': 4.60.0 + '@rollup/rollup-darwin-arm64': 4.60.0 + '@rollup/rollup-darwin-x64': 4.60.0 + '@rollup/rollup-freebsd-arm64': 4.60.0 + '@rollup/rollup-freebsd-x64': 4.60.0 + '@rollup/rollup-linux-arm-gnueabihf': 4.60.0 + '@rollup/rollup-linux-arm-musleabihf': 4.60.0 + '@rollup/rollup-linux-arm64-gnu': 4.60.0 + '@rollup/rollup-linux-arm64-musl': 4.60.0 + '@rollup/rollup-linux-loong64-gnu': 4.60.0 + '@rollup/rollup-linux-loong64-musl': 4.60.0 + '@rollup/rollup-linux-ppc64-gnu': 4.60.0 + '@rollup/rollup-linux-ppc64-musl': 4.60.0 + '@rollup/rollup-linux-riscv64-gnu': 4.60.0 + '@rollup/rollup-linux-riscv64-musl': 4.60.0 + '@rollup/rollup-linux-s390x-gnu': 4.60.0 + '@rollup/rollup-linux-x64-gnu': 4.60.0 + '@rollup/rollup-linux-x64-musl': 4.60.0 + '@rollup/rollup-openbsd-x64': 4.60.0 + '@rollup/rollup-openharmony-arm64': 4.60.0 + '@rollup/rollup-win32-arm64-msvc': 4.60.0 + '@rollup/rollup-win32-ia32-msvc': 4.60.0 + '@rollup/rollup-win32-x64-gnu': 4.60.0 + '@rollup/rollup-win32-x64-msvc': 4.60.0 fsevents: 2.3.3 run-parallel@1.2.0: @@ -4886,7 +4886,7 @@ snapshots: fdir: 6.5.0(picomatch@4.0.3) picomatch: 4.0.3 postcss: 8.5.8 - rollup: 4.59.1 + rollup: 4.60.0 tinyglobby: 0.2.15 optionalDependencies: '@types/node': 24.11.0 From c2fcb7193eadf06be4cfe5f60483df1a5db886ac Mon Sep 17 00:00:00 2001 From: Tony <68118705+Legend-Master@users.noreply.github.com> Date: Thu, 26 Mar 2026 23:39:05 +0800 Subject: [PATCH 57/95] fea(wix): add minimum webview2 version support (#14793) * feat(wix): add minimum webview2 version option * Add change file * Format * Move comments inside `#if` block * add breaking change notes * Add deprecation to description schema * Merge remote-tracking branch 'upstream/dev' into wix-minimum-webview2-version * Merge branch 'dev' into wix-minimum-webview2-version --- .changes/wix-minimum-webview2-version.md | 12 ++++++ crates/tauri-bundler/src/bundle/settings.rs | 9 +++++ .../src/bundle/windows/msi/main.wxs | 40 +++++++++++++++---- .../src/bundle/windows/msi/mod.rs | 7 ++++ .../src/bundle/windows/nsis/mod.rs | 7 +++- crates/tauri-cli/config.schema.json | 12 +++++- crates/tauri-cli/src/helpers/config.rs | 1 + crates/tauri-cli/src/interface/rust.rs | 1 + .../schemas/config.schema.json | 12 +++++- crates/tauri-utils/src/config.rs | 12 ++++++ 10 files changed, 102 insertions(+), 11 deletions(-) create mode 100644 .changes/wix-minimum-webview2-version.md diff --git a/.changes/wix-minimum-webview2-version.md b/.changes/wix-minimum-webview2-version.md new file mode 100644 index 000000000000..2b34203f6467 --- /dev/null +++ b/.changes/wix-minimum-webview2-version.md @@ -0,0 +1,12 @@ +--- +"tauri-bundler": minor:feat +"tauri-cli": minor:feat +"@tauri-apps/cli": minor:feat +--- + +Added support for `minimumWebview2Version` option support for the MSI (Wix) installer, the old `bundle > windows > nsis > minimumWebview2Version` is now deprecated in favor of `bundle > windows > minimumWebview2Version` + +Notes: + +- For anyone relying on the `WVRTINSTALLED` `Property` tag in `main.wxs`, it is now renamed to `INSTALLED_WEBVIEW2_VERSION` +- For `tauri-bundler` lib users, the `WindowsSettings` now has a new field `minimum_webview2_version` which can be a breaking change diff --git a/crates/tauri-bundler/src/bundle/settings.rs b/crates/tauri-bundler/src/bundle/settings.rs index 5e2a81b38d4e..4b4804d1715b 100644 --- a/crates/tauri-bundler/src/bundle/settings.rs +++ b/crates/tauri-bundler/src/bundle/settings.rs @@ -532,6 +532,10 @@ pub struct NsisSettings { /// Try to ensure that the WebView2 version is equal to or newer than this version, /// if the user's WebView2 is older than this version, /// the installer will try to trigger a WebView2 update. + #[deprecated( + since = "2.8.0", + note = "Use `WindowsSettings::minimum_webview2_version` instead." + )] pub minimum_webview2_version: Option, } @@ -587,6 +591,10 @@ pub struct WindowsSettings { /// if you are on another platform and want to cross-compile and sign you will /// need to use another tool like `osslsigncode`. pub sign_command: Option, + /// Try to ensure that the WebView2 version is equal to or newer than this version, + /// if the user's WebView2 is older than this version, + /// the installer will try to trigger a WebView2 update. + pub minimum_webview2_version: Option, } impl WindowsSettings { @@ -612,6 +620,7 @@ mod _default { webview_install_mode: Default::default(), allow_downgrades: true, sign_command: None, + minimum_webview2_version: None, } } } diff --git a/crates/tauri-bundler/src/bundle/windows/msi/main.wxs b/crates/tauri-bundler/src/bundle/windows/msi/main.wxs index a08c3b2cc5dc..dec39dadb4bc 100644 --- a/crates/tauri-bundler/src/bundle/windows/msi/main.wxs +++ b/crates/tauri-bundler/src/bundle/windows/msi/main.wxs @@ -283,38 +283,62 @@ {{#if install_webview}} - - - + + + + {{#if download_bootstrapper}} + - + {{/if}} - {{#if webview2_bootstrapper_path}} + - + {{/if}} - {{#if webview2_installer_path}} + - + + + + {{/if}} + + {{#if minimum_webview2_version}} + + + + + + + + + + + + + {{/if}} diff --git a/crates/tauri-bundler/src/bundle/windows/msi/mod.rs b/crates/tauri-bundler/src/bundle/windows/msi/mod.rs index 4c00d8f333c0..ad0533601686 100644 --- a/crates/tauri-bundler/src/bundle/windows/msi/mod.rs +++ b/crates/tauri-bundler/src/bundle/windows/msi/mod.rs @@ -532,6 +532,13 @@ pub fn build_wix_app_installer( } } + if let Some(minimum_webview2_version) = &settings.windows().minimum_webview2_version { + data.insert( + "minimum_webview2_version", + to_json(minimum_webview2_version), + ); + } + if let Some(license) = settings.license_file() { if license.ends_with(".rtf") { data.insert("license", to_json(license)); diff --git a/crates/tauri-bundler/src/bundle/windows/nsis/mod.rs b/crates/tauri-bundler/src/bundle/windows/nsis/mod.rs index 5b7479a84e3c..21d15aa46e35 100644 --- a/crates/tauri-bundler/src/bundle/windows/nsis/mod.rs +++ b/crates/tauri-bundler/src/bundle/windows/nsis/mod.rs @@ -362,7 +362,12 @@ fn build_nsis_app_installer( if let Some(start_menu_folder) = &nsis.start_menu_folder { data.insert("start_menu_folder", to_json(start_menu_folder)); } - if let Some(minimum_webview2_version) = &nsis.minimum_webview2_version { + #[allow(deprecated)] + if let Some(minimum_webview2_version) = nsis + .minimum_webview2_version + .as_ref() + .or(settings.windows().minimum_webview2_version.as_ref()) + { data.insert( "minimum_webview2_version", to_json(minimum_webview2_version), diff --git a/crates/tauri-cli/config.schema.json b/crates/tauri-cli/config.schema.json index 6b76427aabb4..86bfe5d46b33 100644 --- a/crates/tauri-cli/config.schema.json +++ b/crates/tauri-cli/config.schema.json @@ -131,6 +131,7 @@ "allowDowngrades": true, "certificateThumbprint": null, "digestAlgorithm": null, + "minimumWebview2Version": null, "nsis": null, "signCommand": null, "timestampUrl": null, @@ -2225,6 +2226,7 @@ "allowDowngrades": true, "certificateThumbprint": null, "digestAlgorithm": null, + "minimumWebview2Version": null, "nsis": null, "signCommand": null, "timestampUrl": null, @@ -2667,6 +2669,13 @@ "default": true, "type": "boolean" }, + "minimumWebview2Version": { + "description": "Try to ensure that the WebView2 version is equal to or newer than this version,\n if the user's WebView2 is older than this version,\n the installer will try to trigger a WebView2 update.", + "type": [ + "string", + "null" + ] + }, "wix": { "description": "Configuration for the MSI generated with WiX.", "anyOf": [ @@ -3045,7 +3054,8 @@ ] }, "minimumWebview2Version": { - "description": "Try to ensure that the WebView2 version is equal to or newer than this version,\n if the user's WebView2 is older than this version,\n the installer will try to trigger a WebView2 update.", + "description": "Deprecated: use [`WindowsConfig::minimum_webview2_version`] (`bundle > windows > minimumWebview2Version`) instead.\n\n Try to ensure that the WebView2 version is equal to or newer than this version,\n if the user's WebView2 is older than this version,\n the installer will try to trigger a WebView2 update.", + "deprecated": true, "type": [ "string", "null" diff --git a/crates/tauri-cli/src/helpers/config.rs b/crates/tauri-cli/src/helpers/config.rs index ce1f11c5b3b6..f53d8c8693c5 100644 --- a/crates/tauri-cli/src/helpers/config.rs +++ b/crates/tauri-cli/src/helpers/config.rs @@ -117,6 +117,7 @@ pub fn nsis_settings(config: NsisConfig) -> tauri_bundler::NsisSettings { compression: config.compression, start_menu_folder: config.start_menu_folder, installer_hooks: config.installer_hooks, + #[allow(deprecated)] minimum_webview2_version: config.minimum_webview2_version, } } diff --git a/crates/tauri-cli/src/interface/rust.rs b/crates/tauri-cli/src/interface/rust.rs index 9bd46c585d00..e18e8308f444 100644 --- a/crates/tauri-cli/src/interface/rust.rs +++ b/crates/tauri-cli/src/interface/rust.rs @@ -1657,6 +1657,7 @@ fn tauri_config_to_bundle_settings( webview_install_mode: config.windows.webview_install_mode, allow_downgrades: config.windows.allow_downgrades, sign_command: config.windows.sign_command.map(custom_sign_settings), + minimum_webview2_version: config.windows.minimum_webview2_version, }, license: config.license.or_else(|| { settings diff --git a/crates/tauri-schema-generator/schemas/config.schema.json b/crates/tauri-schema-generator/schemas/config.schema.json index 6b76427aabb4..86bfe5d46b33 100644 --- a/crates/tauri-schema-generator/schemas/config.schema.json +++ b/crates/tauri-schema-generator/schemas/config.schema.json @@ -131,6 +131,7 @@ "allowDowngrades": true, "certificateThumbprint": null, "digestAlgorithm": null, + "minimumWebview2Version": null, "nsis": null, "signCommand": null, "timestampUrl": null, @@ -2225,6 +2226,7 @@ "allowDowngrades": true, "certificateThumbprint": null, "digestAlgorithm": null, + "minimumWebview2Version": null, "nsis": null, "signCommand": null, "timestampUrl": null, @@ -2667,6 +2669,13 @@ "default": true, "type": "boolean" }, + "minimumWebview2Version": { + "description": "Try to ensure that the WebView2 version is equal to or newer than this version,\n if the user's WebView2 is older than this version,\n the installer will try to trigger a WebView2 update.", + "type": [ + "string", + "null" + ] + }, "wix": { "description": "Configuration for the MSI generated with WiX.", "anyOf": [ @@ -3045,7 +3054,8 @@ ] }, "minimumWebview2Version": { - "description": "Try to ensure that the WebView2 version is equal to or newer than this version,\n if the user's WebView2 is older than this version,\n the installer will try to trigger a WebView2 update.", + "description": "Deprecated: use [`WindowsConfig::minimum_webview2_version`] (`bundle > windows > minimumWebview2Version`) instead.\n\n Try to ensure that the WebView2 version is equal to or newer than this version,\n if the user's WebView2 is older than this version,\n the installer will try to trigger a WebView2 update.", + "deprecated": true, "type": [ "string", "null" diff --git a/crates/tauri-utils/src/config.rs b/crates/tauri-utils/src/config.rs index 19035d11af58..2b6304069279 100644 --- a/crates/tauri-utils/src/config.rs +++ b/crates/tauri-utils/src/config.rs @@ -926,9 +926,15 @@ pub struct NsisConfig { /// ``` #[serde(alias = "installer-hooks")] pub installer_hooks: Option, + /// Deprecated: use [`WindowsConfig::minimum_webview2_version`] (`bundle > windows > minimumWebview2Version`) instead. + /// /// Try to ensure that the WebView2 version is equal to or newer than this version, /// if the user's WebView2 is older than this version, /// the installer will try to trigger a WebView2 update. + #[deprecated( + since = "2.10.0", + note = "Use `WindowsConfig::minimum_webview2_version` instead." + )] #[serde(alias = "minimum-webview2-version")] pub minimum_webview2_version: Option, } @@ -1043,6 +1049,11 @@ pub struct WindowsConfig { /// The default value of this flag is `true`. #[serde(default = "default_true", alias = "allow-downgrades")] pub allow_downgrades: bool, + /// Try to ensure that the WebView2 version is equal to or newer than this version, + /// if the user's WebView2 is older than this version, + /// the installer will try to trigger a WebView2 update. + #[serde(alias = "minimum-webview2-version")] + pub minimum_webview2_version: Option, /// Configuration for the MSI generated with WiX. pub wix: Option, /// Configuration for the installer generated with NSIS. @@ -1067,6 +1078,7 @@ impl Default for WindowsConfig { tsp: false, webview_install_mode: Default::default(), allow_downgrades: true, + minimum_webview2_version: None, wix: None, nsis: None, sign_command: None, From 588b3833f2d29dfd72dab6da3a3520a3ac0c6117 Mon Sep 17 00:00:00 2001 From: Lucas Fernandes Nogueira Date: Thu, 26 Mar 2026 13:58:58 -0300 Subject: [PATCH 58/95] feat(bundler): support Liquid Glass icons, closes #14207 (#14671) * feat(bundler): support Liquid Glass icons, closes #14207 the `icon` config now supports loading an Assets.car directly or a `.icon` (Icon Composer asset) that gets compiled into an Assets.car file * fmt * fix build * add version checks * fmt * fix icns fallback * fmt --- .changes/liquid-glass-icon.md | 5 + crates/tauri-bundler/src/bundle/macos/app.rs | 51 +++-- crates/tauri-bundler/src/bundle/macos/icon.rs | 211 +++++++++++++++++- crates/tauri-bundler/src/bundle/macos/ios.rs | 5 +- crates/tauri-bundler/src/bundle/settings.rs | 18 +- examples/.icons/AppIcon.icon/Assets/icon.png | Bin 0 -> 49979 bytes examples/.icons/AppIcon.icon/icon.json | 35 +++ examples/api/src-tauri/tauri.conf.json | 3 +- 8 files changed, 308 insertions(+), 20 deletions(-) create mode 100644 .changes/liquid-glass-icon.md create mode 100644 examples/.icons/AppIcon.icon/Assets/icon.png create mode 100644 examples/.icons/AppIcon.icon/icon.json diff --git a/.changes/liquid-glass-icon.md b/.changes/liquid-glass-icon.md new file mode 100644 index 000000000000..ab00b0fb3603 --- /dev/null +++ b/.changes/liquid-glass-icon.md @@ -0,0 +1,5 @@ +--- +"tauri-bundler": minor:feat +--- + +Added support to Liquid Glass icons. diff --git a/crates/tauri-bundler/src/bundle/macos/app.rs b/crates/tauri-bundler/src/bundle/macos/app.rs index c90f652d8405..5c6581fb6960 100644 --- a/crates/tauri-bundler/src/bundle/macos/app.rs +++ b/crates/tauri-bundler/src/bundle/macos/app.rs @@ -23,7 +23,7 @@ // files into the `Contents` directory of the bundle. use super::{ - icon::create_icns_file, + icon::{app_icon_name_from_assets_car, create_assets_car_file, create_icns_file}, sign::{notarize, notarize_auth, notarize_without_stapling, sign, SignTarget}, }; use crate::{ @@ -76,11 +76,19 @@ pub fn bundle_project(settings: &Settings) -> crate::Result> { let bin_dir = bundle_directory.join("MacOS"); let mut sign_paths = Vec::new(); - let bundle_icon_file: Option = - { create_icns_file(&resources_dir, settings).with_context(|| "Failed to create app icon")? }; + let bundle_icon_file = + create_icns_file(&resources_dir, settings).with_context(|| "Failed to create app icon")?; - create_info_plist(&bundle_directory, bundle_icon_file, settings) - .with_context(|| "Failed to create Info.plist")?; + let assets_car_file = create_assets_car_file(&resources_dir, settings) + .with_context(|| "Failed to create app Assets.car")?; + + create_info_plist( + &bundle_directory, + bundle_icon_file, + assets_car_file, + settings, + ) + .with_context(|| "Failed to create Info.plist")?; let framework_paths = copy_frameworks_to_bundle(&bundle_directory, settings) .with_context(|| "Failed to bundle frameworks")?; @@ -204,6 +212,7 @@ fn copy_custom_files_to_bundle(bundle_directory: &Path, settings: &Settings) -> fn create_info_plist( bundle_dir: &Path, bundle_icon_file: Option, + assets_car_file: Option, settings: &Settings, ) -> crate::Result<()> { let mut plist = plist::Dictionary::new(); @@ -213,17 +222,6 @@ fn create_info_plist( "CFBundleExecutable".into(), settings.main_binary_name()?.into(), ); - if let Some(path) = bundle_icon_file { - plist.insert( - "CFBundleIconFile".into(), - path - .file_name() - .expect("No file name") - .to_string_lossy() - .into_owned() - .into(), - ); - } plist.insert( "CFBundleIdentifier".into(), settings.bundle_identifier().into(), @@ -362,6 +360,27 @@ fn create_info_plist( ); } + if let Some(path) = bundle_icon_file { + plist.insert( + "CFBundleIconFile".into(), + path + .file_name() + .expect("No file name") + .to_string_lossy() + .into_owned() + .into(), + ); + } + + if let Some(assets_car_file) = assets_car_file { + if let Some(icon_name) = app_icon_name_from_assets_car(&assets_car_file) { + // only set CFBundleIconName for the Assets.car, CFBundleIconFile is the fallback icns file + plist.insert("CFBundleIconName".into(), icon_name.clone().into()); + } else { + log::warn!("Failed to get icon name from Assets.car file"); + } + } + if let Some(protocols) = settings.deep_link_protocols() { plist.insert( "CFBundleURLTypes".into(), diff --git a/crates/tauri-bundler/src/bundle/macos/icon.rs b/crates/tauri-bundler/src/bundle/macos/icon.rs index c226fb233b9c..69278ec052ac 100644 --- a/crates/tauri-bundler/src/bundle/macos/icon.rs +++ b/crates/tauri-bundler/src/bundle/macos/icon.rs @@ -4,13 +4,14 @@ // SPDX-License-Identifier: MIT use crate::bundle::Settings; -use crate::utils::{self, fs_utils}; +use crate::utils::{self, fs_utils, CommandExt}; use std::{ cmp::min, ffi::OsStr, fs::{self, File}, io::{self, BufWriter}, path::{Path, PathBuf}, + process::Command, }; use image::GenericImageView; @@ -63,6 +64,11 @@ pub fn create_icns_file(out_dir: &Path, settings: &Settings) -> crate::Result = vec![]; for icon_path in settings.icon_files() { let icon_path = icon_path?; + + if icon_path.extension().map_or(false, |ext| ext == "car") { + continue; + } + let icon = image::open(&icon_path)?; let density = if utils::is_retina(&icon_path) { 2 } else { 1 }; let (w, h) = icon.dimensions(); @@ -113,3 +119,206 @@ fn make_icns_image(img: image::DynamicImage) -> io::Result { }; icns::Image::from_data(pixel_format, img.width(), img.height(), img.into_bytes()) } + +/// Creates an Assets.car file from a .icon file if there are any in the settings. +/// Uses an existing Assets.car file if it exists in the settings. +/// Returns the path to the Assets.car file. +pub fn create_assets_car_file( + out_dir: &Path, + settings: &Settings, +) -> crate::Result> { + let Some(icons) = settings.icons() else { + return Ok(None); + }; + // If one of the icon files is already a CAR file, just use that. + let mut icon_composer_icon_path = None; + for icon in icons { + let icon_path = Path::new(&icon).to_path_buf(); + if icon_path.extension() == Some(OsStr::new("car")) { + let dest_path = out_dir.join("Assets.car"); + fs_utils::copy_file(&icon_path, &dest_path)?; + return Ok(Some(dest_path)); + } + + if icon_path.extension() == Some(OsStr::new("icon")) { + icon_composer_icon_path.replace(icon_path); + } + } + + let Some(icon_composer_icon_path) = icon_composer_icon_path else { + return Ok(None); + }; + + // Check actool version - must be >= 26 + if let Some(version) = get_actool_version() { + // Parse the major version number (before the dot) + let major_version: Option = version.split('.').next().and_then(|s| s.parse().ok()); + + if let Some(major) = major_version { + if major < 26 { + log::error!("actool version is less than 26, skipping Assets.car file creation. Please update Xcode to 26 or above and try again."); + return Ok(None); + } + } else { + // If we can't parse the version, return None to be safe + log::error!("failed to parse actool version, skipping Assets.car file creation"); + return Ok(None); + } + } else { + log::error!("failed to get actool version, skipping Assets.car file creation"); + // If we can't get the version, return None to be safe + return Ok(None); + } + + // Create a temporary directory for actool work + let temp_dir = tempfile::tempdir() + .map_err(|e| crate::Error::GenericError(format!("failed to create temp dir: {e}")))?; + + let icon_dest_path = temp_dir.path().join("Icon.icon"); + let output_path = temp_dir.path().join("out"); + + // Copy the input .icon directory to the temp directory + if icon_composer_icon_path.is_dir() { + fs_utils::copy_dir(&icon_composer_icon_path, &icon_dest_path)?; + } else { + return Err(crate::Error::GenericError(format!( + "{} must be a directory", + icon_composer_icon_path.display() + ))); + } + + // Create the output directory + fs::create_dir_all(&output_path)?; + + // Run actool command + let mut cmd = Command::new("actool"); + cmd.arg(&icon_dest_path); + cmd.arg("--compile"); + cmd.arg(&output_path); + cmd.arg("--output-format"); + cmd.arg("human-readable-text"); + cmd.arg("--notices"); + cmd.arg("--warnings"); + cmd.arg("--output-partial-info-plist"); + cmd.arg(output_path.join("assetcatalog_generated_info.plist")); + cmd.arg("--app-icon"); + cmd.arg("Icon"); + cmd.arg("--include-all-app-icons"); + cmd.arg("--accent-color"); + cmd.arg("AccentColor"); + cmd.arg("--enable-on-demand-resources"); + cmd.arg("NO"); + cmd.arg("--development-region"); + cmd.arg("en"); + cmd.arg("--target-device"); + cmd.arg("mac"); + cmd.arg("--minimum-deployment-target"); + cmd.arg("26.0"); + cmd.arg("--platform"); + cmd.arg("macosx"); + + cmd.output_ok()?; + + let assets_car_path = output_path.join("Assets.car"); + if !assets_car_path.exists() { + return Err(crate::Error::GenericError( + "actool did not generate Assets.car file".to_owned(), + )); + } + + // copy to out_dir + fs_utils::copy_file(&assets_car_path, &out_dir.join("Assets.car"))?; + + Ok(Some(out_dir.join("Assets.car"))) +} + +#[derive(serde::Deserialize)] +struct AssetsCarInfo { + #[serde(rename = "AssetType", default)] + asset_type: String, + #[serde(rename = "Name", default)] + name: String, +} + +pub fn app_icon_name_from_assets_car(assets_car_path: &Path) -> Option { + let Ok(output) = Command::new("assetutil") + .arg("--info") + .arg(assets_car_path) + .output_ok() + .inspect_err(|e| log::error!("Failed to get app icon name from Assets.car file: {e}")) + else { + return None; + }; + + let output = String::from_utf8(output.stdout).ok()?; + let assets_car_info: Vec = serde_json::from_str(&output) + .inspect_err(|e| log::error!("Failed to parse Assets.car file info: {e}")) + .ok()?; + assets_car_info + .iter() + .find(|info| info.asset_type == "Icon Image") + .map(|info| info.name.clone()) +} + +/// Returns the actool short bundle version by running `actool --version --output-format=human-readable-text`. +/// Returns `None` if the command fails or the output cannot be parsed. +pub fn get_actool_version() -> Option { + let Ok(output) = Command::new("actool") + .arg("--version") + .arg("--output-format=human-readable-text") + .output_ok() + .inspect_err(|e| log::error!("Failed to get actool version: {e}")) + else { + return None; + }; + + let output = String::from_utf8(output.stdout).ok()?; + parse_actool_version(&output) +} + +fn parse_actool_version(output: &str) -> Option { + // The output format is: + // /* com.apple.actool.version */ + // bundle-version: 24411 + // short-bundle-version: 26.1 + for line in output.lines() { + let line = line.trim(); + if let Some(version) = line.strip_prefix("short-bundle-version:") { + return Some(version.trim().to_string()); + } + } + + None +} + +#[cfg(test)] +mod tests { + use super::*; + + #[test] + fn test_parse_actool_version() { + let output = r#"/* com.apple.actool.version */ +some other line +bundle-version: 24411 +short-bundle-version: 26.1 +another line +"#; + + let version = parse_actool_version(output).expect("Failed to parse version"); + assert_eq!(version, "26.1"); + } + + #[test] + fn test_parse_actool_version_missing_fields() { + let output = r#"/* com.apple.actool.version */ +bundle-version: 24411 +"#; + + assert!(parse_actool_version(output).is_none()); + } + + #[test] + fn test_parse_actool_version_empty() { + assert!(parse_actool_version("").is_none()); + } +} diff --git a/crates/tauri-bundler/src/bundle/macos/ios.rs b/crates/tauri-bundler/src/bundle/macos/ios.rs index ac035127aad0..644f85027114 100644 --- a/crates/tauri-bundler/src/bundle/macos/ios.rs +++ b/crates/tauri-bundler/src/bundle/macos/ios.rs @@ -106,7 +106,10 @@ fn generate_icon_files(bundle_dir: &Path, settings: &Settings) -> crate::Result< // Fall back to non-PNG files for any missing sizes. for icon_path in settings.icon_files() { let icon_path = icon_path?; - if icon_path.extension() == Some(OsStr::new("png")) { + if icon_path + .extension() + .map_or(false, |ext| ext == "png" || ext == "car") + { continue; } else if icon_path.extension() == Some(OsStr::new("icns")) { let icon_family = icns::IconFamily::read(File::open(&icon_path)?)?; diff --git a/crates/tauri-bundler/src/bundle/settings.rs b/crates/tauri-bundler/src/bundle/settings.rs index 4b4804d1715b..d94708dae5ce 100644 --- a/crates/tauri-bundler/src/bundle/settings.rs +++ b/crates/tauri-bundler/src/bundle/settings.rs @@ -804,6 +804,8 @@ pub struct Settings { local_tools_directory: Option, /// the bundle settings. bundle_settings: BundleSettings, + /// Same as `bundle_settings.icon`, but without the .icon directory. + icon_files: Option>, /// the binaries to bundle. binaries: Vec, /// The target platform. @@ -915,6 +917,14 @@ impl SettingsBuilder { }; let target_platform = TargetPlatform::from_triple(&target); + let icon_files = self.bundle_settings.icon.as_ref().map(|paths| { + paths + .iter() + .filter(|p| !p.ends_with(".icon")) + .cloned() + .collect() + }); + Ok(Settings { log_level: self.log_level.unwrap_or(log::Level::Error), package: self @@ -934,6 +944,7 @@ impl SettingsBuilder { .map(|bins| external_binaries(bins, &target, &target_platform)), ..self.bundle_settings }, + icon_files, target_platform, target, no_sign: self.no_sign, @@ -967,6 +978,11 @@ impl Settings { &self.target_platform } + /// Raw list of icons. + pub fn icons(&self) -> Option<&Vec> { + self.bundle_settings.icon.as_ref() + } + /// Returns the architecture for the binary being bundled (e.g. "arm", "x86" or "x86_64"). pub fn binary_arch(&self) -> Arch { if self.target.starts_with("x86_64") { @@ -1101,7 +1117,7 @@ impl Settings { /// Returns an iterator over the icon files to be used for this bundle. pub fn icon_files(&self) -> ResourcePaths<'_> { - match self.bundle_settings.icon { + match self.icon_files { Some(ref paths) => ResourcePaths::new(paths.as_slice(), false), None => ResourcePaths::new(&[], false), } diff --git a/examples/.icons/AppIcon.icon/Assets/icon.png b/examples/.icons/AppIcon.icon/Assets/icon.png new file mode 100644 index 0000000000000000000000000000000000000000..d1756ce45d624f63b1db660ee6276645cdc52ccf GIT binary patch literal 49979 zcmeEtRa+fRu5Zv9}-Q6uX3ka^k-Q6L$I|O$L?(Q07EjHgde_>zltDa|` zneOW9(zmK3l@+Cs5eX0h006R#w74n&0Qva{34n+F93H$DUjcwYNEvYvb+7D;9JoLO zjf{UvozFd-PCg1w#YrKlzh?QQ(M6ycYYR_wwe{U=fLaCE(#E~5HUvh z?;-yV0QKJpU_fL2e`7u*#Q(kcU*iX?901T)0Jy%3e)(dDDrVC3w&DqTk5#S%RXzZR z-m8E3VP|Xu0M7Y=5T73k7I}1l(dnG^7xx(cMJ3C+M3#V)5*0_J{}HuE*-*zm>+D}6 z-zzvAP)a^NQ#3tbgXj~}(LvGP9I`MUb@QYI`@%t?0Dv#tm(LCSfWQUL>n{0KO6Mz} zYid_51jiQ(f4}+DE-q20|G`XPQqH`GVz-eF9T_ z6Ll)ij19Y9AU#ctS*um};slkGeswlc*7aZvP6pRHd3HBf?uoBqWC)`LG4Tu{Rm}4 z)K~eUz`aIfyjEPWRzG(gE$y(JzfuTej0M1k5&Q^?Ho*qutDZAhg3-nsuZA&g@pXcYKC+cqUP{&0N3_3V7%*=kohO za#25IuH_;_C`!zO)=pU{Uuakw51Qae`G~wKy^L$fL}j{Af<39Ino>-AI?FzW zm9=^*%~&rTXHy54!&^sEPoKM7GFGm3+zBxcP!2^@O&nqohi2r>|(TGoZ@m%n4!trRyZ($9e zs-PgTm?s)um_X~(LQMJ|bsaJut^BxHL(m=5=8Hw04>C*bUrp`JiT$irWY=wI#*hF) z6&!KIh?iLvNCb4q{I3>JcmRO1Wq3z1w2I29-2Sfb8oT9MXPpal=DavcM zFTG4WVctWTiMll+#)+icT_HG?#y+m0Z#bEU*=ChkB9PJxLH0JtGz1DcoD{26w*VKD zqz#LQ6&;a!Q>52c&S@NYn__r=x&(Skn()bK2Ek+!yCeMe(C=FYZi~Y^-)6y~L$2Bg zpIE^BM-MDqyLJ=qzxE#Cu09oIN>Ud*f~j9|&XyiW#kS!y!i$Z+$oQ~& zzMtOgaA_wL(kdBx*3|LS9lk-;Z4IFYt3%Dv2bwYzl&|=wwK&N(;I4dGeeQ1C^aiK6 zPfcu!_3W%U*2@@wF%C;n42Is88gPIjOLm3&)C&01U1H5w-M5qa7CP%tN5l<+y%0r* zQrbK=2G3fzh;gQU;xBYeBjM=!wk&xews*H!M9YcGPYPnI(lIqFMSE1edp z(~8onSznyU1D3M;9LrU_9=ALl@WB~GeFb?EQPfMg%;70Z2QvXeB*Xr*GvvJW)S(Xg z9%+nMrvQOQJOTqTQ`*?QvfT8GfQbv502TgV8uA0|=)I3`WXdyT8oSk^k zYtyDw()jtN^dZi!2J|m`jRpxq0?kZ6W;*O$9hAmbP$lxyOIX=Q0ukq-F;X$`=I)?B zcZ&CdSK@TGZ4l%wf`=qr$QGOMhsObwmOY=@X)4d8gJ<%WO{6jxF74<66~p|te^AIv z)+FFwq@1%5(u^zu1#RnmBoA0X3r;I*k+|0BP^dYX__Nbt5<+i#r8&OW8`=k8-TO}w zB+qughW(@0;_Y&}I`-&i(bhdB=E+<<_r$1=E$7zj&MXf$kqWOB@Z&QTJF zIzGp`WJcjJAcbiz8`g6?MQwg%ru>;XUSc?;ui!a$o=f9Zd)L&OG#Q*Ah3y2Bt{9n! zj)`wPLgu!?aXOTjyM+T<7_6%V+W#4uS8t;mp(;rJwbMc_4ii}PH& zwt4S5abFWztQujkmVigB_Jxp;wOEi+NS_XV$C{*1mAY5+onapxzY#lg&QhVby5>HU zeH3S_Eai{3+MlxEDj(@zdjfvSuau-3wq(V~d@|?@JOuVdHK!*~sP;{c-K|wGS5H@6 z=O+(=afre`0B+v9|2z&iB3zyJloAr8+d`S3qm28}$%c)V(v+XA-_H&-`WexlrzZ_( z7gQ6v10<$O>o4iS^0MXaEkP>db>5F-H5a2m1F?YSE}`XNEG{ni@-1w{FAzHsW90u) z4NuahYLZuRG-Fd2pg&)xr7+fIC1MBuS;GM?ENpeE%{6mWg@jKI&?(5PVkOAM5J{-% z-P!9egUbvEI39V`GupVQQQcSw0~D4X=Cgr~hXV&0;`;!AKuYIXS(1} zLHDtci^m`8lfr9k$wat%kAZtEzF}fuEJjUvRPOh`;8LS^i&&3|M5e8%?^fmGi6dyr zkQ9)8yNPnfpZ?o~-?-EJosS-@WHT(p41YgCY!ZOTsOgd(r38AX9u%1))5v;TB@JjT zJ?kY|BLG(PrLaM#Z%HUq0*HKGpg+SwA`OD-uw$h8wY@h7oWqspRFDd;7o^#jj}fIt0`PUFE|Nx zQnvepo%YMS%MZO>Tc&vlxaL@X^?1`{FRn5zEcl$h9DmKN0^x(I@b*36(2XdHpqbJEsLNE*Esb{O>n zDu`V8Qwrg!sR%I%vpxIUE<6?pWTsLfUhbA-atdTACLYiOn*h#e{}~`S#)d~!waJwG z$ea3_t#5+t&-b*Cpo46epGJ#Oy)w=VNu*dp^}zK?JoLUb*nHlEp-Z;N#Q`~*qq^9o z#RJab99-Y9wg^_4pS>YuOn?ia|CrxTL`L**mS&STcIx2>D#PvA?(p%sp0OqJj=5>b z7^W4ug@O}dowQj+BZJqNawO_H30BEyJ>~9CJ^Z<3he)DjxeO?V2?V7Y{Wlwgv;`5o zrRCi_f?VNqUZBw33uXtHn>UwN?cZX|E_PG-zk)tgZYsUn@06l8gR0{AP695~Z_}7r z?`9p1{|>bl8U*FMEx)0MS_A6q{@e4LueE#IHm>#&PwKIJW8B9`@U+m3)9D);26t)q z_k}*VG~Q>3z5*In=wN(E649yKjfP`|JE6t&dPF&&{h2S=zoL{O<^aaq=J=lmqTUHh zfK>v{KblLUV3iB!2k`u?!e1y>l}*?AEXnj1=ld-L3LnjH^CMAd2WJZMY#R@;;~c(7 z{r<>qAD#GS2ssFe;Jz%#Pl>yLiXltg*G{js$5mp^elAh_2F%jV>5;Z>j#r?>%|Q{) z{})6#87C?t;*BlSn#<1s>cOAVoVo+AQm!w|$Eyxc=816wRx$r$8X?kZ{s1sv_}`GN z&~4}o)Hd)fCP>e8z6LY+rOC^aZ~)Y&vRO)VM}>}^XvSa4;BhyM+2v`jZ2!V2uq^37 zOqOL*nID8!Px#+tTPSdviwCcb+2d|yI#vO0BF9ksXB&-e6VM~#b^$PkLae5AB{1%i zfry0du}GulwK;Rbl}7kcLi1UB`~&r&ti{lQIp##4%)0SO*Sw<7i|pW*;9_#^1u3bu zg7ZR?ZI1S{+yVOMP?B^d6e7gPH`pXb_Md;d9{C=zE&jphTt()%sPmUl0=-Tqy4X@pytc`_rp+=^aMRI)D`1b{)88u^jprvY^P_08V~CS1@((_Y-@B18R|1|6wrCUbA63~D zqsK`B44JA1ff(LnO67JRf0(Quz%`tT+1c@v4tR7ZU$y?i%K?%fVOO@0(-7MeBkGtg z-WJ10S>D>my`_EmgUQhB0ri-x-v{?{2S=B%w(fwq7HP4BD~tTF{>(>ml)a?l0xR=`jj_8@J9mUfb zOg9dkm_XO0gwOwV9PNWEj$h_$?ZjKVB;NhzRv&urAd`~&df)=N28%~R%zLI5ih7&s zk0YaL%&ndeEAT^LB!zj#WIpBKA_P}t(M))Lb-cr={gIFa47G-qTqx~!?{6yVyhsVK24 zc)xm}d!gp>7-9E|(LEH3P^G)ks5YK@kyw?#Nw{d$N zj0)mOZR74%ynK&G!}}4QvXeOt|k$?i+ylFnshJwsaiLW~1x;YjE2`2E{bfk}*vjD@v_BpYXXwwG7biEIm+4T{Av9iBcJ9cCUMznF@)o(o-Cj4L^rVm1Rfkc^4@O7pIQ9l3;|?+a3Wn%_c}S;=oCQv>FhIL$+<_3#Zsk1q%#R((kbu~(%eOG4 z$Od5dt(SMmkZz}$uQRN6tP5L% z+kjs|6!Pf^#OWVDI>^~OS0FAx!M?7v0ZLLY*5|0;G0EbEPDr9mE{kp{rby)~QslIfIQpj-Vo zTR^q~`_I5gloV9Fn6Fynq1TzjCYK_5zJEs7M> zi$N4PN|z5_4r{4*`TSJ?+sh>^wl1YRAhvwusJw)Ep0|j`cYXt>-C32w_q9BPi`aw( zKbhFpOjw#o98SKU5D)4tjJ|*NiFhf@6kMgWLi!vZ+py%J@@bYLK9foK?b4-jqhq25 zoSQql=vT1sr%9u2w{y945tTiU{rh*pDkNjRJHIE(6J@Rp_nG?RT@?7pUiah3=;{wI zjLQ6u3h0?GF~mlN1$#@Sq&Mj|sY7ORu z{(r{qGZQ6fb@@w9{vOx-Jf-OrKfYt%a*dw%4WIkB`=QvIKTXtg=34LZu|vgu@9eHqe6WsG%i}z&+LzJEn%8bR ze`2;3L&4=aSKYe{i}v_H>JsH%@5Wl;jYSN+Xe)J9-e{UxcAOS-mOO*3_5o8vs6AdP zvhp!sI|(?IAORCc2<7n_=2pv>$7h;jly>biff7nd_*du{<30dD6pDKFY=Yq~lZ_MQeS4m1#)d)&-*4!x2f43ApW z1XvEJlyR49G`1Ftcl-E6S&X(C*#h2F{F~dBd~Xg(K8a35C`^Z>h~!})p+|zzmK@s$JW}bR<4)Y@I6in z-d?5RAxJE6KO^S?H0?E`qa$XFoNJ4PTE<5M6h+U{!DCFZiAw`Nb}DhM{Lpso_lbQu#gJ zF&2D%y{ry;juI@(vXPSW)nBBeFeB?@<{k3=t<55=uxo5s24|au?heNC9$u$?`pDvh zR%8tWq{S>C)}h10a%DKmC6s?OglAeZJK&xts!Y1CLD#~?6@$LO0$5eqe)_30-__+M z_3RonhC8B@a0EA-UcYAXt?1T&vqf-=WqCeXUIp3>e+Wt5W+{3#kS!v%gD5Guqnja< zk;d4wVZ-{o)fU&ccwF9&2`PS#lILX{iCXrmsuxI91{KIcGkSTQN|BH@8ZQ8t#WO;( zASh)t6{LJEAk=xJS{sc647rE#ZR{fvcC!pERd~QhJJfZFV;rd*( z_*@l5X~d`)k&5_EMXe&=@tTeY5)ui1?S>_OC=a#BTkU<9s;`CJv3-+K0Fsy)r=ewd}uH9X4=KC(hbY% z;;Q|rf*xKt+q~~&Kk3l`J*C1+h;$(Sn3{w6B*7d3saP9=?@o@^@nb$FY_d7HQFh|3 zYA1k)9m)sV$I^Fj%E+(w#X+f>>8nRQ8Qc29zLfHkP$Fr5+#ls&=VWKQeYEpVPrE6D z41Qfd`yAgW;$4qKGYu1gukv?_rt~*9X0EtGOX%GWzNzL8VF(xdMM!vnz6g=<#=piS zw-c7-YIPYLH*y(TlD{-3H-0P>7%_T^QbrWJnJ;?6{6t7 zG_*I)-5OO$Ex)P<vnv^*jGY zx9be$tRDS;LkFOVp1<+!vV)3zA_pQitWl3?r)9J%PBn2&=x;&`h z&<)Lyc+(Hh_T#^Q+&>$Y`^p9F3yyO$#?CN#N|c-VYm<={0W+2!fw9dh2QTwYs$oHf zQV^d;RSJ9m(cJ&*Q5?lS`10S?+pmcXnJ=kt9u>x}1iPs%0UMR~vKYIOKe@^K!puk{DsT(8{1+y#MZDwvI8xyp7=9IvK&!K(&t) zvZSDN=D7I-1q*Qg4ikhg7++yg@xkqJ@}!%Z$q>v4wAhprD8J(}Q-jmEoUaqo^4!f! zy$i1-E^q_kxq`4mWIojYMtNA+JY7vS_Yz^cY$7~f@n~nFceGV!!NF7j;%*^x-1U-WD)VJ#6Z}!?q5I~7F@{tHQ?9cn>hiRgd`WOMb&OuvN#ef4D#iRx`RUR7 z+P7U5@9X7e?ros1E4eec@i6}L+*&Dwybw|6J+$ns=Owm`kXcf`1OZ!~@aG{vKU@}D z|DVU%(PNaYwQQ4 zM()@BQntL;yT;hOCs!WqRy6iqXA#AnKq=N|V2xUOhjDmo? zH?J)Xb|3bk3nO1g0YezcY9C3oGD1ZlC4IOFLSRuLT65?5P~pi4kHAM6D8F1)WUEs@ zrPnE}FyC7K{XOLPVIoAxgn{6u14NNvM5t2T$&%H%oA4T)cWncL zXfAH22_J9rVCHmS{?&J~|B1NOkDyx?{w{CIK#)?v5kmxUC#LV^1;-zx!_q#L?DK-< zi)Hsr_v$WCy3mg%@0eE1SOWGEO4SV4E_!sU1o+*c06!q>xnfML*A8%?RXm-f-@8j0 zj;6{<`9~iXP<78z|LP!=!pdHZ7J;=bR(=R|r!dFa7U8QxNC}e+VgRJDO3I%C=0=Z8 zz*)SuO>~=~EUm5dF?X#c&BJ!S2WGl2b!V+Uwq~n)`R_sg!l_3Hi@*3m(`pZdy@s0i zhK1c`#0adQ`-xg1apm`OwTD^+Vxt_DV@@lOu{Fj?+2EJ2tj-50JR;vq-2BQEqI0|Q zo3D9yDI_LXADoi;oBhuZ)z`O$?zGo+&R=cFPw6ZvAnTC={f8G}tXZ@dS2te!e`gwj zd~_c5A}FVDZSV;ov@?D1zMg+P{sTL$e@}Nowh0{ktPS-g@NB*g;z}=zQ@!pS#MNbr zlhPDli2CV=e^Xff7zVfW`oHcD>2>umV|lWM9trjZ88dt&bJE!n*?^2~rnZ6IO@6Te zH8?76O|`5|&pZwqPusOYNJL1~`^^8?bmYvKdZ=!|w%P0BZhB+SOh;SZMF7T|$>WiH zX$4<4#;@pqDvbGG9HwS3m_VpPYv}w!^m=(h2n!;FKJ8YB^4|x-#xqDJgFupk(#+UmbVgM0^c{2TZ zWZVe>TmkM;3`3XP?G9O_Yef;l8noO%)&7;W-pysa#}LkFx~YW^)LuChI$-C<=^OFL zgiDMdzsI_Q%eU_$bcMjOam#BMe^5qQ3J{47xKrQoEDhjHX!@=4E5y3{z{LGDWb$}~ zw*3-us6cFI7lH!Nw<|D-myjJl)YYJPK5FUIYw*UvNnaEP6j{xCStf9LhsyIQKB7ob zvN=>j*tms5p{$dDWYy&_V|r8UM_4|VO&x6imLTHB_s8{pOr+FGA0;Qn%Cr%+dCe^#74cLa!bJy?7?w z_rYAzbBt=ICnUemeNr1aUTj9j0oBhR%xr)8vgpDTptn3qR0~5A<`D)DaBhQ_1o=pl zaFO#~LaD7esr3vT?t!ux<&qgRZ*D4;_}99u4TR{azKWZK2{{kV@(PK<__y>rx_I!1 zSuLXE&_m-`6w);ahhUybj&j31Ju8g)I#kjvLK2zcBY%1<&Sa`TuCq&OYFy+xWU8dr z>agS6>V{c*$UUy#@(lTJ6S2F$rnyfllPZJz&^N+IR%qpUuK?{Y^yd?daFsw&2Sd)m z5_v4)*Dq6!kAn62973G?m=T||8?yxsHa0+Bliu%-{I87r9~(Phgt; z=qBpCc$qTwH&E9hx_W_! zt4=xwPV*+a5~KpS`4eqc-;}mP#Dh|!pIN99sYGW!}6`;-xbP#pg$@743G#?)8usz9}O)Td&}L&iW<1Y4`q^SAW-=UrVh59vlsi5t@FpgUt{X!C*Dr@rk!BT6{f! zJvk$-Ap{b~Nn1jjmppj}OJ~nVWR&yBmeq1xbU2lIe zCy!t+UVUO=!hfsXA`)o{o$~1Y-R26DjB2@~E+*f=mpX1F)Xn3K6iY^-esZoBRs_(v z&d%)U7abttxBlWzcfj!#!r8jHgd)P``Xhajw&{6B^Z=AqXzP}un=IH?QMzoHf~Bg8 zYw4DS0QVJ98g^XPgWTan$Ij?r)a#|bu_F7TU5AkH;Zqh!OJ zcdvadAIYXiC^Z0Omweb;FX<=h)r)RrH7(T;@5U%TOWHpxUZIaO17 z5IMdFw^Kr} zKh%X7OGuM(QkA447E80H3cDUw4jsjIm;aRUbO@v2%e#nh#16fHjkGz2%A%OSDQSq;=j*&7JUxXX*z5D&xjm=r3#}3OcnCK?2YMW*+o^?O z7w@6qeWKT5!T8I&uESCs!)COx_+E7tv0UR%@Vzm+tUU}pRN}F-WRi2|<#cTGO2!Ej z`_ud~)m{Yxzr$_@qJ~e89& z963Q{{#CBP>TV+U=0PK-h?3+*Pw%^bfGglf3^`=!N4K=LHTqI5m&WAKirf0O#3Hzj z?d`&sTdzZklh9QzE4BNYYI}IS~N(T`&u&%Gt zh6i+J`~U0MANHqEYMLWd)iJAucCFU6dzY|^o6dP}jg7Rbj0SO&Avyy-5iX)cv5fm< zZntdxRqbe{6z@wzBHrt5YfE}4C4F>a4YKrCs(Mze@du0QrAwQqWX&g~E?)EQwvO$s z?+2$h-JGIdE1_OiMN}-ih!t7aRgjDyIv2@R5x`K&SI&{%u}mkIb{Nky4wStD4c>ah>-HD zJts?pUtRKp=OjD!UZFRB7atY%@-}|(J4kb-zr1pXaP^ANT(arUY%2XHE{KJwhK4%t18icr?1{Cw zfA-vkx_~9YjwN;8uhb>m8KyJ*E7&g!YU_p1)hBMtrG6j->V;juNQ$8nHn@FL0b!Y4 zD8NlvdSr?Q3PrDO%KM{DO~rFe&3GQI#H=QlyHDQ(5t~Y&x58B?A;q4M8&Os=>?-K( zzqGa=5nBaQ;w1U@OiUWBiDk1r47(LYKAto1 zzY}*h2}UQrtKe?s@P9wC-iF-OE4|;|`U23fZ-{PQ*22#cUxrh2F?NLQD zq$47Z+yCye?Y+Ik-dkvS3xNTp>>WcP|MpYA)p+1Dm%xOC+z0}QWaO7(+a>NhImSqH z*l0dnYTl&^_UiMMH<94a!0vvxF}Hh{o{r|g)cKz>{cjMT0t11FmNQv~!&}1iX2|ZN z&Y;;RE#V%KM^W?dO>J4tv%2bat1%~`w~qApJnwTnMr!fe`bw=Jj&eIHKnm5(N^peA zw`2zYb#vKeyUTJQ>>5Fd)R3qar+?5U@Dv&BopkOpxW>Fl*o^i7y(;yo98ZLp;AfA2 zz0@+MZnllMS)CuLl$5+DEUBoAo1mNJRa6p#I+BgtR^@|c-&dM0r!IeOVE`V4G_goL z1}Vr!VM&P@KdFl?NDULq)FcZtFcd7}QeYyI<-2_6@bH9}c=R~v5a#zl0U8GM=j~}7lxyfJ>LO-+Tri)B z21KJJYv%9BLK!^_%%e24Be=j>6G!Ou+rC~swMX`$TV;AgG=@X`4cK3JOtuq7CZ&PF zN84QgnX+{Fq>&}uU)ykjH>zFe`KzDc^K${y?KS1Z#uEnhf*lp7!ttKjt)-u_<1^Oda5KV4{)tS^2?XZc6qbV-pf=MXRs3x(IS&{+Z^ zxC%HVQZpJ8HT59jVhG^>%f<8A9`Mtc<5L;dLxY zc|!S8~yA+s1Xr z{dFyg&{>0`+Xm1*-md*<9)9oFY1HXH{G+LZg^_!uA&5@nPeCHRdNw75(%ufM_eb0G zN7hwN##h7K`bB&8BFe7?4?7-bT2(0@O${!s4u`_#gl4QnC$axEwgy54W4S#HVQOPN zNU4X%maTX@Ag$jWGuciVv9-Xm6t);e7k`13qBx~ER8gO&?L4{IqvH*gwE@bJFCXmK zFD&wYml?&H&ik9W0;E5-y0@NU6u4*@Z5;;x+xu}`QG>s3wiXe=CZaGWyc)G4i6N=7 zhShipMFO>Y9Nn*yd6? zJ(>dVd>bE0n8l|-0$S3ENMExgPkqc+?I_FoISy8>OlPiu@nCF3>P-*$cB2cv$MxMm z7nqSkSeVX5gFz318WeZ^O_Jy~x~2v`USwiS8O`9V7G-Bx)t914HIMc^3-H?isX@wd zFV#oq_p|Y{xT1WuHvWf0O|7;$7%byF#$!4^$+FBa95q023CF86$#3McfaqiSQwua* zaeA)g$mF*g7l9x-%1Gk1>&MOH9DyC)@HZ@lkB!G}C?+MSo8#|DFW5wE)05PQh4dMb z`CDwouLdEqcV9r&SA-UdyN~J1b}M`P6AJ1KwjFCa!wy9_lS!F)t>%kC)Yi!{^E;6h zRhUlWnPYrj2uO=?7YH^^a+8|tP>KPyRmSwIP*rXObq*gtJEQXp%+ogf(Z6B_RiVc) zp3{L`+Vgvl0;vpihFX||A3lB`3VGQpZ&kOC;6tok-2%4{-j7PzmG_4=QrANxAAG)A zbb?lOSrHi3AzODp$MLF5GWLb5@oyy;25=a^UB z*1B3{N%&Xl7a^>nl6OM(R|I?hf(@)vkyo+M>2NmLm7xI1KYt8}NN-OPE%TDR@r)%e zx(esLSLz;Uawt8omFA|`5xZHom<+gIZW1L$ax8K-_j>6qOgwLfMig}u!k7$n(?eIM zPv5&~0kiowdGC`N*FHLFGKFxwp%IkA^_yK;S3q&W^|U3o&94=DkS-Es;=FaQYmgpG z?3jd3FIyAMdFzY&*tSI7#O?%;QTF$hOtGtz3bniDBHTmWvb-Zrj;WbZ z!ZLbdY&6{vl`9H!Re&R`Mjh~scHkIZic;hb&8wSgNd|-Sgl#KzD1n7&`_carJpkYm zDIVmE8O+igD{#h=Vof>RWlWE^;v1Z^G5^fsHZ$D~3TMpP`Z!Km{)w`?x?G3bq1nSj z}i|r_i9wK>qLVS7m&)sC04m4U9kJl`7(}>+J z+RIHIYqMtH;2Iyc;OrSFV>k1$~vOVNDQSl8V63Fqr)F5$5%Jit+4 z07G{h8dqtjbTfhU_HmdUnUST^FEP;SN9@`{Z@e%TEFG=$`g6ZL{v$pHiLuY9B6B@Y}PD zvBU`KH$H=4weUr^UsV4!yq*TuIRhfa_18j==OIN>YMfM!wr>Bn)_;XfD0+3#rl1=C zXl5$T<5<`wzLN6FVs}4M!l?p=wz!u4wX)G52{V#AjtWSkbW}T?t+Slr63* ztFdXFgnvInV4eL`TYDzsB$6Or^R(KW>Wc2cPEme^+~sG=;JW@@Mm8Di9FC3__3qdn$Fx5<;ZXBU8^if%XP^ za35Bf=Oz2pjG-@xi|8G4j!q}Pf$g;puI_2Aj_6HlS3~zW0~;XPP@WswsExB&5`_vKCe>j@TZeNAkj z)I*x$f@EK#2YP=<@Q;ShqLk8@Zzae8s}gq?Ts z|0Cf5-*^2iJcS-zIUn?MoQ{5yjP$m|TMzhs0)IBQ_tNIjDQ*94a}2(|r>*{(q#GBP zzm2-3c05sCcw*H6HAeFZC)M4Jledjw&f=b6+W_dLPpzkI-%=l89j+PL4p12}>2W}H`_H;L4I(4EQ1=9Oglo&=#nrbK6B zBioW{@9)*onFsZW_TCWnnheiiPn2=TuMBtM>ff_uvAhi2J&qc_WT_YLVjUe*-QI7! zYvin3g?k7wFtxd_8o4|8$czc&sW;K0$@{xu3zf!kZG5*|AXR2|T04!D#YjBTE!tVk zTRiB#?9dVWsPrt%@JCgdGe}rd7Po`F(BLiJ(&~Ugi)vK+ij#U$Z2pW@3vc})0LUWd zZo+vWZ1jjnqYRFWP4u6p$*F(HdA|BjDZT&hs0#6?5F6p2H z>Y}RFCRZO*HSq0J{2nF9-n%cwdp6I|OfRYIjSad)qCup%M>Oz|UjcS6&beMM9;kjNU_={YQHa`FM{7qt2uODt^bTALs+$o0ndMRkYEko?6ln0gRk0 zgdt!9s%>_G$6R`aE9`-lmz!T4FFZ|zT8zH^vkJ6dHgp}_4&*Q|V1Io5wVcyqm_Rf- zgGyRn&#yg%ojGqBuOJzTZvyf1vH2Ogb3=Fj(LYWSKmI2{g(I=`KC#t(y2ny`BJ@-! ze4B*@U{E|Zqq9Eu4S@+#l~qR4c&s%t@z!Z-We!TAm_!oXOUkTXUBdM3i9;MAsj}xW z?$RM=t*g7k(HBVT5t?Y8APkm$rYx6kU}5#?68OFGRipE)x*5XpfrGeYwaXO_Gk_0y_PhfDvfS|;6=IkwL;~CNz5iLI+0~B7c zATP6PD)y)=794Y^h-gOIDY;#6{3Z0m`)U&ZX9mNqB{G+LEu-h1t&qW91PWFHT`uul zxB1Ri@+|8g4$3BDeZa4pX;b>CuXp>{P;Y;5g#x{mZYydO7uu&bNtY7m=z5}hk=eTV zd9PR-7umi46OC@op0<#yrI>?#hb*W}mz}oJs9|P# zgaa6^KYX?cfG_bbWf>!xxTZ7~+DgH#erIpz)Bg^l+#l0he{K9Sk3veq;LarZaKzIo z@efFO3V&UXe(qve0I+Jc@!J=*DoywY=iAo^CsV>lUIk_jaOUN+j~obbR&6=V@;F66 zCM%-N(b8p2KalVC=yovTN3l~uVIS)#n3o4psxm-B|A=tYhBV%8f*W~d)oJ^Mvlgu> zMyn4_ctUd0-BRHK<(25oRt{kvO7H;Z+aQJaUk*I3 zfM?~_3*Jluq#RKwT^}nfYG^R^=8qbq#UBWT010(g1ljqoQH7s(baA?6U)6V6v&oYn z(T;Gnb`ba!A?u+&9T*obfH%3$Pf5aj%c@Z+XTjt2ICquzd7QKjlH+f{G}m;`0HxgR zwbv!Dt_;4|X;8nG8^}L`Rg#enV2rrggeLApyZ~|(z5Dcs{yFe_cvE(++v{lPN0NYW z35Flg@`u#AD~ApuU&70?d$_NQI(X-VqvnLX()q4EKRIx11!tyqfUCb<+FR$5SXUYE6{k4dadbjO9z-!J`7{8g+!dBswv4C4DsG`v5tgtkQGx|?{ zBl*SM3V#6wxw;XYYGNGK2cFEUaT-EyqM+hOhHD{96eD{29Kid zznc0PyBH!4x=7m25ifpd${QKhfbVVM2&IO7j*aefa+i5l%z6XuSuWvD16dCxQVMwm zg1&hJ<(lwb>x5B-&wU4G>1#6NpeW(lb8tg_uY4(Q{(1P>S$2C~{VO)==CMHLk=J;o z;;|4txm<5tci)&%m--)$u7aVhZV3jL;!+%n6)#$}xVuAfX>ph05Q-GH;_mKVG&sdw zi@Uo+l9%uOfz8d`&1QDa&K!(ZM9O2IX07`0;Ur2*DS*euDXi%2I(}*#+tr%*^kutU zcxP_jJQM!Qv@%g$kH)CEH?s}h>baz8a{r4hBo`@o;6zkHVVyRc8YcJR{rk$YG|+PJ z^^?@^3}b-v#pd@FB^J}2zX#83p>9g&h;Vu&<8!U$r1R;ZpUxADOO%)&*(^UWl|k2~ zL|EZ)$Z;ju(iNk=8)2RZU+$W0eu4Tw?i0d>Hi4R;Ndeje{Y^+WyVSdKts+m!FmsQ= zdjLnj!I$$pRr{91`HwS(OpzwR6wr^SyjjTBW4Ze6kH*)y-wP6{KSdPbM3kVS4~wzQ z!6QDC51yQ6d-)6hUP~qZ1b=p?^b#&QPT0jWF zBaq0ps#ENBeNIm@g#afSK%qX9R3dbK8mEAVXQs)VI}bkM=qVI2xwR5KkiKl5L6yYC zjb@c=b;Dy@xwUz!>*hhJH%fo@u=ssl{HZPX;O?v3N* zp|4${yM*qpKBWV!0)V=cT5(M7ewqO#jPK#JT6P#0rjO$`aJqedZ7u$zBtj}nLr@Bz zwecr&$;tMF(AQEv#%`WQJC7%{nbm^M=)CH~yaki*{6h*k&*!vN(6bN=ff0iK?jA}s z%%m360Myvt0P?gRZUyj~6k4VUeGSqlwt^4n9+_>GhC`DYwDIlOgEV?L=Y4{b%720zAQi)^ej z&oN%?^qLM&i%29+>VdHsQWOpW0YU*!WE9RZWE%o{K`Y3}?neH=0bt%^(kxl)3}0NB z%U5)Ik%T@ag2Eeu4+NFGL*E|#o+h3zF{H>@{)+XH8{rrgeoHDa#2J&}ov zr7q9r<-VrO%0*D~nHF$)Bt$#^3G*Al2yFP0E7-zLXy%ylnC(1Bh%gK~S2^Ct#s5?* zwr_G>uo^4H8t)I&oML@#v0%7H!!_LE*QEI|+EH_w^VlM!O&!%FjdN2I&=bI2b(?>G zoUbnrU}S+k8pHT!(TlO7nD5(br`^i}r#n>KeBTHH(<2btHY5LG3qCW^EBx?0ln@*> zD^ioc=W>#(#}<=L6;C4E!c7_LcY=8oTu){S2+^m((}Zi@|h2j&wAi`aeJ)oWOT2 zGvZC>T`QQ+@JqQm9-oU>RJBg0KQ555Rm7^1S8fxfiw|mH)xjjYA@>{?M$eM^hxY>t zAe|%tUt&DlubG!~W8dx%yqOy<=rn*=$vTtp^D6p3e{u-fJ=HjjTR(>!M$lLX-3#^r zPj_d%jJqiS7am&`VmN8B|@Hz-D(-8}!0F#`P&QJ9>9a!zXWBsp0PZIqQrLh$=i zYr2408_J)wzQ8{I0x{@j)AL?8E1-(dl(o#XrVh2nd+NP*k&x_61Env$`6z}P+;*#z z95+81T5~nO#(#RgG?y(8{h@6+U_+0A~6PLal8%2Z=$S3YZ7FsSrra2j@tC^5r##{6q2?Z`1 zYhPk?l^NwYPLNK?E+N55Ju`|->X}iIY~6Tui)%0V74+X*J47_^6;N0v_J-9Ha6((O z`psVr;?!vw?u**0L>yY6tzQupdAk+l?IC#ER<-Vn_RL(Z8$yHn^CD_TEnM!dPYm4e zEsoQhER5Zw1a+a8#xFQtO|fp*Kbh)xrqxJpGW5(j@VS|94)?CZK_Y{_N@qr{-4VR% zH;aokZ18K!uWzEZZA@hkn_>M^@nXWvDU2T!ojka)S{rTvt9Hq&zQtrHHp4^Ihn%|$ z8MVC^UfiLjO}`4QjcR?Qs6=j)6?92^+h)WAZT;(P6-ur5a_R9O=HAz(k}92I&*As) zA({oJ0uVlsTg7qm(fS;8-T!K4y9I^Z9~S#UdU8~|=0*Q3x=X2%Q8VzWykpfUM=|lO zyyNKr)d?65={pp z$|{r&X@9VTpDPF0k3Kl!fNS_!#8~`n%pxd_&o^WEC)C`s$z}n*(#&07l?v#EXFwiU zE@qqq%wY69c{pbW_-uX|WihSLkq_uOnW54|XJ<oz~S4NHWjhh*AS8y^`Xo60~F$Qx#HSdHQ>E_9CXzf;XlJztS}H*Y^;n z2FJh0Yy97ZdGZ%Klw7O24F3>ySy@>1L3!IfDY_6&#ePH3iD#e>_R36&=N|JOqTk4j^D`}F&KIaF@0|;>4z8RjxvjkG?A72Lue6# zv*%t5%<~50i-!N`yulWjKF<)B6KO4*b?x!psQxqv`YCj)$DBVyQw(6FQduA2OOUbGYm2qA!dT z1G2{2%2uhRw7h1D>Is@}2$VU0s@PAe%95k}pr`gO7<4Hsm<~-iHbLYAcpwvuh6_0m zEB0#h;E8t~`W-EO`JH8Z-C0X$T&(+cS@iTHV3YlO;%Ux{*?9$uQv|mC%8-9-5(Pb1 z2G1a*U{)Bi#FhiuRvT<7VuQ5CTsxU?(%!#2){qvb>~4`kM?2q}g%J22U&Ls84psFy z2l*4w0mhGaS!rB%o?;#OS<0?m2=#Ab)%hL4R!?5jk6Tb1B?&Qv{) zwbG)eYn4do2-RYZ-&Ts;)R03--PAX%{@8EKPz(Bv`%T@uzHmm(qqtK%P@B8N%g3m4 zJsc!2%xqen=w~1QlkS`Q_a ztCJR4IZDT#v;WFQLG0VXU-;otBkzUj0VEUC=V*;&zjf90$-+onM=<Mbu%Y z-XON^NtZEo#^l{loNj@q<;{bfKCW#+45mK|(D43d6ZDIh^k{Quv;Vu&joz0Rw!_pZ+c#FQhFL*I@}>t6{#!)yl)_ynYq|8e+R?Jx;KX`d{ z9_^eCSX)mQ{`>F%vg!fw`>1_Oe#p6ty(Flr(35gy^K+&*eCDPGZa0=`({r&5i(Ky_ zVPb=i+>CA23akkiC_&iX5ZbWmHfTspl`rp5ioetDnP*|yaX`Pk02$os*dy`n$^qoB ze=d;DgMtMkL(mZIe!D|s9QsY&&W)$C*94~oD{x4SS}JeS&(*ENVBrD>SIIl1v>gVu z$dk28G4{E?@a>M@zRFC1QGakZ(A+={j6vy)c*@hO-9JE1U9Y0CZaSj(S!3q!E#EI1 zi-x?$!Iz+SPvV|ov+rF#Z4c>P4qMnGTJK+S8!TssX6)zsH9Z%I$5BU-oMUfquXDBq zm@s~>m~?b-M|V@;14!g^YpJb^t9{BeS;=)xi2ba=ab=8s2gg5~R{lAZl>y)KvxC6J ziOH74Br)PXyHe8LZw~GP-9`52vDb{04e)8u?moC z_3}5wLR3~Dmr(-g)4e9P(9avskmlm4fQKQg%ufp5-O-%lp+OZ;;T%1-^e^%QE(_q> z`oUeA+D14!9+hwLH=Ah6afT|@bHE2Seg-1K8yzl-Lz||m zYUQX)`I{V<>J~KuCt0B8;!W?Z-8kOtRM&TmmeerlStg!*oi#I3{mi1A_BWbI99GL| z@fFvV#>b7R83q_=W1a4Ga2_Zc0NFb+GZ}Ajtci|2it=`}%K_t!vpFsu2=md=;VK$0 zbK~)&Cgodg;(R-it|G$_DlegQ{3(@QT%|Q)np_W6YUE}Bc%{S*C!s4ueuxmu;%8Rd zA^SbkH%|NN%Q)x`ejHCu>H})z3ULyY3?~FCfTt`kGrZK8h{JA-hB5Z7RL~>z%Z|fT z{XQ>d4Irp$1p!t^_4vh-P~#kf!jJU6rMbS`%-=_a?woGGtL^#M%xj(3`WgEOaPb7eT@mIzNaEAi4mSfuiRm;1uq13sQQSwdJ$ap01at^<0P=>u zIZcu9bGd4pDTd7nTAAD^>(2026#m|Chlp1iQv}X!6p2ELH;q&aso{*4{rBC@ zXF3$ugPk(I6I1p>nJ{CAo#jK{e*tn7@=X%-#nwIHgk>dj`8ro=tA9y%W|U0=%w`KN zg`I$5Pu}L-_Ep4J$dBTD#B4t1%9ql`vJ@F^cJ^PvC+fbxy2|>YIkCL637sZ!Cz8MD z`SB{1%8nmWb6tkK!G&>9)a#oHLrJL2vs+(UfxYQ`V(TQs6l6cno77@pd_Tl7AYbBe z0&JV9iO&UHLfNJ2dfu-m+SC5d(&#@%+%zOdEFZKW#Sm?!T2{a_Ix}~!E$XuwTo~tV zo&4&qjc5>pDC{7H+qps_BmQc#fkSxoH1tM4cnaK}Asp>QDw)m@w{ijg{1C-x4flsA z5A~`p_v1PDb51x@F5%-prTjV{AkR4tc7&JT%8v~$P63RuxfRaf= z1P9X3Jm}*?l^GfqyMioD`6AGtdkVzlq&<=%6Ich^p?Kd|aVtC(=YRM5u1yER zs9$^w&U=#tg(;sQo2io}RJrv`0r$;bRx&9a((0?YUCCzZ0pMOWCYroR%{#1)9?VYv z&_58hfq~3|pcnYAn^Qu}%a@-1Le=MgFU#gpG`13u0tplfih&bzihQZk*iVMGq|kDl zQ0PPy!%Nt2m8r`0Hw*oFFpl@yI~+LvD*Xf;ikCz8o2(fl&B-^K#SKt-6iY{Ic{0cu zk9D>6IBw!`(@$G4H${O3i17?*=wpQa3g-3qW)FqVKTmn`b^*ohwliU}j+eh#I`@>> zhZWpiOZ3Cy_rjmve@mFX`x6|AmGtrlh1xHggZ8WJivxjHiNlf01+azXW(@X^0j;wM zzYa+rUQovf4M1^Cx!>_2zizQrAc~fD;&Vxat+8?a`CD*wKw#9(A!4ne@ZtBVdQKTZXyv2GKt1njFiGswdOA8YzPzk z$wgZ*ADiPa`eqDOf{D{@m8F;xe~P9OMi5Rpig^mJ;66tMV6tPiAs#P<*pd(4L8F3i zL^Al4VNUBfH_{UU;awaQ7n4xjORF$(Mvce7{%kMv;M~Xb669dA|>2MX^k@Tu| z?ycpNkX$z1Fj24+?^nDzEsa7cWS$idi1)GkTF05RXU9V5BbeIt|Ls3~`ZpBdldAbT zCx73Z80Rop%2u`!u(&74DQZ4;U6Kmm@*Mf~BcdLgexY3dd?5A0IzbHVw!4W^V_l!6 zh_qxOymT?O|9nH#fv+mELD^=fU1E9M0{3Zrle0Ge6LWad*EB|?FWJFfH9mtA&23Qz z9UDefC6f6z5d6FtX(=Y3;&;Mq->+V%p-|*NIOnfCg%9TZsU8i;KPcQ@i0XAYkberu zS>Qu9C;k)OA@)CQjA{_mUozX8kxOQ|o*%QH_SJs65UYi3*goqu)1K{SpeOFW&+${r zH>Q^6ki5nz0YoO~1Rd08@`P+g?kaR21^%OL1qo=O9$a<~kB>|f1@ zax6@_EZ+&hRq-Wq4#>$Colaamg-;L3&>_=h@Bm1}7;yD~z2Elf0g_78Y!5=m1x*(D zSckhyaYEyc4vep*tW3H$3lRIDPVlfwc_XlS+*}e-xqbTj$Z6$|35||S z@L$W24`U%Scexsx+=1F#BTPsNP>#OPy&nr`?k^!fJu_qgbbkj!7=kD}H5}@{h%R5H zHchEHXk|#KaR4>|90086j|20w*U<56BA|p+#YZl_{;}fYDd)u8k4bu54{f~M(m0ZIARd29QVJO83{Iem<=PAPC>uW$3i@T5?LnQJn(jJ{Hh zeq_W|DZ|Mct$|3QOpfcP+oS|p_A%Vzv@S3S|zclBUBP+7V&9Zv22 zZ^JPc36lIK(D94``-J^hZbV&hVDPePZ*rjU8(h_ddJn;PdW3gsvwHyQwdsvX8Ko4* za3l>^yac<`@&#LSIc%O20mKAi?SJIi0L5yRSmxX&kb7i|m2QH#1az5k?hUA3uLU44 z7Uy|yaCu)imfn;OL7GE1ZM$S(MI?s&_E#rV4JoNS-3CnP@`X&iG97~E%>)dpsd1ix zTa_!$DSoUCmrsII<>#mzWLf&mUEIfEymXcR>)vmTFi|xKKn)AU(B?2*?`W<3?3*Bg zDJfriBSpp9JDJGzf*A&(Z=QvD^~J-xVOq6 za>?5E=tx-!w~r0jF90-^=H7FN!Zdph;{K1#k*EBEI{B`K{iuxO&N-?%AXp3Z~PQ<>G<$kM)iQ)n62U$El&xh!58WFO=gZ|~(T z9ILGt{|JkN_crwU$eGKxC}J7luWH=|&F+H&PeZPtkV}NGLBTyrJiCPk7qsjg5-mLGXyWaE>iscJ}7>U`%y&y&*P{eXgj8*9GVJi${k87pYY3W z+#d;Q3DY!WKoULyZN@_#znzlfOw!Bvzx(`DYO)v2B+$n>dBR52?34`j$3((hh z!~m51Pq>drmF2SOBkx2bBk`eq!t`(0Rq$<&7(e~%;G}r7(9W0*b+n}QAg3xzwLu2 zTQUwrM|ZHD6d|$ihu{Bv1c6@RQnmn|xmwGv_DPPJV8@ZRdYF7kbmQ*1^nJ|1D-j=S z_pKeJWeExD8Z1+;cn^Z&IgbRnBBSMPezx0C>ZPKmzH$VmQxhe6TU8sg}Tvm8?J*cgOp#?!GB=Xmwl_#)$dj<-QD-x}P>m67>>B--!ICwRyxN zC4mxca1-P}vtjkq6f2Opt}qxQl1{18+5J$u&RS(KTMyV!IlI~%`B7Q=)#5>xIn0jW;(RvDx%V_yv$H0JZ@zEyCouYZA>I{{%;{rl`eJ{?)<<96KvM&AYX587N9zt#Gr?`-j;u107ej? zK>dKhoPveL0eDE>x&VroyEGnJ+70JO{;@N+&u=UV>w*pp5kZI?zP4Zrs1x7516YKN zTw9@!<}Q6D2CL4Y1OyvK^ieXg8-pe1Clc>ftH+@9woF$LY?#CB*()-}1;lE2vP~;} zk5t0UKC!Y3*cX3^IS-?eUzZz#KLuX7!{sRheMB*9<#a+Np`emZ=YQ0HyZMIP!)h>cpYBtE+259oJutizb zZ|rzwnT-VF6%N*8G!9bmKFhu+4m)%db7tt#h3qH7+Na`%sN1dkE!7e|gncxq0qAUq z_21LZjm%yHDQ+G!7^cPsNn;sivAc=e-HN(^XGAaNEL335pb}AlnsFbwqMh2%(~nXq zQ9ljML(I;=P@OED<;^9P4X7t?F)N=0ArC}A%NIGtlxivkQr_x#BOt-9$MiM&A!rr>L&W6U$znS z01=4FEBX0DGz#0Evkf?RL-e1szd#9>$S$);fRfQUh>iJ6!GcBCKyMOgdgGDGGHye3 z4}#5P3g}$Mh~&o!cc9t2F?%<7y~; z&!4q|me}8JV^!#6uLVtlGdItf2#l#o{z5ymPKLj^u??2IfW~XQC);-}=&~vnwwyN* zI`*sbI`W`e%;}z{1TAzysH|^U$dV|EiQ6F*@9dr+p=;X7%yi)=6{Wj12K}c%c?O@dZSou}Q7mB#I zNDX8D`BFBCT}-AkkY#z4`EiMS55kyj3zQx<8`LIVtO7oK!QL*Tpj!;=Z!)<TNq`7En4Nlre+?0^DN2Qr3$f@`ch%lJZQ}Ykw-6WyM&d~w4 zU;uB+q(8eS312f{|Aw+yD^iBd{c!Z97OM!oY=~N^Ozpv#WF`>qYKUQC4=P<_w&O=B zuLN^9m!SKC9H_(eTQh3DsFkh!-0OL}lMsyt{>l`)nunL0rmnnk-WLh&QyErWyfp@4 z6~BvpN>4Su%zc>@n{e4&Tkntv+kPh0kQuFLezV@2b#(HOYk7+-mxd3!| zOMF9~FZAvXRZr(72niw{*`&`-R=+bD77sS3jP#91O>*ff&eIBfv zUN2#k|DpABPqPv*#|%$^$ddWeY;FZdb^4_7mURdnFDo>iZ#r15DZ^%p0Be>yVc>u{ zbmN2mv1a)?XP+ANipJm&xtpQqLRwX0|W!ne{>zcXv{%8C)%C=$$WKHUv1i-t8Z z{maH2<^(+_2NO_Hg;T#|k?*Z5!@|PgI}#gP)lkCxRa7=oR~(WuMx|8I5r3`eQ7E_7 z?4_Yv$D2u0d08^BZNx<$w|PcYcQHU9@rOEB1udoN1LgZ3fEO)EZ5La%s4VzCajIA$ zi5F}Zhg&-vQ6_w(X_6^x4Is5Z$Zq0%QvKn*ipV*4 z%N_E0e$C-Z%V%u*)zl5mh1(PKbXD3$cHBl1-ifRp97bQI$<0Fv9~HLQ9H{4~DkG1= zX)~bPyS%K8((Ai&`sG`M2~lrTyR&p#hOrRDOQmQL#j%%2kf?XZj z@~LppdezK9Uzx|;r&R(Z;^XQ_*O!=wxW2*R!luyt_*0T<6+bE4&J*>+{PycZOcl}B z(`Ly`NXn6+x9t6k)y3BOIpxwX3S#*Em`U~ocv&uUgQGdCQG>~9BNs{a=S;Kj6y76XQ0Hy0(n@5AW>l>%C zE8HbYT4b>EhktoPpf2M%iW}R0qxrbQ=q*Gfk!_@ANc1SiI>ZsU<`Ia0!K_+RZw$V$-}GF z!xtSb$iDVDh+CtBwPf^V@rMK7L#h9Fbt!REihvLBb+VjfhE2(36*Yp1);X%~bRU#< zfiX8+DmDe*R*Ya`kXS+IN1zFH5-uo@N<_xLwDYoLgQ*nQk005PRo=HGPaq*XnocdA zs=y{#pPAxqKe6%!+V!{?C-M-6IR)J|QPu}Y?^tf(hb+~b4TqIHk`LX+Q=K`=Nv{%3v zTcFXD!E5xh*b4|Bf@Y|RHsVkm`H??*mJozMA01ZQ`8QqX0=^#vwUJGM=WjOJztuS3 zT`Ci8YLo#(-f1{w;V7h~-V56+f8~U>6Cta%->l<~hw>oX{}ueILt0WcwQ!IzMF@Q> z7#|h|Id7@cIcqRSrB>eX$%Q5#KSKMHm7xvgOH;BA19W$m;|h)e`?c9~_%-3?|i z8D;!n0}?9qlF&_*3SZXyi|>nX?K{W4G&UmiOP{l^+LRAB z?+o?_;#KT^;&S{Bscqw_pxp}YKA)nLj(c8M$$ZaFo($c><<`BB}z$Jq^k{4_)kmZp5w;&W_YF@RoWVe$H`XP%y zNUrDahcvgTVp2R@m-VxJyKYa9shc8gew9Ce30_GCO%@Y`YzBTy&Op0oueKjVoEXi` z@Ly2$ehh>n)(QQju9!MtR83gik!p#r(!^_}@vb4;;(O1gJz^lXL4^hE*7T*m{6xriImUgQ7YUtqL zLf58;kF33pLRzR6gF9vI<@FQM8yJdG{BjTY@1)(jSnw~zQt8G+ytYlx8{|SvO<1}Q z(5|&_H^8z}_vB#rHl~cq5YO5eDybWrdA`dAlfMyeR+WaoB!_$Y+qOzb@$1PMe!m;3 z&5D_NJ6`#h^2z!FOq76qaf+@FXAI@AoTZ9jz6;x*Q5Efw@63wEdnW;vCE@^h2sf<0 zrqak3So;<^;Jp(B{3;|KPFwtF@pBH$eh~Ict=@q32x>$mkKA>Otm6HM?bYN%n$T_X z5efL}x1k)Tc>MnFP~yfT!y=F1uP+Wb;=(=o$ux{mCk!jY>IX~>hevl z-#HTym7vEx&3{2FVjg<>Z8^@KxHv?42>GW&2cjsHU?_;k?$~F1hxj#UsSw*Lc`;kF zuSrJc$hwwlP{`OjqF@V)6ZPK6L(pP*BC>DoUCl{#?!$&@kV#qX3&oL4ZxZUot=D?d zM&ib`gG^*ht!Xeh&C1VY^|$YT2m4CU{R09vV_I{Tn$2y4A04;3zLi8NFy8$m;XVp8 z?JbI16@C5QFJzeCPlMQ(NGrkGhj&Ip9{j$i)8T}lu(n2~_xl3Otpca9PHK6gljgf~ zGTaSRNLY7oUw}fmxc%FKG*q&)Y9vCp>SqyZy&N?gY;WOJ&T;7Y@KpHQ3ET%lXO18O zl->O0_+hCKrstIOvn-RW&91$mk@U+C5vTOSC52R<4m-fU$;ukCf;6~yxrzp#)>Ej1 z)fIb_K?w~`W@sL()f*`4cK2%y49VvNNG zy@Kk-%@?XH8U4G%&Yj0@60aj7wc)0BpqR>&=C~p0a8l!#EDH<*QFD^qzg1yRHu&@7 zRL1e`myN^Kz&w$m!xLxFirwg2wt^wmr}_`EVF4hQd0A*fzO8&Rk}gDM9ui8wEFFiu z%fExm`;jpZd+MIR#<-ofD_IbfiT=g7tcuMX9qN8$GVzsPNXYi#et9gt_GfF9J9D6K zmM-7aO&sVbw~QBgKAhZx2VNJ8(CtlnFwSCf_ziX|K+|Q;%HwS<`*NqB7M*_%qgpv4 z*EWP!n9FA%kFaZsCQ^8F{Uy^NcN|*xYp+ZSF$szaUjug@w3uF!xN%gDuNF>vgan4N zkqz?J8r#@_FZDR}Z(La@%jftLtO*=)y&J55^Mc;SlFAp$aY0E&DrSft8tM~`;4&vaJg-DsJRlL86L%lNF_h4ql!}!k%erb z{v&3#4?aPMFAPgj~Pp9TR^5B0W zZVtPMX=o)`(>2xjGd=ivwdhMf-Nyf~Kdbffw*B>nLr)Sp@I;g{`Nz*&RkcD8-W!?# zI|UWW_F@WApi5-TP+GJI6-${c4iiIXPMli!73JRQv`$JZeg+fuQ{eX+i-&X0F_fHq zG}at<>Bq?uHZ1_q>}si=kbS;%_yLCg$>tuzD6IVIG~vE~i1&!~3Ga0gGr-ZNrU;jGNXn<3opkEDJH#yL!MILvX%iVsTE$MeAT^(#1O9?!yiwbKK0 zW3xSMZ9eC{JWV{}>Ih=S+hqFl#te-6rztei1h4O)-D^10e)WAT3c9?$e5e2XI(}fU z2=bpArm|`0-8cWPu0(K0jTV*{Lhq#vP+(G@J8B_y6DAEEh#3;kdSB?`RToS{64^9p zHtcR_^`5kf1jw1vYlyhK;necIm`AL{XMV-8p;#Jd>>?R-r#H)K7pYSbfq>fE?akeE z^O#0k73=<{Uj4={?~5p%PBVSL_XWlrtsct`*`G(XG>w=y@$iNX39{tENUrVFS#mXHR#s0Pejv=;otILzfYU9pV0N+QF2Ke1uo0>A7qJdx^%lCfTg~v}(GqzV z7d|FH0@f31Qvrn@gvhku{r6o26wODW5YfR=OwEz%?3MI`TT@oNIw!j@&iq-~|0t>B zqlnm|zv!7bU+sZ%@n@37Hm1}G2(pN~&vRz`P$~82VRDR7(E-@Gf^0Eq36b5WkC~P4 zx>;Os`l{@I(uXG1lhVm3Q^d8QJVU_S0;qqQTnVDUP|Hv zj4SJfF?~pwNz9D!rjB#Ve=r2@geC$a$=v)B${YzB4 zvB29cS*kMOmJarJqoArup*o?@`SZS4Yms<{BqS>K6wj(+h>v0|xGCbbzD1-gldlWD zVO+nEJK7tJMTXTaRAY4v!yeOj4Gdn+J47IIFqi$f@U&2|=Tux68*jGTj~AltZ^kMh z`?=ZyO^C9Q;7*!f>@zVrd})(wvL#ZQlt%F-8GSSTgn3f+S?%ix1C`Am2^JuUMXxYW z4Pt>v4DeN>twY@QcNWJrm_{Y;YekVq;&U%w^Dhi?JX%F;;BT{&JmrHt*Q+mCe2Jz} z!mWnc?E%x_<^bDwsn|a!u{8kV*C6x}o-o|bjH^W!)bcK0e|usV#FzVqc5Lt^p1WNP zw;Ts8`s!;6gDD_s`mBT2Q?f7=%wADzW55CwqplE<~_KMl$2dx){Ql8k7G zU%Uqy>idtxr7XO4@iM1NNXc23Xt(^A35k^5zJ7Qzta2OpBFsP~C#O~RKO}ha0||Sm zeSp`-ph!|()emb%?Invuddvu{I0woV7+u|I6@H75%{*W`_R#rAF+#@(h24f77+)Ka zZkjfz(uAcg``eFFN>X}2lg^|D(y=#58NKK3WK9yJ7kzk>+ z8&&<2w#63=^-SK6O{&%*b5?>Cj?dEwF;*bK9%Ne@y!O|h4VBgs+Q<5LFD_ec+mX3Q zc}Y6@^VeKu9@dH-bScJ(=*kvUTQ9f@Y9hKvm!~Hx=|b1Z1fpm|a45(z&-%=Mc5<12m6p{tUjV`3{BokGZrIGBJ+Q9SvOOO(K(G53X+}U0{-IP+f3c5OX z|IX3B!a1{_V9xZlUkKx+;6b z=WS#D?|mB@UJ(u~IpQJ7pVG7z@zOs29yzHv(BQNw+XSi|F(ennng<8$g#vwxybm5t zoCD1$B82*__xq?JwCcrOD=J( z$DO%9-U>!LNc@`~w5NKnV*ZQ9*av~^BtV-WlTmx#nCnJwY_7EFzp{K=w5pY0)3Llg%87{YH+3(1US}#$}?OeR?>v z5AF8q(=!PefOs*Ft=k%K{6vK<#= zP0Osd#tbgVZ2ZW$rpu>~u3zvEwCCl7{lpMjk6m>`DZi>A1V)ui7QK>z<#?BeNt&3p z?Pov&)e#xpPYeucVxB*}W!i?>l3Ltp&q6t+1gp2Tr#|}-ubM|fc~*TJ<8zT(0trE} zDzESN_@W7YNy$43hNWAJ-%=8h>0G#nXa$k-qRp3TQ|lNDD2|VUP5c_nHd1q{Ao?54~_VbB!sSxgyf&`hV?x z7LW)eBBb@+z+Z@ujIASGjsXanfi78vL{)8BHGQ&G8vo6E1bTEBS8v%Xr%}uktI%{MqZs zpXL-c@ICMb7z$eS{s}8Y%E<~JgI&$j;Tf-1UDAc%_|P}!Erh0&CdX|Z6%dBWV8{21 z#2U@Z`iDv2omeDkIK$xF=2yngEC(Q${eu({m?Lu!T|i=8zEzh()chDNl%LlSC^ z-DzfvUVOL;PU?f8tFofI+0*BD9M;_Ab4Z8x>$?z0bY%`Y$3lTqu9pD<=b{26g( zU#u?U-UiN2?q#n_xm5FU2J$l*rE~H(mc*~&3NCm9D{UzZm;Ck)!5?D3rs%We=;xR?o=pUw|40F9 zN!5PTk1)z;@WPV~sJ(9-R6!KC1b~0**;b8wE(4Wp#5$*fInAguf6}C=9wLxHLr#*? z3{14uR@T20ABVT|3<1 zdS1lp^}6pT2aB2%^+}yZFVOMP*^hZ z`o**a%6c(}K7$m|P%1T9W8MWlan%NdG&OF6(0YGBc~3#*N8iFc=uAOtmX)jh>$stW z?~u+00rUBDJ?=?_9#+n7zRw=GVG09{(q4wS`E>sCd1-R*kH^c02)+v1+?>yWaUR@z zs)au8((@6y3}%8eDy?bzDTPNybJsyFg0JBx-Bb<%p=!O=FG}Bv0Am;=jF4GPiuVBf zwG4&yN0gyyCCT@?!(C@2xopT9whR)`vQ1afgxA%F` zlMSs2jjPOhtl|;zEtv>f#|`fp_YR}{^Bwl;Qmq*&DW*W7>`<}(q|g~>i3!S5N2lw& zn8_h+a4zNmcMaU-B^Ou0JS?tYbX`^9X~GV$N(U$SV)7^Inzh7mCMp+KLWwR20|A#m z6|x0HkNgO<I4WiijAeu1@v!9}+u~t3Tpo+C^JvpH3jm-W_7Cv`?0qIF{!OA!T6UFz7Lic_@B+ zNaz8ysDrI!7+ShSas=?hn;co5Eb;cP$fhi>}PNAz&7odALN9a%`R5c zUXjyEgNOSBMGZlL8wZ!;S>tPgj0y?Q0^xX+a}(Z8rSu6YDjBO|=*DqB(G_BzZa#G` z?>oa5Tt6k?e&I*LKiw`*3^ADdCwQHP(dl&udv?;r2ro_PTxFTwOOc63+w6UYA|}S% zatJB!c=r}#K_mz$#c#(~j``!(e&}N&2*@0M8(061t0CcOF6Ii>(0jiq+eY&i{z>~3 ztyR!V&Bm~pI%>#Vj`d``@*J*z`_T zoM82^4vYxMEO-ieN-wwMZ3ecpP`-M6jSk0Qpot8zE~Z>)?pIwAF5*+lj^k_84d3ft z>t|32&6Y%lQ&|xU+6+Ex9sKKb-|(WBG&Z3ZH1|i#4ORxGoY%a(wKRb$C+Fvx3*WfO z`+5EFGp5^2gc!riCTabJ+?6t))Q(t2jixW~2Q_kIr*;68 zc4f2-!|)J)_4|0j(fCYPr~OhhkMMVISJIo=qMr10wS0~ACMygP;h@d4)4==2uCA)b zKj#_OYD~g*bjOJ#lHzh)JGuk5QRXW&>m48D_3>a=k&TBbe6tCp#jlR0e*leQG_qI( zdTwe4AL^rbazpoCDSS(XmY}HOe0FYCK^X z@d4OK8Smn{kOr2{L_w{+Cd(!YFO zaWQm=ztEhVjX@`k%b&p$^Y4b}HMWb$Up`!4E#@a+;0}VNB{fUaWM1!u;IY{pNu|I( zX8wm2v&NUq=iOsKiR3ftL+Yh?ory@*VRXpljV7?N3j;p<6CzlT9~>2LhW7-!fFN3g z-}S1~+i~!x;{&=!uU<-$i%d1gO#F}6VR^K3P9^U^Gx|D*EX>98>2H1Gs;HVQ92ULs zExRhiWv-)#c~t2<6-oU8?5j^!rKFM?+}OIh(MwaQbUYPWf*GTW4YsfgTc$FPKUB62 zTYxF#%|i{n%Qc0j@x$&r(J-Z1nC^nzQKM_<((1#WDOJ_4pPF-&;Y`QaImUuRiD-v1 zp{K9}eTO)HBKzZjD{&FcTx=JIlmA_iq4oB=YOWyI0fwkFg}^yyvuq+XIZnrMA?AN} zBe~Dg1q6ZDl-*WG-MO=DTiUE#@hD!+t18@zSTl6`BL4~~!+2yW1ZO0FswAAH9Ovv8 z8y8>~9PpV1=DQ+fj_Qa3FEguxeVy(g2j__}cPn^OJcT6*t;T6UMfs@MN$}Q7QRlu zi`{C~*cH<>T{(d89%oi;DNl3hqr&2jQnFm6%0ubQ2`F zX%1;kKH<0r`}poX#PDO|_Z8MkwSS7n53|}Z?DO_Dhrs$`6ZI*VjXOGRk4L*}o~*$! zRq)?m-JSAnZM05aOV*d5%$UGR&!W0W#n_>rLi)~BG|tAV6)_O$w?P5CtNbvp5?6dQ z`kDyrU2MM1zMl&Dy|H|c7U*XJy%~^&Za}8FQn?@E`E=E>=qa9Ty@qdR_iSt0D?wup zIh<@lURTmNht;pfp69V-)~qo<#r@Ac`goCN5KGq_K9xasjH_QcYx|rCX7odfE=0Dc{;nZ+2uwr}u%zrU@qp6#wC+i5 z@I%{d7ry`5?>Qu)t?V8-eH+h2(cA9!3>6Wmg&D~v#so=|i@NH3!doS-9K)ogwt2Q1 zuv0flHD#rRrsHK0=rNk5~m z;`;gd_4o-MNY%wT8FiE3xm~7|Bz;cHTOE(OeMo7wkdP55$iW{f2!`*?0s&3 zE0s{ODkG)l=}3!oV16l08_S=GS!YH{l_RfY!@G^e3?znq_L$^aI&m!M?(l_Le-&mj zRxOj58nWOW@=Cys7PeysK*T5j(U=U-0TxJ&t?c8g z%=j6vTTi2_74r#xfI&)x+Tk6|NPCpQS<0&5b8~4{T*2%0 zWtNxEcXS0el-e4Nvruzp!h>dXox*fhsxBoEEd!4ndQAgF-0RbkccP&fgx3H&WMFYM z1|VbvgAm|SE7rsr=&@XDb4??i#bP;P7PdM_MeHI>C+7RHvOJ%+Xd??Efhhj5X=7jQ z!(<}-0h2~5bWs8L#UYr~dkeaXr*{V~Qa0(nW%yVA7h2IchzLN(g-kD0oH#39NtkV8t@$6%xjk$AjshMDj7M;%yh@_f zTptlFF@)6=$crZ}6{%x%r>TQUA8c+oWFuU0Gs-aikXj`+(S#Cu zOaO^5J7wi;_UYB+dp>&!{||(oAh$GnRFODI0VVViaN~wbpi-4AJDz=zO$|gUR(T`&b0@+;=!IVggnt%me~DW zce`3A_(|~L$CgY(gqi^rG7|J8Tm0gwOztmm%1#wYDw%V8kMFB-Y_hE(c4@?b-N=*J z<0{HrlXIljdp_@lEeWd@WxtWNWmgJ4Rl|t|&^6c#f#l@Ds@AfdeOFz(`ZjpsPJ0PnGLs*S@}^N!L?Do`L#~|W z^|a;X3xZlUb%Z6kKn|8H0(c5!4VwT4Sr}C&5m8*HT#NbMy|Tplk7NIQ{o^odDJZ~R zF&rEROnz$)EA5k!9OQ5V)9_^^;#*F84uMaaN-tB9qroBLU(w(9Q)6_oHaVOd+Q>(*k>W&9~Ad8 zo4$Hgp<_)e8EU#w6%W`sPIzxjO2ow&7pC~Oj6sH>YWo!nG0ZKQKTUWuvC!!MMK0uN zS&~|L#+?>#qZ$LXD*cJW+*CgFO;%CMxVQ>lbNz>49?w8u_Z^RDO^FEU(8>2Rpac|~+u znkHMSwT=iU6L4x{V*GDU8n~|{kWpaU_{m3Y{B2?*u?=*7{mGX9*uJ2LOD*L03XH8} z6c$?}aDoJ!GWxItc4YIv3Bs)}m6iFlF99Qtbg*A$#%3aOMoXZd^P^Zcnf*|^Lvz3V z*FC3&wUK@`X`d;>VrPhhl}Oz~PTs!#%Px+eDd(CGus!@@B|ex*BM?yr8&wX8QE0Ci zQo|X7OaC=Rz{PQb>#WFLsq`-r6sjeJ z(oR=X*lFk}8zIb>+iBvrZ>jtoG!|OR4!QgjjpRKPE8LHDijUQ4S~LsRS9e5_DuMM6 zDa_D0s;IZ*b@^JA&J(H5-8B}sq{Fc26wes{Q;Ik<1OMXakfM;uGB}!lj-zO5Gn(n`7 z*nyI2zLJ<^vdzi7Cg_x8!goC5F`JEJS#F=J{U}QeFIz+&v0b+q{S~+B5e`y%gO9~M z7QC3m(Q}ZodDM=!Er<;m3m&9|aALv?x58V`Og-LbJ`n`9f17&U9diC!i-`{de?6{A zM$l~gcDOX~X}9~L(H4|i!GImD3BYu7y{!_TC9ZIEo`n;G!`#gnI?+GTC{wYJJGA%; zs;%U047w0rwAeVvriWoXQf(g!7uG)$OPsi}jaYp?zDwEE;k`o`40{)ZBzI4AG$ z)5+?Ky3#>?d?tEi725$?Jw00VIRWMs$$`vYtpdm)xf8O`zdr$Z(72=K5wZbfZwWKrtE^GY-ZmM}{wjXSbW9nS$e%=az*21#c` zP*6gW5_|jgVjiRz_ggj}JAWC@0v2{qO?(!@4{`E9s$wX%IZn8{L{$*D4(J z3Gfo8_7?C*hw2}brCL?jCcZ~XT>*u<>d{wDUks_2xTxvOY^H!Pjs2>mu0IjK|EOVD zPi(@7)Eh~f2tIuF_M_3X0-{JHgg5y+x*{bln&$pBo2L&r*Wmj(Y*?JyUpbDpXr?MQ zP1W+$&<)IVrI89trO0XrOH2mZqP(i#C%y3$dF-^ zjFllI1jr%%`MV&dzS938=wLcu-24R}*=6i z%6q9Fu%FCHAACbKLHg)nyga@QuW`1n5wSU}b>&<1?$sT%L%U(|q#yw2ePe~!3l8*C zc?}+tGF1e@95l@yV3UYQx6RdV6a{lH?>@N-NI}WEy5%BIPp1ab8wa?zo0&1sR*0zo zNd#njl=G%m&R+E&5t!_(cHR+dJ4@B_4b|FB*BlvaI57>7a(;pj<#+> z82S|wD3cTkKfCjNa~G5cB1?yw-g(s*yH{NE&in{|E&o9_dD6#THq@eh_qLw018xW+ zRg$_QPuMMsP+-p-PgOg!j&B3>3fn^=H%_;2)vf9AJX06^5Pb`@hYdk*{{kBl+wnc2 z#_+4|BbOxUN$_h)zA4vCO-9p2pIA=v2G)*P%O1o=IA~Lr=Sp){@vUWO)QccZ-Ej`a zWcQvpj?E`^bITo~;I$55u8V65fjX0WJ~AJf;%}JB#DVKyQh}sIf!A$({v|J*qy
j#(n6`cTK z7WaNlSbCU2SYaJ~J9!EIl=Absd61in`6c7 z2!rKnZY-bA9QxOd{4Z=S0_3y53^x15sxx56rA9s3^eZ7eRU*!T!jS;brox|@Dmbs@ z)LV{9g3&pS@bdnpPmjzHE^TUkmTaE`4_*q=x`t*bmC67J>8E`rU!L>bFU8ItpIBK1 zt(tU#bBZILUVIruUJQMfM)-V%6~kN+00(_J2iOS{_jN4?CDqbi{V#5oC*4Ics&)CL zfXG;fbi@h`QbCfpy~%g39f;ohc>dZaaPZ>!3@VVdYc9woE=YPAJ!M1bIamkPi`ic2 z=3^)V0L54|3FQZKFz=&B6nu}0Bs6*^vk6umxWDbO?2NMj(q%JH0LEv(0$S2O6<(Rz6q_TTo5=jq3I z1^Mj{;w{@ZApHzNSjiXISH&A%b}i6rLUlvlSK#hjMIJ(KX5fOCMyc+NjS2rMP&OL-kT@XW&D|OMh!+FR^9qfpeKhJXtBu<}k_Gqld1UUogeKE` zMNL%XNxW3J0P<^fy8N{}el#M$1(>4P(D;IPd4JZT(mR9GkKtg9jtR5eH#&zS>8#@GR%W3)WdwTfIV-;V;gDS{Wri zspuIA1wsTXFH_( z^OMtaCG-tXX4EI@`fjlW{)p5*!^a^KWusC6=q{RcQgzY2{k$FNW>E+dwP*Pys-WNR z6yR{%y{MhDi=Jg5%f9QCS!_f0Yf-w9P!Dd0?>-@4wJihJ#I~jE;qqP_MzHmK+(7sA zwABxmOVYf34Xd~249uYFxHjhju)>@|azjc=ClaXa6eAn=J9PFRrFm{-I?wqXU`5On zM)uAw9hq(e+uETgY0ABb{p^n0*~&axWAA${`(xx?AlD-*o(f*v?Nv=4()iAk$xB<& zrGeKkHs8+`l2B6Fw@X%UFL@dg!j4J`?Yjg9!OxGw6932*KgR$RFIKB?y;+#o)7n{g zL^s_2;w`&d<$Q&T>nXf_&fo=-&9{>T+cnrN-hPDU`etnykC%_k(5JUZn&WpH-wKP|-=6QPL;+I;sbYSMWotrw>4(9M zCqA>k@Ijgf%85^!9Vb>XJ<3Dozp2&xe)V|AWVF(`W#V&&C){=&>$*ENLjP(;M zlSg7yCf;ZXaYW>`l-aA`{Z{NG|AlIEKHE$kpK-!`U}WJG9WS0L4puU_~`;D?Fealy0X-<}1EccbywkMOL)WgdPk zW{%$HX9x@R8M%l245B&V|9>qq6X8oql;2WYlA+i}_q)chCkFQ%vx|ys&)b&cyL?oX zHOaFChr{XAKiPT7r;mp8-(F#E1xVu*>36zEio1&Ya#z;020=SH{&T?hz&ENy0=?IC zRQ;V??ZuC#L?%U$voY!P}DX_)CCsy6-b}4 zR~ucq*?0P^6auWd$Yp1Yonm{d`Ll+~MHLr1vvB(H?BvN?-kEq#UdDv8HiqG!p7H{< zzHR2?4}KLqeU57~#q|(n9i~*U!Y{fvc`CfkF?ix*d#jr})6^S21S*Lr9QlBxJ$6jk z%;@Fwc(-mBd^Wj=Bf_bJP3@r}`iYK3NpB7qYgd2nvc;auHJVG#EV>?gk!#XL|Ej|- z07z9Tt(#3dy-t5$WUQq|=_R&xeLQlni!nvaeb)`eWN_>>g}zSWc#q)XV~)8g7rdG| zg83mDXtCS70;cKWO6wsK`}vyD;f#_cgIq#|B-(gT6O1V4JKgxM`umJv`(rR27TT0) zh@VUAhHL5axx$8ZfKxKRo1#hI*I3ikE`jNzIykeVSq*3O+`5E#%*Yu@$R@bo%^yCgP4dx$?N+N$<4V>l;qZ z43gkjD*&hAhBg*`ZBD?%BumAf5_9p3DZLVUg6cl=FIEi}+X(E4!9Pa+f%`dle>~kY zO{!`axsp*(!TnYQCMUGk`GZ@i98|1`&pP9$8EXTY@~@&Tmwu^1HLoQ_y<%d5R5^B! z@x5Z%!w@_A5~Y}g93v4n{i}5JHW5B$8JD>KMF<0A2!2h*S4P1cL-|5s79sApQ=?<^ z2_J&cSe~=Bb`3dfkteP*MZ`LTO**#cs#HYWeWrbe=xGbcvkKgA?PQR@8G{#5f{(Qv zMjF>>(DZc?+5mV)JI>ZdvR_!o>KBgb8^nqp+tF%Oaeaf?k3s?2sl>=B{dTcy{dO%n z+YFEklA?*ee5&j+e{n=vYFI-#>er3qG?|lzUj13oAi0<&C?4U?iC>Ab2R@9}dbn#B zPR4qHT1qcF{B;|f9p&`CN_}m?A9^}Tg||9lm$}|od@U(<3anzmgEvd^v-bnYHMBw} z3xsxhZ_^lmHj9kdM!peie2B{lKV82~Np~V^cuMk4{0Pu_8aQzY5)GJ%bMXCql%rPL z$&a8mKD{_KiJd7~-OoKId)Pgz(i837wS_ z`{8iqe8xSnz?yQyownR}zqj8)8I&(}9>J`x{3!hQ+_8O9!5yRt$8+Z^bUvT{uUa<$ z^ZK`W`pLB5P5~EbCk>Pk1sHjA1jzcG@{U$J^=BeWPEA4qPlUsijHARYEm1%lw_zdF z;M@~*?a#0b;CYqFQLExNU~+CDsvnJyA6Pvck{ zNGUrs%yzKoZErT;eOh2Yf!2vuQ9O%frbH(F*t;A!R+p#jbq!m)@&l6Rt-k*is=Q4` zS9!(EF1B1{haJ=$kQAIaJ1Xa^Z>u~AG%=zs_!B!b|8_IFgGdX*QQVl^m?*NA#g<9* zM|Y(I)Sx>t?w`LyI-jyoV)`YX8_Q*yW6YtIkW}@^J9m&<8!<@^Hqq8YN{&#aD0-NN zpdr@Unnh5E%YV$u`M!yK=GK;)hkiAIfnutT13!S&hgIF@OEl2oSri-}6&?Ka`d6@4 zSOQ7j-#Y}r07ZDhQiRYlOo3#ZFxVugoaiw1g$ z&OAB$mV5a;3-WI9l?rDeYD`p$O?bF2g%W6OO=|se`WM<%RT-m_M~!6&b8v)!J=h#u z>r^}2M$#d;?KV6%a+`_rE?Y|bTR60Xyj&x0B$ugu@1dTp3H|m>`;YUiH>l}qhukEE zOzE5^-3jPB^b)?PKaB~Xg+9RlmGH8EplsB9UdJZPk^6Y2Sdp^x6Dv1RAx;g-3A&At zVhSBDDd^9<$3(Q(F8SG?J4?$>ch>XWmZhnx^hUVQRVYE4LB)tcTvByu^ki(j8%wwH_j+;xK3Tq1hw0-v(ji}QIN zJAnJ>vXml|)tB7`BTuJy&riROoq=Po7y;MZO#^Hy7e56kWA8tTA6B_w#gTG2SfPDH zFJ-do1#dIb#BLP@Ph<#b>10r_Zk`%Ti{Yr}XpR)^A;PW}F7W|#Q;AnGmz$sf%W8|n zm9|R($TfuSn~(+siOtkkN`VNsD{UWchi*?uDGtNvs)~vGA(}fml;TcdyU#i~va~mW z==4u1InZ5nSMvzLh(-WutdxfQMQj%ZJ^)($0kvDq5Khw!E*!y|zcak&A@}NPf>f4T3Y<8(77d#ZM7$|={ zd@3a7!7_zsc7zY>7=Mv=uXehX5CT6L~llK;U@;vrNLcHf};69z)cf zhBbpskIggkh=PB<>y^3I?I9<+;~E#U#-^0^8Tau9mtt7?=2He;gc2 z-iUtfpki+ZcYq=9ZzKswC!>2-akmS$9gF@6$n7L%iY{yv$!YOwD+Q3S)qGz{Cb)9QsmfSqDO#cDHSz51U|*<(h*JmG!ZJECrA@+j}XAOYyUtLxO#MDHi{UX+ST{ zwh4Q!ghgp_L0W{!w=16gyAOTS{hk{6IupSG4Z5+g|JWw%n@{iFYd9yu#H9QNiJVEq zfi?)Z>9PiP_XWpIgD2g}@-^VF*p+!pY+Yt8dtt`>WVW#Gqn*-2PiyHFA42+%4;sON z7-qz35-6GdFQ2s;phwZNe-fk3lWPL9;Z*N%qabB6yiPe^7gc)d6~s~>W9$251{R}R z6{EKKU$ieepBr}2eV=Y_=nv?aN)m%#zW={&;u6NViOWE1@>>g>UkBRm1M}vpkqzDg zxv*5^9CZP`Fs&)i!pwe?_cDLT(;*q*qvmgR7S~ZfE@z_XO>{f2vVM>rJtAG{5-LIu zZhj%6z82u<5!ij)yFdu)WNLN6NDyOipa4vrTA%%{Kpd-^8E?zWyMEh`-I{jfW>vsK z0_-WN0oPL+G_2any+F>#;o#>$M-vf^1MkkZ!@H3$Sut}Pv+?RaB-1m@X1n6Q^4&!)Kop1iG z^EdAZ0|RH-0Vmh*uK5UMFci=L24Q;n9#9;o&?jnEA@W!KkpsT>K9@Ni{dT)f0Avb~ zAU$_^Ubrhokn`;%9X1L}z_d3QXs^vt``MgWFgPZvM4e*pui6S4=HVkS$iPkg(# zhRK-pGi|prP2|h-bj_I;UA$LRE&shC) z*9Nc4?XUA7Fh+!N=k=9vo4~=A6dcWGtZGY06YeIO>F#ID7*f#5(6{@&evB+^dte+X+S})l`Ps2zIBRIhT`_?L6T6rkq&V=@U z00}xQ;7P&Gt%N4SgW4&$tBT37FF&_`&+yj;6O-YtCI+??jJRE$RmnYw+ePR0>|$_< zRRw$oY9hGqGti|}?(}+J*g^=Q4gmln$LY7MBRGyP^ap%5R5zWBjn138MiZnf#W6)- z1~n&efjQ%%i?NI2{aHc0m!U<*&d--*H(#_ejR(Rgjxh!uAZ3OqB7vMq*UfK$P(G3r zfWZ{v+M0xRQo4xp1rfFe71XPjdi#7&N5R$37^L}&4oEXKA)J(f5(4!5g!R`uKHD=B z!5@_U=aEkRq-_iqaivq_A$)MqfZn;)+VpjC&#Pr~$v(;3b{nvW{ZgU1lXy0=4z`AP zHF$6g8fQSXB4>TXiea3Js;9>nCMB*9P^6&SYAkOa!EbRIu$!{Zw||WntUV)%=RsYuaGq5BBaKXKZKkr9A1n86;IMozQLJl=QV zQLV}v_icQItVf#<3c4-+b3qLES;}ItGUO^qJ#Y?P9BtM3XZL7mHD_7C$td$lqd8g#7G3FJ9 zC?q=p!M8)^M9;B!N--N!nTXKy=w@Lb$Nu-r(uSkXd>j`RWGJ;|0Hm!%H3>G#>B$C>~5*erFo>G(O4uWx&RGUy|| z`55deGqb2L*JW+`bh<0MzQR?LM{9^wf-Hle#-jU+S(-R# z$$9wjzJioWx!J~Owtb@Cq|f5ANS98o9LFmC+%wD<1W4F*M}z{52WjPemI%eXiT^@T z896x7iuq!|3Y&==8M0hd23{&cV2a%1FH+ty5XHdS{5$&T)Ss^D@|Ilt+UE?NnM*MO zXXTsRoY@Ohc1ZmvXh@r9euy45CI^ea@mW}qWvSBGFh%VMO{%I8{? zr>ZKfo3*gWZci2>oVAPG!L+%LlyP&J1D|lloZ{t|#xNcO0g99O5WLxVa0Xsv$O*9h z4zb3`6lRwBGm%li-0o}a_)-8V%AWDuVR+!MB01CpHUmmnT#&oFlY*|`Orzoa)dobx z+9^4JjpL_9TAni2kyQ253z2XTfX>Vz3IM?A*g%(p6)uVwR!iYGL($IP;Ch=GP*%=+ z!?Jha`#pPF9pVB+lhv|iil`R1!-{x?aWNqdv|o>?c=n$8w;Nz#{&v6@+tBU>`u5kr zZ2bEHf~i}FB_e?R_J{IBNa8nwFPv;uxE(Q$#{AwMPrnGRU5tb36V^x_k^;EIRAyMb z@kmHQ2(yQA>8}~hEAMmI2PA3tK|SOSXMR^%jwdLPWO{!qyB?X)s1g!|#5~08U}lKf zX+6+wTB?Gd_fBB3MEBbgS8eZaZO|a;*7&Ojfs>P1Bc;GB_EVzsYl2c}Su8~;bizOo zLQDA(W@)5hM&3o!Q?G}^!H(wurBP$A)IE_oY$*3@;1VD731kQbH`!nT*`JtGIGpx# zGf&-wlKDC3qmd+;8#ceZmthyZkoVh+{610#JD`Yhbio*zN5;#2!Q0_PM>5a zD*azgWs;|CVg+_&SPm}FRb;ZsLu&fA|9eG`V0fuSr3MUDHNtQ0$Z>~Qp)v}1b$wLJ z1j65;FifqOH;IJb!|*q7s044WRL4~NzOCn2;!|(Y$=lesLbyI@g~%Gub{rEv4mSRE z$T>aGws~al?gO=RD!*4|iS-5o$tn*n|14Lkl&ebm(T{i9*E73%7W)_WmEs)veX!u$; z<)56YiMGDk_*{?6v@Trp7WTj9n=%zCZx8;1Q7si>h6OM*(Y}4+z%Z^2fvLdpBz_BPWJa=X@t2RoRYHx8UDc(FMDes0#t{m zJN~UZ$e5hu)m+P0YCvsy#gNyUH=C`7IXXc&lq<( zO=8fzy=*Cq(L{Mx-sr04QO1bafq?WCbYv*Nlnqbb7jbK3#5TOO&jZRZt`;q=3l_Kf zwbFyo9ag`ZTaEe*d1r-qtj4l_+xE^?v|B}lH@%#hmQ%17FXroFh^odA;zkaY%b+cr z1vBbDoXxt_A`j@Zn@HrUimr|C*wO@|IiAYrs(9b;?+{Q)7N{&IT?EEHwYeZCK0EfAr>{ zSRY-~R@`MDWMVA+;iNa-&W+>Y#$o&c!?x}-bSxEyh4U4SP=i5ny@cCOJQpekPUBr) z%`_)A332nP6s;}efR~4!0G;Xu3VUqyjuPl zBj#Z;-t*TJfm@)F)3;ogmTr@EM)&o)4C0lYKD<`V?}Az6Qlbw7v$n=QuK>--&qz=J zCW{L4GdjWuURi9z`*yad_4?oR`D2>DOx(^+x}x-o#wm6rKePc3R)_suk) zNa)2_=Fl*eNDkTBb3(dy^J=4CNadCJaec>Yy{S*h&4#`3^!i>VO7o`YG|OL=ft?KZ zZDFt_IvPWK%sCztP#l&eCZdU2tx2g)L6c>?=e|^|)VIv&nm6ehc1VL3Dd`o#J8MTm zahs$0vQ!{j-ril&)?TpOW=m8o32$HdQOX2Dt2J+1`qJ*Sz}-YGSO1C7H*j8`I7qv` z-Z#NVZ~k7(&o=lg*jNtqR^G}kt5mjL*sbWYE3WhW-D~ApZv1)e5FTE0{^~O;z^(lO zb{Z9dBQ{KRPl8Y)yHs?}w@C&XDfb08K@=4NK!*l|P#4AM%#yNe#3~|-%b|mkMfjR1seCoi?DE5+n0dikSY)(~K(n8h zfDn%VdVBj Date: Sat, 28 Mar 2026 02:03:30 +0200 Subject: [PATCH 59/95] feat: cover more cases for data-tauri-drag=region="deep", add example for QA (#15164) --- crates/tauri/Cargo.toml | 4 + crates/tauri/src/window/scripts/drag.js | 70 ++-- examples/drag/README.md | 3 + examples/drag/index.html | 418 ++++++++++++++++++++++++ examples/drag/main.rs | 24 ++ examples/drag/tauri.conf.json | 35 ++ 6 files changed, 523 insertions(+), 31 deletions(-) create mode 100644 examples/drag/README.md create mode 100644 examples/drag/index.html create mode 100644 examples/drag/main.rs create mode 100644 examples/drag/tauri.conf.json diff --git a/crates/tauri/Cargo.toml b/crates/tauri/Cargo.toml index 071076fa442b..874b986aaac1 100644 --- a/crates/tauri/Cargo.toml +++ b/crates/tauri/Cargo.toml @@ -240,6 +240,10 @@ path = "../../examples/commands/main.rs" name = "helloworld" path = "../../examples/helloworld/main.rs" +[[example]] +name = "drag" +path = "../../examples/drag/main.rs" + [[example]] name = "multiwebview" path = "../../examples/multiwebview/main.rs" diff --git a/crates/tauri/src/window/scripts/drag.js b/crates/tauri/src/window/scripts/drag.js index 2b533549a895..5a0b1244fdc1 100644 --- a/crates/tauri/src/window/scripts/drag.js +++ b/crates/tauri/src/window/scripts/drag.js @@ -9,53 +9,61 @@ // moves after the double click, it should be cancelled (see https://github.com/tauri-apps/tauri/issues/8306) //-----------------------// const TAURI_DRAG_REGION_ATTR = 'data-tauri-drag-region' + const CLICKABLE_TAGS = new Set([ + 'A', + 'BUTTON', + 'INPUT', + 'SELECT', + 'TEXTAREA', + 'LABEL', + 'SUMMARY' + ]) + const INTERACTIVE_ROLES = new Set([ + 'button', + 'link', + 'menuitem', + 'tab', + 'checkbox', + 'radio', + 'switch', + 'option' + ]) function isClickableElement(el) { - const tag = el.tagName && el.tagName.toLowerCase() - return ( - tag === 'a' - || tag === 'button' - || tag === 'input' - || tag === 'select' - || tag === 'textarea' - || tag === 'label' - || tag === 'summary' + CLICKABLE_TAGS.has(el.tagName) || (el.hasAttribute('contenteditable') && el.getAttribute('contenteditable') !== 'false') || (el.hasAttribute('tabindex') && el.getAttribute('tabindex') !== '-1') + || INTERACTIVE_ROLES.has(el.getAttribute('role')) ) } - // Walk the composed path from target upward. If a clickable element or a - // data-tauri-drag-region="false" element is encountered, return false (don't drag). - // Otherwise return true. + // Walk the composed path from target upward. // // Supported values for data-tauri-drag-region: - // (bare / no value) -> self: only direct clicks on this element trigger drag - // "deep" -> deep: clicks anywhere in the subtree trigger drag - // "false" -> disabled: drag is blocked here (and for ancestors) + // (bare / no value / "true") -> self: only direct clicks on this element trigger drag + // "deep" -> deep: clicks anywhere in the subtree trigger drag + // "false" -> disabled: drag is blocked here (and for ancestors) + // + // Clickable elements (buttons, links, etc.) normally block dragging, + // but if they themselves carry data-tauri-drag-region they act as drag regions. function isDragRegion(composedPath) { for (const el of composedPath) { if (!(el instanceof HTMLElement)) continue - // if we hit a clickable element or a disabled drag region, don't drag - if ( - isClickableElement(el) - || el.getAttribute(TAURI_DRAG_REGION_ATTR) === 'false' - ) { - return false - } - const attr = el.getAttribute(TAURI_DRAG_REGION_ATTR) - if (attr !== null) { - // deep: the whole subtree is a drag region - if (attr === 'deep') return true - // bare (or any unrecognized value): self-only - if (el === composedPath[0]) return true - // click was on a child of a self-only region - stop walking, don't drag - return false - } + + // clickable without explicit drag region → blocks drag + if (isClickableElement(el) && attr === null) return false + // no attr → keep walking up + if (attr === null) continue + // explicitly disabled + if (attr === 'false') return false + // subtree drag — any descendant triggers + if (attr === 'deep') return true + // bare or "true" attr — only direct clicks on this element + if (attr === '' || attr === 'true') return el === composedPath[0] } return false diff --git a/examples/drag/README.md b/examples/drag/README.md new file mode 100644 index 000000000000..593d5753cd9a --- /dev/null +++ b/examples/drag/README.md @@ -0,0 +1,3 @@ +# Drag Window Example + +To execute run the following on the root directory of the repository: `cargo run --example drag`. diff --git a/examples/drag/index.html b/examples/drag/index.html new file mode 100644 index 000000000000..49208b182506 --- /dev/null +++ b/examples/drag/index.html @@ -0,0 +1,418 @@ + + + + + + + + + +

Drag.js Paths & Configuration - QA Test Suite

+ +
+

Configuration Reference

+
+ Attribute: data-tauri-drag-region +
+
+ +
+

Drag Region Values

+
bare / no value → self (direct clicks only)
+
"deep" → deep (subtree clicks)
+
"false" → disabled (drag blocked)
+
+ +
+

QA Test Cases - Try Dragging Each Section

+ +
+
+ 1. No Attribute (Default - Should NOT Drag) +
+
+ No data-tauri-drag-region attribute +
+
+ +
+
+ 2. Bare Attribute (Self Only - Should Drag Direct Click) +
+
+ data-tauri-drag-region (bare) +
+
+ +
+
+ 3. Deep Attribute (Should Drag from Subtree) +
+
+ data-tauri-drag-region="deep" +
+ Nested content - should also drag from here +
+
+
+ +
+
4. False Attribute (Drag Disabled)
+
+ data-tauri-drag-region="false" (drag disabled) +
+
+ +
+
+ 5. Drag Region with Clickable Element (Button Blocks Drag) +
+
+ data-tauri-drag-region with button inside + +
+
+ +
+
+ 6. Drag Region with Input (Input Blocks Drag) +
+
+ data-tauri-drag-region with input inside + +
+
+ +
+
+ 7. Deep Drag Region with Clickable Elements +
+
+ data-tauri-drag-region="deep" with clickables +
+ + Link (Blocks) +
+
+
+ +
+
+ 8. Deep Drag Region with Non-Clickable Text +
+
+ data-tauri-drag-region="deep" with text +
+ Just plain text - should drag from here +
+
+
+ +
+
9. Nested: False Blocks Parent Drag
+
+ data-tauri-drag-region="deep" parent +
+ data-tauri-drag-region="false" child (blocks parent drag) +
+
+
+ +
+
+ 10. Double Click to Maximize (Test Platform Behavior) +
+
+ Double-click to test maximize (platform-dependent) +
+
+ macOS: Maximize on mouseup if cursor unmoved | Windows/Linux: Maximize + on double-click +
+
+ +
+
+ 11. Deep Drag Region with ARIA Roles (Role Elements Should Block Drag) +
+
+ data-tauri-drag-region="deep" with role-based elements +
+
role="button" (Blocks)
+
role="link" (Blocks)
+ +
Plain text between role boxes (Drags)
+
+
+
+ +
+
+ 12. Clickable Element with Bare Drag Region (Button Should Drag on + Direct Click) +
+
+ + + Link with data-tauri-drag-region (Should Drag) + +
+
+ +
+
+ 13. Clickable Element with Deep Drag Region (Should Drag from + Children) +
+ +
+ +
+
+ 14. Clickable Element with False Drag Region (Should NOT Drag) +
+ +
+ +
+
+ 15. ARIA Role Element with Drag Region (Should Drag) +
+
+
+ role="button" with data-tauri-drag-region (Should Drag) +
+ +
+
+ +
+
+ 16. Bare Drag Region with ARIA Role Child (Role Child Should Block + Drag) +
+
+ data-tauri-drag-region (bare) parent +
+ +
role="switch" (Blocks)
+
role="option" (Blocks)
+
+
+
+
+ +
+

Clickable Tags (Prevent Drag)

+

+    
+ +
+

Interactive Roles (Prevent Drag)

+

+    
+ +
+

Window Commands

+
+ Command: plugin:window|start_dragging +
+
+ Command: plugin:window|internal_toggle_maximize +
+
+ + + + diff --git a/examples/drag/main.rs b/examples/drag/main.rs new file mode 100644 index 000000000000..3f913e593ae0 --- /dev/null +++ b/examples/drag/main.rs @@ -0,0 +1,24 @@ +// Copyright 2019-2024 Tauri Programme within The Commons Conservancy +// SPDX-License-Identifier: Apache-2.0 +// SPDX-License-Identifier: MIT + +#![cfg_attr(not(debug_assertions), windows_subsystem = "windows")] + +fn main() { + tauri::Builder::default() + .run(generate_context()) + .expect("error while running tauri application"); +} + +fn generate_context() -> tauri::Context { + let mut context = tauri::generate_context!("../../examples/drag/tauri.conf.json"); + for cmd in [ + "plugin:window|start_dragging", + "plugin:window|internal_toggle_maximize", + ] { + context + .runtime_authority_mut() + .__allow_command(cmd.to_string(), tauri_utils::acl::ExecutionContext::Local); + } + context +} diff --git a/examples/drag/tauri.conf.json b/examples/drag/tauri.conf.json new file mode 100644 index 000000000000..ef823497a316 --- /dev/null +++ b/examples/drag/tauri.conf.json @@ -0,0 +1,35 @@ +{ + "$schema": "../../crates/tauri-schema-generator/schemas/config.schema.json", + "productName": "Hello World", + "version": "0.1.0", + "identifier": "com.tauri.helloworld", + "build": { + "frontendDist": ["index.html"] + }, + "app": { + "withGlobalTauri": true, + "windows": [ + { + "title": "Welcome to Tauri!", + "width": 800, + "height": 600, + "resizable": true, + "fullscreen": false + } + ], + "security": { + "csp": "default-src 'self'; connect-src ipc: http://ipc.localhost" + } + }, + "bundle": { + "active": true, + "targets": "all", + "icon": [ + "../.icons/32x32.png", + "../.icons/128x128.png", + "../.icons/128x128@2x.png", + "../.icons/icon.icns", + "../.icons/icon.ico" + ] + } +} From d1dfe6018d6f3fa9e2b79ef037ebb358603f60d0 Mon Sep 17 00:00:00 2001 From: Fabian-Lars <30730186+FabianLars@users.noreply.github.com> Date: Tue, 31 Mar 2026 12:44:38 +0200 Subject: [PATCH 60/95] chore(deps): update ctor and napi (#15183) --- Cargo.lock | 93 +++++++++---------- crates/tauri-utils/Cargo.toml | 5 +- .../src/platform/starting_binary.rs | 2 +- packages/cli/Cargo.toml | 7 +- 4 files changed, 54 insertions(+), 53 deletions(-) diff --git a/Cargo.lock b/Cargo.lock index f0b7ea703886..ae1efa3b0c81 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -1223,7 +1223,7 @@ dependencies = [ "num-traits", "serde", "wasm-bindgen", - "windows-link", + "windows-link 0.1.1", ] [[package]] @@ -1397,9 +1397,9 @@ checksum = "6245d59a3e82a7fc217c5828a6692dbc6dfb63a0c8c90495621f7b9d79704a0e" [[package]] name = "convert_case" -version = "0.8.0" +version = "0.11.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "baaaa0ecca5b51987b9423ccdc971514dd8b0bb7b4060b983d3664dad3f1f89f" +checksum = "affbf0190ed2caf063e3def54ff444b449371d55c58e513a95ab98eca50adb49" dependencies = [ "unicode-segmentation", ] @@ -1671,19 +1671,9 @@ dependencies = [ [[package]] name = "ctor" -version = "0.2.9" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "32a2785755761f3ddc1492979ce1e48d2c00d09311c39e4466429188f3dd6501" -dependencies = [ - "quote", - "syn 2.0.117", -] - -[[package]] -name = "ctor" -version = "0.4.2" +version = "0.8.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "a4735f265ba6a1188052ca32d461028a7d1125868be18e287e756019da7607b5" +checksum = "352d39c2f7bef1d6ad73db6f5160efcaed66d94ef8c6c573a8410c00bf909a98" dependencies = [ "ctor-proc-macro", "dtor", @@ -1691,9 +1681,9 @@ dependencies = [ [[package]] name = "ctor-proc-macro" -version = "0.0.5" +version = "0.0.7" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "4f211af61d8efdd104f96e57adf5e426ba1bc3ed7a4ead616e15e5881fd79c4d" +checksum = "52560adf09603e58c9a7ee1fe1dcb95a16927b17c127f0ac02d6e768a0e25bc1" [[package]] name = "ctr" @@ -2143,18 +2133,18 @@ dependencies = [ [[package]] name = "dtor" -version = "0.0.6" +version = "0.3.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "97cbdf2ad6846025e8e25df05171abfb30e3ababa12ee0a0e44b9bbe570633a8" +checksum = "f1057d6c64987086ff8ed0fd3fbf377a6b7d205cc7715868cd401705f715cbe4" dependencies = [ "dtor-proc-macro", ] [[package]] name = "dtor-proc-macro" -version = "0.0.5" +version = "0.0.6" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "7454e41ff9012c00d53cf7f475c5e3afa3b91b7c90568495495e8d9bf47a1055" +checksum = "f678cf4a922c215c63e0de95eb1ff08a958a81d47e485cf9da1e27bf6305cfa5" [[package]] name = "duct" @@ -4418,12 +4408,12 @@ dependencies = [ [[package]] name = "libloading" -version = "0.8.6" +version = "0.9.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "fc2f4eb4bc735547cfed7c0a4922cbd04a4655978c09b54f1f7b228750664c34" +checksum = "754ca22de805bb5744484a5b151a9e1a8e837d5dc232c2d7d8c2e3492edc8b60" dependencies = [ "cfg-if", - "windows-targets 0.52.6", + "windows-link 0.2.1", ] [[package]] @@ -4770,12 +4760,13 @@ dependencies = [ [[package]] name = "napi" -version = "3.0.0" +version = "3.8.4" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "abf3f418eeb94d86f02f3388324017e1e21e36937e4b1d8075ea5843d980f766" +checksum = "fb7848c221fb7bb789e02f01875287ebb1e078b92a6566a34de01ef8806e7c2b" dependencies = [ "bitflags 2.7.0", - "ctor 0.4.2", + "ctor", + "futures", "napi-build", "napi-sys", "nohash-hasher", @@ -4784,18 +4775,18 @@ dependencies = [ [[package]] name = "napi-build" -version = "2.2.2" +version = "2.3.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "fff539e61c5e3dd4d7d283610662f5d672c2aea0f158df78af694f13dbb3287b" +checksum = "d376940fd5b723c6893cd1ee3f33abbfd86acb1cd1ec079f3ab04a2a3bc4d3b1" [[package]] name = "napi-derive" -version = "3.0.0" +version = "3.5.3" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "ce09c2a155c7c38447a6ff1711899375bdd8f9dd5a50aad700a9c765c9f8a375" +checksum = "60867ff9a6f76e82350e0c3420cb0736f5866091b61d7d8a024baa54b0ec17dd" dependencies = [ - "convert_case 0.8.0", - "ctor 0.4.2", + "convert_case 0.11.0", + "ctor", "napi-derive-backend", "proc-macro2", "quote", @@ -4804,11 +4795,11 @@ dependencies = [ [[package]] name = "napi-derive-backend" -version = "2.0.0" +version = "5.0.2" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "17923387d68ecfe057a04a38ee89aeb41f415c43b4c7a508a3683bf0c1511c5a" +checksum = "f0864cf6a82e2cfb69067374b64c9253d7e910e5b34db833ed7495dda56ccb18" dependencies = [ - "convert_case 0.8.0", + "convert_case 0.11.0", "proc-macro2", "quote", "semver", @@ -4817,11 +4808,11 @@ dependencies = [ [[package]] name = "napi-sys" -version = "3.0.0" +version = "3.2.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "3e4e7135a8f97aa0f1509cce21a8a1f9dcec1b50d8dee006b48a5adb69a9d64d" +checksum = "8eb602b84d7c1edae45e50bbf1374696548f36ae179dfa667f577e384bb90c2b" dependencies = [ - "libloading 0.8.6", + "libloading 0.9.0", ] [[package]] @@ -9185,7 +9176,7 @@ dependencies = [ "anyhow", "brotli", "cargo_metadata", - "ctor 0.2.9", + "ctor", "dom_query", "dunce", "getrandom 0.3.3", @@ -10652,7 +10643,7 @@ dependencies = [ "windows-collections", "windows-core 0.61.0", "windows-future", - "windows-link", + "windows-link 0.1.1", "windows-numerics", ] @@ -10682,7 +10673,7 @@ checksum = "4763c1de310c86d75a878046489e2e5ba02c649d185f21c67d4cf8a56d098980" dependencies = [ "windows-implement", "windows-interface", - "windows-link", + "windows-link 0.1.1", "windows-result", "windows-strings 0.4.0", ] @@ -10694,7 +10685,7 @@ source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "7a1d6bbefcb7b60acd19828e1bc965da6fcf18a7e39490c5f8be71e54a19ba32" dependencies = [ "windows-core 0.61.0", - "windows-link", + "windows-link 0.1.1", ] [[package]] @@ -10725,6 +10716,12 @@ version = "0.1.1" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "76840935b766e1b0a05c0066835fb9ec80071d4c09a16f6bd5f7e655e3c14c38" +[[package]] +name = "windows-link" +version = "0.2.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "f0805222e57f7521d6a62e36fa9163bc891acd422f971defe97d64e70d0a4fe5" + [[package]] name = "windows-numerics" version = "0.2.0" @@ -10732,7 +10729,7 @@ source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "9150af68066c4c5c07ddc0ce30421554771e528bde427614c61038bc2c92c2b1" dependencies = [ "windows-core 0.61.0", - "windows-link", + "windows-link 0.1.1", ] [[package]] @@ -10741,7 +10738,7 @@ version = "0.5.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "6c44a98275e31bfd112bb06ba96c8ab13c03383a3753fdddd715406a1824c7e0" dependencies = [ - "windows-link", + "windows-link 0.1.1", "windows-result", "windows-strings 0.3.1", ] @@ -10752,7 +10749,7 @@ version = "0.3.2" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "c64fd11a4fd95df68efcfee5f44a294fe71b8bc6a91993e2791938abcc712252" dependencies = [ - "windows-link", + "windows-link 0.1.1", ] [[package]] @@ -10761,7 +10758,7 @@ version = "0.3.1" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "87fa48cc5d406560701792be122a10132491cff9d0aeb23583cc2dcafc847319" dependencies = [ - "windows-link", + "windows-link 0.1.1", ] [[package]] @@ -10770,7 +10767,7 @@ version = "0.4.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "7a2ba9642430ee452d5a7aa78d72907ebe8cfda358e8cb7918a2050581322f97" dependencies = [ - "windows-link", + "windows-link 0.1.1", ] [[package]] diff --git a/crates/tauri-utils/Cargo.toml b/crates/tauri-utils/Cargo.toml index 0c4feb51ff11..0bf36fe88ba1 100644 --- a/crates/tauri-utils/Cargo.toml +++ b/crates/tauri-utils/Cargo.toml @@ -33,7 +33,10 @@ serde_with = "3" aes-gcm = { version = "0.10", optional = true } getrandom = { version = "0.3", optional = true, features = ["std"] } serialize-to-javascript = { version = "0.1.2", optional = true } -ctor = "0.2" +ctor = { version = "0.8", default-features = false, features = [ + "std", + "proc_macro", +] } json5 = { version = "0.4", optional = true } # Part of public api in error type toml = { version = ">=0.9, <=1", features = ["parse"] } diff --git a/crates/tauri-utils/src/platform/starting_binary.rs b/crates/tauri-utils/src/platform/starting_binary.rs index 226d2f8d0de4..14db842ff9b8 100644 --- a/crates/tauri-utils/src/platform/starting_binary.rs +++ b/crates/tauri-utils/src/platform/starting_binary.rs @@ -11,7 +11,7 @@ use std::{ /// A cached version of the current binary using [`ctor`] to cache it before even `main` runs. #[ctor] #[used] -pub(super) static STARTING_BINARY: StartingBinary = StartingBinary::new(); +pub(super) static STARTING_BINARY: StartingBinary = unsafe { StartingBinary::new() }; /// Represents a binary path that was cached when the program was loaded. pub(super) struct StartingBinary(std::io::Result); diff --git a/packages/cli/Cargo.toml b/packages/cli/Cargo.toml index ebe853b45ce2..d0a8f623246a 100644 --- a/packages/cli/Cargo.toml +++ b/packages/cli/Cargo.toml @@ -2,18 +2,19 @@ edition = "2021" name = "tauri-cli-node" version = "0.0.0" +rust-version = "1.88" [lib] crate-type = ["cdylib"] [dependencies] -napi = "3" -napi-derive = "3" +napi = "3.8" +napi-derive = "3.5" tauri-cli = { path = "../../crates/tauri-cli", default-features = false } log = "0.4.21" [build-dependencies] -napi-build = "2.2" +napi-build = "2.3" [features] default = ["tauri-cli/default"] From 55bca4ece8ce9e57b97e11c89d0abfae00da350f Mon Sep 17 00:00:00 2001 From: lanyeeee Date: Wed, 1 Apr 2026 12:14:20 +0800 Subject: [PATCH 61/95] feat: add `eval_with_callback` to Webview and WebviewWindow (#14925) * feat: add `eval_with_callback` to Webview and WebviewWindow * docs: fix eval_with_callback docs and add change file --------- Co-authored-by: Tony <68118705+Legend-Master@users.noreply.github.com> --- .changes/eval-with-callback.md | 7 +++ crates/tauri-runtime-wry/src/lib.rs | 63 ++++++++++++++++++++++ crates/tauri-runtime/src/lib.rs | 10 ++++ crates/tauri/src/test/mock_runtime.rs | 13 +++++ crates/tauri/src/webview/mod.rs | 16 ++++++ crates/tauri/src/webview/webview_window.rs | 12 +++++ 6 files changed, 121 insertions(+) create mode 100644 .changes/eval-with-callback.md diff --git a/.changes/eval-with-callback.md b/.changes/eval-with-callback.md new file mode 100644 index 000000000000..c43cf0841c06 --- /dev/null +++ b/.changes/eval-with-callback.md @@ -0,0 +1,7 @@ +--- +'tauri': 'minor:feat' +'tauri-runtime': 'minor:feat' +'tauri-runtime-wry': 'minor:feat' +--- + +Add `eval_with_callback` to the Tauri webview APIs and runtime dispatch layers. diff --git a/crates/tauri-runtime-wry/src/lib.rs b/crates/tauri-runtime-wry/src/lib.rs index f196a08de544..772c392a2632 100644 --- a/crates/tauri-runtime-wry/src/lib.rs +++ b/crates/tauri-runtime-wry/src/lib.rs @@ -1475,6 +1475,15 @@ pub enum WebviewMessage { EvaluateScript(String), #[cfg(all(feature = "tracing", not(target_os = "android")))] EvaluateScript(String, Sender<()>, tracing::Span), + #[cfg(not(all(feature = "tracing", not(target_os = "android"))))] + EvaluateScriptWithCallback(String, Box), + #[cfg(all(feature = "tracing", not(target_os = "android")))] + EvaluateScriptWithCallback( + String, + Box, + Sender<()>, + tracing::Span, + ), CookiesForUrl(Url, Sender>>>), Cookies(Sender>>>), SetCookie(tauri_runtime::Cookie<'static>), @@ -1830,6 +1839,46 @@ impl WebviewDispatch for WryWebviewDispatcher { ) } + #[cfg(all(feature = "tracing", not(target_os = "android")))] + fn eval_script_with_callback>( + &self, + script: S, + callback: impl Fn(String) + Send + 'static, + ) -> Result<()> { + // use a channel so the EvaluateScript task uses the current span as parent + let (tx, rx) = channel(); + getter!( + self, + rx, + Message::Webview( + *self.window_id.lock().unwrap(), + self.webview_id, + WebviewMessage::EvaluateScriptWithCallback( + script.into(), + Box::new(callback), + tx, + tracing::Span::current(), + ), + ) + ) + } + + #[cfg(not(all(feature = "tracing", not(target_os = "android"))))] + fn eval_script_with_callback>( + &self, + script: S, + callback: impl Fn(String) + Send + 'static, + ) -> Result<()> { + send_user_message( + &self.context, + Message::Webview( + *self.window_id.lock().unwrap(), + self.webview_id, + WebviewMessage::EvaluateScriptWithCallback(script.into(), Box::new(callback)), + ), + ) + } + fn set_zoom(&self, scale_factor: f64) -> Result<()> { send_user_message( &self.context, @@ -3712,6 +3761,20 @@ fn handle_user_message( log::error!("{e}"); } } + #[cfg(all(feature = "tracing", not(target_os = "android")))] + WebviewMessage::EvaluateScriptWithCallback(script, callback, tx, span) => { + let _span = span.entered(); + if let Err(e) = webview.evaluate_script_with_callback(&script, callback) { + log::error!("{e}"); + } + tx.send(()).unwrap(); + } + #[cfg(not(all(feature = "tracing", not(target_os = "android"))))] + WebviewMessage::EvaluateScriptWithCallback(script, callback) => { + if let Err(e) = webview.evaluate_script_with_callback(&script, callback) { + log::error!("{e}"); + } + } WebviewMessage::Navigate(url) => { if let Err(e) = webview.load_url(url.as_str()) { log::error!("failed to navigate to url {}: {}", url, e); diff --git a/crates/tauri-runtime/src/lib.rs b/crates/tauri-runtime/src/lib.rs index d0aefa010b2a..5e32cfa8c5be 100644 --- a/crates/tauri-runtime/src/lib.rs +++ b/crates/tauri-runtime/src/lib.rs @@ -590,6 +590,16 @@ pub trait WebviewDispatch: Debug + Clone + Send + Sync + Sized + ' /// Executes javascript on the window this [`WindowDispatch`] represents. fn eval_script>(&self, script: S) -> Result<()>; + /// Evaluate JavaScript with callback function on the webview this [`WebviewDispatch`] represents. + /// The evaluation result will be serialized into a JSON string and passed to the callback function. + /// + /// Exception is ignored because of the limitation on Windows. You can catch it yourself and return as string as a workaround. + fn eval_script_with_callback>( + &self, + script: S, + callback: impl Fn(String) + Send + 'static, + ) -> Result<()>; + /// Moves the webview to the given window. fn reparent(&self, window_id: WindowId) -> Result<()>; diff --git a/crates/tauri/src/test/mock_runtime.rs b/crates/tauri/src/test/mock_runtime.rs index 7913e9ac014c..f51c488ec143 100644 --- a/crates/tauri/src/test/mock_runtime.rs +++ b/crates/tauri/src/test/mock_runtime.rs @@ -593,6 +593,19 @@ impl WebviewDispatch for MockWebviewDispatcher { Ok(()) } + fn eval_script_with_callback>( + &self, + script: S, + callback: impl Fn(String) + Send + 'static, + ) -> Result<()> { + self + .last_evaluated_script + .lock() + .unwrap() + .replace(script.into()); + Ok(()) + } + fn url(&self) -> Result { Ok(self.url.lock().unwrap().clone()) } diff --git a/crates/tauri/src/webview/mod.rs b/crates/tauri/src/webview/mod.rs index 8b66459dc12d..cf300288f4fd 100644 --- a/crates/tauri/src/webview/mod.rs +++ b/crates/tauri/src/webview/mod.rs @@ -1896,6 +1896,22 @@ tauri::Builder::default() .map_err(Into::into) } + /// Evaluate JavaScript with callback function on this webview. + /// The evaluation result will be serialized into a JSON string and passed to the callback function. + /// + /// Exception is ignored because of the limitation on Windows. You can catch it yourself and return as string as a workaround. + pub fn eval_with_callback( + &self, + js: impl Into, + callback: impl Fn(String) + Send + 'static, + ) -> crate::Result<()> { + self + .webview + .dispatcher + .eval_script_with_callback(js.into(), callback) + .map_err(Into::into) + } + /// Register a JS event listener and return its identifier. pub(crate) fn listen_js( &self, diff --git a/crates/tauri/src/webview/webview_window.rs b/crates/tauri/src/webview/webview_window.rs index dc6098014d4a..c49abec0cbe7 100644 --- a/crates/tauri/src/webview/webview_window.rs +++ b/crates/tauri/src/webview/webview_window.rs @@ -2363,6 +2363,18 @@ impl WebviewWindow { self.webview.eval(js) } + /// Evaluate JavaScript with callback function on this webview. + /// The evaluation result will be serialized into a JSON string and passed to the callback function. + /// + /// Exception is ignored because of the limitation on Windows. You can catch it yourself and return as string as a workaround. + pub fn eval_with_callback( + &self, + js: impl Into, + callback: impl Fn(String) + Send + 'static, + ) -> crate::Result<()> { + self.webview.eval_with_callback(js, callback) + } + /// Opens the developer tools window (Web Inspector). /// The devtools is only enabled on debug builds or with the `devtools` feature flag. /// From 01f0ea0f9973581758e490c50821523e0d90b1ad Mon Sep 17 00:00:00 2001 From: "dependabot[bot]" <49699333+dependabot[bot]@users.noreply.github.com> Date: Tue, 7 Apr 2026 12:52:05 +0800 Subject: [PATCH 62/95] chore(deps-dev): bump vite from 8.0.0 to 8.0.5 (#15204) * chore(deps-dev): bump vite from 8.0.0 to 8.0.5 Bumps [vite](https://github.com/vitejs/vite/tree/HEAD/packages/vite) from 8.0.0 to 8.0.5. - [Release notes](https://github.com/vitejs/vite/releases) - [Changelog](https://github.com/vitejs/vite/blob/main/packages/vite/CHANGELOG.md) - [Commits](https://github.com/vitejs/vite/commits/v8.0.5/packages/vite) --- updated-dependencies: - dependency-name: vite dependency-version: 8.0.5 dependency-type: direct:development ... Signed-off-by: dependabot[bot] * Fix audit --------- Signed-off-by: dependabot[bot] Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com> Co-authored-by: Tony --- examples/api/package.json | 2 +- pnpm-lock.yaml | 370 +++++++++++++++++++++----------------- 2 files changed, 207 insertions(+), 165 deletions(-) diff --git a/examples/api/package.json b/examples/api/package.json index 55f43f5df387..d51a35a93bc3 100644 --- a/examples/api/package.json +++ b/examples/api/package.json @@ -19,6 +19,6 @@ "@unocss/extractor-svelte": "^66.6.6", "svelte": "^5.53.11", "unocss": "^66.6.6", - "vite": "^8.0.0" + "vite": "^8.0.5" } } diff --git a/pnpm-lock.yaml b/pnpm-lock.yaml index 07556356ac4b..758287962fbd 100644 --- a/pnpm-lock.yaml +++ b/pnpm-lock.yaml @@ -32,7 +32,7 @@ importers: version: 1.2.2 '@sveltejs/vite-plugin-svelte': specifier: ^7.0.0 - version: 7.0.0(svelte@5.53.11)(vite@8.0.0(@types/node@24.11.0)(esbuild@0.27.3)(jiti@2.6.1)(terser@5.46.0)) + version: 7.0.0(svelte@5.53.11)(vite@8.0.5(@emnapi/core@1.8.1)(@emnapi/runtime@1.8.1)(@types/node@24.11.0)(esbuild@0.27.3)(jiti@2.6.1)(terser@5.46.0)) '@unocss/extractor-svelte': specifier: ^66.6.6 version: 66.6.6 @@ -41,10 +41,10 @@ importers: version: 5.53.11 unocss: specifier: ^66.6.6 - version: 66.6.6(vite@8.0.0(@types/node@24.11.0)(esbuild@0.27.3)(jiti@2.6.1)(terser@5.46.0)) + version: 66.6.6(@emnapi/core@1.8.1)(@emnapi/runtime@1.8.1)(vite@8.0.5(@emnapi/core@1.8.1)(@emnapi/runtime@1.8.1)(@types/node@24.11.0)(esbuild@0.27.3)(jiti@2.6.1)(terser@5.46.0)) vite: - specifier: ^8.0.0 - version: 8.0.0(@types/node@24.11.0)(esbuild@0.27.3)(jiti@2.6.1)(terser@5.46.0) + specifier: ^8.0.5 + version: 8.0.5(@emnapi/core@1.8.1)(@emnapi/runtime@1.8.1)(@types/node@24.11.0)(esbuild@0.27.3)(jiti@2.6.1)(terser@5.46.0) examples/file-associations: {} @@ -99,7 +99,7 @@ importers: devDependencies: '@napi-rs/cli': specifier: ^3.5.1 - version: 3.5.1(@emnapi/runtime@1.8.1)(@types/node@24.11.0) + version: 3.5.1(@emnapi/core@1.8.1)(@emnapi/runtime@1.8.1)(@types/node@24.11.0) '@types/node': specifier: ^24.11.0 version: 24.11.0 @@ -968,8 +968,11 @@ packages: resolution: {integrity: sha512-7cmzIu+Vbupriudo7UudoMRH2OA3cTw67vva8MxeoAe5S7vPFI7z0vp0pMXiA25S8IUJefImQ90FeJjl8fjEaQ==} engines: {node: '>= 10'} - '@napi-rs/wasm-runtime@1.1.1': - resolution: {integrity: sha512-p64ah1M1ld8xjWv3qbvFwHiFVWrq1yFvV4f7w+mzaqiR4IlSgkqhcRdHwsGgomwzBH51sRY4NEowLxnaBjcW/A==} + '@napi-rs/wasm-runtime@1.1.2': + resolution: {integrity: sha512-sNXv5oLJ7ob93xkZ1XnxisYhGYXfaG9f65/ZgYuAu3qt7b3NadcOEhLvx28hv31PgX8SZJRYrAIPQilQmFpLVw==} + peerDependencies: + '@emnapi/core': ^1.7.1 + '@emnapi/runtime': ^1.7.1 '@napi-rs/wasm-tools-android-arm-eabi@1.0.1': resolution: {integrity: sha512-lr07E/l571Gft5v4aA1dI8koJEmF1F0UigBbsqg9OWNzg80H3lDPO+auv85y3T/NHE3GirDk7x/D3sLO57vayw==} @@ -1247,13 +1250,12 @@ packages: cpu: [x64] os: [win32] - '@oxc-project/runtime@0.115.0': - resolution: {integrity: sha512-Rg8Wlt5dCbXhQnsXPrkOjL1DTSvXLgb2R/KYfnf1/K+R0k6UMLEmbQXPM+kwrWqSmWA2t0B1EtHy2/3zikQpvQ==} - engines: {node: ^20.19.0 || >=22.12.0} - '@oxc-project/types@0.115.0': resolution: {integrity: sha512-4n91DKnebUS4yjUHl2g3/b2T+IUdCfmoZGhmwsovZCDaJSs+QkVAM+0AqqTxHSsHfeiMuueT75cZaZcT/m0pSw==} + '@oxc-project/types@0.122.0': + resolution: {integrity: sha512-oLAl5kBpV4w69UtFZ9xqcmTi+GENWOcPF7FCrczTiBbmC0ibXxCwyvZGbO39rCVEuLGAZM84DH0pUIyyv/YJzA==} + '@polka/url@1.0.0-next.29': resolution: {integrity: sha512-wwQAWhWSuHaag8c4q/KN/vCoeOJYshAIvMQwD4GpSb3OiZklFfvAgmj0VCBBImRpuF/aFgIRzllXlVX93Jevww==} @@ -1269,103 +1271,103 @@ packages: '@quansync/fs@1.0.0': resolution: {integrity: sha512-4TJ3DFtlf1L5LDMaM6CanJ/0lckGNtJcMjQ1NAV6zDmA0tEHKZtxNKin8EgPaVX1YzljbxckyT2tJrpQKAtngQ==} - '@rolldown/binding-android-arm64@1.0.0-rc.9': - resolution: {integrity: sha512-lcJL0bN5hpgJfSIz/8PIf02irmyL43P+j1pTCfbD1DbLkmGRuFIA4DD3B3ZOvGqG0XiVvRznbKtN0COQVaKUTg==} + '@rolldown/binding-android-arm64@1.0.0-rc.12': + resolution: {integrity: sha512-pv1y2Fv0JybcykuiiD3qBOBdz6RteYojRFY1d+b95WVuzx211CRh+ytI/+9iVyWQ6koTh5dawe4S/yRfOFjgaA==} engines: {node: ^20.19.0 || >=22.12.0} cpu: [arm64] os: [android] - '@rolldown/binding-darwin-arm64@1.0.0-rc.9': - resolution: {integrity: sha512-J7Zk3kLYFsLtuH6U+F4pS2sYVzac0qkjcO5QxHS7OS7yZu2LRs+IXo+uvJ/mvpyUljDJ3LROZPoQfgBIpCMhdQ==} + '@rolldown/binding-darwin-arm64@1.0.0-rc.12': + resolution: {integrity: sha512-cFYr6zTG/3PXXF3pUO+umXxt1wkRK/0AYT8lDwuqvRC+LuKYWSAQAQZjCWDQpAH172ZV6ieYrNnFzVVcnSflAg==} engines: {node: ^20.19.0 || >=22.12.0} cpu: [arm64] os: [darwin] - '@rolldown/binding-darwin-x64@1.0.0-rc.9': - resolution: {integrity: sha512-iwtmmghy8nhfRGeNAIltcNXzD0QMNaaA5U/NyZc1Ia4bxrzFByNMDoppoC+hl7cDiUq5/1CnFthpT9n+UtfFyg==} + '@rolldown/binding-darwin-x64@1.0.0-rc.12': + resolution: {integrity: sha512-ZCsYknnHzeXYps0lGBz8JrF37GpE9bFVefrlmDrAQhOEi4IOIlcoU1+FwHEtyXGx2VkYAvhu7dyBf75EJQffBw==} engines: {node: ^20.19.0 || >=22.12.0} cpu: [x64] os: [darwin] - '@rolldown/binding-freebsd-x64@1.0.0-rc.9': - resolution: {integrity: sha512-DLFYI78SCiZr5VvdEplsVC2Vx53lnA4/Ga5C65iyldMVaErr86aiqCoNBLl92PXPfDtUYjUh+xFFor40ueNs4Q==} + '@rolldown/binding-freebsd-x64@1.0.0-rc.12': + resolution: {integrity: sha512-dMLeprcVsyJsKolRXyoTH3NL6qtsT0Y2xeuEA8WQJquWFXkEC4bcu1rLZZSnZRMtAqwtrF/Ib9Ddtpa/Gkge9Q==} engines: {node: ^20.19.0 || >=22.12.0} cpu: [x64] os: [freebsd] - '@rolldown/binding-linux-arm-gnueabihf@1.0.0-rc.9': - resolution: {integrity: sha512-CsjTmTwd0Hri6iTw/DRMK7kOZ7FwAkrO4h8YWKoX/kcj833e4coqo2wzIFywtch/8Eb5enQ/lwLM7w6JX1W5RQ==} + '@rolldown/binding-linux-arm-gnueabihf@1.0.0-rc.12': + resolution: {integrity: sha512-YqWjAgGC/9M1lz3GR1r1rP79nMgo3mQiiA+Hfo+pvKFK1fAJ1bCi0ZQVh8noOqNacuY1qIcfyVfP6HoyBRZ85Q==} engines: {node: ^20.19.0 || >=22.12.0} cpu: [arm] os: [linux] - '@rolldown/binding-linux-arm64-gnu@1.0.0-rc.9': - resolution: {integrity: sha512-2x9O2JbSPxpxMDhP9Z74mahAStibTlrBMW0520+epJH5sac7/LwZW5Bmg/E6CXuEF53JJFW509uP+lSedaUNxg==} + '@rolldown/binding-linux-arm64-gnu@1.0.0-rc.12': + resolution: {integrity: sha512-/I5AS4cIroLpslsmzXfwbe5OmWvSsrFuEw3mwvbQ1kDxJ822hFHIx+vsN/TAzNVyepI/j/GSzrtCIwQPeKCLIg==} engines: {node: ^20.19.0 || >=22.12.0} cpu: [arm64] os: [linux] libc: [glibc] - '@rolldown/binding-linux-arm64-musl@1.0.0-rc.9': - resolution: {integrity: sha512-JA1QRW31ogheAIRhIg9tjMfsYbglXXYGNPLdPEYrwFxdbkQCAzvpSCSHCDWNl4hTtrol8WeboCSEpjdZK8qrCg==} + '@rolldown/binding-linux-arm64-musl@1.0.0-rc.12': + resolution: {integrity: sha512-V6/wZztnBqlx5hJQqNWwFdxIKN0m38p8Jas+VoSfgH54HSj9tKTt1dZvG6JRHcjh6D7TvrJPWFGaY9UBVOaWPw==} engines: {node: ^20.19.0 || >=22.12.0} cpu: [arm64] os: [linux] libc: [musl] - '@rolldown/binding-linux-ppc64-gnu@1.0.0-rc.9': - resolution: {integrity: sha512-aOKU9dJheda8Kj8Y3w9gnt9QFOO+qKPAl8SWd7JPHP+Cu0EuDAE5wokQubLzIDQWg2myXq2XhTpOVS07qqvT+w==} + '@rolldown/binding-linux-ppc64-gnu@1.0.0-rc.12': + resolution: {integrity: sha512-AP3E9BpcUYliZCxa3w5Kwj9OtEVDYK6sVoUzy4vTOJsjPOgdaJZKFmN4oOlX0Wp0RPV2ETfmIra9x1xuayFB7g==} engines: {node: ^20.19.0 || >=22.12.0} cpu: [ppc64] os: [linux] libc: [glibc] - '@rolldown/binding-linux-s390x-gnu@1.0.0-rc.9': - resolution: {integrity: sha512-OalO94fqj7IWRn3VdXWty75jC5dk4C197AWEuMhIpvVv2lw9fiPhud0+bW2ctCxb3YoBZor71QHbY+9/WToadA==} + '@rolldown/binding-linux-s390x-gnu@1.0.0-rc.12': + resolution: {integrity: sha512-nWwpvUSPkoFmZo0kQazZYOrT7J5DGOJ/+QHHzjvNlooDZED8oH82Yg67HvehPPLAg5fUff7TfWFHQS8IV1n3og==} engines: {node: ^20.19.0 || >=22.12.0} cpu: [s390x] os: [linux] libc: [glibc] - '@rolldown/binding-linux-x64-gnu@1.0.0-rc.9': - resolution: {integrity: sha512-cVEl1vZtBsBZna3YMjGXNvnYYrOJ7RzuWvZU0ffvJUexWkukMaDuGhUXn0rjnV0ptzGVkvc+vW9Yqy6h8YX4pg==} + '@rolldown/binding-linux-x64-gnu@1.0.0-rc.12': + resolution: {integrity: sha512-RNrafz5bcwRy+O9e6P8Z/OCAJW/A+qtBczIqVYwTs14pf4iV1/+eKEjdOUta93q2TsT/FI0XYDP3TCky38LMAg==} engines: {node: ^20.19.0 || >=22.12.0} cpu: [x64] os: [linux] libc: [glibc] - '@rolldown/binding-linux-x64-musl@1.0.0-rc.9': - resolution: {integrity: sha512-UzYnKCIIc4heAKgI4PZ3dfBGUZefGCJ1TPDuLHoCzgrMYPb5Rv6TLFuYtyM4rWyHM7hymNdsg5ik2C+UD9VDbA==} + '@rolldown/binding-linux-x64-musl@1.0.0-rc.12': + resolution: {integrity: sha512-Jpw/0iwoKWx3LJ2rc1yjFrj+T7iHZn2JDg1Yny1ma0luviFS4mhAIcd1LFNxK3EYu3DHWCps0ydXQ5i/rrJ2ig==} engines: {node: ^20.19.0 || >=22.12.0} cpu: [x64] os: [linux] libc: [musl] - '@rolldown/binding-openharmony-arm64@1.0.0-rc.9': - resolution: {integrity: sha512-+6zoiF+RRyf5cdlFQP7nm58mq7+/2PFaY2DNQeD4B87N36JzfF/l9mdBkkmTvSYcYPE8tMh/o3cRlsx1ldLfog==} + '@rolldown/binding-openharmony-arm64@1.0.0-rc.12': + resolution: {integrity: sha512-vRugONE4yMfVn0+7lUKdKvN4D5YusEiPilaoO2sgUWpCvrncvWgPMzK00ZFFJuiPgLwgFNP5eSiUlv2tfc+lpA==} engines: {node: ^20.19.0 || >=22.12.0} cpu: [arm64] os: [openharmony] - '@rolldown/binding-wasm32-wasi@1.0.0-rc.9': - resolution: {integrity: sha512-rgFN6sA/dyebil3YTlL2evvi/M+ivhfnyxec7AccTpRPccno/rPoNlqybEZQBkcbZu8Hy+eqNJCqfBR8P7Pg8g==} + '@rolldown/binding-wasm32-wasi@1.0.0-rc.12': + resolution: {integrity: sha512-ykGiLr/6kkiHc0XnBfmFJuCjr5ZYKKofkx+chJWDjitX+KsJuAmrzWhwyOMSHzPhzOHOy7u9HlFoa5MoAOJ/Zg==} engines: {node: '>=14.0.0'} cpu: [wasm32] - '@rolldown/binding-win32-arm64-msvc@1.0.0-rc.9': - resolution: {integrity: sha512-lHVNUG/8nlF1IQk1C0Ci574qKYyty2goMiPlRqkC5R+3LkXDkL5Dhx8ytbxq35m+pkHVIvIxviD+TWLdfeuadA==} + '@rolldown/binding-win32-arm64-msvc@1.0.0-rc.12': + resolution: {integrity: sha512-5eOND4duWkwx1AzCxadcOrNeighiLwMInEADT0YM7xeEOOFcovWZCq8dadXgcRHSf3Ulh1kFo/qvzoFiCLOL1Q==} engines: {node: ^20.19.0 || >=22.12.0} cpu: [arm64] os: [win32] - '@rolldown/binding-win32-x64-msvc@1.0.0-rc.9': - resolution: {integrity: sha512-G0oA4+w1iY5AGi5HcDTxWsoxF509hrFIPB2rduV5aDqS9FtDg1CAfa7V34qImbjfhIcA8C+RekocJZA96EarwQ==} + '@rolldown/binding-win32-x64-msvc@1.0.0-rc.12': + resolution: {integrity: sha512-PyqoipaswDLAZtot351MLhrlrh6lcZPo2LSYE+VDxbVk24LVKAGOuE4hb8xZQmrPAuEtTZW8E6D2zc5EUZX4Lw==} engines: {node: ^20.19.0 || >=22.12.0} cpu: [x64] os: [win32] - '@rolldown/pluginutils@1.0.0-rc.9': - resolution: {integrity: sha512-w6oiRWgEBl04QkFZgmW+jnU1EC9b57Oihi2ot3HNWIQRqgHp5PnYDia5iZ5FF7rpa4EQdiqMDXjlqKGXBhsoXw==} + '@rolldown/pluginutils@1.0.0-rc.12': + resolution: {integrity: sha512-HHMwmarRKvoFsJorqYlFeFRzXZqCt2ETQlEDOb9aqssrnVBB1/+xgTGtuTrIk5vzLNX1MjMtTf7W9z3tsSbrxw==} '@rollup/plugin-terser@1.0.0': resolution: {integrity: sha512-FnCxhTBx6bMOYQrar6C8h3scPt8/JwIzw3+AJ2K++6guogH5fYaIFia+zZuhqv0eo1RN7W1Pz630SyvLbDjhtQ==} @@ -1783,8 +1785,8 @@ packages: blake3-wasm@2.1.5: resolution: {integrity: sha512-F1+K8EbfOZE49dtoPtmxUQrpXaBIl3ICvasLh+nJta0xkz+9kF/7uet9fLnwKqhDrmj6g+6K3Tw9yQPUg2ka5g==} - brace-expansion@5.0.4: - resolution: {integrity: sha512-h+DEnpVvxmfVefa4jFbCf5HdH5YMDXRsmKflpf1pILZWRFlTbJpxeU55nJl4Smt5HQaGzg1o6RHFPJaOqnmBDg==} + brace-expansion@5.0.5: + resolution: {integrity: sha512-VZznLgtwhn+Mact9tfiwx64fA9erHH/MCXEUfB/0bX/6Fz6ny5EGTXYltMocqg4xFAQZtnO3DHWWXi8RiuN7cQ==} engines: {node: 18 || 20 || >=22} braces@3.0.3: @@ -1868,8 +1870,8 @@ packages: resolution: {integrity: sha512-3sUqbMEc77XqpdNO7FRyRog+eW3ph+GYCbj+rK+uYyRMuwsVy0rMiVtPn+QJlKFvWP/1PYpapqYn0Me2knFn+A==} engines: {node: '>=0.10.0'} - defu@6.1.4: - resolution: {integrity: sha512-mEQCMmwJu317oSz8CwdIOdwf3xMif1ttiM8LTufzc3g6kR+9Pe236twL8j3IYT1F7GfRgGcW6MWxzZjLIkuHIg==} + defu@6.1.6: + resolution: {integrity: sha512-f8mefEW4WIVg4LckePx3mALjQSPQgFlg9U8yaPdlsbdYcHQyj9n2zL2LJEA52smeYxOvmd/nB7TpMtHGMTHcug==} destr@2.0.5: resolution: {integrity: sha512-ugFTXCtDZunbzasqBxrK93Ik/DRYsO6S/fedkWEMKqt04xZ4csmnmwGDBAb07QWNaGMAmnTIemsYZCksjATwsA==} @@ -2316,12 +2318,12 @@ packages: picocolors@1.1.1: resolution: {integrity: sha512-xceH2snhtb5M9liqDsmEw56le376mTZkEX/jEb/RxNFyegNul7eNslCXP9FDj/Lcu0X8KEyMceP2ntpaHrDEVA==} - picomatch@2.3.1: - resolution: {integrity: sha512-JU3teHTNjmE2VCGFzuY8EXzCDVwEqB2a8fsIvwaStHhAWJEeVd1o1QD80CU6+ZdEXXSLbSsuLwJjkCBWqRQUVA==} + picomatch@2.3.2: + resolution: {integrity: sha512-V7+vQEJ06Z+c5tSye8S+nHUfI51xoXIXjHQ99cQtKUkQqqO1kO/KCJUfZXuB47h/YBlDhah2H3hdUGXn8ie0oA==} engines: {node: '>=8.6'} - picomatch@4.0.3: - resolution: {integrity: sha512-5gTmgEY/sqK6gFXLIsQNH19lWb4ebPDLA4SdLP7dsWkIXHWlG66oPuVvXSGFPppYZz8ZDZq0dYYrbHfBCVUb1Q==} + picomatch@4.0.4: + resolution: {integrity: sha512-QP88BAKvMam/3NxH6vj2o21R6MjxZUAd6nlwAS/pnGvN9IVLocLHxGYIzFhg6fUQ+5th6P4dv4eW9jX3DSIj7A==} engines: {node: '>=12'} pkg-types@1.3.1: @@ -2367,8 +2369,8 @@ packages: resolution: {integrity: sha512-g6QUff04oZpHs0eG5p83rFLhHeV00ug/Yf9nZM6fLeUrPguBTkTQOdpAWWspMh55TZfVQDPaN3NQJfbVRAxdIw==} engines: {iojs: '>=1.0.0', node: '>=0.10.0'} - rolldown@1.0.0-rc.9: - resolution: {integrity: sha512-9EbgWge7ZH+yqb4d2EnELAntgPTWbfL8ajiTW+SyhJEC4qhBbkCKbqFV4Ge4zmu5ziQuVbWxb/XwLZ+RIO7E8Q==} + rolldown@1.0.0-rc.12: + resolution: {integrity: sha512-yP4USLIMYrwpPHEFB5JGH1uxhcslv6/hL0OyvTuY+3qlOSJvZ7ntYnoWpehBxufkgN0cvXxppuTu5hHa/zPh+A==} engines: {node: ^20.19.0 || >=22.12.0} hasBin: true @@ -2391,8 +2393,8 @@ packages: engines: {node: '>=10'} hasBin: true - serialize-javascript@7.0.4: - resolution: {integrity: sha512-DuGdB+Po43Q5Jxwpzt1lhyFSYKryqoNjQSA9M92tyw0lyHIOur+XCalOUe0KTJpyqzT8+fQ5A0Jf7vCx/NKmIg==} + serialize-javascript@7.0.5: + resolution: {integrity: sha512-F4LcB0UqUl1zErq+1nYEEzSHJnIwb3AF2XWB94b+afhrekOUijwooAYqFyRbjYkm2PAKBabx6oYv/xDxNi8IBw==} engines: {node: '>=20.0.0'} sharp@0.34.5: @@ -2558,8 +2560,8 @@ packages: uri-js@4.4.1: resolution: {integrity: sha512-7rKUyy33Q1yc98pQ1DAmLtwX109F7TIfWlW1Ydo8Wl1ii1SeHieeh0HHfPeL2fMXK6z0s8ecKs9frCuLJvndBg==} - vite@7.3.1: - resolution: {integrity: sha512-w+N7Hifpc3gRjZ63vYBXA56dvvRlNWRczTdmCBBa+CotUzAPf5b7YMdMR/8CQoeYE5LX3W4wj6RYTgonm1b9DA==} + vite@7.3.2: + resolution: {integrity: sha512-Bby3NOsna2jsjfLVOHKes8sGwgl4TT0E6vvpYgnAYDIF/tie7MRaFthmKuHx1NSXjiTueXH3do80FMQgvEktRg==} engines: {node: ^20.19.0 || >=22.12.0} hasBin: true peerDependencies: @@ -2598,14 +2600,14 @@ packages: yaml: optional: true - vite@8.0.0: - resolution: {integrity: sha512-fPGaRNj9Zytaf8LEiBhY7Z6ijnFKdzU/+mL8EFBaKr7Vw1/FWcTBAMW0wLPJAGMPX38ZPVCVgLceWiEqeoqL2Q==} + vite@8.0.5: + resolution: {integrity: sha512-nmu43Qvq9UopTRfMx2jOYW5l16pb3iDC1JH6yMuPkpVbzK0k+L7dfsEDH4jRgYFmsg0sTAqkojoZgzLMlwHsCQ==} engines: {node: ^20.19.0 || >=22.12.0} hasBin: true peerDependencies: '@types/node': ^20.19.0 || >=22.12.0 - '@vitejs/devtools': ^0.0.0-alpha.31 - esbuild: ^0.27.0 + '@vitejs/devtools': ^0.1.0 + esbuild: ^0.27.0 || ^0.28.0 jiti: '>=1.21.0' less: ^4.0.0 sass: ^1.70.0 @@ -3175,11 +3177,11 @@ snapshots: '@jridgewell/resolve-uri': 3.1.2 '@jridgewell/sourcemap-codec': 1.5.5 - '@napi-rs/cli@3.5.1(@emnapi/runtime@1.8.1)(@types/node@24.11.0)': + '@napi-rs/cli@3.5.1(@emnapi/core@1.8.1)(@emnapi/runtime@1.8.1)(@types/node@24.11.0)': dependencies: '@inquirer/prompts': 8.3.0(@types/node@24.11.0) - '@napi-rs/cross-toolchain': 1.0.3 - '@napi-rs/wasm-tools': 1.0.1 + '@napi-rs/cross-toolchain': 1.0.3(@emnapi/core@1.8.1)(@emnapi/runtime@1.8.1) + '@napi-rs/wasm-tools': 1.0.1(@emnapi/core@1.8.1)(@emnapi/runtime@1.8.1) '@octokit/rest': 22.0.1 clipanion: 4.0.0-rc.4(typanion@3.14.0) colorette: 2.0.20 @@ -3192,6 +3194,7 @@ snapshots: optionalDependencies: '@emnapi/runtime': 1.8.1 transitivePeerDependencies: + - '@emnapi/core' - '@napi-rs/cross-toolchain-arm64-target-aarch64' - '@napi-rs/cross-toolchain-arm64-target-armv7' - '@napi-rs/cross-toolchain-arm64-target-ppc64le' @@ -3206,12 +3209,14 @@ snapshots: - node-addon-api - supports-color - '@napi-rs/cross-toolchain@1.0.3': + '@napi-rs/cross-toolchain@1.0.3(@emnapi/core@1.8.1)(@emnapi/runtime@1.8.1)': dependencies: - '@napi-rs/lzma': 1.4.5 - '@napi-rs/tar': 1.1.0 + '@napi-rs/lzma': 1.4.5(@emnapi/core@1.8.1)(@emnapi/runtime@1.8.1) + '@napi-rs/tar': 1.1.0(@emnapi/core@1.8.1)(@emnapi/runtime@1.8.1) debug: 4.4.3 transitivePeerDependencies: + - '@emnapi/core' + - '@emnapi/runtime' - supports-color '@napi-rs/lzma-android-arm-eabi@1.4.5': @@ -3253,9 +3258,12 @@ snapshots: '@napi-rs/lzma-linux-x64-musl@1.4.5': optional: true - '@napi-rs/lzma-wasm32-wasi@1.4.5': + '@napi-rs/lzma-wasm32-wasi@1.4.5(@emnapi/core@1.8.1)(@emnapi/runtime@1.8.1)': dependencies: - '@napi-rs/wasm-runtime': 1.1.1 + '@napi-rs/wasm-runtime': 1.1.2(@emnapi/core@1.8.1)(@emnapi/runtime@1.8.1) + transitivePeerDependencies: + - '@emnapi/core' + - '@emnapi/runtime' optional: true '@napi-rs/lzma-win32-arm64-msvc@1.4.5': @@ -3267,7 +3275,7 @@ snapshots: '@napi-rs/lzma-win32-x64-msvc@1.4.5': optional: true - '@napi-rs/lzma@1.4.5': + '@napi-rs/lzma@1.4.5(@emnapi/core@1.8.1)(@emnapi/runtime@1.8.1)': optionalDependencies: '@napi-rs/lzma-android-arm-eabi': 1.4.5 '@napi-rs/lzma-android-arm64': 1.4.5 @@ -3282,10 +3290,13 @@ snapshots: '@napi-rs/lzma-linux-s390x-gnu': 1.4.5 '@napi-rs/lzma-linux-x64-gnu': 1.4.5 '@napi-rs/lzma-linux-x64-musl': 1.4.5 - '@napi-rs/lzma-wasm32-wasi': 1.4.5 + '@napi-rs/lzma-wasm32-wasi': 1.4.5(@emnapi/core@1.8.1)(@emnapi/runtime@1.8.1) '@napi-rs/lzma-win32-arm64-msvc': 1.4.5 '@napi-rs/lzma-win32-ia32-msvc': 1.4.5 '@napi-rs/lzma-win32-x64-msvc': 1.4.5 + transitivePeerDependencies: + - '@emnapi/core' + - '@emnapi/runtime' '@napi-rs/tar-android-arm-eabi@1.1.0': optional: true @@ -3323,9 +3334,12 @@ snapshots: '@napi-rs/tar-linux-x64-musl@1.1.0': optional: true - '@napi-rs/tar-wasm32-wasi@1.1.0': + '@napi-rs/tar-wasm32-wasi@1.1.0(@emnapi/core@1.8.1)(@emnapi/runtime@1.8.1)': dependencies: - '@napi-rs/wasm-runtime': 1.1.1 + '@napi-rs/wasm-runtime': 1.1.2(@emnapi/core@1.8.1)(@emnapi/runtime@1.8.1) + transitivePeerDependencies: + - '@emnapi/core' + - '@emnapi/runtime' optional: true '@napi-rs/tar-win32-arm64-msvc@1.1.0': @@ -3337,7 +3351,7 @@ snapshots: '@napi-rs/tar-win32-x64-msvc@1.1.0': optional: true - '@napi-rs/tar@1.1.0': + '@napi-rs/tar@1.1.0(@emnapi/core@1.8.1)(@emnapi/runtime@1.8.1)': optionalDependencies: '@napi-rs/tar-android-arm-eabi': 1.1.0 '@napi-rs/tar-android-arm64': 1.1.0 @@ -3351,12 +3365,15 @@ snapshots: '@napi-rs/tar-linux-s390x-gnu': 1.1.0 '@napi-rs/tar-linux-x64-gnu': 1.1.0 '@napi-rs/tar-linux-x64-musl': 1.1.0 - '@napi-rs/tar-wasm32-wasi': 1.1.0 + '@napi-rs/tar-wasm32-wasi': 1.1.0(@emnapi/core@1.8.1)(@emnapi/runtime@1.8.1) '@napi-rs/tar-win32-arm64-msvc': 1.1.0 '@napi-rs/tar-win32-ia32-msvc': 1.1.0 '@napi-rs/tar-win32-x64-msvc': 1.1.0 + transitivePeerDependencies: + - '@emnapi/core' + - '@emnapi/runtime' - '@napi-rs/wasm-runtime@1.1.1': + '@napi-rs/wasm-runtime@1.1.2(@emnapi/core@1.8.1)(@emnapi/runtime@1.8.1)': dependencies: '@emnapi/core': 1.8.1 '@emnapi/runtime': 1.8.1 @@ -3390,9 +3407,12 @@ snapshots: '@napi-rs/wasm-tools-linux-x64-musl@1.0.1': optional: true - '@napi-rs/wasm-tools-wasm32-wasi@1.0.1': + '@napi-rs/wasm-tools-wasm32-wasi@1.0.1(@emnapi/core@1.8.1)(@emnapi/runtime@1.8.1)': dependencies: - '@napi-rs/wasm-runtime': 1.1.1 + '@napi-rs/wasm-runtime': 1.1.2(@emnapi/core@1.8.1)(@emnapi/runtime@1.8.1) + transitivePeerDependencies: + - '@emnapi/core' + - '@emnapi/runtime' optional: true '@napi-rs/wasm-tools-win32-arm64-msvc@1.0.1': @@ -3404,7 +3424,7 @@ snapshots: '@napi-rs/wasm-tools-win32-x64-msvc@1.0.1': optional: true - '@napi-rs/wasm-tools@1.0.1': + '@napi-rs/wasm-tools@1.0.1(@emnapi/core@1.8.1)(@emnapi/runtime@1.8.1)': optionalDependencies: '@napi-rs/wasm-tools-android-arm-eabi': 1.0.1 '@napi-rs/wasm-tools-android-arm64': 1.0.1 @@ -3415,10 +3435,13 @@ snapshots: '@napi-rs/wasm-tools-linux-arm64-musl': 1.0.1 '@napi-rs/wasm-tools-linux-x64-gnu': 1.0.1 '@napi-rs/wasm-tools-linux-x64-musl': 1.0.1 - '@napi-rs/wasm-tools-wasm32-wasi': 1.0.1 + '@napi-rs/wasm-tools-wasm32-wasi': 1.0.1(@emnapi/core@1.8.1)(@emnapi/runtime@1.8.1) '@napi-rs/wasm-tools-win32-arm64-msvc': 1.0.1 '@napi-rs/wasm-tools-win32-ia32-msvc': 1.0.1 '@napi-rs/wasm-tools-win32-x64-msvc': 1.0.1 + transitivePeerDependencies: + - '@emnapi/core' + - '@emnapi/runtime' '@nodelib/fs.scandir@2.1.5': dependencies: @@ -3543,9 +3566,12 @@ snapshots: '@oxc-parser/binding-openharmony-arm64@0.115.0': optional: true - '@oxc-parser/binding-wasm32-wasi@0.115.0': + '@oxc-parser/binding-wasm32-wasi@0.115.0(@emnapi/core@1.8.1)(@emnapi/runtime@1.8.1)': dependencies: - '@napi-rs/wasm-runtime': 1.1.1 + '@napi-rs/wasm-runtime': 1.1.2(@emnapi/core@1.8.1)(@emnapi/runtime@1.8.1) + transitivePeerDependencies: + - '@emnapi/core' + - '@emnapi/runtime' optional: true '@oxc-parser/binding-win32-arm64-msvc@0.115.0': @@ -3557,10 +3583,10 @@ snapshots: '@oxc-parser/binding-win32-x64-msvc@0.115.0': optional: true - '@oxc-project/runtime@0.115.0': {} - '@oxc-project/types@0.115.0': {} + '@oxc-project/types@0.122.0': {} + '@polka/url@1.0.0-next.29': {} '@poppinss/colors@4.1.6': @@ -3579,58 +3605,61 @@ snapshots: dependencies: quansync: 1.0.0 - '@rolldown/binding-android-arm64@1.0.0-rc.9': + '@rolldown/binding-android-arm64@1.0.0-rc.12': optional: true - '@rolldown/binding-darwin-arm64@1.0.0-rc.9': + '@rolldown/binding-darwin-arm64@1.0.0-rc.12': optional: true - '@rolldown/binding-darwin-x64@1.0.0-rc.9': + '@rolldown/binding-darwin-x64@1.0.0-rc.12': optional: true - '@rolldown/binding-freebsd-x64@1.0.0-rc.9': + '@rolldown/binding-freebsd-x64@1.0.0-rc.12': optional: true - '@rolldown/binding-linux-arm-gnueabihf@1.0.0-rc.9': + '@rolldown/binding-linux-arm-gnueabihf@1.0.0-rc.12': optional: true - '@rolldown/binding-linux-arm64-gnu@1.0.0-rc.9': + '@rolldown/binding-linux-arm64-gnu@1.0.0-rc.12': optional: true - '@rolldown/binding-linux-arm64-musl@1.0.0-rc.9': + '@rolldown/binding-linux-arm64-musl@1.0.0-rc.12': optional: true - '@rolldown/binding-linux-ppc64-gnu@1.0.0-rc.9': + '@rolldown/binding-linux-ppc64-gnu@1.0.0-rc.12': optional: true - '@rolldown/binding-linux-s390x-gnu@1.0.0-rc.9': + '@rolldown/binding-linux-s390x-gnu@1.0.0-rc.12': optional: true - '@rolldown/binding-linux-x64-gnu@1.0.0-rc.9': + '@rolldown/binding-linux-x64-gnu@1.0.0-rc.12': optional: true - '@rolldown/binding-linux-x64-musl@1.0.0-rc.9': + '@rolldown/binding-linux-x64-musl@1.0.0-rc.12': optional: true - '@rolldown/binding-openharmony-arm64@1.0.0-rc.9': + '@rolldown/binding-openharmony-arm64@1.0.0-rc.12': optional: true - '@rolldown/binding-wasm32-wasi@1.0.0-rc.9': + '@rolldown/binding-wasm32-wasi@1.0.0-rc.12(@emnapi/core@1.8.1)(@emnapi/runtime@1.8.1)': dependencies: - '@napi-rs/wasm-runtime': 1.1.1 + '@napi-rs/wasm-runtime': 1.1.2(@emnapi/core@1.8.1)(@emnapi/runtime@1.8.1) + transitivePeerDependencies: + - '@emnapi/core' + - '@emnapi/runtime' optional: true - '@rolldown/binding-win32-arm64-msvc@1.0.0-rc.9': + '@rolldown/binding-win32-arm64-msvc@1.0.0-rc.12': optional: true - '@rolldown/binding-win32-x64-msvc@1.0.0-rc.9': + '@rolldown/binding-win32-x64-msvc@1.0.0-rc.12': optional: true - '@rolldown/pluginutils@1.0.0-rc.9': {} + '@rolldown/pluginutils@1.0.0-rc.12': {} '@rollup/plugin-terser@1.0.0(rollup@4.60.0)': dependencies: - serialize-javascript: 7.0.4 + serialize-javascript: 7.0.5 smob: 1.6.1 terser: 5.46.0 optionalDependencies: @@ -3649,7 +3678,7 @@ snapshots: dependencies: '@types/estree': 1.0.8 estree-walker: 2.0.2 - picomatch: 4.0.3 + picomatch: 4.0.4 optionalDependencies: rollup: 4.60.0 @@ -3738,14 +3767,14 @@ snapshots: dependencies: acorn: 8.16.0 - '@sveltejs/vite-plugin-svelte@7.0.0(svelte@5.53.11)(vite@8.0.0(@types/node@24.11.0)(esbuild@0.27.3)(jiti@2.6.1)(terser@5.46.0))': + '@sveltejs/vite-plugin-svelte@7.0.0(svelte@5.53.11)(vite@8.0.5(@emnapi/core@1.8.1)(@emnapi/runtime@1.8.1)(@types/node@24.11.0)(esbuild@0.27.3)(jiti@2.6.1)(terser@5.46.0))': dependencies: deepmerge: 4.3.1 magic-string: 0.30.21 obug: 2.1.1 svelte: 5.53.11 - vite: 8.0.0(@types/node@24.11.0)(esbuild@0.27.3)(jiti@2.6.1)(terser@5.46.0) - vitefu: 1.1.2(vite@8.0.0(@types/node@24.11.0)(esbuild@0.27.3)(jiti@2.6.1)(terser@5.46.0)) + vite: 8.0.5(@emnapi/core@1.8.1)(@emnapi/runtime@1.8.1)(@types/node@24.11.0)(esbuild@0.27.3)(jiti@2.6.1)(terser@5.46.0) + vitefu: 1.1.2(vite@8.0.5(@emnapi/core@1.8.1)(@emnapi/runtime@1.8.1)(@types/node@24.11.0)(esbuild@0.27.3)(jiti@2.6.1)(terser@5.46.0)) '@tybys/wasm-util@0.10.1': dependencies: @@ -3965,11 +3994,14 @@ snapshots: '@unocss/core': 66.6.6 magic-string: 0.30.21 - '@unocss/transformer-attributify-jsx@66.6.6': + '@unocss/transformer-attributify-jsx@66.6.6(@emnapi/core@1.8.1)(@emnapi/runtime@1.8.1)': dependencies: '@unocss/core': 66.6.6 - oxc-parser: 0.115.0 - oxc-walker: 0.7.0(oxc-parser@0.115.0) + oxc-parser: 0.115.0(@emnapi/core@1.8.1)(@emnapi/runtime@1.8.1) + oxc-walker: 0.7.0(oxc-parser@0.115.0(@emnapi/core@1.8.1)(@emnapi/runtime@1.8.1)) + transitivePeerDependencies: + - '@emnapi/core' + - '@emnapi/runtime' '@unocss/transformer-compile-class@66.6.6': dependencies: @@ -3985,7 +4017,7 @@ snapshots: dependencies: '@unocss/core': 66.6.6 - '@unocss/vite@66.6.6(vite@8.0.0(@types/node@24.11.0)(esbuild@0.27.3)(jiti@2.6.1)(terser@5.46.0))': + '@unocss/vite@66.6.6(vite@8.0.5(@emnapi/core@1.8.1)(@emnapi/runtime@1.8.1)(@types/node@24.11.0)(esbuild@0.27.3)(jiti@2.6.1)(terser@5.46.0))': dependencies: '@jridgewell/remapping': 2.3.5 '@unocss/config': 66.6.6 @@ -3996,7 +4028,7 @@ snapshots: pathe: 2.0.3 tinyglobby: 0.2.15 unplugin-utils: 0.3.1 - vite: 8.0.0(@types/node@24.11.0)(esbuild@0.27.3)(jiti@2.6.1)(terser@5.46.0) + vite: 8.0.5(@emnapi/core@1.8.1)(@emnapi/runtime@1.8.1)(@types/node@24.11.0)(esbuild@0.27.3)(jiti@2.6.1)(terser@5.46.0) '@vitest/expect@4.0.18': dependencies: @@ -4007,13 +4039,13 @@ snapshots: chai: 6.2.2 tinyrainbow: 3.0.3 - '@vitest/mocker@4.0.18(vite@7.3.1(@types/node@24.11.0)(jiti@2.6.1)(lightningcss@1.32.0)(terser@5.46.0))': + '@vitest/mocker@4.0.18(vite@7.3.2(@types/node@24.11.0)(jiti@2.6.1)(lightningcss@1.32.0)(terser@5.46.0))': dependencies: '@vitest/spy': 4.0.18 estree-walker: 3.0.3 magic-string: 0.30.21 optionalDependencies: - vite: 7.3.1(@types/node@24.11.0)(jiti@2.6.1)(lightningcss@1.32.0)(terser@5.46.0) + vite: 7.3.2(@types/node@24.11.0)(jiti@2.6.1)(lightningcss@1.32.0)(terser@5.46.0) '@vitest/pretty-format@4.0.18': dependencies: @@ -4064,7 +4096,7 @@ snapshots: blake3-wasm@2.1.5: {} - brace-expansion@5.0.4: + brace-expansion@5.0.5: dependencies: balanced-match: 4.0.4 @@ -4126,7 +4158,7 @@ snapshots: deepmerge@4.3.1: {} - defu@6.1.4: {} + defu@6.1.6: {} destr@2.0.5: {} @@ -4293,9 +4325,9 @@ snapshots: dependencies: reusify: 1.1.0 - fdir@6.5.0(picomatch@4.0.3): + fdir@6.5.0(picomatch@4.0.4): optionalDependencies: - picomatch: 4.0.3 + picomatch: 4.0.4 file-entry-cache@8.0.0: dependencies: @@ -4469,7 +4501,7 @@ snapshots: micromatch@4.0.8: dependencies: braces: 3.0.3 - picomatch: 2.3.1 + picomatch: 2.3.2 miniflare@4.20260317.0: dependencies: @@ -4485,7 +4517,7 @@ snapshots: minimatch@10.2.4: dependencies: - brace-expansion: 5.0.4 + brace-expansion: 5.0.5 mlly@1.8.0: dependencies: @@ -4523,7 +4555,7 @@ snapshots: type-check: 0.4.0 word-wrap: 1.2.5 - oxc-parser@0.115.0: + oxc-parser@0.115.0(@emnapi/core@1.8.1)(@emnapi/runtime@1.8.1): dependencies: '@oxc-project/types': 0.115.0 optionalDependencies: @@ -4543,15 +4575,18 @@ snapshots: '@oxc-parser/binding-linux-x64-gnu': 0.115.0 '@oxc-parser/binding-linux-x64-musl': 0.115.0 '@oxc-parser/binding-openharmony-arm64': 0.115.0 - '@oxc-parser/binding-wasm32-wasi': 0.115.0 + '@oxc-parser/binding-wasm32-wasi': 0.115.0(@emnapi/core@1.8.1)(@emnapi/runtime@1.8.1) '@oxc-parser/binding-win32-arm64-msvc': 0.115.0 '@oxc-parser/binding-win32-ia32-msvc': 0.115.0 '@oxc-parser/binding-win32-x64-msvc': 0.115.0 + transitivePeerDependencies: + - '@emnapi/core' + - '@emnapi/runtime' - oxc-walker@0.7.0(oxc-parser@0.115.0): + oxc-walker@0.7.0(oxc-parser@0.115.0(@emnapi/core@1.8.1)(@emnapi/runtime@1.8.1)): dependencies: magic-regexp: 0.10.0 - oxc-parser: 0.115.0 + oxc-parser: 0.115.0(@emnapi/core@1.8.1)(@emnapi/runtime@1.8.1) p-limit@3.1.0: dependencies: @@ -4577,9 +4612,9 @@ snapshots: picocolors@1.1.1: {} - picomatch@2.3.1: {} + picomatch@2.3.2: {} - picomatch@4.0.3: {} + picomatch@4.0.4: {} pkg-types@1.3.1: dependencies: @@ -4615,26 +4650,29 @@ snapshots: reusify@1.1.0: {} - rolldown@1.0.0-rc.9: + rolldown@1.0.0-rc.12(@emnapi/core@1.8.1)(@emnapi/runtime@1.8.1): dependencies: - '@oxc-project/types': 0.115.0 - '@rolldown/pluginutils': 1.0.0-rc.9 + '@oxc-project/types': 0.122.0 + '@rolldown/pluginutils': 1.0.0-rc.12 optionalDependencies: - '@rolldown/binding-android-arm64': 1.0.0-rc.9 - '@rolldown/binding-darwin-arm64': 1.0.0-rc.9 - '@rolldown/binding-darwin-x64': 1.0.0-rc.9 - '@rolldown/binding-freebsd-x64': 1.0.0-rc.9 - '@rolldown/binding-linux-arm-gnueabihf': 1.0.0-rc.9 - '@rolldown/binding-linux-arm64-gnu': 1.0.0-rc.9 - '@rolldown/binding-linux-arm64-musl': 1.0.0-rc.9 - '@rolldown/binding-linux-ppc64-gnu': 1.0.0-rc.9 - '@rolldown/binding-linux-s390x-gnu': 1.0.0-rc.9 - '@rolldown/binding-linux-x64-gnu': 1.0.0-rc.9 - '@rolldown/binding-linux-x64-musl': 1.0.0-rc.9 - '@rolldown/binding-openharmony-arm64': 1.0.0-rc.9 - '@rolldown/binding-wasm32-wasi': 1.0.0-rc.9 - '@rolldown/binding-win32-arm64-msvc': 1.0.0-rc.9 - '@rolldown/binding-win32-x64-msvc': 1.0.0-rc.9 + '@rolldown/binding-android-arm64': 1.0.0-rc.12 + '@rolldown/binding-darwin-arm64': 1.0.0-rc.12 + '@rolldown/binding-darwin-x64': 1.0.0-rc.12 + '@rolldown/binding-freebsd-x64': 1.0.0-rc.12 + '@rolldown/binding-linux-arm-gnueabihf': 1.0.0-rc.12 + '@rolldown/binding-linux-arm64-gnu': 1.0.0-rc.12 + '@rolldown/binding-linux-arm64-musl': 1.0.0-rc.12 + '@rolldown/binding-linux-ppc64-gnu': 1.0.0-rc.12 + '@rolldown/binding-linux-s390x-gnu': 1.0.0-rc.12 + '@rolldown/binding-linux-x64-gnu': 1.0.0-rc.12 + '@rolldown/binding-linux-x64-musl': 1.0.0-rc.12 + '@rolldown/binding-openharmony-arm64': 1.0.0-rc.12 + '@rolldown/binding-wasm32-wasi': 1.0.0-rc.12(@emnapi/core@1.8.1)(@emnapi/runtime@1.8.1) + '@rolldown/binding-win32-arm64-msvc': 1.0.0-rc.12 + '@rolldown/binding-win32-x64-msvc': 1.0.0-rc.12 + transitivePeerDependencies: + - '@emnapi/core' + - '@emnapi/runtime' rollup@4.60.0: dependencies: @@ -4679,7 +4717,7 @@ snapshots: semver@7.7.4: {} - serialize-javascript@7.0.4: {} + serialize-javascript@7.0.5: {} sharp@0.34.5: dependencies: @@ -4779,8 +4817,8 @@ snapshots: tinyglobby@0.2.15: dependencies: - fdir: 6.5.0(picomatch@4.0.3) - picomatch: 4.0.3 + fdir: 6.5.0(picomatch@4.0.4) + picomatch: 4.0.4 tinyrainbow@3.0.3: {} @@ -4827,7 +4865,7 @@ snapshots: unconfig@7.5.0: dependencies: '@quansync/fs': 1.0.0 - defu: 6.1.4 + defu: 6.1.6 jiti: 2.6.1 quansync: 1.0.0 unconfig-core: 7.5.0 @@ -4842,7 +4880,7 @@ snapshots: universal-user-agent@7.0.3: {} - unocss@66.6.6(vite@8.0.0(@types/node@24.11.0)(esbuild@0.27.3)(jiti@2.6.1)(terser@5.46.0)): + unocss@66.6.6(@emnapi/core@1.8.1)(@emnapi/runtime@1.8.1)(vite@8.0.5(@emnapi/core@1.8.1)(@emnapi/runtime@1.8.1)(@types/node@24.11.0)(esbuild@0.27.3)(jiti@2.6.1)(terser@5.46.0)): dependencies: '@unocss/cli': 66.6.6 '@unocss/core': 66.6.6 @@ -4856,35 +4894,37 @@ snapshots: '@unocss/preset-wind': 66.6.6 '@unocss/preset-wind3': 66.6.6 '@unocss/preset-wind4': 66.6.6 - '@unocss/transformer-attributify-jsx': 66.6.6 + '@unocss/transformer-attributify-jsx': 66.6.6(@emnapi/core@1.8.1)(@emnapi/runtime@1.8.1) '@unocss/transformer-compile-class': 66.6.6 '@unocss/transformer-directives': 66.6.6 '@unocss/transformer-variant-group': 66.6.6 - '@unocss/vite': 66.6.6(vite@8.0.0(@types/node@24.11.0)(esbuild@0.27.3)(jiti@2.6.1)(terser@5.46.0)) + '@unocss/vite': 66.6.6(vite@8.0.5(@emnapi/core@1.8.1)(@emnapi/runtime@1.8.1)(@types/node@24.11.0)(esbuild@0.27.3)(jiti@2.6.1)(terser@5.46.0)) transitivePeerDependencies: + - '@emnapi/core' + - '@emnapi/runtime' - vite unplugin-utils@0.3.1: dependencies: pathe: 2.0.3 - picomatch: 4.0.3 + picomatch: 4.0.4 unplugin@2.3.11: dependencies: '@jridgewell/remapping': 2.3.5 acorn: 8.16.0 - picomatch: 4.0.3 + picomatch: 4.0.4 webpack-virtual-modules: 0.6.2 uri-js@4.4.1: dependencies: punycode: 2.3.1 - vite@7.3.1(@types/node@24.11.0)(jiti@2.6.1)(lightningcss@1.32.0)(terser@5.46.0): + vite@7.3.2(@types/node@24.11.0)(jiti@2.6.1)(lightningcss@1.32.0)(terser@5.46.0): dependencies: esbuild: 0.27.3 - fdir: 6.5.0(picomatch@4.0.3) - picomatch: 4.0.3 + fdir: 6.5.0(picomatch@4.0.4) + picomatch: 4.0.4 postcss: 8.5.8 rollup: 4.60.0 tinyglobby: 0.2.15 @@ -4895,13 +4935,12 @@ snapshots: lightningcss: 1.32.0 terser: 5.46.0 - vite@8.0.0(@types/node@24.11.0)(esbuild@0.27.3)(jiti@2.6.1)(terser@5.46.0): + vite@8.0.5(@emnapi/core@1.8.1)(@emnapi/runtime@1.8.1)(@types/node@24.11.0)(esbuild@0.27.3)(jiti@2.6.1)(terser@5.46.0): dependencies: - '@oxc-project/runtime': 0.115.0 lightningcss: 1.32.0 - picomatch: 4.0.3 + picomatch: 4.0.4 postcss: 8.5.8 - rolldown: 1.0.0-rc.9 + rolldown: 1.0.0-rc.12(@emnapi/core@1.8.1)(@emnapi/runtime@1.8.1) tinyglobby: 0.2.15 optionalDependencies: '@types/node': 24.11.0 @@ -4909,15 +4948,18 @@ snapshots: fsevents: 2.3.3 jiti: 2.6.1 terser: 5.46.0 + transitivePeerDependencies: + - '@emnapi/core' + - '@emnapi/runtime' - vitefu@1.1.2(vite@8.0.0(@types/node@24.11.0)(esbuild@0.27.3)(jiti@2.6.1)(terser@5.46.0)): + vitefu@1.1.2(vite@8.0.5(@emnapi/core@1.8.1)(@emnapi/runtime@1.8.1)(@types/node@24.11.0)(esbuild@0.27.3)(jiti@2.6.1)(terser@5.46.0)): optionalDependencies: - vite: 8.0.0(@types/node@24.11.0)(esbuild@0.27.3)(jiti@2.6.1)(terser@5.46.0) + vite: 8.0.5(@emnapi/core@1.8.1)(@emnapi/runtime@1.8.1)(@types/node@24.11.0)(esbuild@0.27.3)(jiti@2.6.1)(terser@5.46.0) vitest@4.0.18(@types/node@24.11.0)(jiti@2.6.1)(lightningcss@1.32.0)(terser@5.46.0): dependencies: '@vitest/expect': 4.0.18 - '@vitest/mocker': 4.0.18(vite@7.3.1(@types/node@24.11.0)(jiti@2.6.1)(lightningcss@1.32.0)(terser@5.46.0)) + '@vitest/mocker': 4.0.18(vite@7.3.2(@types/node@24.11.0)(jiti@2.6.1)(lightningcss@1.32.0)(terser@5.46.0)) '@vitest/pretty-format': 4.0.18 '@vitest/runner': 4.0.18 '@vitest/snapshot': 4.0.18 @@ -4928,13 +4970,13 @@ snapshots: magic-string: 0.30.21 obug: 2.1.1 pathe: 2.0.3 - picomatch: 4.0.3 + picomatch: 4.0.4 std-env: 3.10.0 tinybench: 2.9.0 tinyexec: 1.0.2 tinyglobby: 0.2.15 tinyrainbow: 3.0.3 - vite: 7.3.1(@types/node@24.11.0)(jiti@2.6.1)(lightningcss@1.32.0)(terser@5.46.0) + vite: 7.3.2(@types/node@24.11.0)(jiti@2.6.1)(lightningcss@1.32.0)(terser@5.46.0) why-is-node-running: 2.3.0 optionalDependencies: '@types/node': 24.11.0 From 9cb60bbc7576055f7fd84060dba0171f8d64c574 Mon Sep 17 00:00:00 2001 From: signadou <39036502+signadou@users.noreply.github.com> Date: Tue, 7 Apr 2026 09:34:01 -0600 Subject: [PATCH 63/95] feat: add Bring All to Front predefined menu item type (#14307) * Add Bring All to Front predefined menu item type * Format and update changefile * Update .changes/add-bring-all-to-front-predefined-menu-item-type.md --- ...-all-to-front-predefined-menu-item-type.md | 6 +++++ crates/tauri/src/menu/builders/menu.rs | 25 +++++++++++++++++++ crates/tauri/src/menu/plugin.rs | 4 +++ crates/tauri/src/menu/predefined.rs | 23 +++++++++++++++++ .../api/src/components/MenuItemBuilder.svelte | 3 ++- packages/api/src/menu/predefinedMenuItem.ts | 1 + 6 files changed, 61 insertions(+), 1 deletion(-) create mode 100644 .changes/add-bring-all-to-front-predefined-menu-item-type.md diff --git a/.changes/add-bring-all-to-front-predefined-menu-item-type.md b/.changes/add-bring-all-to-front-predefined-menu-item-type.md new file mode 100644 index 000000000000..b27261856723 --- /dev/null +++ b/.changes/add-bring-all-to-front-predefined-menu-item-type.md @@ -0,0 +1,6 @@ +--- +'tauri': 'minor:feat' +'@tauri-apps/api': 'minor:feat' +--- + +Add Bring All to Front predefined menu item type diff --git a/crates/tauri/src/menu/builders/menu.rs b/crates/tauri/src/menu/builders/menu.rs index 2bf38fd56707..bd24f2a9725f 100644 --- a/crates/tauri/src/menu/builders/menu.rs +++ b/crates/tauri/src/menu/builders/menu.rs @@ -642,6 +642,31 @@ macro_rules! shared_menu_builder { .push(PredefinedMenuItem::services(self.manager, Some(text.as_ref())).map(|i| i.kind())); self } + + /// Add Bring All to Front menu item to the menu. + /// + /// ## Platform-specific: + /// + /// - **Windows / Linux:** Unsupported. + pub fn bring_all_to_front(mut self) -> Self { + self + .items + .push(PredefinedMenuItem::bring_all_to_front(self.manager, None).map(|i| i.kind())); + self + } + + /// Add Bring All to Front menu item with specified text to the menu. + /// + /// ## Platform-specific: + /// + /// - **Windows / Linux:** Unsupported. + pub fn bring_all_to_front_with_text>(mut self, text: S) -> Self { + self.items.push( + PredefinedMenuItem::bring_all_to_front(self.manager, Some(text.as_ref())) + .map(|i| i.kind()), + ); + self + } } }; } diff --git a/crates/tauri/src/menu/plugin.rs b/crates/tauri/src/menu/plugin.rs index 6db48a3d10ad..84ab54a98d22 100644 --- a/crates/tauri/src/menu/plugin.rs +++ b/crates/tauri/src/menu/plugin.rs @@ -91,6 +91,7 @@ enum Predefined { Quit, About(Option), Services, + BringAllToFront, } #[derive(Deserialize)] @@ -303,6 +304,9 @@ impl PredefinedMenuItemPayload { PredefinedMenuItem::about(webview, self.text.as_deref(), metadata) } Predefined::Services => PredefinedMenuItem::services(webview, self.text.as_deref()), + Predefined::BringAllToFront => { + PredefinedMenuItem::bring_all_to_front(webview, self.text.as_deref()) + } } } } diff --git a/crates/tauri/src/menu/predefined.rs b/crates/tauri/src/menu/predefined.rs index b2571361565b..cab7fb7b03b7 100644 --- a/crates/tauri/src/menu/predefined.rs +++ b/crates/tauri/src/menu/predefined.rs @@ -384,6 +384,29 @@ impl PredefinedMenuItem { Ok(Self(Arc::new(item))) } + /// Bring All to Front menu item + /// + /// ## Platform-specific: + /// + /// - **Windows / Linux:** Unsupported. + pub fn bring_all_to_front>(manager: &M, text: Option<&str>) -> crate::Result { + let handle = manager.app_handle(); + let app_handle = handle.clone(); + + let text = text.map(|t| t.to_owned()); + + let item = run_main_thread!(handle, || { + let item = muda::PredefinedMenuItem::bring_all_to_front(text.as_deref()); + PredefinedMenuItemInner { + id: item.id().clone(), + inner: Some(item), + app_handle, + } + })?; + + Ok(Self(Arc::new(item))) + } + /// Returns a unique identifier associated with this menu item. pub fn id(&self) -> &MenuId { &self.0.id diff --git a/examples/api/src/components/MenuItemBuilder.svelte b/examples/api/src/components/MenuItemBuilder.svelte index d907e0951a7b..0f93436978a4 100644 --- a/examples/api/src/components/MenuItemBuilder.svelte +++ b/examples/api/src/components/MenuItemBuilder.svelte @@ -32,7 +32,8 @@ 'ShowAll', 'CloseWindow', 'Quit', - 'Services' + 'Services', + 'BringAllToFront' ] function onKindChange(event) { diff --git a/packages/api/src/menu/predefinedMenuItem.ts b/packages/api/src/menu/predefinedMenuItem.ts index fed9a543facc..1517a35fa970 100644 --- a/packages/api/src/menu/predefinedMenuItem.ts +++ b/packages/api/src/menu/predefinedMenuItem.ts @@ -102,6 +102,7 @@ export interface PredefinedMenuItemOptions { | 'CloseWindow' | 'Quit' | 'Services' + | 'BringAllToFront' | { About: AboutMetadata | null } From 8d55ee5ccf2209ebbf16d331c2289cdc95844f8d Mon Sep 17 00:00:00 2001 From: Xuhui Zheng <2529677678@qq.com> Date: Wed, 8 Apr 2026 16:10:55 +0800 Subject: [PATCH 64/95] feat(windows): NSIS uninstaller icon and header image support (#15201) * feat: NSIS uninstaller support. * chore: fix typo and update schema. * fix: comments and alias. * fix: add pages for uninst sidebar. * chore: fix typo in comments of fields. * fix: group HEADERIMAGE. * fix: remove welcome/finish of uninstaller. * fix: remove uninstaller_sidebar_image. * Update crates/tauri-utils/src/config.rs Co-authored-by: Tony <68118705+Legend-Master@users.noreply.github.com> * chore: revert comments. * chore: update schema. * Update crates/tauri-utils/src/config.rs Co-authored-by: Tony <68118705+Legend-Master@users.noreply.github.com> * Update crates/tauri-utils/src/config.rs Co-authored-by: Tony <68118705+Legend-Master@users.noreply.github.com> * fix: typo of installer_icon. * chore: add change file. * fix: typo. * chore: update config.json. * Update .changes/feat-uninstaller-icon-image.md Co-authored-by: Tony <68118705+Legend-Master@users.noreply.github.com> * fix: revert alias. * chore: update comments in settings.rs. * chore: update comments. * fix: installer.nsi * fix: installer.nsi --------- Co-authored-by: Tony <68118705+Legend-Master@users.noreply.github.com> --- .changes/feat-uninstaller-icon-image.md | 13 +++++++++++ crates/tauri-bundler/src/bundle/settings.rs | 7 ++++++ .../src/bundle/windows/nsis/installer.nsi | 22 +++++++++++++++++-- .../src/bundle/windows/nsis/mod.rs | 14 ++++++++++++ crates/tauri-cli/config.schema.json | 14 ++++++++++++ crates/tauri-cli/src/helpers/config.rs | 2 ++ .../schemas/config.schema.json | 14 ++++++++++++ crates/tauri-utils/src/config.rs | 10 +++++++++ 8 files changed, 94 insertions(+), 2 deletions(-) create mode 100644 .changes/feat-uninstaller-icon-image.md diff --git a/.changes/feat-uninstaller-icon-image.md b/.changes/feat-uninstaller-icon-image.md new file mode 100644 index 000000000000..af2177e17263 --- /dev/null +++ b/.changes/feat-uninstaller-icon-image.md @@ -0,0 +1,13 @@ +--- +"tauri-bundler": minor:feat +"tauri-cli": minor:feat +"@tauri-apps/cli": minor:feat +"tauri-utils": minor:feat +--- + +Added uninstaller icon and uninstaller header image support for NSIS installer. + +Notes: + +- For `tauri-bundler` lib users, the `NsisSettings` now has 2 new fields `uninstaller_icon` and `uninstaller_header_image` which can be a breaking change +- When bundling with NSIS, users can add `uninstallerIcon` and `uninstallerHeaderImage` under `bundle > windows > nsis` to configure them. diff --git a/crates/tauri-bundler/src/bundle/settings.rs b/crates/tauri-bundler/src/bundle/settings.rs index d94708dae5ce..815f342cd592 100644 --- a/crates/tauri-bundler/src/bundle/settings.rs +++ b/crates/tauri-bundler/src/bundle/settings.rs @@ -470,6 +470,13 @@ pub struct NsisSettings { pub sidebar_image: Option, /// The path to an icon file used as the installer icon. pub installer_icon: Option, + /// The path to an icon file used as the uninstaller icon. + pub uninstaller_icon: Option, + /// The path to a bitmap file to display on the header of uninstallers pages. + /// Defaults to [`Self::header_image`]. If this is set but [`Self::header_image`] is not, a default image from NSIS will be applied to `header_image` + /// + /// The recommended dimensions are 150px x 57px. + pub uninstaller_header_image: Option, /// Whether the installation will be for all users or just the current user. pub install_mode: NSISInstallerMode, /// A list of installer languages. diff --git a/crates/tauri-bundler/src/bundle/windows/nsis/installer.nsi b/crates/tauri-bundler/src/bundle/windows/nsis/installer.nsi index e178c49ea12c..a48a46149f6d 100644 --- a/crates/tauri-bundler/src/bundle/windows/nsis/installer.nsi +++ b/crates/tauri-bundler/src/bundle/windows/nsis/installer.nsi @@ -41,6 +41,8 @@ ${StrLoc} !define INSTALLERICON "{{installer_icon}}" !define SIDEBARIMAGE "{{sidebar_image}}" !define HEADERIMAGE "{{header_image}}" +!define UNINSTALLERICON "{{uninstaller_icon}}" +!define UNINSTALLERHEADERIMAGE "{{uninstaller_header_image}}" !define MAINBINARYNAME "{{main_binary_name}}" !define MAINBINARYSRCPATH "{{main_binary_path}}" !define BUNDLEID "{{bundle_id}}" @@ -129,10 +131,26 @@ VIAddVersionKey "ProductVersion" "${VERSION}" !define MUI_WELCOMEFINISHPAGE_BITMAP "${SIDEBARIMAGE}" !endif -; Installer header image +; Enable header images for installer and uninstaller pages when either image is configured. !if "${HEADERIMAGE}" != "" !define MUI_HEADERIMAGE - !define MUI_HEADERIMAGE_BITMAP "${HEADERIMAGE}" +!else if "${UNINSTALLERHEADERIMAGE}" != "" + !define MUI_HEADERIMAGE +!endif + +; Installer header image +!if "${HEADERIMAGE}" != "" + !define MUI_HEADERIMAGE_BITMAP "${HEADERIMAGE}" +!endif + +; Uninstaller header image +!if "${UNINSTALLERHEADERIMAGE}" != "" + !define MUI_HEADERIMAGE_UNBITMAP "${UNINSTALLERHEADERIMAGE}" +!endif + +; Uninstaller icon +!if "${UNINSTALLERICON}" != "" + !define MUI_UNICON "${UNINSTALLERICON}" !endif ; Define registry key to store installer language diff --git a/crates/tauri-bundler/src/bundle/windows/nsis/mod.rs b/crates/tauri-bundler/src/bundle/windows/nsis/mod.rs index 21d15aa46e35..85370834f80c 100644 --- a/crates/tauri-bundler/src/bundle/windows/nsis/mod.rs +++ b/crates/tauri-bundler/src/bundle/windows/nsis/mod.rs @@ -354,6 +354,20 @@ fn build_nsis_app_installer( ); } + if let Some(uninstaller_icon) = &nsis.uninstaller_icon { + data.insert( + "uninstaller_icon", + to_json(dunce::canonicalize(uninstaller_icon)?), + ); + } + + if let Some(uninstaller_header_image) = &nsis.uninstaller_header_image { + data.insert( + "uninstaller_header_image", + to_json(dunce::canonicalize(uninstaller_header_image)?), + ); + } + if let Some(installer_hooks) = &nsis.installer_hooks { let installer_hooks = dunce::canonicalize(installer_hooks)?; data.insert("installer_hooks", to_json(installer_hooks)); diff --git a/crates/tauri-cli/config.schema.json b/crates/tauri-cli/config.schema.json index 86bfe5d46b33..a489c8881542 100644 --- a/crates/tauri-cli/config.schema.json +++ b/crates/tauri-cli/config.schema.json @@ -2996,6 +2996,20 @@ "null" ] }, + "uninstallerIcon": { + "description": "The path to an icon file used as the uninstaller icon.", + "type": [ + "string", + "null" + ] + }, + "uninstallerHeaderImage": { + "description": "The path to a bitmap file to display on the header of uninstallers pages.\n Defaults to [`Self::header_image`]. If this is set but [`Self::header_image`] is not, a default image from NSIS will be applied to `header_image`\n\n The recommended dimensions are 150px x 57px.", + "type": [ + "string", + "null" + ] + }, "installMode": { "description": "Whether the installation will be for all users or just the current user.", "default": "currentUser", diff --git a/crates/tauri-cli/src/helpers/config.rs b/crates/tauri-cli/src/helpers/config.rs index f53d8c8693c5..75fb6b1ac605 100644 --- a/crates/tauri-cli/src/helpers/config.rs +++ b/crates/tauri-cli/src/helpers/config.rs @@ -110,6 +110,8 @@ pub fn nsis_settings(config: NsisConfig) -> tauri_bundler::NsisSettings { header_image: config.header_image, sidebar_image: config.sidebar_image, installer_icon: config.installer_icon, + uninstaller_icon: config.uninstaller_icon, + uninstaller_header_image: config.uninstaller_header_image, install_mode: config.install_mode, languages: config.languages, custom_language_files: config.custom_language_files, diff --git a/crates/tauri-schema-generator/schemas/config.schema.json b/crates/tauri-schema-generator/schemas/config.schema.json index 86bfe5d46b33..a489c8881542 100644 --- a/crates/tauri-schema-generator/schemas/config.schema.json +++ b/crates/tauri-schema-generator/schemas/config.schema.json @@ -2996,6 +2996,20 @@ "null" ] }, + "uninstallerIcon": { + "description": "The path to an icon file used as the uninstaller icon.", + "type": [ + "string", + "null" + ] + }, + "uninstallerHeaderImage": { + "description": "The path to a bitmap file to display on the header of uninstallers pages.\n Defaults to [`Self::header_image`]. If this is set but [`Self::header_image`] is not, a default image from NSIS will be applied to `header_image`\n\n The recommended dimensions are 150px x 57px.", + "type": [ + "string", + "null" + ] + }, "installMode": { "description": "Whether the installation will be for all users or just the current user.", "default": "currentUser", diff --git a/crates/tauri-utils/src/config.rs b/crates/tauri-utils/src/config.rs index 2b6304069279..cb974ac93428 100644 --- a/crates/tauri-utils/src/config.rs +++ b/crates/tauri-utils/src/config.rs @@ -857,9 +857,19 @@ pub struct NsisConfig { /// The recommended dimensions are 164px x 314px. #[serde(alias = "sidebar-image")] pub sidebar_image: Option, + // TODO: Change the alias to installer-icon in v3 /// The path to an icon file used as the installer icon. #[serde(alias = "install-icon")] pub installer_icon: Option, + /// The path to an icon file used as the uninstaller icon. + #[serde(alias = "uninstaller-icon")] + pub uninstaller_icon: Option, + /// The path to a bitmap file to display on the header of uninstallers pages. + /// Defaults to [`Self::header_image`]. If this is set but [`Self::header_image`] is not, a default image from NSIS will be applied to `header_image` + /// + /// The recommended dimensions are 150px x 57px. + #[serde(alias = "uninstaller-header-image")] + pub uninstaller_header_image: Option, /// Whether the installation will be for all users or just the current user. #[serde(default, alias = "install-mode")] pub install_mode: NSISInstallerMode, From df950820c2c7f079610b94a48851a4049c59e600 Mon Sep 17 00:00:00 2001 From: Lucas Fernandes Nogueira Date: Mon, 13 Apr 2026 14:41:27 -0300 Subject: [PATCH 65/95] feat(mobile): add file association support (#14486) --- .changes/file-association.md | 9 + .changes/mobile-file-associations.md | 7 + Cargo.lock | 1 + crates/tauri-build/src/lib.rs | 5 + crates/tauri-build/src/mobile.rs | 141 +++++++++- crates/tauri-bundler/src/bundle/macos/app.rs | 103 +------- crates/tauri-cli/config.schema.json | 36 +++ crates/tauri-cli/src/mobile/ios/build.rs | 11 +- crates/tauri-cli/src/mobile/ios/dev.rs | 11 +- crates/tauri-plugin/src/build/mobile.rs | 92 +------ crates/tauri-runtime-wry/src/lib.rs | 2 +- crates/tauri-runtime/src/lib.rs | 2 +- .../schemas/config.schema.json | 36 +++ crates/tauri-utils/Cargo.toml | 1 + crates/tauri-utils/src/build.rs | 71 +++++ crates/tauri-utils/src/config.rs | 248 +++++++++++++++++- crates/tauri/src/app.rs | 9 +- examples/api/src-tauri/src/lib.rs | 4 + examples/api/src-tauri/tauri.conf.json | 31 +++ .../file-associations/src-tauri/src/main.rs | 2 +- 20 files changed, 635 insertions(+), 187 deletions(-) create mode 100644 .changes/file-association.md create mode 100644 .changes/mobile-file-associations.md diff --git a/.changes/file-association.md b/.changes/file-association.md new file mode 100644 index 000000000000..6e95978db5a8 --- /dev/null +++ b/.changes/file-association.md @@ -0,0 +1,9 @@ +--- +"tauri": minor:feat +"tauri-build": minor:feat +"tauri-plugin": minor:feat +"tauri-cli": minor:feat +"tauri-bundler": minor:feat +--- + +Implement file association for Android and iOS. diff --git a/.changes/mobile-file-associations.md b/.changes/mobile-file-associations.md new file mode 100644 index 000000000000..308a50a2bece --- /dev/null +++ b/.changes/mobile-file-associations.md @@ -0,0 +1,7 @@ +--- +"tauri": minor:feat +"tauri-runtime": minor:feat +"tauri-runtime-wry": minor:feat +--- + +Trigger `RunEvent::Opened` on Android. diff --git a/Cargo.lock b/Cargo.lock index ae1efa3b0c81..79acbb6495ca 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -9190,6 +9190,7 @@ dependencies = [ "log", "memchr", "phf 0.11.3", + "plist", "proc-macro2", "quote", "regex", diff --git a/crates/tauri-build/src/lib.rs b/crates/tauri-build/src/lib.rs index a6baf947665c..004cf3d1924c 100644 --- a/crates/tauri-build/src/lib.rs +++ b/crates/tauri-build/src/lib.rs @@ -497,6 +497,11 @@ pub fn try_build(attributes: Attributes) -> Result<()> { if let Some(project_dir) = env::var_os("TAURI_ANDROID_PROJECT_PATH").map(PathBuf::from) { mobile::generate_gradle_files(project_dir)?; + + // Update Android manifest with file associations + if let Some(associations) = config.bundle.file_associations.as_ref() { + mobile::update_android_manifest_file_associations(associations)?; + } } cfg_alias("dev", is_dev()); diff --git a/crates/tauri-build/src/mobile.rs b/crates/tauri-build/src/mobile.rs index 3dcd4136c8c4..80f0613db8e4 100644 --- a/crates/tauri-build/src/mobile.rs +++ b/crates/tauri-build/src/mobile.rs @@ -2,10 +2,147 @@ // SPDX-License-Identifier: Apache-2.0 // SPDX-License-Identifier: MIT -use std::path::PathBuf; +use std::{collections::HashSet, path::PathBuf}; use anyhow::{Context, Result}; -use tauri_utils::write_if_changed; +use tauri_utils::{config::AndroidIntentAction, write_if_changed}; + +/// Updates the Android manifest to add file association intent filters +pub fn update_android_manifest_file_associations( + associations: &[tauri_utils::config::FileAssociation], +) -> Result<()> { + if associations.is_empty() { + return Ok(()); + } + + let intent_filters = generate_file_association_intent_filters(associations); + tauri_utils::build::update_android_manifest("tauri-file-associations", "activity", intent_filters) +} + +fn generate_file_association_intent_filters( + associations: &[tauri_utils::config::FileAssociation], +) -> String { + let mut filters = String::new(); + + for association in associations { + // Get mime types - use explicit mime_type, or infer from extensions + let mut mime_types = HashSet::new(); + + if let Some(mime_type) = &association.mime_type { + mime_types.insert(( + mime_type.clone(), + association.android_intent_action_filters.clone(), + )); + } else { + // Infer mime types from extensions + for ext in &association.ext { + if let Some(mime) = extension_to_mime_type(&ext.0) { + mime_types.insert((mime, association.android_intent_action_filters.clone())); + } + } + } + + // If we have mime types, create intent filters + if !mime_types.is_empty() { + for (mime_type, actions) in &mime_types { + filters.push_str("\n"); + if let Some(actions) = actions { + for action in actions { + let action = match action { + AndroidIntentAction::Send => "SEND", + AndroidIntentAction::SendMultiple => "SEND_MULTIPLE", + AndroidIntentAction::View => "VIEW", + _ => unimplemented!(), + }; + filters.push_str(&format!( + " \n" + )); + } + } else { + filters.push_str(" \n"); + filters.push_str(" \n"); + filters.push_str(" \n"); + } + filters.push_str(" \n"); + filters.push_str(" \n"); + filters.push_str(&format!( + " \n", + mime_type + )); + + // Add file scheme and path patterns for extensions + if !association.ext.is_empty() { + // Create path patterns for each extension + // Android's pathPattern needs \\. (double backslash-dot) in XML to match a literal dot + let path_patterns: Vec = association + .ext + .iter() + .map(|ext| format!(".*\\\\.{}", ext.0)) + .collect(); + + for pattern in &path_patterns { + filters.push_str(&format!( + " \n", + pattern + )); + } + } + + filters.push_str("\n"); + } + } else if !association.ext.is_empty() { + // If no mime type but we have extensions, use a generic approach + filters.push_str("\n"); + filters.push_str(" \n"); + filters.push_str(" \n"); + filters.push_str(" \n"); + + for ext in &association.ext { + // Android's pathPattern needs \\. (double backslash-dot) in XML to match a literal dot + filters.push_str(&format!( + " \n", + ext.0 + )); + } + + filters.push_str("\n"); + } + } + + filters +} + +fn extension_to_mime_type(ext: &str) -> Option { + Some( + match ext.to_lowercase().as_str() { + "png" => "image/png", + "jpg" | "jpeg" => "image/jpeg", + "gif" => "image/gif", + "bmp" => "image/bmp", + "webp" => "image/webp", + "svg" => "image/svg+xml", + "ico" => "image/x-icon", + "tiff" | "tif" => "image/tiff", + "heic" | "heif" => "image/heic", + "mp4" => "video/mp4", + "mov" => "video/quicktime", + "avi" => "video/x-msvideo", + "mkv" => "video/x-matroska", + "mp3" => "audio/mpeg", + "wav" => "audio/wav", + "aac" => "audio/aac", + "m4a" => "audio/mp4", + "pdf" => "application/pdf", + "txt" => "text/plain", + "html" | "htm" => "text/html", + "json" => "application/json", + "xml" => "application/xml", + "rtf" => "application/rtf", + _ => return None, + } + .to_string(), + ) +} pub fn generate_gradle_files(project_dir: PathBuf) -> Result<()> { let gradle_settings_path = project_dir.join("tauri.settings.gradle"); diff --git a/crates/tauri-bundler/src/bundle/macos/app.rs b/crates/tauri-bundler/src/bundle/macos/app.rs index 5c6581fb6960..1dc22c4579cf 100644 --- a/crates/tauri-bundler/src/bundle/macos/app.rs +++ b/crates/tauri-bundler/src/bundle/macos/app.rs @@ -262,102 +262,15 @@ fn create_info_plist( } if let Some(associations) = settings.file_associations() { - let exported_associations = associations - .iter() - .filter_map(|association| { - association.exported_type.as_ref().map(|exported_type| { - let mut dict = plist::Dictionary::new(); - - dict.insert( - "UTTypeIdentifier".into(), - exported_type.identifier.clone().into(), - ); - if let Some(description) = &association.description { - dict.insert("UTTypeDescription".into(), description.clone().into()); - } - if let Some(conforms_to) = &exported_type.conforms_to { - dict.insert( - "UTTypeConformsTo".into(), - plist::Value::Array(conforms_to.iter().map(|s| s.clone().into()).collect()), - ); - } - - let mut specification = plist::Dictionary::new(); - specification.insert( - "public.filename-extension".into(), - plist::Value::Array( - association - .ext - .iter() - .map(|s| s.to_string().into()) - .collect(), - ), - ); - if let Some(mime_type) = &association.mime_type { - specification.insert("public.mime-type".into(), mime_type.clone().into()); - } - - dict.insert("UTTypeTagSpecification".into(), specification.into()); - - plist::Value::Dictionary(dict) - }) - }) - .collect::>(); - - if !exported_associations.is_empty() { - plist.insert( - "UTExportedTypeDeclarations".into(), - plist::Value::Array(exported_associations), - ); + if let Some(file_associations_plist) = + tauri_utils::config::file_associations_plist(associations) + { + if let Some(plist_dict) = file_associations_plist.as_dictionary() { + for (key, value) in plist_dict { + plist.insert(key.clone(), value.clone()); + } + } } - - plist.insert( - "CFBundleDocumentTypes".into(), - plist::Value::Array( - associations - .iter() - .map(|association| { - let mut dict = plist::Dictionary::new(); - - if !association.ext.is_empty() { - dict.insert( - "CFBundleTypeExtensions".into(), - plist::Value::Array( - association - .ext - .iter() - .map(|ext| ext.to_string().into()) - .collect(), - ), - ); - } - - if let Some(content_types) = &association.content_types { - dict.insert( - "LSItemContentTypes".into(), - plist::Value::Array(content_types.iter().map(|s| s.to_string().into()).collect()), - ); - } - - dict.insert( - "CFBundleTypeName".into(), - association - .name - .as_ref() - .unwrap_or(&association.ext[0].0) - .to_string() - .into(), - ); - dict.insert( - "CFBundleTypeRole".into(), - association.role.to_string().into(), - ); - dict.insert("LSHandlerRank".into(), association.rank.to_string().into()); - plist::Value::Dictionary(dict) - }) - .collect(), - ), - ); } if let Some(path) = bundle_icon_file { diff --git a/crates/tauri-cli/config.schema.json b/crates/tauri-cli/config.schema.json index a489c8881542..c759643a9ad8 100644 --- a/crates/tauri-cli/config.schema.json +++ b/crates/tauri-cli/config.schema.json @@ -2517,6 +2517,16 @@ "type": "null" } ] + }, + "androidIntentActionFilters": { + "description": "Intent action filters for this file association.\n\n By default all filters are used.", + "type": [ + "array", + "null" + ], + "items": { + "$ref": "#/definitions/AndroidIntentAction" + } } }, "additionalProperties": false @@ -2622,6 +2632,32 @@ }, "additionalProperties": false }, + "AndroidIntentAction": { + "description": "Android intent action.", + "oneOf": [ + { + "description": "ACTION_SEND.\n\n ", + "type": "string", + "enum": [ + "send" + ] + }, + { + "description": "ACTION_SEND_MULTIPLE.\n\n ", + "type": "string", + "enum": [ + "sendMultiple" + ] + }, + { + "description": "ACTION_VIEW.\n\n ", + "type": "string", + "enum": [ + "view" + ] + } + ] + }, "WindowsConfig": { "description": "Windows bundler configuration.\n\n See more: ", "type": "object", diff --git a/crates/tauri-cli/src/mobile/ios/build.rs b/crates/tauri-cli/src/mobile/ios/build.rs index a016ccca3263..762654c4ad1d 100644 --- a/crates/tauri-cli/src/mobile/ios/build.rs +++ b/crates/tauri-cli/src/mobile/ios/build.rs @@ -243,8 +243,15 @@ pub fn run(options: Options, noise_level: NoiseLevel, dirs: &Dirs) -> Result Result< if dirs.tauri.join("Info.ios.plist").exists() { src_plists.push(dirs.tauri.join("Info.ios.plist").into()); } - if let Some(info_plist) = &tauri_config.bundle.ios.info_plist { - src_plists.push(info_plist.clone().into()); + { + if let Some(info_plist) = &tauri_config.bundle.ios.info_plist { + src_plists.push(info_plist.clone().into()); + } + if let Some(associations) = tauri_config.bundle.file_associations.as_ref() { + if let Some(file_associations) = tauri_utils::config::file_associations_plist(associations) { + src_plists.push(file_associations.into()); + } + } } let merged_info_plist = merge_plist(src_plists)?; merged_info_plist diff --git a/crates/tauri-plugin/src/build/mobile.rs b/crates/tauri-plugin/src/build/mobile.rs index 2ff795aca796..edccc50cc7de 100644 --- a/crates/tauri-plugin/src/build/mobile.rs +++ b/crates/tauri-plugin/src/build/mobile.rs @@ -5,8 +5,7 @@ //! Mobile-specific build utilities. use std::{ - env::var_os, - fs::{copy, create_dir, create_dir_all, read_to_string, remove_dir_all, write}, + fs::{copy, create_dir, create_dir_all, remove_dir_all}, path::{Path, PathBuf}, }; @@ -17,7 +16,7 @@ use super::{build_var, cfg_alias}; #[cfg(target_os = "macos")] pub fn update_entitlements(f: F) -> Result<()> { if let (Some(project_path), Ok(app_name)) = ( - var_os("TAURI_IOS_PROJECT_PATH").map(PathBuf::from), + std::env::var_os("TAURI_IOS_PROJECT_PATH").map(PathBuf::from), std::env::var("TAURI_IOS_APP_NAME"), ) { update_plist_file( @@ -34,7 +33,7 @@ pub fn update_entitlements(f: F) -> Result<() #[cfg(target_os = "macos")] pub fn update_info_plist(f: F) -> Result<()> { if let (Some(project_path), Ok(app_name)) = ( - var_os("TAURI_IOS_PROJECT_PATH").map(PathBuf::from), + std::env::var_os("TAURI_IOS_PROJECT_PATH").map(PathBuf::from), std::env::var("TAURI_IOS_APP_NAME"), ) { update_plist_file( @@ -48,16 +47,9 @@ pub fn update_info_plist(f: F) -> Result<()> Ok(()) } +/// Updates the Android manifest by inserting XML content into a specified parent tag. pub fn update_android_manifest(block_identifier: &str, parent: &str, insert: String) -> Result<()> { - if let Some(project_path) = var_os("TAURI_ANDROID_PROJECT_PATH").map(PathBuf::from) { - let manifest_path = project_path.join("app/src/main/AndroidManifest.xml"); - let manifest = read_to_string(&manifest_path)?; - let rewritten = insert_into_xml(&manifest, block_identifier, parent, &insert); - if rewritten != manifest { - write(manifest_path, rewritten)?; - } - } - Ok(()) + tauri_utils::build::update_android_manifest(block_identifier, parent, insert) } pub(crate) fn setup( @@ -161,7 +153,7 @@ fn update_plist_file, F: FnOnce(&mut plist::Dictionary)>( let path = path.as_ref(); if path.exists() { - let plist_str = read_to_string(path)?; + let plist_str = std::fs::read_to_string(path)?; let mut plist = plist::Value::from_reader(Cursor::new(&plist_str))?; if let Some(dict) = plist.as_dictionary_mut() { f(dict); @@ -170,7 +162,7 @@ fn update_plist_file, F: FnOnce(&mut plist::Dictionary)>( plist::to_writer_xml(writer, &plist)?; let new_plist_str = String::from_utf8(plist_buf)?; if new_plist_str != plist_str { - write(path, new_plist_str)?; + std::fs::write(path, new_plist_str)?; } } } @@ -178,72 +170,14 @@ fn update_plist_file, F: FnOnce(&mut plist::Dictionary)>( Ok(()) } -fn xml_block_comment(id: &str) -> String { - format!("") -} - -fn insert_into_xml(xml: &str, block_identifier: &str, parent_tag: &str, contents: &str) -> String { - let block_comment = xml_block_comment(block_identifier); - - let mut rewritten = Vec::new(); - let mut found_block = false; - let parent_closing_tag = format!(""); - for line in xml.split('\n') { - if line.contains(&block_comment) { - found_block = !found_block; - continue; - } - - // found previous block which should be removed - if found_block { - continue; - } - - if let Some(index) = line.find(&parent_closing_tag) { - let indentation = " ".repeat(index + 4); - rewritten.push(format!("{indentation}{block_comment}")); - for l in contents.split('\n') { - rewritten.push(format!("{indentation}{l}")); - } - rewritten.push(format!("{indentation}{block_comment}")); - } - - rewritten.push(line.to_string()); - } - - rewritten.join("\n") -} - #[cfg(test)] mod tests { #[test] - fn insert_into_xml() { - let manifest = r#" - - - - -"#; - let id = "tauritest"; - let new = super::insert_into_xml(manifest, id, "application", ""); - - let block_id_comment = super::xml_block_comment(id); - let expected = format!( - r#" - - - - {block_id_comment} - - {block_id_comment} - -"# - ); - - assert_eq!(new, expected); - - // assert it's still the same after an empty update - let new = super::insert_into_xml(&expected, id, "application", ""); - assert_eq!(new, expected); + fn update_android_manifest() { + use tauri_utils::build::update_android_manifest; + + // This test would require setting up the environment, so we just verify it compiles + // The actual implementation is tested in tauri-utils + let _result = update_android_manifest("test", "activity", "".to_string()); } } diff --git a/crates/tauri-runtime-wry/src/lib.rs b/crates/tauri-runtime-wry/src/lib.rs index 772c392a2632..42a22d1026ce 100644 --- a/crates/tauri-runtime-wry/src/lib.rs +++ b/crates/tauri-runtime-wry/src/lib.rs @@ -4371,7 +4371,7 @@ fn handle_event_loop( ); } }, - #[cfg(any(target_os = "macos", target_os = "ios"))] + #[cfg(any(target_os = "macos", target_os = "ios", target_os = "android"))] Event::Opened { urls } => { callback(RunEvent::Opened { urls }); } diff --git a/crates/tauri-runtime/src/lib.rs b/crates/tauri-runtime/src/lib.rs index 5e32cfa8c5be..eac06fbe95ef 100644 --- a/crates/tauri-runtime/src/lib.rs +++ b/crates/tauri-runtime/src/lib.rs @@ -223,7 +223,7 @@ pub enum RunEvent { /// This event is useful as a place to put your code that should be run after all state-changing events have been handled and you want to do stuff (updating state, performing calculations, etc) that happens as the "main body" of your event loop. MainEventsCleared, /// Emitted when the user wants to open the specified resource with the app. - #[cfg(any(target_os = "macos", target_os = "ios"))] + #[cfg(any(target_os = "macos", target_os = "ios", target_os = "android"))] Opened { urls: Vec }, /// Emitted when the NSApplicationDelegate's applicationShouldHandleReopen gets called #[cfg(target_os = "macos")] diff --git a/crates/tauri-schema-generator/schemas/config.schema.json b/crates/tauri-schema-generator/schemas/config.schema.json index a489c8881542..c759643a9ad8 100644 --- a/crates/tauri-schema-generator/schemas/config.schema.json +++ b/crates/tauri-schema-generator/schemas/config.schema.json @@ -2517,6 +2517,16 @@ "type": "null" } ] + }, + "androidIntentActionFilters": { + "description": "Intent action filters for this file association.\n\n By default all filters are used.", + "type": [ + "array", + "null" + ], + "items": { + "$ref": "#/definitions/AndroidIntentAction" + } } }, "additionalProperties": false @@ -2622,6 +2632,32 @@ }, "additionalProperties": false }, + "AndroidIntentAction": { + "description": "Android intent action.", + "oneOf": [ + { + "description": "ACTION_SEND.\n\n ", + "type": "string", + "enum": [ + "send" + ] + }, + { + "description": "ACTION_SEND_MULTIPLE.\n\n ", + "type": "string", + "enum": [ + "sendMultiple" + ] + }, + { + "description": "ACTION_VIEW.\n\n ", + "type": "string", + "enum": [ + "view" + ] + } + ] + }, "WindowsConfig": { "description": "Windows bundler configuration.\n\n See more: ", "type": "object", diff --git a/crates/tauri-utils/Cargo.toml b/crates/tauri-utils/Cargo.toml index 0bf36fe88ba1..133c8644c979 100644 --- a/crates/tauri-utils/Cargo.toml +++ b/crates/tauri-utils/Cargo.toml @@ -55,6 +55,7 @@ cargo_metadata = { version = "0.19", optional = true } serde-untagged = "0.1" uuid = { version = "1", features = ["serde"] } http = "1" +plist = "1" [target."cfg(target_os = \"macos\")".dependencies] swift-rs = { version = "1", optional = true, features = ["build"] } diff --git a/crates/tauri-utils/src/build.rs b/crates/tauri-utils/src/build.rs index 53e98e28d912..463b7000934a 100644 --- a/crates/tauri-utils/src/build.rs +++ b/crates/tauri-utils/src/build.rs @@ -94,3 +94,74 @@ fn link_xcode_library(name: &str, source: impl AsRef) { println!("cargo:rustc-link-search=native={}", lib_out_dir.display()); println!("cargo:rustc-link-lib=static={name}"); } + +/// Updates the Android manifest by inserting XML content into a specified parent tag. +/// +/// The content is wrapped in auto-generated comments and will replace any existing +/// content with the same block identifier. +/// +/// # Arguments +/// +/// * `block_identifier` - A unique identifier for the block (used in comments) +/// * `parent` - The parent XML tag name (e.g., "activity", "application") +/// * `insert` - The XML content to insert +pub fn update_android_manifest( + block_identifier: &str, + parent: &str, + insert: String, +) -> anyhow::Result<()> { + use std::{ + env::var_os, + fs::{read_to_string, write}, + path::PathBuf, + }; + + if let Some(project_path) = var_os("TAURI_ANDROID_PROJECT_PATH").map(PathBuf::from) { + let manifest_path = project_path.join("app/src/main/AndroidManifest.xml"); + if !manifest_path.exists() { + return Ok(()); + } + let manifest = read_to_string(&manifest_path)?; + let rewritten = insert_into_xml(&manifest, block_identifier, parent, &insert); + if rewritten != manifest { + write(&manifest_path, rewritten)?; + } + } + Ok(()) +} + +fn xml_block_comment(id: &str) -> String { + format!("") +} + +fn insert_into_xml(xml: &str, block_identifier: &str, parent_tag: &str, contents: &str) -> String { + let block_comment = xml_block_comment(block_identifier); + + let mut rewritten = Vec::new(); + let mut found_block = false; + let parent_closing_tag = format!(""); + for line in xml.split('\n') { + if line.contains(&block_comment) { + found_block = !found_block; + continue; + } + + // found previous block which should be removed + if found_block { + continue; + } + + if let Some(index) = line.find(&parent_closing_tag) { + let indentation = " ".repeat(index + 4); + rewritten.push(format!("{indentation}{block_comment}")); + for l in contents.split('\n') { + rewritten.push(format!("{indentation}{l}")); + } + rewritten.push(format!("{indentation}{block_comment}")); + } + + rewritten.push(line.to_string()); + } + + rewritten.join("\n") +} diff --git a/crates/tauri-utils/src/config.rs b/crates/tauri-utils/src/config.rs index cb974ac93428..78df2f4fa56b 100644 --- a/crates/tauri-utils/src/config.rs +++ b/crates/tauri-utils/src/config.rs @@ -39,7 +39,7 @@ use serde_with::skip_serializing_none; use url::Url; use std::{ - collections::HashMap, + collections::{HashMap, HashSet}, fmt::{self, Display}, fs::read_to_string, path::PathBuf, @@ -1207,6 +1207,31 @@ pub struct FileAssociation { /// /// You should define this if the associated file is a custom file type defined by your application. pub exported_type: Option, + /// Intent action filters for this file association. + /// + /// By default all filters are used. + #[serde(alias = "android-intent-action-filters")] + pub android_intent_action_filters: Option>, +} + +/// Android intent action. +#[derive(Debug, PartialEq, Eq, Clone, Deserialize, Serialize, Hash)] +#[cfg_attr(feature = "schema", derive(JsonSchema))] +#[serde(rename_all = "camelCase")] +#[non_exhaustive] +pub enum AndroidIntentAction { + /// ACTION_SEND. + /// + /// + Send, + /// ACTION_SEND_MULTIPLE. + /// + /// + SendMultiple, + /// ACTION_VIEW. + /// + /// + View, } /// The exported type definition. Maps to a `UTExportedTypeDeclarations` entry on macOS. @@ -1223,6 +1248,227 @@ pub struct ExportedFileAssociation { pub conforms_to: Option>, } +impl FileAssociation { + /// Infers UTIs (Uniform Type Identifiers) from file extensions and mime types. + /// This is useful for macOS and iOS to automatically populate `LSItemContentTypes` + /// in the Info.plist for share sheet and file association support. + /// + /// Returns a vector of UTIs that should be included in `LSItemContentTypes`. + /// Explicitly provided content types are included first, followed by inferred types. + pub fn infer_content_types(&self) -> HashSet { + let mut content_types = HashSet::new(); + + // when we have an exported type, we only reference it + if let Some(exported_type) = &self.exported_type { + content_types.insert(exported_type.identifier.clone()); + return content_types; + } + + // Start with explicitly provided content types + if let Some(explicit_types) = &self.content_types { + content_types.extend(explicit_types.iter().cloned()); + } + + // Infer from extensions and add to content_types (avoiding duplicates) + for ext in &self.ext { + if let Some(uti) = extension_to_uti(&ext.0) { + content_types.insert(uti.to_string()); + } + } + + // Also infer from mime type if available (avoiding duplicates) + if let Some(mime_type) = &self.mime_type { + if let Some(uti) = mime_type_to_uti(mime_type) { + content_types.insert(uti.to_string()); + } + } + + content_types + } +} + +/// Generates plist dictionary entries for file associations. +/// This is used by both macOS and iOS bundlers to populate Info.plist. +/// +/// Returns a plist dictionary containing `UTExportedTypeDeclarations` and `CFBundleDocumentTypes` +/// if there are any file associations configured. +pub fn file_associations_plist(associations: &[FileAssociation]) -> Option { + use plist::{Dictionary, Value}; + + if associations.is_empty() { + return None; + } + + let exported_associations = associations + .iter() + .filter_map(|association| { + association.exported_type.as_ref().map(|exported_type| { + let mut dict = Dictionary::new(); + + dict.insert( + "UTTypeIdentifier".into(), + exported_type.identifier.clone().into(), + ); + if let Some(description) = &association.description { + dict.insert("UTTypeDescription".into(), description.clone().into()); + } + if let Some(conforms_to) = &exported_type.conforms_to { + dict.insert( + "UTTypeConformsTo".into(), + Value::Array(conforms_to.iter().map(|s| s.clone().into()).collect()), + ); + } + + let mut specification = Dictionary::new(); + specification.insert( + "public.filename-extension".into(), + Value::Array( + association + .ext + .iter() + .map(|s| s.to_string().into()) + .collect(), + ), + ); + if let Some(mime_type) = &association.mime_type { + specification.insert("public.mime-type".into(), mime_type.clone().into()); + } + + dict.insert("UTTypeTagSpecification".into(), specification.into()); + + Value::Dictionary(dict) + }) + }) + .collect::>(); + + let document_types = associations + .iter() + .map(|association| { + let mut dict = Dictionary::new(); + + if !association.ext.is_empty() { + dict.insert( + "CFBundleTypeExtensions".into(), + Value::Array( + association + .ext + .iter() + .map(|ext| ext.to_string().into()) + .collect(), + ), + ); + } + + // For macOS/iOS share sheet, we need LSItemContentTypes with standard UTIs + let content_types = association.infer_content_types(); + + // Add LSItemContentTypes if we have any content types + if !content_types.is_empty() { + dict.insert( + "LSItemContentTypes".into(), + Value::Array(content_types.iter().map(|s| s.clone().into()).collect()), + ); + } + + let type_name = association + .name + .clone() + .or_else(|| association.ext.first().map(|ext| ext.0.clone())) + .unwrap_or_default(); + dict.insert("CFBundleTypeName".into(), type_name.into()); + dict.insert( + "CFBundleTypeRole".into(), + association.role.to_string().into(), + ); + dict.insert("LSHandlerRank".into(), association.rank.to_string().into()); + + Value::Dictionary(dict) + }) + .collect::>(); + + if exported_associations.is_empty() && document_types.is_empty() { + return None; + } + + let mut plist = Dictionary::new(); + if !exported_associations.is_empty() { + plist.insert( + "UTExportedTypeDeclarations".into(), + Value::Array(exported_associations), + ); + } + if !document_types.is_empty() { + plist.insert("CFBundleDocumentTypes".into(), Value::Array(document_types)); + } + + Some(Value::Dictionary(plist)) +} + +/// Maps file extensions to their standard UTIs for macOS/iOS share sheet support +fn extension_to_uti(ext: &str) -> Option<&'static str> { + match ext.to_lowercase().as_str() { + // Images + "png" => Some("public.png"), + "jpg" | "jpeg" => Some("public.jpeg"), + "gif" => Some("com.compuserve.gif"), + "bmp" => Some("com.microsoft.bmp"), + "tiff" | "tif" => Some("public.tiff"), + "ico" => Some("com.microsoft.ico"), + "heic" | "heif" => Some("public.heif-standard-image"), + "webp" => Some("org.webmproject.webp"), + "svg" => Some("public.svg-image"), + // Videos + "mp4" => Some("public.mpeg-4"), + "mov" => Some("com.apple.quicktime-movie"), + "avi" => Some("public.avi"), + "mkv" => Some("public.mpeg-4"), + // Audio + "mp3" => Some("public.mp3"), + "wav" => Some("com.microsoft.waveform-audio"), + "aac" => Some("public.aac-audio"), + "m4a" => Some("public.mpeg-4-audio"), + // Documents + "pdf" => Some("com.adobe.pdf"), + "txt" => Some("public.plain-text"), + "rtf" => Some("public.rtf"), + "html" | "htm" => Some("public.html"), + "json" => Some("public.json"), + "xml" => Some("public.xml"), + _ => None, + } +} + +/// Infers UTIs from mime type +fn mime_type_to_uti(mime_type: &str) -> Option<&'static str> { + match mime_type { + "image/png" => Some("public.png"), + "image/jpeg" | "image/jpg" => Some("public.jpeg"), + "image/gif" => Some("com.compuserve.gif"), + "image/bmp" => Some("com.microsoft.bmp"), + "image/tiff" => Some("public.tiff"), + "image/heic" | "image/heif" => Some("public.heif-standard-image"), + "image/webp" => Some("org.webmproject.webp"), + "image/svg+xml" => Some("public.svg-image"), + mime if mime.starts_with("image/") => Some("public.image"), + "video/mp4" => Some("public.mpeg-4"), + "video/quicktime" => Some("com.apple.quicktime-movie"), + "video/x-msvideo" => Some("public.avi"), + mime if mime.starts_with("video/") => Some("public.movie"), + "audio/mpeg" | "audio/mp3" => Some("public.mp3"), + "audio/wav" | "audio/wave" => Some("com.microsoft.waveform-audio"), + "audio/aac" => Some("public.aac-audio"), + "audio/mp4" => Some("public.mpeg-4-audio"), + mime if mime.starts_with("audio/") => Some("public.audio"), + "application/pdf" => Some("com.adobe.pdf"), + "text/plain" => Some("public.plain-text"), + "text/rtf" => Some("public.rtf"), + "text/html" => Some("public.html"), + "application/json" => Some("public.json"), + "application/xml" | "text/xml" => Some("public.xml"), + _ => None, + } +} + /// Deep link protocol configuration. #[derive(Debug, PartialEq, Eq, Clone, Deserialize, Serialize)] #[cfg_attr(feature = "schema", derive(JsonSchema))] diff --git a/crates/tauri/src/app.rs b/crates/tauri/src/app.rs index 6550b76f1cbe..e7bd44fa5d0d 100644 --- a/crates/tauri/src/app.rs +++ b/crates/tauri/src/app.rs @@ -230,8 +230,11 @@ pub enum RunEvent { /// This event is useful as a place to put your code that should be run after all state-changing events have been handled and you want to do stuff (updating state, performing calculations, etc) that happens as the "main body" of your event loop. MainEventsCleared, /// Emitted when the user wants to open the specified resource with the app. - #[cfg(any(target_os = "macos", target_os = "ios"))] - #[cfg_attr(docsrs, doc(cfg(any(target_os = "macos", feature = "ios"))))] + #[cfg(any(target_os = "macos", target_os = "ios", target_os = "android"))] + #[cfg_attr( + docsrs, + doc(cfg(any(target_os = "macos", target_os = "ios", target_os = "android"))) + )] Opened { /// The URL of the resources that is being open. urls: Vec, @@ -2565,7 +2568,7 @@ fn on_event_loop_event( #[allow(unreachable_code)] t.into() } - #[cfg(any(target_os = "macos", target_os = "ios"))] + #[cfg(any(target_os = "macos", target_os = "ios", target_os = "android"))] RuntimeRunEvent::Opened { urls } => RunEvent::Opened { urls }, #[cfg(target_os = "macos")] RuntimeRunEvent::Reopen { diff --git a/examples/api/src-tauri/src/lib.rs b/examples/api/src-tauri/src/lib.rs index 47cc753f4c8b..51fc659e5bc2 100644 --- a/examples/api/src-tauri/src/lib.rs +++ b/examples/api/src-tauri/src/lib.rs @@ -222,6 +222,10 @@ pub fn run_app) + Send + 'static>( .build() .unwrap(); } + #[cfg(any(target_os = "macos", target_os = "ios", target_os = "android"))] + RunEvent::Opened { urls } => { + println!("opened urls: {:?}", urls); + } _ => (), } }) diff --git a/examples/api/src-tauri/tauri.conf.json b/examples/api/src-tauri/tauri.conf.json index babd73b0754e..5ed38e5442fe 100644 --- a/examples/api/src-tauri/tauri.conf.json +++ b/examples/api/src-tauri/tauri.conf.json @@ -76,6 +76,37 @@ }, "bundle": { "active": true, + "fileAssociations": [ + { + "ext": ["png"], + "mimeType": "image/png", + "rank": "Default" + }, + { + "ext": ["jpg", "jpeg"], + "mimeType": "image/jpeg", + "rank": "Alternate" + }, + { + "ext": ["gif"], + "mimeType": "image/gif", + "rank": "Owner" + }, + { + "ext": ["taurijson"], + "exportedType": { + "identifier": "com.tauri.dev-file-associations-demo.taurijson", + "conformsTo": ["public.json"] + } + }, + { + "ext": ["taurid"], + "exportedType": { + "identifier": "com.tauri.dev-file-associations-demo.tauridata", + "conformsTo": ["public.data"] + } + } + ], "icon": [ "../../.icons/32x32.png", "../../.icons/128x128.png", diff --git a/examples/file-associations/src-tauri/src/main.rs b/examples/file-associations/src-tauri/src/main.rs index c2c631e24774..cdca9fd73313 100644 --- a/examples/file-associations/src-tauri/src/main.rs +++ b/examples/file-associations/src-tauri/src/main.rs @@ -83,7 +83,7 @@ fn main() { .run( #[allow(unused_variables)] |app, event| { - #[cfg(any(target_os = "macos", target_os = "ios"))] + #[cfg(any(target_os = "macos", target_os = "ios", target_os = "android"))] if let tauri::RunEvent::Opened { urls } = event { let files = urls .into_iter() From 1a2336108d53b78d9743835a295516bee3e7d3e9 Mon Sep 17 00:00:00 2001 From: "dependabot[bot]" <49699333+dependabot[bot]@users.noreply.github.com> Date: Tue, 14 Apr 2026 12:12:12 +0800 Subject: [PATCH 66/95] chore(deps): bump rand from 0.9.1 to 0.9.3 (#15234) Bumps [rand](https://github.com/rust-random/rand) from 0.9.1 to 0.9.3. - [Release notes](https://github.com/rust-random/rand/releases) - [Changelog](https://github.com/rust-random/rand/blob/0.9.3/CHANGELOG.md) - [Commits](https://github.com/rust-random/rand/compare/rand_core-0.9.1...0.9.3) --- updated-dependencies: - dependency-name: rand dependency-version: 0.9.3 dependency-type: direct:production ... Signed-off-by: dependabot[bot] Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com> --- Cargo.lock | 10 +++++----- 1 file changed, 5 insertions(+), 5 deletions(-) diff --git a/Cargo.lock b/Cargo.lock index 79acbb6495ca..447af55c33fc 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -6569,9 +6569,9 @@ dependencies = [ [[package]] name = "rand" -version = "0.9.1" +version = "0.9.3" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "9fbfd9d094a40bf3ae768db9361049ace4c0e04a4fd6b359518bd7b73a73dd97" +checksum = "7ec095654a25171c2124e9e3393a930bddbffdc939556c914957a4c3e0a87166" dependencies = [ "rand_chacha 0.9.0", "rand_core 0.9.3", @@ -8909,7 +8909,7 @@ dependencies = [ "phf 0.11.3", "plist", "pretty_assertions", - "rand 0.9.1", + "rand 0.9.3", "rayon", "regex", "resvg", @@ -9027,7 +9027,7 @@ dependencies = [ "os_pipe", "p12", "plist", - "rand 0.9.1", + "rand 0.9.3", "regex", "serde", "serde_json", @@ -9843,7 +9843,7 @@ dependencies = [ "http 1.3.1", "httparse", "log", - "rand 0.9.1", + "rand 0.9.3", "sha1", "thiserror 2.0.12", "utf-8", From 82786278f99cf2b56057c1271e0df5e0d5c57cfa Mon Sep 17 00:00:00 2001 From: Jeff Tsang <36611384+JeffTsang@users.noreply.github.com> Date: Tue, 14 Apr 2026 19:14:23 +0800 Subject: [PATCH 67/95] fix(macos/ios): Add handler for web content process termination (fix #14371) (#14523) --- .changes/web-content-process-termination.md | 7 +++++ crates/tauri-runtime-wry/src/lib.rs | 29 +++++++++++++++++++++ crates/tauri-runtime/src/webview.rs | 8 ++++++ crates/tauri/src/app.rs | 28 ++++++++++++++++++++ crates/tauri/src/ipc/protocol.rs | 4 +++ crates/tauri/src/manager/mod.rs | 10 +++++++ crates/tauri/src/manager/webview.rs | 29 +++++++++++++++++++++ 7 files changed, 115 insertions(+) create mode 100644 .changes/web-content-process-termination.md diff --git a/.changes/web-content-process-termination.md b/.changes/web-content-process-termination.md new file mode 100644 index 000000000000..c10fc18cdb69 --- /dev/null +++ b/.changes/web-content-process-termination.md @@ -0,0 +1,7 @@ +--- +"tauri": "minor:feat" +"tauri-runtime": "minor:feat" +"tauri-runtime-wry": "minor:feat" +--- + +Add handler for web content process termination on macOS and iOS. diff --git a/crates/tauri-runtime-wry/src/lib.rs b/crates/tauri-runtime-wry/src/lib.rs index 42a22d1026ce..6c537de6cf43 100644 --- a/crates/tauri-runtime-wry/src/lib.rs +++ b/crates/tauri-runtime-wry/src/lib.rs @@ -5054,6 +5054,35 @@ You may have it installed on another user account, but it is not available for t webview_builder = webview_builder.with_allow_link_preview(webview_attributes.allow_link_preview); + + if let Some(on_web_content_process_terminate_handler) = + pending.on_web_content_process_terminate_handler + { + webview_builder = webview_builder + .with_on_web_content_process_terminate_handler(on_web_content_process_terminate_handler); + } else { + log::debug!("web content process terminated"); + let context_ = context.clone(); + let window_id_ = window_id.clone(); + webview_builder = webview_builder.with_on_web_content_process_terminate_handler(move || { + if let Ok(windows) = &context_.main_thread.windows.0.try_borrow() { + if let Some(window) = windows.get(&*window_id_.lock().unwrap()) { + if let Some(webview) = window.webviews.iter().find(|w| w.id == id) { + match webview.reload() { + Ok(_) => log::debug!("webview reloaded"), + Err(e) => log::error!("failed to reload webview: {}", e), + } + } else { + log::error!("failed to find webview") + } + } else { + log::error!("failed to get window") + } + } else { + log::error!("failed to borrow windows") + } + }); + } } #[cfg(target_os = "ios")] diff --git a/crates/tauri-runtime/src/webview.rs b/crates/tauri-runtime/src/webview.rs index 49707858dcb9..1cd929226cf1 100644 --- a/crates/tauri-runtime/src/webview.rs +++ b/crates/tauri-runtime/src/webview.rs @@ -41,6 +41,9 @@ type DocumentTitleChangedHandler = dyn Fn(String) + Send + 'static; type DownloadHandler = dyn Fn(DownloadEvent) -> bool + Send + Sync; +#[cfg(any(target_os = "macos", target_os = "ios"))] +type OnWebContentProcessTerminateHandler = dyn Fn() + Send; + #[cfg(target_os = "ios")] type InputAccessoryViewBuilderFn = dyn Fn(&objc2_ui_kit::UIView) -> Option> + Send @@ -225,6 +228,9 @@ pub struct PendingWebview> { pub on_page_load_handler: Option>, pub download_handler: Option>, + + #[cfg(any(target_os = "macos", target_os = "ios"))] + pub on_web_content_process_terminate_handler: Option>, } impl> PendingWebview { @@ -251,6 +257,8 @@ impl> PendingWebview { web_resource_request_handler: None, on_page_load_handler: None, download_handler: None, + #[cfg(any(target_os = "macos", target_os = "ios"))] + on_web_content_process_terminate_handler: None, }) } } diff --git a/crates/tauri/src/app.rs b/crates/tauri/src/app.rs index e7bd44fa5d0d..8bd9df66ee8c 100644 --- a/crates/tauri/src/app.rs +++ b/crates/tauri/src/app.rs @@ -67,6 +67,9 @@ pub type SetupHook = Box) -> std::result::Result<(), Box> + Send>; /// A closure that is run every time a page starts or finishes loading. pub type OnPageLoad = dyn Fn(&Webview, &PageLoadPayload<'_>) + Send + Sync + 'static; +/// A closure that is run when the web content process terminates. +#[cfg(any(target_os = "macos", target_os = "ios"))] +pub type OnWebContentProcessTerminate = dyn Fn(&Webview) + Send + Sync + 'static; pub type ChannelInterceptor = Box, CallbackFn, usize, &InvokeResponseBody) -> bool + Send + Sync + 'static>; @@ -1483,6 +1486,10 @@ pub struct Builder { /// Page load hook. on_page_load: Option>>, + /// Web content process termination hook. + #[cfg(any(target_os = "macos", target_os = "ios"))] + on_web_content_process_terminate: Option>>, + /// All passed plugins plugins: PluginStore, @@ -1569,6 +1576,8 @@ impl Builder { .into_string(), channel_interceptor: None, on_page_load: None, + #[cfg(any(target_os = "macos", target_os = "ios"))] + on_web_content_process_terminate: None, plugins: PluginStore::default(), uri_scheme_protocols: Default::default(), state: StateManager::new(), @@ -1749,6 +1758,23 @@ tauri::Builder::default() self } + /// Defines the web content process termination hook. + /// + /// ## Platform-specific + /// + /// - **Linux / Windows / Android:** Unsupported. + #[cfg(any(target_os = "macos", target_os = "ios"))] + #[must_use] + pub fn on_web_content_process_terminate(mut self, on_web_content_process_terminate: F) -> Self + where + F: Fn(&Webview) + Send + Sync + 'static, + { + self + .on_web_content_process_terminate + .replace(Arc::new(on_web_content_process_terminate)); + self + } + /// Adds a Tauri application plugin. /// /// A plugin is created using the [`crate::plugin::Builder`] struct.Check its documentation for more information. @@ -2197,6 +2223,8 @@ tauri::Builder::default() self.plugins, self.invoke_handler, self.on_page_load, + #[cfg(any(target_os = "macos", target_os = "ios"))] + self.on_web_content_process_terminate, self.uri_scheme_protocols, self.state, #[cfg(desktop)] diff --git a/crates/tauri/src/ipc/protocol.rs b/crates/tauri/src/ipc/protocol.rs index 1b1e08b8f9b4..72dea2821b07 100644 --- a/crates/tauri/src/ipc/protocol.rs +++ b/crates/tauri/src/ipc/protocol.rs @@ -571,6 +571,8 @@ mod tests { PluginStore::default(), Box::new(|_| false), None, + #[cfg(any(target_os = "macos", target_os = "ios"))] + None, Default::default(), StateManager::new(), Default::default(), @@ -687,6 +689,8 @@ mod tests { PluginStore::default(), Box::new(|_| false), None, + #[cfg(any(target_os = "macos", target_os = "ios"))] + None, Default::default(), StateManager::new(), Default::default(), diff --git a/crates/tauri/src/manager/mod.rs b/crates/tauri/src/manager/mod.rs index ca46ded96132..8215cf1335c6 100644 --- a/crates/tauri/src/manager/mod.rs +++ b/crates/tauri/src/manager/mod.rs @@ -31,6 +31,9 @@ use crate::{ Assets, Context, DebugAppIcon, EventName, Pattern, Runtime, StateManager, Webview, Window, }; +#[cfg(any(target_os = "macos", target_os = "ios"))] +use crate::app::OnWebContentProcessTerminate; + #[cfg(desktop)] mod menu; #[cfg(all(desktop, feature = "tray-icon"))] @@ -251,6 +254,9 @@ impl AppManager { plugins: PluginStore, invoke_handler: Box>, on_page_load: Option>>, + #[cfg(any(target_os = "macos", target_os = "ios"))] on_web_content_process_terminate: Option< + Arc>, + >, uri_scheme_protocols: HashMap>>, state: StateManager, #[cfg(desktop)] menu_event_listener: Vec>>, @@ -284,6 +290,8 @@ impl AppManager { webviews: Mutex::default(), invoke_handler, on_page_load, + #[cfg(any(target_os = "macos", target_os = "ios"))] + on_web_content_process_terminate, uri_scheme_protocols: Mutex::new(uri_scheme_protocols), event_listeners: Arc::new(webview_event_listeners), invoke_initialization_script, @@ -756,6 +764,8 @@ mod test { PluginStore::default(), Box::new(|_| false), None, + #[cfg(any(target_os = "macos", target_os = "ios"))] + None, Default::default(), StateManager::new(), Default::default(), diff --git a/crates/tauri/src/manager/webview.rs b/crates/tauri/src/manager/webview.rs index 4845f4fa6e99..57e617e71a9e 100644 --- a/crates/tauri/src/manager/webview.rs +++ b/crates/tauri/src/manager/webview.rs @@ -28,6 +28,9 @@ use crate::{ EventLoopMessage, EventTarget, Manager, Runtime, Scopes, UriSchemeContext, Webview, Window, }; +#[cfg(any(target_os = "macos", target_os = "ios"))] +use crate::app::OnWebContentProcessTerminate; + use super::{ window::{DragDropPayload, DRAG_DROP_EVENT, DRAG_ENTER_EVENT, DRAG_LEAVE_EVENT, DRAG_OVER_EVENT}, {AppManager, EmitPayload}, @@ -70,6 +73,9 @@ pub struct WebviewManager { pub invoke_handler: Box>, /// The page load hook, invoked when the webview performs a navigation. pub on_page_load: Option>>, + /// The web content process termination hook. + #[cfg(any(target_os = "macos", target_os = "ios"))] + pub on_web_content_process_terminate: Option>>, /// The webview protocols available to all webviews. pub uri_scheme_protocols: Mutex>>>, /// Webview event listeners to all webviews. @@ -304,6 +310,29 @@ impl WebviewManager { } })); + #[cfg(any(target_os = "macos", target_os = "ios"))] + if pending.on_web_content_process_terminate_handler.is_none() { + let app_manager_ = manager.manager_owned(); + if app_manager_ + .webview + .on_web_content_process_terminate + .is_some() + { + let label_ = pending.label.clone(); + pending + .on_web_content_process_terminate_handler + .replace(Box::new(move || { + if let Some(w) = app_manager_.get_webview(&label_) { + if let Some(on_web_content_process_terminate) = + &app_manager_.webview.on_web_content_process_terminate + { + on_web_content_process_terminate(&w); + } + } + })); + } + } + #[cfg(feature = "protocol-asset")] if !registered_scheme_protocols.contains(&"asset".into()) { let asset_scope = app_manager From 013a4e7c5416e7966085e02ae1575a9a82f85a0d Mon Sep 17 00:00:00 2001 From: bovirus <1262554+bovirus@users.noreply.github.com> Date: Wed, 15 Apr 2026 06:54:13 +0200 Subject: [PATCH 68/95] changes(nsis): update Italian translations (#15175) * Italian language update * Base NSIS script improvements - Add on top left after program name the program version. Es. "Tauri 1.0.0.0" - Add in file description "installer" after program name. Es. "Tauri installer" * Italian language improvement * Add Italian language update to Tauri packages Added Italian language update for various Tauri packages. * Remove space * Apply suggestions from code review Co-authored-by: Tony <68118705+Legend-Master@users.noreply.github.com> * Revert changes in `installer.nsi` * what has changed??? --------- Co-authored-by: Tony <68118705+Legend-Master@users.noreply.github.com> Co-authored-by: Tony --- .changes/change-pr-15175.md | 7 ++++ .../bundle/windows/nsis/languages/Italian.nsh | 38 +++++++++---------- 2 files changed, 26 insertions(+), 19 deletions(-) create mode 100644 .changes/change-pr-15175.md diff --git a/.changes/change-pr-15175.md b/.changes/change-pr-15175.md new file mode 100644 index 000000000000..dc485c25ded5 --- /dev/null +++ b/.changes/change-pr-15175.md @@ -0,0 +1,7 @@ +--- +"tauri-bundler": patch:changes +"@tauri-apps/cli": patch:changes +"tauri-cli": patch:changes +--- + +Update NSIS installer Italian translations diff --git a/crates/tauri-bundler/src/bundle/windows/nsis/languages/Italian.nsh b/crates/tauri-bundler/src/bundle/windows/nsis/languages/Italian.nsh index bca96544da58..f505e4e8ec98 100644 --- a/crates/tauri-bundler/src/bundle/windows/nsis/languages/Italian.nsh +++ b/crates/tauri-bundler/src/bundle/windows/nsis/languages/Italian.nsh @@ -1,27 +1,27 @@ -LangString addOrReinstall ${LANG_ITALIAN} "Aggiungi/Reinstalla componenti" -LangString alreadyInstalled ${LANG_ITALIAN} "Già installato" -LangString alreadyInstalledLong ${LANG_ITALIAN} "${PRODUCTNAME} ${VERSION} è già installato. Seleziona l'operazione che vuoi eseguire e clicca Avanti per continuare." -LangString appRunning ${LANG_ITALIAN} "{{product_name}} è in esecuzione! Chiudi e poi riprova." -LangString appRunningOkKill ${LANG_ITALIAN} "{{product_name}} è in esecuzione!$\nSeleziona OK per chiuderlo" -LangString chooseMaintenanceOption ${LANG_ITALIAN} "Seleziona l'operazione di manutenzione da eseguire." -LangString choowHowToInstall ${LANG_ITALIAN} "Seleziona come vuoi installare ${PRODUCTNAME}." -LangString createDesktop ${LANG_ITALIAN} "Crea scorciatoia sul Desktop" +LangString addOrReinstall ${LANG_ITALIAN} "Aggiungi/reinstalla componenti" +LangString alreadyInstalled ${LANG_ITALIAN} "Programma già installato" +LangString alreadyInstalledLong ${LANG_ITALIAN} "${PRODUCTNAME} ${VERSION} è già installato.$\nPer continuare scegli l'operazione da eseguire e seleziona 'Avanti'." +LangString appRunning ${LANG_ITALIAN} "{{product_name}} è in esecuzione!$\nChiudi {product_name}} e riprova." +LangString appRunningOkKill ${LANG_ITALIAN} "{{product_name}} è in esecuzione!$\nPer chiudere {product_name} seleziona 'OK'" +LangString chooseMaintenanceOption ${LANG_ITALIAN} "Scegli l'operazione di manutenzione da eseguire." +LangString choowHowToInstall ${LANG_ITALIAN} "Scegli come vuoi installare ${PRODUCTNAME}." +LangString createDesktop ${LANG_ITALIAN} "Crea collegamento sul desktop" LangString dontUninstall ${LANG_ITALIAN} "Non disinstallare" -LangString dontUninstallDowngrade ${LANG_ITALIAN} "Non disinstallare (Il downgrade senza la disinstallazione è disabilitato per questo installer)" -LangString failedToKillApp ${LANG_ITALIAN} "Impossibile chiudere {{product_name}}. Chiudi e poi riprova" -LangString installingWebview2 ${LANG_ITALIAN} "Installando WebView2..." -LangString newerVersionInstalled ${LANG_ITALIAN} "Una versione più recente di ${PRODUCTNAME} è già installata! Non è consigliato installare una versione più vecchia. Se vuoi comunque procedere, è meglio prima disinstallare la versione corrente. Seleziona l'operazione che vuoi eseguire e clicca Avanti per continuare." +LangString dontUninstallDowngrade ${LANG_ITALIAN} "Non disinstallare (per questo installer il downgrade senza la disinstallazione è disabilitato)" +LangString failedToKillApp ${LANG_ITALIAN} "Impossibile chiudere {{product_name}}.$\nChiudi {product_name} e poi riprova" +LangString installingWebview2 ${LANG_ITALIAN} "Installazione WebView2..." +LangString newerVersionInstalled ${LANG_ITALIAN} "È già installata una versione più recente di ${PRODUCTNAME}!$\nNon è consigliato installare una versione più vecchia.$\nSe vuoi comunque procedere, è meglio prima disinstallare la versione attuale.$\nPer continuare scegli l'operazione da eseguire e seleziona 'Avanti'." LangString older ${LANG_ITALIAN} "più vecchia" -LangString olderOrUnknownVersionInstalled ${LANG_ITALIAN} "Una versione $R4 di ${PRODUCTNAME} è installata nel tuo sistema. È consigliato che disinstalli la versione corrente prima di procedere all'installazione. Seleziona l'operazione che vuoi eseguire e clicca Avanti per continuare." -LangString silentDowngrades ${LANG_ITALIAN} "I downgrade sono disabilitati per questo installer, impossibile procedere con l'installer silenzioso, usa invece l'installer con interfaccia grafica.$\n" +LangString olderOrUnknownVersionInstalled ${LANG_ITALIAN} "Nel sistema è installata una versione $R4 di ${PRODUCTNAME}.$\nPrima di procedere all'installazione è consigliabile disinstallare la versione attuale.$\nPer continuare scegli l'operazione da eseguire e seleziona 'Avanti'." +LangString silentDowngrades ${LANG_ITALIAN} "Per questo installer i downgrade sono disabilitati , impossibile procedere con l'installer silenzioso, usa invece l'installer con interfaccia grafica.$\n" LangString unableToUninstall ${LANG_ITALIAN} "Impossibile disinstallare!" LangString uninstallApp ${LANG_ITALIAN} "Disinstalla ${PRODUCTNAME}" LangString uninstallBeforeInstalling ${LANG_ITALIAN} "Disinstalla prima di installare" LangString unknown ${LANG_ITALIAN} "sconosciuta" -LangString webview2AbortError ${LANG_ITALIAN} "Errore nell'installazione di WebView2! L'app non può funzionare senza. Prova a riavviare l'installer." -LangString webview2DownloadError ${LANG_ITALIAN} "Errore: Il download di WebView2 è fallito - $0" -LangString webview2DownloadSuccess ${LANG_ITALIAN} "Bootstrapper WebView2 scaricato con successo" -LangString webview2Downloading ${LANG_ITALIAN} "Scaricando il bootstrapper WebView2..." -LangString webview2InstallError ${LANG_ITALIAN} "Errore: L'installazione di WebView2 è fallita con il codice $1" +LangString webview2AbortError ${LANG_ITALIAN} "Errore nell'installazione di WebView2!$\nL'app non può funzionare senza.$\nProva a riavviare l'installer." +LangString webview2DownloadError ${LANG_ITALIAN} "Errore: il download di WebView2 è fallito - $0" +LangString webview2DownloadSuccess ${LANG_ITALIAN} "Download bootstrapper WebView2 completato" +LangString webview2Downloading ${LANG_ITALIAN} "Download bootstrapper WebView2..." +LangString webview2InstallError ${LANG_ITALIAN} "Errore: l'installazione di WebView2 è fallita con codice errore $1" LangString webview2InstallSuccess ${LANG_ITALIAN} "WebView2 installato correttamente" LangString deleteAppData ${LANG_ITALIAN} "Cancella i dati dell'applicazione" From ad239b6871ab130db0696ea6617b04855d09f376 Mon Sep 17 00:00:00 2001 From: Lucas Nogueira Date: Thu, 16 Apr 2026 15:57:24 -0300 Subject: [PATCH 69/95] chore: fix clippy warnings --- crates/tauri-build/src/lib.rs | 6 ++---- crates/tauri-utils/src/acl/build.rs | 4 ++-- examples/api/src-tauri/src/lib.rs | 12 +++++------- 3 files changed, 9 insertions(+), 13 deletions(-) diff --git a/crates/tauri-build/src/lib.rs b/crates/tauri-build/src/lib.rs index 004cf3d1924c..972455e2d485 100644 --- a/crates/tauri-build/src/lib.rs +++ b/crates/tauri-build/src/lib.rs @@ -687,10 +687,8 @@ pub fn try_build(attributes: Attributes) -> Result<()> { } } } - "msvc" => { - if env::var_os("STATIC_VCRUNTIME").is_some_and(|v| v == "true") { - static_vcruntime::build(); - } + "msvc" if env::var_os("STATIC_VCRUNTIME").is_some_and(|v| v == "true") => { + static_vcruntime::build(); } _ => (), } diff --git a/crates/tauri-utils/src/acl/build.rs b/crates/tauri-utils/src/acl/build.rs index 44867f3f954d..2fa3d646cdaa 100644 --- a/crates/tauri-utils/src/acl/build.rs +++ b/crates/tauri-utils/src/acl/build.rs @@ -463,8 +463,8 @@ pub fn generate_allowed_commands( let capabilities = crate::acl::get_capabilities(&config, capabilities_from_files, None)?; let permission_entries = capabilities - .into_iter() - .flat_map(|(_, capabilities)| capabilities.permissions); + .into_values() + .flat_map(|capabilities| capabilities.permissions); let mut allowed_commands = AllowedCommands { has_app_acl: has_app_manifest(&acl), ..Default::default() diff --git a/examples/api/src-tauri/src/lib.rs b/examples/api/src-tauri/src/lib.rs index 51fc659e5bc2..84fdb35ecb32 100644 --- a/examples/api/src-tauri/src/lib.rs +++ b/examples/api/src-tauri/src/lib.rs @@ -186,14 +186,12 @@ pub fn run_app) + Send + 'static>( app.run(move |_app_handle, _event| { #[cfg(not(test))] match &_event { + // Keep the event loop running even if all windows are closed + // This allow us to catch tray icon events when there is no window + // if we manually requested an exit (code is Some(_)) we will let it go through #[cfg(desktop)] - RunEvent::ExitRequested { api, code, .. } => { - // Keep the event loop running even if all windows are closed - // This allow us to catch tray icon events when there is no window - // if we manually requested an exit (code is Some(_)) we will let it go through - if code.is_none() { - api.prevent_exit(); - } + RunEvent::ExitRequested { api, code, .. } if code.is_none() => { + api.prevent_exit(); } #[cfg(desktop)] RunEvent::WindowEvent { From e15516705ab64e6a109e6e1682729141d16021de Mon Sep 17 00:00:00 2001 From: "renovate[bot]" <29139614+renovate[bot]@users.noreply.github.com> Date: Sat, 18 Apr 2026 12:20:41 +0800 Subject: [PATCH 70/95] chore(deps): update dependency typescript to v6 (#15158) * chore(deps): update dependency typescript to v6 * Update typescript-eslint --------- Co-authored-by: renovate[bot] <29139614+renovate[bot]@users.noreply.github.com> Co-authored-by: Tony --- .../tauri-cli/templates/plugin/package.json | 2 +- packages/api/package.json | 4 +- pnpm-lock.yaml | 220 +++++++++--------- 3 files changed, 113 insertions(+), 113 deletions(-) diff --git a/crates/tauri-cli/templates/plugin/package.json b/crates/tauri-cli/templates/plugin/package.json index 1dd60abc81e3..3235e3fd18f9 100644 --- a/crates/tauri-cli/templates/plugin/package.json +++ b/crates/tauri-cli/templates/plugin/package.json @@ -27,7 +27,7 @@ "devDependencies": { "@rollup/plugin-typescript": "^12.0.0", "rollup": "^4.9.6", - "typescript": "^5.3.3", + "typescript": "^6.0.0", "tslib": "^2.6.2" } } diff --git a/packages/api/package.json b/packages/api/package.json index 3f4c5a1ecd42..fe0273f36493 100644 --- a/packages/api/package.json +++ b/packages/api/package.json @@ -57,7 +57,7 @@ "globals": "^17.4.0", "rollup": "4.60.0", "tslib": "^2.8.1", - "typescript": "^5.9.3", - "typescript-eslint": "^8.56.1" + "typescript": "^6.0.0", + "typescript-eslint": "^8.58.2" } } diff --git a/pnpm-lock.yaml b/pnpm-lock.yaml index 758287962fbd..248ebe420e15 100644 --- a/pnpm-lock.yaml +++ b/pnpm-lock.yaml @@ -60,7 +60,7 @@ importers: version: 1.0.0(rollup@4.60.0) '@rollup/plugin-typescript': specifier: 12.3.0 - version: 12.3.0(rollup@4.60.0)(tslib@2.8.1)(typescript@5.9.3) + version: 12.3.0(rollup@4.60.0)(tslib@2.8.1)(typescript@6.0.2) '@types/eslint': specifier: ^9.6.1 version: 9.6.1 @@ -89,11 +89,11 @@ importers: specifier: ^2.8.1 version: 2.8.1 typescript: - specifier: ^5.9.3 - version: 5.9.3 + specifier: ^6.0.0 + version: 6.0.2 typescript-eslint: - specifier: ^8.56.1 - version: 8.56.1(eslint@10.0.2(jiti@2.6.1))(typescript@5.9.3) + specifier: ^8.58.2 + version: 8.58.2(eslint@10.0.2(jiti@2.6.1))(typescript@6.0.2) packages/cli: devDependencies: @@ -1587,63 +1587,63 @@ packages: '@types/trusted-types@2.0.7': resolution: {integrity: sha512-ScaPdn1dQczgbl0QFTeTOmVHFULt394XJgOQNoyVhZ6r2vLnMLJfBPd53SB52T/3G36VI1/g2MZaX0cwDuXsfw==} - '@typescript-eslint/eslint-plugin@8.56.1': - resolution: {integrity: sha512-Jz9ZztpB37dNC+HU2HI28Bs9QXpzCz+y/twHOwhyrIRdbuVDxSytJNDl6z/aAKlaRIwC7y8wJdkBv7FxYGgi0A==} + '@typescript-eslint/eslint-plugin@8.58.2': + resolution: {integrity: sha512-aC2qc5thQahutKjP+cl8cgN9DWe3ZUqVko30CMSZHnFEHyhOYoZSzkGtAI2mcwZ38xeImDucI4dnqsHiOYuuCw==} engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0} peerDependencies: - '@typescript-eslint/parser': ^8.56.1 + '@typescript-eslint/parser': ^8.58.2 eslint: ^8.57.0 || ^9.0.0 || ^10.0.0 - typescript: '>=4.8.4 <6.0.0' + typescript: '>=4.8.4 <6.1.0' - '@typescript-eslint/parser@8.56.1': - resolution: {integrity: sha512-klQbnPAAiGYFyI02+znpBRLyjL4/BrBd0nyWkdC0s/6xFLkXYQ8OoRrSkqacS1ddVxf/LDyODIKbQ5TgKAf/Fg==} + '@typescript-eslint/parser@8.58.2': + resolution: {integrity: sha512-/Zb/xaIDfxeJnvishjGdcR4jmr7S+bda8PKNhRGdljDM+elXhlvN0FyPSsMnLmJUrVG9aPO6dof80wjMawsASg==} engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0} peerDependencies: eslint: ^8.57.0 || ^9.0.0 || ^10.0.0 - typescript: '>=4.8.4 <6.0.0' + typescript: '>=4.8.4 <6.1.0' - '@typescript-eslint/project-service@8.56.1': - resolution: {integrity: sha512-TAdqQTzHNNvlVFfR+hu2PDJrURiwKsUvxFn1M0h95BB8ah5jejas08jUWG4dBA68jDMI988IvtfdAI53JzEHOQ==} + '@typescript-eslint/project-service@8.58.2': + resolution: {integrity: sha512-Cq6UfpZZk15+r87BkIh5rDpi38W4b+Sjnb8wQCPPDDweS/LRCFjCyViEbzHk5Ck3f2QDfgmlxqSa7S7clDtlfg==} engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0} peerDependencies: - typescript: '>=4.8.4 <6.0.0' + typescript: '>=4.8.4 <6.1.0' - '@typescript-eslint/scope-manager@8.56.1': - resolution: {integrity: sha512-YAi4VDKcIZp0O4tz/haYKhmIDZFEUPOreKbfdAN3SzUDMcPhJ8QI99xQXqX+HoUVq8cs85eRKnD+rne2UAnj2w==} + '@typescript-eslint/scope-manager@8.58.2': + resolution: {integrity: sha512-SgmyvDPexWETQek+qzZnrG6844IaO02UVyOLhI4wpo82dpZJY9+6YZCKAMFzXb7qhx37mFK1QcPQ18tud+vo6Q==} engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0} - '@typescript-eslint/tsconfig-utils@8.56.1': - resolution: {integrity: sha512-qOtCYzKEeyr3aR9f28mPJqBty7+DBqsdd63eO0yyDwc6vgThj2UjWfJIcsFeSucYydqcuudMOprZ+x1SpF3ZuQ==} + '@typescript-eslint/tsconfig-utils@8.58.2': + resolution: {integrity: sha512-3SR+RukipDvkkKp/d0jP0dyzuls3DbGmwDpVEc5wqk5f38KFThakqAAO0XMirWAE+kT00oTauTbzMFGPoAzB0A==} engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0} peerDependencies: - typescript: '>=4.8.4 <6.0.0' + typescript: '>=4.8.4 <6.1.0' - '@typescript-eslint/type-utils@8.56.1': - resolution: {integrity: sha512-yB/7dxi7MgTtGhZdaHCemf7PuwrHMenHjmzgUW1aJpO+bBU43OycnM3Wn+DdvDO/8zzA9HlhaJ0AUGuvri4oGg==} + '@typescript-eslint/type-utils@8.58.2': + resolution: {integrity: sha512-Z7EloNR/B389FvabdGeTo2XMs4W9TjtPiO9DAsmT0yom0bwlPyRjkJ1uCdW1DvrrrYP50AJZ9Xc3sByZA9+dcg==} engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0} peerDependencies: eslint: ^8.57.0 || ^9.0.0 || ^10.0.0 - typescript: '>=4.8.4 <6.0.0' + typescript: '>=4.8.4 <6.1.0' - '@typescript-eslint/types@8.56.1': - resolution: {integrity: sha512-dbMkdIUkIkchgGDIv7KLUpa0Mda4IYjo4IAMJUZ+3xNoUXxMsk9YtKpTHSChRS85o+H9ftm51gsK1dZReY9CVw==} + '@typescript-eslint/types@8.58.2': + resolution: {integrity: sha512-9TukXyATBQf/Jq9AMQXfvurk+G5R2MwfqQGDR2GzGz28HvY/lXNKGhkY+6IOubwcquikWk5cjlgPvD2uAA7htQ==} engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0} - '@typescript-eslint/typescript-estree@8.56.1': - resolution: {integrity: sha512-qzUL1qgalIvKWAf9C1HpvBjif+Vm6rcT5wZd4VoMb9+Km3iS3Cv9DY6dMRMDtPnwRAFyAi7YXJpTIEXLvdfPxg==} + '@typescript-eslint/typescript-estree@8.58.2': + resolution: {integrity: sha512-ELGuoofuhhoCvNbQjFFiobFcGgcDCEm0ThWdmO4Z0UzLqPXS3KFvnEZ+SHewwOYHjM09tkzOWXNTv9u6Gqtyuw==} engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0} peerDependencies: - typescript: '>=4.8.4 <6.0.0' + typescript: '>=4.8.4 <6.1.0' - '@typescript-eslint/utils@8.56.1': - resolution: {integrity: sha512-HPAVNIME3tABJ61siYlHzSWCGtOoeP2RTIaHXFMPqjrQKCGB9OgUVdiNgH7TJS2JNIQ5qQ4RsAUDuGaGme/KOA==} + '@typescript-eslint/utils@8.58.2': + resolution: {integrity: sha512-QZfjHNEzPY8+l0+fIXMvuQ2sJlplB4zgDZvA+NmvZsZv3EQwOcc1DuIU1VJUTWZ/RKouBMhDyNaBMx4sWvrzRA==} engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0} peerDependencies: eslint: ^8.57.0 || ^9.0.0 || ^10.0.0 - typescript: '>=4.8.4 <6.0.0' + typescript: '>=4.8.4 <6.1.0' - '@typescript-eslint/visitor-keys@8.56.1': - resolution: {integrity: sha512-KiROIzYdEV85YygXw6BI/Dx4fnBlFQu6Mq4QE4MOH9fFnhohw6wX/OAvDY2/C+ut0I3RSPKenvZJIVYqJNkhEw==} + '@typescript-eslint/visitor-keys@8.58.2': + resolution: {integrity: sha512-f1WO2Lx8a9t8DARmcWAUPJbu0G20bJlj8L4z72K00TMeJAoyLr/tHhI/pzYBLrR4dXWkcxO1cWYZEOX8DKHTqA==} engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0} '@unocss/cli@66.6.6': @@ -2236,8 +2236,8 @@ packages: engines: {node: '>=18.0.0'} hasBin: true - minimatch@10.2.4: - resolution: {integrity: sha512-oRjTw/97aTBN0RHbYCdtF1MQfvusSIBQM0IZEgzl6426+8jSC0nF1a/GmnVLpfB9yyr6g6FTqWqiZVbxrtaCIg==} + minimatch@10.2.5: + resolution: {integrity: sha512-MULkVLfKGYDFYejP07QOurDLLQpcjk7Fw+7jXS2R2czRQzR56yHRveU5NDJEOviH+hETZKSkIk5c+T23GjFUMg==} engines: {node: 18 || 20 || >=22} mlly@1.8.0: @@ -2465,8 +2465,8 @@ packages: resolution: {integrity: sha512-W/KYk+NFhkmsYpuHq5JykngiOCnxeVL8v8dFnqxSD8qEEdRfXk1SDM6JzNqcERbcGYj9tMrDQBYV9cjgnunFIg==} engines: {node: '>=18'} - tinyglobby@0.2.15: - resolution: {integrity: sha512-j2Zq4NyQYG5XMST4cbs02Ak8iJUdxRM0XI5QyxXuZOzKOINmWurp3smXu3y5wDcJrptwpSjgXHzIQxR0omXljQ==} + tinyglobby@0.2.16: + resolution: {integrity: sha512-pn99VhoACYR8nFHhxqix+uvsbXineAasWm5ojXoN8xEwK5Kd3/TrhNn1wByuD52UxWRLy8pu+kRMniEi6Eq9Zg==} engines: {node: '>=12.0.0'} tinyrainbow@3.0.3: @@ -2481,8 +2481,8 @@ packages: resolution: {integrity: sha512-sf4i37nQ2LBx4m3wB74y+ubopq6W/dIzXg0FDGjsYnZHVa1Da8FH853wlL2gtUhg+xJXjfk3kUZS3BRoQeoQBQ==} engines: {node: '>=6'} - ts-api-utils@2.4.0: - resolution: {integrity: sha512-3TaVTaAv2gTiMB35i3FiGJaRfwb3Pyn/j3m/bfAvGe8FB7CF6u+LMYqYlDh7reQf7UNvoTvdfAqHGmPGOSsPmA==} + ts-api-utils@2.5.0: + resolution: {integrity: sha512-OJ/ibxhPlqrMM0UiNHJ/0CKQkoKF243/AEmplt3qpRgkW8VG7IfOS41h7V8TjITqdByHzrjcS/2si+y4lIh8NA==} engines: {node: '>=18.12'} peerDependencies: typescript: '>=4.8.4' @@ -2500,15 +2500,15 @@ packages: type-level-regexp@0.1.17: resolution: {integrity: sha512-wTk4DH3cxwk196uGLK/E9pE45aLfeKJacKmcEgEOA/q5dnPGNxXt0cfYdFxb57L+sEpf1oJH4Dnx/pnRcku9jg==} - typescript-eslint@8.56.1: - resolution: {integrity: sha512-U4lM6pjmBX7J5wk4szltF7I1cGBHXZopnAXCMXb3+fZ3B/0Z3hq3wS/CCUB2NZBNAExK92mCU2tEohWuwVMsDQ==} + typescript-eslint@8.58.2: + resolution: {integrity: sha512-V8iSng9mRbdZjl54VJ9NKr6ZB+dW0J3TzRXRGcSbLIej9jV86ZRtlYeTKDR/QLxXykocJ5icNzbsl2+5TzIvcQ==} engines: {node: ^18.18.0 || ^20.9.0 || >=21.1.0} peerDependencies: eslint: ^8.57.0 || ^9.0.0 || ^10.0.0 - typescript: '>=4.8.4 <6.0.0' + typescript: '>=4.8.4 <6.1.0' - typescript@5.9.3: - resolution: {integrity: sha512-jl1vZzPDinLr9eUt3J/t7V6FgNEw9QjvBPdysz9KfQDD41fQrC2Y4vKQdiaUpFT4bXlb1RHhLpp8wtm6M5TgSw==} + typescript@6.0.2: + resolution: {integrity: sha512-bGdAIrZ0wiGDo5l8c++HWtbaNCWTS4UTv7RaTH/ThVIgjkveJt83m74bBHMJkuCbslY8ixgLBVZJIOiQlQTjfQ==} engines: {node: '>=14.17'} hasBin: true @@ -2883,7 +2883,7 @@ snapshots: dependencies: '@eslint/object-schema': 3.0.2 debug: 4.4.3 - minimatch: 10.2.4 + minimatch: 10.2.5 transitivePeerDependencies: - supports-color @@ -3665,11 +3665,11 @@ snapshots: optionalDependencies: rollup: 4.60.0 - '@rollup/plugin-typescript@12.3.0(rollup@4.60.0)(tslib@2.8.1)(typescript@5.9.3)': + '@rollup/plugin-typescript@12.3.0(rollup@4.60.0)(tslib@2.8.1)(typescript@6.0.2)': dependencies: '@rollup/pluginutils': 5.3.0(rollup@4.60.0) resolve: 1.22.11 - typescript: 5.9.3 + typescript: 6.0.2 optionalDependencies: rollup: 4.60.0 tslib: 2.8.1 @@ -3805,95 +3805,95 @@ snapshots: '@types/trusted-types@2.0.7': {} - '@typescript-eslint/eslint-plugin@8.56.1(@typescript-eslint/parser@8.56.1(eslint@10.0.2(jiti@2.6.1))(typescript@5.9.3))(eslint@10.0.2(jiti@2.6.1))(typescript@5.9.3)': + '@typescript-eslint/eslint-plugin@8.58.2(@typescript-eslint/parser@8.58.2(eslint@10.0.2(jiti@2.6.1))(typescript@6.0.2))(eslint@10.0.2(jiti@2.6.1))(typescript@6.0.2)': dependencies: '@eslint-community/regexpp': 4.12.2 - '@typescript-eslint/parser': 8.56.1(eslint@10.0.2(jiti@2.6.1))(typescript@5.9.3) - '@typescript-eslint/scope-manager': 8.56.1 - '@typescript-eslint/type-utils': 8.56.1(eslint@10.0.2(jiti@2.6.1))(typescript@5.9.3) - '@typescript-eslint/utils': 8.56.1(eslint@10.0.2(jiti@2.6.1))(typescript@5.9.3) - '@typescript-eslint/visitor-keys': 8.56.1 + '@typescript-eslint/parser': 8.58.2(eslint@10.0.2(jiti@2.6.1))(typescript@6.0.2) + '@typescript-eslint/scope-manager': 8.58.2 + '@typescript-eslint/type-utils': 8.58.2(eslint@10.0.2(jiti@2.6.1))(typescript@6.0.2) + '@typescript-eslint/utils': 8.58.2(eslint@10.0.2(jiti@2.6.1))(typescript@6.0.2) + '@typescript-eslint/visitor-keys': 8.58.2 eslint: 10.0.2(jiti@2.6.1) ignore: 7.0.5 natural-compare: 1.4.0 - ts-api-utils: 2.4.0(typescript@5.9.3) - typescript: 5.9.3 + ts-api-utils: 2.5.0(typescript@6.0.2) + typescript: 6.0.2 transitivePeerDependencies: - supports-color - '@typescript-eslint/parser@8.56.1(eslint@10.0.2(jiti@2.6.1))(typescript@5.9.3)': + '@typescript-eslint/parser@8.58.2(eslint@10.0.2(jiti@2.6.1))(typescript@6.0.2)': dependencies: - '@typescript-eslint/scope-manager': 8.56.1 - '@typescript-eslint/types': 8.56.1 - '@typescript-eslint/typescript-estree': 8.56.1(typescript@5.9.3) - '@typescript-eslint/visitor-keys': 8.56.1 + '@typescript-eslint/scope-manager': 8.58.2 + '@typescript-eslint/types': 8.58.2 + '@typescript-eslint/typescript-estree': 8.58.2(typescript@6.0.2) + '@typescript-eslint/visitor-keys': 8.58.2 debug: 4.4.3 eslint: 10.0.2(jiti@2.6.1) - typescript: 5.9.3 + typescript: 6.0.2 transitivePeerDependencies: - supports-color - '@typescript-eslint/project-service@8.56.1(typescript@5.9.3)': + '@typescript-eslint/project-service@8.58.2(typescript@6.0.2)': dependencies: - '@typescript-eslint/tsconfig-utils': 8.56.1(typescript@5.9.3) - '@typescript-eslint/types': 8.56.1 + '@typescript-eslint/tsconfig-utils': 8.58.2(typescript@6.0.2) + '@typescript-eslint/types': 8.58.2 debug: 4.4.3 - typescript: 5.9.3 + typescript: 6.0.2 transitivePeerDependencies: - supports-color - '@typescript-eslint/scope-manager@8.56.1': + '@typescript-eslint/scope-manager@8.58.2': dependencies: - '@typescript-eslint/types': 8.56.1 - '@typescript-eslint/visitor-keys': 8.56.1 + '@typescript-eslint/types': 8.58.2 + '@typescript-eslint/visitor-keys': 8.58.2 - '@typescript-eslint/tsconfig-utils@8.56.1(typescript@5.9.3)': + '@typescript-eslint/tsconfig-utils@8.58.2(typescript@6.0.2)': dependencies: - typescript: 5.9.3 + typescript: 6.0.2 - '@typescript-eslint/type-utils@8.56.1(eslint@10.0.2(jiti@2.6.1))(typescript@5.9.3)': + '@typescript-eslint/type-utils@8.58.2(eslint@10.0.2(jiti@2.6.1))(typescript@6.0.2)': dependencies: - '@typescript-eslint/types': 8.56.1 - '@typescript-eslint/typescript-estree': 8.56.1(typescript@5.9.3) - '@typescript-eslint/utils': 8.56.1(eslint@10.0.2(jiti@2.6.1))(typescript@5.9.3) + '@typescript-eslint/types': 8.58.2 + '@typescript-eslint/typescript-estree': 8.58.2(typescript@6.0.2) + '@typescript-eslint/utils': 8.58.2(eslint@10.0.2(jiti@2.6.1))(typescript@6.0.2) debug: 4.4.3 eslint: 10.0.2(jiti@2.6.1) - ts-api-utils: 2.4.0(typescript@5.9.3) - typescript: 5.9.3 + ts-api-utils: 2.5.0(typescript@6.0.2) + typescript: 6.0.2 transitivePeerDependencies: - supports-color - '@typescript-eslint/types@8.56.1': {} + '@typescript-eslint/types@8.58.2': {} - '@typescript-eslint/typescript-estree@8.56.1(typescript@5.9.3)': + '@typescript-eslint/typescript-estree@8.58.2(typescript@6.0.2)': dependencies: - '@typescript-eslint/project-service': 8.56.1(typescript@5.9.3) - '@typescript-eslint/tsconfig-utils': 8.56.1(typescript@5.9.3) - '@typescript-eslint/types': 8.56.1 - '@typescript-eslint/visitor-keys': 8.56.1 + '@typescript-eslint/project-service': 8.58.2(typescript@6.0.2) + '@typescript-eslint/tsconfig-utils': 8.58.2(typescript@6.0.2) + '@typescript-eslint/types': 8.58.2 + '@typescript-eslint/visitor-keys': 8.58.2 debug: 4.4.3 - minimatch: 10.2.4 + minimatch: 10.2.5 semver: 7.7.4 - tinyglobby: 0.2.15 - ts-api-utils: 2.4.0(typescript@5.9.3) - typescript: 5.9.3 + tinyglobby: 0.2.16 + ts-api-utils: 2.5.0(typescript@6.0.2) + typescript: 6.0.2 transitivePeerDependencies: - supports-color - '@typescript-eslint/utils@8.56.1(eslint@10.0.2(jiti@2.6.1))(typescript@5.9.3)': + '@typescript-eslint/utils@8.58.2(eslint@10.0.2(jiti@2.6.1))(typescript@6.0.2)': dependencies: '@eslint-community/eslint-utils': 4.9.1(eslint@10.0.2(jiti@2.6.1)) - '@typescript-eslint/scope-manager': 8.56.1 - '@typescript-eslint/types': 8.56.1 - '@typescript-eslint/typescript-estree': 8.56.1(typescript@5.9.3) + '@typescript-eslint/scope-manager': 8.58.2 + '@typescript-eslint/types': 8.58.2 + '@typescript-eslint/typescript-estree': 8.58.2(typescript@6.0.2) eslint: 10.0.2(jiti@2.6.1) - typescript: 5.9.3 + typescript: 6.0.2 transitivePeerDependencies: - supports-color - '@typescript-eslint/visitor-keys@8.56.1': + '@typescript-eslint/visitor-keys@8.58.2': dependencies: - '@typescript-eslint/types': 8.56.1 + '@typescript-eslint/types': 8.58.2 eslint-visitor-keys: 5.0.1 '@unocss/cli@66.6.6': @@ -3911,7 +3911,7 @@ snapshots: magic-string: 0.30.21 pathe: 2.0.3 perfect-debounce: 2.1.0 - tinyglobby: 0.2.15 + tinyglobby: 0.2.16 unplugin-utils: 0.3.1 '@unocss/config@66.6.6': @@ -4026,7 +4026,7 @@ snapshots: chokidar: 5.0.0 magic-string: 0.30.21 pathe: 2.0.3 - tinyglobby: 0.2.15 + tinyglobby: 0.2.16 unplugin-utils: 0.3.1 vite: 8.0.5(@emnapi/core@1.8.1)(@emnapi/runtime@1.8.1)(@types/node@24.11.0)(esbuild@0.27.3)(jiti@2.6.1)(terser@5.46.0) @@ -4255,7 +4255,7 @@ snapshots: imurmurhash: 0.1.4 is-glob: 4.0.3 json-stable-stringify-without-jsonify: 1.0.1 - minimatch: 10.2.4 + minimatch: 10.2.5 natural-compare: 1.4.0 optionator: 0.9.4 optionalDependencies: @@ -4515,7 +4515,7 @@ snapshots: - bufferutil - utf-8-validate - minimatch@10.2.4: + minimatch@10.2.5: dependencies: brace-expansion: 5.0.5 @@ -4815,7 +4815,7 @@ snapshots: tinyexec@1.0.2: {} - tinyglobby@0.2.15: + tinyglobby@0.2.16: dependencies: fdir: 6.5.0(picomatch@4.0.4) picomatch: 4.0.4 @@ -4828,9 +4828,9 @@ snapshots: totalist@3.0.1: {} - ts-api-utils@2.4.0(typescript@5.9.3): + ts-api-utils@2.5.0(typescript@6.0.2): dependencies: - typescript: 5.9.3 + typescript: 6.0.2 tslib@2.8.1: {} @@ -4842,18 +4842,18 @@ snapshots: type-level-regexp@0.1.17: {} - typescript-eslint@8.56.1(eslint@10.0.2(jiti@2.6.1))(typescript@5.9.3): + typescript-eslint@8.58.2(eslint@10.0.2(jiti@2.6.1))(typescript@6.0.2): dependencies: - '@typescript-eslint/eslint-plugin': 8.56.1(@typescript-eslint/parser@8.56.1(eslint@10.0.2(jiti@2.6.1))(typescript@5.9.3))(eslint@10.0.2(jiti@2.6.1))(typescript@5.9.3) - '@typescript-eslint/parser': 8.56.1(eslint@10.0.2(jiti@2.6.1))(typescript@5.9.3) - '@typescript-eslint/typescript-estree': 8.56.1(typescript@5.9.3) - '@typescript-eslint/utils': 8.56.1(eslint@10.0.2(jiti@2.6.1))(typescript@5.9.3) + '@typescript-eslint/eslint-plugin': 8.58.2(@typescript-eslint/parser@8.58.2(eslint@10.0.2(jiti@2.6.1))(typescript@6.0.2))(eslint@10.0.2(jiti@2.6.1))(typescript@6.0.2) + '@typescript-eslint/parser': 8.58.2(eslint@10.0.2(jiti@2.6.1))(typescript@6.0.2) + '@typescript-eslint/typescript-estree': 8.58.2(typescript@6.0.2) + '@typescript-eslint/utils': 8.58.2(eslint@10.0.2(jiti@2.6.1))(typescript@6.0.2) eslint: 10.0.2(jiti@2.6.1) - typescript: 5.9.3 + typescript: 6.0.2 transitivePeerDependencies: - supports-color - typescript@5.9.3: {} + typescript@6.0.2: {} ufo@1.6.3: {} @@ -4927,7 +4927,7 @@ snapshots: picomatch: 4.0.4 postcss: 8.5.8 rollup: 4.60.0 - tinyglobby: 0.2.15 + tinyglobby: 0.2.16 optionalDependencies: '@types/node': 24.11.0 fsevents: 2.3.3 @@ -4941,7 +4941,7 @@ snapshots: picomatch: 4.0.4 postcss: 8.5.8 rolldown: 1.0.0-rc.12(@emnapi/core@1.8.1)(@emnapi/runtime@1.8.1) - tinyglobby: 0.2.15 + tinyglobby: 0.2.16 optionalDependencies: '@types/node': 24.11.0 esbuild: 0.27.3 @@ -4974,7 +4974,7 @@ snapshots: std-env: 3.10.0 tinybench: 2.9.0 tinyexec: 1.0.2 - tinyglobby: 0.2.15 + tinyglobby: 0.2.16 tinyrainbow: 3.0.3 vite: 7.3.2(@types/node@24.11.0)(jiti@2.6.1)(lightningcss@1.32.0)(terser@5.46.0) why-is-node-running: 2.3.0 From 17809403af640fe4d9b8f0f11538b3212be10951 Mon Sep 17 00:00:00 2001 From: sftse Date: Sun, 19 Apr 2026 15:33:21 +0200 Subject: [PATCH 71/95] Non-breaking version of PR 15127 (#15262) --- .changes/change-pr-15262.md | 5 +++++ crates/tauri/src/ipc/protocol.rs | 14 +++++--------- 2 files changed, 10 insertions(+), 9 deletions(-) create mode 100644 .changes/change-pr-15262.md diff --git a/.changes/change-pr-15262.md b/.changes/change-pr-15262.md new file mode 100644 index 000000000000..9f54c0eb4f43 --- /dev/null +++ b/.changes/change-pr-15262.md @@ -0,0 +1,5 @@ +--- +"tauri": patch:enhance +--- + +Remove a clone, no user-facing changes. diff --git a/crates/tauri/src/ipc/protocol.rs b/crates/tauri/src/ipc/protocol.rs index 72dea2821b07..53a0e33a87bd 100644 --- a/crates/tauri/src/ipc/protocol.rs +++ b/crates/tauri/src/ipc/protocol.rs @@ -466,15 +466,11 @@ fn parse_invoke_request( (body, content_type) = crate::utils::pattern::isolation::RawIsolationPayload::try_from(&body) .and_then(|raw| { - let content_type = raw.content_type().clone(); - crypto_keys.decrypt(raw).map(|decrypted| { - ( - decrypted, - content_type - .parse() - .unwrap_or(mime::APPLICATION_OCTET_STREAM), - ) - }) + let content_type = raw + .content_type() + .parse() + .unwrap_or(mime::APPLICATION_OCTET_STREAM); + Ok((crypto_keys.decrypt(raw)?, content_type)) }) .map_err(|e| e.to_string())?; } From 5e49bd8d5a4416fa3cd62d2684258826db9bc8b1 Mon Sep 17 00:00:00 2001 From: Tony <68118705+Legend-Master@users.noreply.github.com> Date: Mon, 20 Apr 2026 00:32:54 +0800 Subject: [PATCH 72/95] docs: nsis default languages (#15260) * docs: nsis default languages * Fix links and add `.` --- crates/tauri-bundler/src/bundle/settings.rs | 7 ++++--- crates/tauri-cli/config.schema.json | 4 ++-- crates/tauri-runtime-wry/src/lib.rs | 2 +- crates/tauri-schema-generator/schemas/config.schema.json | 4 ++-- crates/tauri-utils/src/config.rs | 5 +++-- crates/tauri/src/scope/fs.rs | 2 +- 6 files changed, 13 insertions(+), 11 deletions(-) diff --git a/crates/tauri-bundler/src/bundle/settings.rs b/crates/tauri-bundler/src/bundle/settings.rs index 815f342cd592..7580a0adbc95 100644 --- a/crates/tauri-bundler/src/bundle/settings.rs +++ b/crates/tauri-bundler/src/bundle/settings.rs @@ -479,9 +479,10 @@ pub struct NsisSettings { pub uninstaller_header_image: Option, /// Whether the installation will be for all users or just the current user. pub install_mode: NSISInstallerMode, - /// A list of installer languages. + /// A list of installer languages. Default to `["English"]` if not set. + /// /// By default the OS language is used. If the OS language is not in the list of languages, the first language will be used. - /// To allow the user to select the language, set `display_language_selector` to `true`. + /// To allow the user to select the language, set [`Self::display_language_selector`] to `true`. /// /// See for the complete list of languages. pub languages: Option>, @@ -490,7 +491,7 @@ pub struct NsisSettings { /// /// See for an example `.nsi` file. /// - /// **Note**: the key must be a valid NSIS language and it must be added to [`NsisConfig`]languages array, + /// **Note**: the key must be a valid NSIS language and it must be added to the [`Self::languages`] array, pub custom_language_files: Option>, /// Whether to display a language selector dialog before the installer and uninstaller windows are rendered or not. /// By default the OS language is selected, with a fallback to the first language in the `languages` array. diff --git a/crates/tauri-cli/config.schema.json b/crates/tauri-cli/config.schema.json index c759643a9ad8..2fefb6a64b2f 100644 --- a/crates/tauri-cli/config.schema.json +++ b/crates/tauri-cli/config.schema.json @@ -3056,7 +3056,7 @@ ] }, "languages": { - "description": "A list of installer languages.\n By default the OS language is used. If the OS language is not in the list of languages, the first language will be used.\n To allow the user to select the language, set `display_language_selector` to `true`.\n\n See for the complete list of languages.", + "description": "A list of installer languages. Default to `[\"English\"]` if not set.\n\n By default the OS language is used. If the OS language is not in the list of languages, the first language will be used.\n To allow the user to select the language, set `display_language_selector` to `true`.\n\n See for the complete list of languages.", "type": [ "array", "null" @@ -3066,7 +3066,7 @@ } }, "customLanguageFiles": { - "description": "A key-value pair where the key is the language and the\n value is the path to a custom `.nsh` file that holds the translated text for tauri's custom messages.\n\n See for an example `.nsh` file.\n\n **Note**: the key must be a valid NSIS language and it must be added to [`NsisConfig`] languages array,", + "description": "A key-value pair where the key is the language and the\n value is the path to a custom `.nsh` file that holds the translated text for tauri's custom messages.\n\n See for an example `.nsh` file.\n\n **Note**: the key must be a valid NSIS language and it must be added to the [`Self::languages`] array,", "type": [ "object", "null" diff --git a/crates/tauri-runtime-wry/src/lib.rs b/crates/tauri-runtime-wry/src/lib.rs index 6c537de6cf43..cbb59a30b736 100644 --- a/crates/tauri-runtime-wry/src/lib.rs +++ b/crates/tauri-runtime-wry/src/lib.rs @@ -818,7 +818,7 @@ impl WindowBuilder for WindowBuilderWrapper { #[cfg(target_os = "macos")] { // TODO: find a proper way to prevent webview being pushed out of the window. - // Workround for issue: https://github.com/tauri-apps/tauri/issues/10225 + // Workaround for issue: https://github.com/tauri-apps/tauri/issues/10225 // The window requires `NSFullSizeContentViewWindowMask` flag to prevent devtools // pushing the content view out of the window. // By setting the default style to `TitleBarStyle::Visible` should fix the issue for most of the users. diff --git a/crates/tauri-schema-generator/schemas/config.schema.json b/crates/tauri-schema-generator/schemas/config.schema.json index c759643a9ad8..2fefb6a64b2f 100644 --- a/crates/tauri-schema-generator/schemas/config.schema.json +++ b/crates/tauri-schema-generator/schemas/config.schema.json @@ -3056,7 +3056,7 @@ ] }, "languages": { - "description": "A list of installer languages.\n By default the OS language is used. If the OS language is not in the list of languages, the first language will be used.\n To allow the user to select the language, set `display_language_selector` to `true`.\n\n See for the complete list of languages.", + "description": "A list of installer languages. Default to `[\"English\"]` if not set.\n\n By default the OS language is used. If the OS language is not in the list of languages, the first language will be used.\n To allow the user to select the language, set `display_language_selector` to `true`.\n\n See for the complete list of languages.", "type": [ "array", "null" @@ -3066,7 +3066,7 @@ } }, "customLanguageFiles": { - "description": "A key-value pair where the key is the language and the\n value is the path to a custom `.nsh` file that holds the translated text for tauri's custom messages.\n\n See for an example `.nsh` file.\n\n **Note**: the key must be a valid NSIS language and it must be added to [`NsisConfig`] languages array,", + "description": "A key-value pair where the key is the language and the\n value is the path to a custom `.nsh` file that holds the translated text for tauri's custom messages.\n\n See for an example `.nsh` file.\n\n **Note**: the key must be a valid NSIS language and it must be added to the [`Self::languages`] array,", "type": [ "object", "null" diff --git a/crates/tauri-utils/src/config.rs b/crates/tauri-utils/src/config.rs index 78df2f4fa56b..e74c93ed93b2 100644 --- a/crates/tauri-utils/src/config.rs +++ b/crates/tauri-utils/src/config.rs @@ -873,7 +873,8 @@ pub struct NsisConfig { /// Whether the installation will be for all users or just the current user. #[serde(default, alias = "install-mode")] pub install_mode: NSISInstallerMode, - /// A list of installer languages. + /// A list of installer languages. Default to `["English"]` if not set. + /// /// By default the OS language is used. If the OS language is not in the list of languages, the first language will be used. /// To allow the user to select the language, set `display_language_selector` to `true`. /// @@ -884,7 +885,7 @@ pub struct NsisConfig { /// /// See for an example `.nsh` file. /// - /// **Note**: the key must be a valid NSIS language and it must be added to [`NsisConfig`] languages array, + /// **Note**: the key must be a valid NSIS language and it must be added to the [`Self::languages`] array, pub custom_language_files: Option>, /// Whether to display a language selector dialog before the installer and uninstaller windows are rendered or not. /// By default the OS language is selected, with a fallback to the first language in the `languages` array. diff --git a/crates/tauri/src/scope/fs.rs b/crates/tauri/src/scope/fs.rs index 36a9a1ebc53f..2e978f3a95ff 100644 --- a/crates/tauri/src/scope/fs.rs +++ b/crates/tauri/src/scope/fs.rs @@ -77,7 +77,7 @@ fn push_pattern, F: Fn(&str) -> Result crate::Result<()> { - // Reconstruct pattern path components with appropraite separator + // Reconstruct pattern path components with appropriate separator // so `some\path/to/dir/**\*` would be `some/path/to/dir/**/*` on Unix // and `some\path\to\dir\**\*` on Windows. let path: PathBuf = pattern.as_ref().components().collect(); From 60407d603d6564743a59be8de45c304af293fb06 Mon Sep 17 00:00:00 2001 From: Xuhui Zheng <2529677678@qq.com> Date: Mon, 20 Apr 2026 17:18:02 +0800 Subject: [PATCH 73/95] feat(windows): append .rc content support. (#15263) * feat(windows): append .rc content support. * chore: update api comments. * chore: add change file. * Update crates/tauri-build/src/lib.rs Co-authored-by: Tony <68118705+Legend-Master@users.noreply.github.com> * fix: appending logic. * chore: update comments. --------- Co-authored-by: Tony <68118705+Legend-Master@users.noreply.github.com> --- .changes/append-rc-content-support.md | 5 +++++ crates/tauri-build/src/lib.rs | 16 ++++++++++++++++ 2 files changed, 21 insertions(+) create mode 100644 .changes/append-rc-content-support.md diff --git a/.changes/append-rc-content-support.md b/.changes/append-rc-content-support.md new file mode 100644 index 000000000000..cfe01754f4d7 --- /dev/null +++ b/.changes/append-rc-content-support.md @@ -0,0 +1,5 @@ +--- +"tauri-build": minor:feat +--- + +Allow users to append extra `.rc` content by `append_rc_content` in `WindowsAttributes`. diff --git a/crates/tauri-build/src/lib.rs b/crates/tauri-build/src/lib.rs index 972455e2d485..cdf44f50edc3 100644 --- a/crates/tauri-build/src/lib.rs +++ b/crates/tauri-build/src/lib.rs @@ -242,6 +242,8 @@ pub struct WindowsAttributes { /// /// [application manifest]: https://learn.microsoft.com/en-us/windows/win32/sbscs/application-manifests app_manifest: Option, + /// A series of strings containing additional .rc content to be appended to the generated resource file on Windows. + append_rc_content: Vec, } impl Default for WindowsAttributes { @@ -256,6 +258,7 @@ impl WindowsAttributes { Self { window_icon_path: Default::default(), app_manifest: Some(include_str!("windows-app-manifest.xml").into()), + append_rc_content: Vec::new(), } } @@ -265,6 +268,7 @@ impl WindowsAttributes { Self { app_manifest: None, window_icon_path: Default::default(), + append_rc_content: Vec::new(), } } @@ -334,6 +338,14 @@ impl WindowsAttributes { self.app_manifest = Some(manifest.as_ref().to_string()); self } + + /// Append additional .rc content to the generated resource file on Windows. + /// This can be called multiple times to append multiple contents. + #[must_use] + pub fn append_rc_content>(mut self, content: S) -> Self { + self.append_rc_content.push(content.into()); + self + } } /// The attributes used on the build. @@ -613,6 +625,10 @@ pub fn try_build(attributes: Attributes) -> Result<()> { res.set_manifest(&manifest); } + for content in attributes.windows_attributes.append_rc_content { + res.append_rc_content(&content); + } + if let Some(version_str) = &config.version { if let Ok(v) = Version::parse(version_str) { let version = (v.major << 48) | (v.minor << 32) | (v.patch << 16); From 0ed2495f66b03da640a90f0c682f80d562e4ae10 Mon Sep 17 00:00:00 2001 From: Lucas Fernandes Nogueira Date: Mon, 20 Apr 2026 10:50:00 -0300 Subject: [PATCH 74/95] chore(tauri-utils): update mime_type documentation (#15253) --- crates/tauri-cli/config.schema.json | 2 +- crates/tauri-schema-generator/schemas/config.schema.json | 2 +- crates/tauri-utils/src/config.rs | 8 +++++++- 3 files changed, 9 insertions(+), 3 deletions(-) diff --git a/crates/tauri-cli/config.schema.json b/crates/tauri-cli/config.schema.json index 2fefb6a64b2f..c8d038cb3c03 100644 --- a/crates/tauri-cli/config.schema.json +++ b/crates/tauri-cli/config.schema.json @@ -2492,7 +2492,7 @@ ] }, "mimeType": { - "description": "The mime-type e.g. 'image/png' or 'text/plain'. Linux-only.", + "description": "The mime-type of the association, e.g. `'image/png'` or `'text/plain'`.\n\n - **Linux**: written as `MimeType=` in the `.desktop` file.\n - **macOS / iOS**: added as `public.mime-type` in the `UTTypeTagSpecification` dictionary of\n the `UTExportedTypeDeclarations` entry in `Info.plist`.\n - **Android**: used as `android:mimeType` in the `` element of an ``\n in `AndroidManifest.xml`.", "type": [ "string", "null" diff --git a/crates/tauri-schema-generator/schemas/config.schema.json b/crates/tauri-schema-generator/schemas/config.schema.json index 2fefb6a64b2f..c8d038cb3c03 100644 --- a/crates/tauri-schema-generator/schemas/config.schema.json +++ b/crates/tauri-schema-generator/schemas/config.schema.json @@ -2492,7 +2492,7 @@ ] }, "mimeType": { - "description": "The mime-type e.g. 'image/png' or 'text/plain'. Linux-only.", + "description": "The mime-type of the association, e.g. `'image/png'` or `'text/plain'`.\n\n - **Linux**: written as `MimeType=` in the `.desktop` file.\n - **macOS / iOS**: added as `public.mime-type` in the `UTTypeTagSpecification` dictionary of\n the `UTExportedTypeDeclarations` entry in `Info.plist`.\n - **Android**: used as `android:mimeType` in the `` element of an ``\n in `AndroidManifest.xml`.", "type": [ "string", "null" diff --git a/crates/tauri-utils/src/config.rs b/crates/tauri-utils/src/config.rs index e74c93ed93b2..060dd5d9668b 100644 --- a/crates/tauri-utils/src/config.rs +++ b/crates/tauri-utils/src/config.rs @@ -1198,7 +1198,13 @@ pub struct FileAssociation { /// The app's role with respect to the type. Maps to `CFBundleTypeRole` on macOS. #[serde(default)] pub role: BundleTypeRole, - /// The mime-type e.g. 'image/png' or 'text/plain'. Linux-only. + /// The mime-type of the association, e.g. `'image/png'` or `'text/plain'`. + /// + /// - **Linux**: written as `MimeType=` in the `.desktop` file. + /// - **macOS / iOS**: added as `public.mime-type` in the `UTTypeTagSpecification` dictionary of + /// the `UTExportedTypeDeclarations` entry in `Info.plist`. + /// - **Android**: used as `android:mimeType` in the `` element of an `` + /// in `AndroidManifest.xml`. #[serde(alias = "mime-type")] pub mime_type: Option, /// The ranking of this app among apps that declare themselves as editors or viewers of the given file type. Maps to `LSHandlerRank` on macOS. From 212eeafca9ac781c4320facab8d7903d81e5e39f Mon Sep 17 00:00:00 2001 From: sftse Date: Thu, 23 Apr 2026 05:34:12 +0200 Subject: [PATCH 75/95] Audit CI fix, RUSTSEC advisories (#15282) * build: bump rustls-webpki because RUSTSEC advisory * build: bump scc, sdd to not use yanked versions * build: bump rand 0.8.x because RUSTSEC advisory * build: bump rand 0.9.x to skip yanked version * build: ignore RUSTSEC advisories until we can upgrade Full list 2024-0429 glib 0.18.5 unsoundness, fixed by moving to gtk4 2026-0097 rand unsoundness, fixed by removing kuchikiki from deps in v3 2026-0049 rustls, fixed by updating apple-codesign to 0.28.0 2026-0098 rustls, fixed by updating apple-codesign to 0.28.0 2026-0099 rustls, fixed by updating apple-codesign to 0.28.0 * fmt audit.toml --- .cargo/audit.toml | 13 +++++++++++ Cargo.lock | 56 +++++++++++++++++++++++------------------------ 2 files changed, 41 insertions(+), 28 deletions(-) diff --git a/.cargo/audit.toml b/.cargo/audit.toml index b6dd47060380..0e271c7fbbca 100644 --- a/.cargo/audit.toml +++ b/.cargo/audit.toml @@ -8,4 +8,17 @@ ignore = [ "RUSTSEC-2024-0370", # time crate can't be updated in the repo because of MSRV, users are unaffected "RUSTSEC-2026-0009", + # rand unsoundness, fixed when we remove kuchikiki from deps in v3, currently + # remains for semver reasons but is not built in default configuration + "RUSTSEC-2026-0097", + # glib 0.18.5 unsoundness, fixed by updating to gtk4 + "RUSTSEC-2024-0429", + # rustls, fixed when updating to apple-codesign 0.28.0 + "RUSTSEC-2026-0049", + # rustls, fixed when updating to apple-codesign 0.28.0 + "RUSTSEC-2026-0098", + # rustls, fixed when updating to apple-codesign 0.28.0 + "RUSTSEC-2026-0099", + # rustls, fixed when updating to apple-codesign 0.28.0 + "RUSTSEC-2026-0104", ] diff --git a/Cargo.lock b/Cargo.lock index 447af55c33fc..2a699ed2b154 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -292,7 +292,7 @@ dependencies = [ "pkcs1", "pkcs8", "plist", - "rand 0.8.5", + "rand 0.8.6", "rasn", "rayon", "regex", @@ -359,7 +359,7 @@ dependencies = [ "flate2", "log", "md-5", - "rand 0.8.5", + "rand 0.8.6", "reqwest 0.11.27", "scroll", "serde", @@ -4142,7 +4142,7 @@ dependencies = [ "jsonrpsee-types", "parking_lot", "pin-project", - "rand 0.8.5", + "rand 0.8.6", "rustc-hash", "serde", "serde_json", @@ -5014,7 +5014,7 @@ dependencies = [ "num-integer", "num-iter", "num-traits", - "rand 0.8.5", + "rand 0.8.6", "serde", "smallvec", "zeroize", @@ -5978,7 +5978,7 @@ dependencies = [ "p256", "p384", "p521", - "rand 0.8.5", + "rand 0.8.6", "ripemd", "rsa", "sha1", @@ -6082,7 +6082,7 @@ source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "5d5285893bb5eb82e6aaf5d59ee909a06a16737a8970984dd7746ba9283498d6" dependencies = [ "phf_shared 0.10.0", - "rand 0.8.5", + "rand 0.8.6", ] [[package]] @@ -6092,7 +6092,7 @@ source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "3c80231409c20246a13fddb31776fb942c38553c51e871f8cbd687a4cfb5843d" dependencies = [ "phf_shared 0.11.3", - "rand 0.8.5", + "rand 0.8.6", ] [[package]] @@ -6440,7 +6440,7 @@ dependencies = [ "bitflags 2.7.0", "lazy_static", "num-traits", - "rand 0.8.5", + "rand 0.8.6", "rand_chacha 0.3.1", "rand_xorshift", "regex-syntax", @@ -6507,7 +6507,7 @@ checksum = "588f6378e4dd99458b60ec275b4477add41ce4fa9f64dcba6f15adccb19b50d6" dependencies = [ "env_logger 0.8.4", "log", - "rand 0.8.5", + "rand 0.8.6", ] [[package]] @@ -6558,9 +6558,9 @@ dependencies = [ [[package]] name = "rand" -version = "0.8.5" +version = "0.8.6" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "34af8d1a0e25924bc5b7c43c079c942339d8f0a8b57c39049bef581b46327404" +checksum = "5ca0ecfa931c29007047d1bc58e623ab12e5590e8c7cc53200d5202b69266d8a" dependencies = [ "libc", "rand_chacha 0.3.1", @@ -6569,9 +6569,9 @@ dependencies = [ [[package]] name = "rand" -version = "0.9.3" +version = "0.9.4" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "7ec095654a25171c2124e9e3393a930bddbffdc939556c914957a4c3e0a87166" +checksum = "44c5af06bb1b7d3216d91932aed5265164bf384dc89cd6ba05cf59a35f5f76ea" dependencies = [ "rand_chacha 0.9.0", "rand_core 0.9.3", @@ -6725,7 +6725,7 @@ dependencies = [ "once_cell", "paste", "profiling", - "rand 0.8.5", + "rand 0.8.6", "rand_chacha 0.3.1", "simd_helpers", "system-deps", @@ -7170,7 +7170,7 @@ dependencies = [ "borsh", "bytes", "num-traits", - "rand 0.8.5", + "rand 0.8.6", "rkyv", "serde", "serde_json", @@ -7282,7 +7282,7 @@ dependencies = [ "once_cell", "ring", "rustls-pki-types", - "rustls-webpki 0.103.8", + "rustls-webpki 0.103.13", "subtle", "zeroize", ] @@ -7365,7 +7365,7 @@ dependencies = [ "rustls 0.23.35", "rustls-native-certs 0.8.3", "rustls-platform-verifier-android", - "rustls-webpki 0.103.8", + "rustls-webpki 0.103.13", "security-framework 3.5.1", "security-framework-sys", "webpki-root-certs", @@ -7401,9 +7401,9 @@ dependencies = [ [[package]] name = "rustls-webpki" -version = "0.103.8" +version = "0.103.13" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "2ffdfa2f5286e2247234e03f680868ac2815974dc39e00ea15adc445d0aafe52" +checksum = "61c429a8649f110dddef65e2a5ad240f747e85f7758a6bccc7e5777bd33f756e" dependencies = [ "ring", "rustls-pki-types", @@ -7483,9 +7483,9 @@ dependencies = [ [[package]] name = "scc" -version = "2.3.0" +version = "2.4.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "28e1c91382686d21b5ac7959341fcb9780fa7c03773646995a87c950fa7be640" +checksum = "46e6f046b7fef48e2660c57ed794263155d713de679057f2d0c169bfc6e756cc" dependencies = [ "sdd", ] @@ -7574,9 +7574,9 @@ dependencies = [ [[package]] name = "sdd" -version = "3.0.5" +version = "3.0.10" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "478f121bb72bbf63c52c93011ea1791dca40140dfe13f8336c4c5ac952c33aa9" +checksum = "490dcfcbfef26be6800d11870ff2df8774fa6e86d047e3e8c8a76b25655e41ca" [[package]] name = "seahash" @@ -8266,7 +8266,7 @@ dependencies = [ "http 1.3.1", "httparse", "log", - "rand 0.8.5", + "rand 0.8.6", "sha1", ] @@ -8909,7 +8909,7 @@ dependencies = [ "phf 0.11.3", "plist", "pretty_assertions", - "rand 0.9.3", + "rand 0.9.4", "rayon", "regex", "resvg", @@ -9027,7 +9027,7 @@ dependencies = [ "os_pipe", "p12", "plist", - "rand 0.9.3", + "rand 0.9.4", "regex", "serde", "serde_json", @@ -9822,7 +9822,7 @@ dependencies = [ "http 1.3.1", "httparse", "log", - "rand 0.8.5", + "rand 0.8.6", "rustls 0.22.4", "rustls-native-certs 0.7.3", "rustls-pki-types", @@ -9843,7 +9843,7 @@ dependencies = [ "http 1.3.1", "httparse", "log", - "rand 0.9.3", + "rand 0.9.4", "sha1", "thiserror 2.0.12", "utf-8", From b3f62a2feed78c62aa5054fc74bc0b6291543b0c Mon Sep 17 00:00:00 2001 From: "dependabot[bot]" <49699333+dependabot[bot]@users.noreply.github.com> Date: Thu, 23 Apr 2026 11:52:45 +0800 Subject: [PATCH 76/95] chore(deps): bump openssl from 0.10.72 to 0.10.78 (#15284) Bumps [openssl](https://github.com/rust-openssl/rust-openssl) from 0.10.72 to 0.10.78. - [Release notes](https://github.com/rust-openssl/rust-openssl/releases) - [Commits](https://github.com/rust-openssl/rust-openssl/compare/openssl-v0.10.72...openssl-v0.10.78) --- updated-dependencies: - dependency-name: openssl dependency-version: 0.10.78 dependency-type: indirect ... Signed-off-by: dependabot[bot] Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com> --- Cargo.lock | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/Cargo.lock b/Cargo.lock index 2a699ed2b154..4f857d95cedc 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -5429,9 +5429,9 @@ checksum = "c08d65885ee38876c4f86fa503fb49d7b507c2b62552df7c70b2fce627e06381" [[package]] name = "openssl" -version = "0.10.72" +version = "0.10.78" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "fedfea7d58a1f73118430a55da6a286e7b044961736ce96a16a17068ea25e5da" +checksum = "f38c4372413cdaaf3cc79dd92d29d7d9f5ab09b51b10dded508fb90bb70b9222" dependencies = [ "bitflags 2.7.0", "cfg-if", @@ -5476,9 +5476,9 @@ dependencies = [ [[package]] name = "openssl-sys" -version = "0.9.107" +version = "0.9.114" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "8288979acd84749c744a9014b4382d42b8f7b2592847b5afb2ed29e5d16ede07" +checksum = "13ce1245cd07fcc4cfdb438f7507b0c7e4f3849a69fd84d52374c66d83741bb6" dependencies = [ "cc", "libc", From de2a2d1aa590d7a430831b0bbc7942aa6e56fb8a Mon Sep 17 00:00:00 2001 From: AetherWing Date: Thu, 23 Apr 2026 14:11:22 +0800 Subject: [PATCH 77/95] feat(webview2): add option to disable browser-level autofill on Windows (#14722) * feat(webview2): add option to disable browser-level autofill on Windows * docs(api): set disableAutofill api since to 2.11.0 * docs(disable_autofill ): unify documentation * Update .changes/.disable-autofill.md Co-authored-by: Tony <68118705+Legend-Master@users.noreply.github.com> * refactor(runtime): rename disable_autofill to general_autofill_enabled * refactor(api): delete general autofill option in WindowOptions Co-authored-by: Copilot * Update crates/tauri-runtime-wry/src/lib.rs Co-authored-by: Tony <68118705+Legend-Master@users.noreply.github.com> * fix: fix default value for general_autofill_enabled * fix(schema): fix default value for general_autofill_enabled * Clean up * Revert new line --------- Co-authored-by: Tony <68118705+Legend-Master@users.noreply.github.com> Co-authored-by: Tony --- .changes/disable-autofill.md | 9 ++++ crates/tauri-cli/config.schema.json | 5 +++ crates/tauri-runtime-wry/src/lib.rs | 3 +- crates/tauri-runtime/src/webview.rs | 45 ++++++++++++++++++- .../schemas/config.schema.json | 5 +++ crates/tauri-utils/src/config.rs | 24 +++++++++- crates/tauri/src/webview/mod.rs | 23 ++++++++++ crates/tauri/src/webview/webview_window.rs | 23 ++++++++++ packages/api/src/webview.ts | 19 ++++++++ 9 files changed, 153 insertions(+), 3 deletions(-) create mode 100644 .changes/disable-autofill.md diff --git a/.changes/disable-autofill.md b/.changes/disable-autofill.md new file mode 100644 index 000000000000..41dfd62dc042 --- /dev/null +++ b/.changes/disable-autofill.md @@ -0,0 +1,9 @@ +--- +'tauri-runtime': 'minor:feat' +'tauri-runtime-wry': 'minor:feat' +'tauri-utils': 'minor:feat' +'tauri': 'minor:feat' +'@tauri-apps/api': 'minor:feat' +--- + +Add a WebView option to control browser-level general autofill behavior. This option does not disable password or credit card autofill. On Windows (WebView2), setting it to true disables the general autofill "Suggestions" UI, which may appear even when `autocomplete="off"` is specified on input elements. On Linux, macOS, iOS, and Android, this option is currently unsupported and performs no operation. \ No newline at end of file diff --git a/crates/tauri-cli/config.schema.json b/crates/tauri-cli/config.schema.json index c8d038cb3c03..f4381d54c1f0 100644 --- a/crates/tauri-cli/config.schema.json +++ b/crates/tauri-cli/config.schema.json @@ -625,6 +625,11 @@ "string", "null" ] + }, + "generalAutofillEnabled": { + "description": "Controls the WebView's browser-level general autofill behavior.\n\n **This option does not disable password or credit card autofill.**\n\n When set to `false`, the WebView will not automatically populate\n general form fields using previously stored data such as addresses\n or contact information.\n\n If not specified, this is `true` by default.\n\n ## Platform-specific\n\n - **Windows**: Supported. WebView2's autofill feature (called\n \"Suggestions\") may not honor `autocomplete=\"off\"` on input\n elements in some cases.\n - **Linux / Android / iOS / macOS**: Unsupported and performs no\n operation.", + "default": true, + "type": "boolean" } }, "additionalProperties": false diff --git a/crates/tauri-runtime-wry/src/lib.rs b/crates/tauri-runtime-wry/src/lib.rs index cbb59a30b736..da4cb6a637c0 100644 --- a/crates/tauri-runtime-wry/src/lib.rs +++ b/crates/tauri-runtime-wry/src/lib.rs @@ -4760,7 +4760,8 @@ You may have it installed on another user account, but it is not available for t .with_accept_first_mouse(webview_attributes.accept_first_mouse) .with_incognito(webview_attributes.incognito) .with_clipboard(webview_attributes.clipboard) - .with_hotkeys_zoom(webview_attributes.zoom_hotkeys_enabled); + .with_hotkeys_zoom(webview_attributes.zoom_hotkeys_enabled) + .with_general_autofill_enabled(webview_attributes.general_autofill_enabled); if url != "about:blank" { webview_builder = webview_builder.with_url(&url); diff --git a/crates/tauri-runtime/src/webview.rs b/crates/tauri-runtime/src/webview.rs index 1cd929226cf1..d4f7e0145313 100644 --- a/crates/tauri-runtime/src/webview.rs +++ b/crates/tauri-runtime/src/webview.rs @@ -371,6 +371,24 @@ pub struct WebviewAttributes { /// see https://docs.rs/objc2-web-kit/latest/objc2_web_kit/struct.WKWebView.html#method.allowsLinkPreview pub allow_link_preview: bool, pub scroll_bar_style: ScrollBarStyle, + /// Controls the WebView's browser-level general autofill behavior. + /// + /// **This option does not disable password or credit card autofill.** + /// + /// When set to `false`, the WebView will not automatically populate + /// general form fields using previously stored data such as addresses + /// or contact information. + /// + /// If not specified, this is `true` by default. + /// + /// ## Platform-specific + /// + /// - **Windows**: Supported. WebView2's autofill feature (called + /// "Suggestions") may not honor `autocomplete="off"` on input + /// elements in some cases. + /// - **Linux / Android / iOS / macOS**: Unsupported and performs no + /// operation. + pub general_autofill_enabled: bool, /// Allows overriding the keyboard accessory view on iOS. /// Returning `None` effectively removes the view. /// @@ -441,7 +459,8 @@ impl From<&WindowConfig> for WebviewAttributes { #[cfg(windows)] ConfigScrollBarStyle::FluentOverlay => ScrollBarStyle::FluentOverlay, _ => ScrollBarStyle::Default, - }); + }) + .general_autofill_enabled(config.general_autofill_enabled); #[cfg(any(not(target_os = "macos"), feature = "macos-private-api"))] { @@ -516,6 +535,7 @@ impl WebviewAttributes { javascript_disabled: false, allow_link_preview: true, scroll_bar_style: ScrollBarStyle::Default, + general_autofill_enabled: true, #[cfg(target_os = "ios")] input_accessory_view_builder: None, #[cfg(windows)] @@ -807,6 +827,29 @@ impl WebviewAttributes { self.scroll_bar_style = style; self } + + /// Controls the WebView's browser-level general autofill behavior. + /// + /// **This option does not disable password or credit card autofill.** + /// + /// When set to `false`, the WebView will not automatically populate + /// general form fields using previously stored data such as addresses + /// or contact information. + /// + /// By default, this is `true`. + /// + /// ## Platform-specific + /// + /// - **Windows**: Supported. WebView2's autofill feature (called + /// "Suggestions") may not honor `autocomplete="off"` on input + /// elements in some cases. + /// - **Linux / Android / iOS / macOS**: Unsupported and performs no + /// operation. + #[must_use] + pub fn general_autofill_enabled(mut self, enabled: bool) -> Self { + self.general_autofill_enabled = enabled; + self + } } /// IPC handler. diff --git a/crates/tauri-schema-generator/schemas/config.schema.json b/crates/tauri-schema-generator/schemas/config.schema.json index c8d038cb3c03..f4381d54c1f0 100644 --- a/crates/tauri-schema-generator/schemas/config.schema.json +++ b/crates/tauri-schema-generator/schemas/config.schema.json @@ -625,6 +625,11 @@ "string", "null" ] + }, + "generalAutofillEnabled": { + "description": "Controls the WebView's browser-level general autofill behavior.\n\n **This option does not disable password or credit card autofill.**\n\n When set to `false`, the WebView will not automatically populate\n general form fields using previously stored data such as addresses\n or contact information.\n\n If not specified, this is `true` by default.\n\n ## Platform-specific\n\n - **Windows**: Supported. WebView2's autofill feature (called\n \"Suggestions\") may not honor `autocomplete=\"off\"` on input\n elements in some cases.\n - **Linux / Android / iOS / macOS**: Unsupported and performs no\n operation.", + "default": true, + "type": "boolean" } }, "additionalProperties": false diff --git a/crates/tauri-utils/src/config.rs b/crates/tauri-utils/src/config.rs index 060dd5d9668b..e4aeee7ea797 100644 --- a/crates/tauri-utils/src/config.rs +++ b/crates/tauri-utils/src/config.rs @@ -2270,6 +2270,25 @@ pub struct WindowConfig { /// By default the system uses the foreground scene. #[serde(default, alias = "requested-by-scene-identifier")] pub requested_by_scene_identifier: Option, + /// Controls the WebView's browser-level general autofill behavior. + /// + /// **This option does not disable password or credit card autofill.** + /// + /// When set to `false`, the WebView will not automatically populate + /// general form fields using previously stored data such as addresses + /// or contact information. + /// + /// If not specified, this is `true` by default. + /// + /// ## Platform-specific + /// + /// - **Windows**: Supported. WebView2's autofill feature (called + /// "Suggestions") may not honor `autocomplete="off"` on input + /// elements in some cases. + /// - **Linux / Android / iOS / macOS**: Unsupported and performs no + /// operation. + #[serde(default = "default_true", alias = "general-autofill-enabled")] + pub general_autofill_enabled: bool, } impl Default for WindowConfig { @@ -2335,6 +2354,7 @@ impl Default for WindowConfig { activity_name: None, created_by_activity_name: None, requested_by_scene_identifier: None, + general_autofill_enabled: true, } } } @@ -3872,6 +3892,7 @@ mod build { let activity_name = opt_lit(self.activity_name.as_ref()); let created_by_activity_name = opt_lit(self.created_by_activity_name.as_ref()); let requested_by_scene_identifier = opt_lit(self.requested_by_scene_identifier.as_ref()); + let general_autofill_enabled = self.general_autofill_enabled; literal_struct!( tokens, @@ -3935,7 +3956,8 @@ mod build { scroll_bar_style, activity_name, created_by_activity_name, - requested_by_scene_identifier + requested_by_scene_identifier, + general_autofill_enabled ); } } diff --git a/crates/tauri/src/webview/mod.rs b/crates/tauri/src/webview/mod.rs index cf300288f4fd..b86eb01a223c 100644 --- a/crates/tauri/src/webview/mod.rs +++ b/crates/tauri/src/webview/mod.rs @@ -1179,6 +1179,29 @@ fn main() { self } + /// Controls the WebView's browser-level general autofill behavior. + /// + /// **This option does not disable password or credit card autofill.** + /// + /// When set to `false`, the WebView will not automatically populate + /// general form fields using previously stored data such as addresses + /// or contact information. + /// + /// By default, this is `true`. + /// + /// ## Platform-specific + /// + /// - **Windows**: Supported. WebView2's autofill feature (called + /// "Suggestions") may not honor `autocomplete="off"` on input + /// elements in some cases. + /// - **Linux / Android / iOS / macOS**: Unsupported and performs no + /// operation. + #[must_use] + pub fn general_autofill_enabled(mut self, enabled: bool) -> Self { + self.webview_attributes = self.webview_attributes.general_autofill_enabled(enabled); + self + } + /// Whether to show a link preview when long pressing on links. Available on macOS and iOS only. /// /// Default is true. diff --git a/crates/tauri/src/webview/webview_window.rs b/crates/tauri/src/webview/webview_window.rs index c49abec0cbe7..95bf67719399 100644 --- a/crates/tauri/src/webview/webview_window.rs +++ b/crates/tauri/src/webview/webview_window.rs @@ -1226,6 +1226,29 @@ impl> WebviewWindowBuilder<'_, R, M> { self } + /// Controls the WebView's browser-level general autofill behavior. + /// + /// **This option does not disable password or credit card autofill.** + /// + /// When set to `false`, the WebView will not automatically populate + /// general form fields using previously stored data such as addresses + /// or contact information. + /// + /// By default, this is `true`. + /// + /// ## Platform-specific + /// + /// - **Windows**: Supported. WebView2's autofill feature (called + /// "Suggestions") may not honor `autocomplete="off"` on input + /// elements in some cases. + /// - **Linux / Android / iOS / macOS**: Unsupported and performs no + /// operation. + #[must_use] + pub fn general_autofill_enabled(mut self, enabled: bool) -> Self { + self.webview_builder = self.webview_builder.general_autofill_enabled(enabled); + self + } + /// Allows overriding the keyboard accessory view on iOS. /// Returning `None` effectively removes the view. /// diff --git a/packages/api/src/webview.ts b/packages/api/src/webview.ts index 47a497fb6c84..968983c02eda 100644 --- a/packages/api/src/webview.ts +++ b/packages/api/src/webview.ts @@ -897,6 +897,25 @@ interface WebviewOptions { * - **Linux / Android / iOS / macOS**: Unsupported. Only supports `Default` and performs no operation. */ scrollBarStyle?: ScrollBarStyle + /** + * Controls the WebView's browser-level general autofill behavior. + * + * **This option does not disable password or credit card autofill.** + * + * When set to `false`, the WebView will not automatically populate general form + * fields using previously stored data such as addresses or contact information. + * + * If not specified, this is `true` by default. + * + * ## Platform-specific + * + * - **Windows**: Supported. WebView2's autofill feature (called "Suggestions") + * may not honor `autocomplete="off"` on input elements in some cases. + * - **Linux / Android / iOS / macOS**: Unsupported and performs no operation. + * + * @since 2.11.0 + */ + generalAutofillEnabled?: boolean } export { Webview, getCurrentWebview, getAllWebviews } From 9922f282560788fb899339e73f9e3654f1fe56f9 Mon Sep 17 00:00:00 2001 From: "renovate[bot]" <29139614+renovate[bot]@users.noreply.github.com> Date: Thu, 23 Apr 2026 23:34:30 +0800 Subject: [PATCH 78/95] chore(deps): update rust crate tray-icon to 0.22 (#15203) * chore(deps): update rust crate tray-icon to 0.22 * Add change file * Update lock --------- Co-authored-by: renovate[bot] <29139614+renovate[bot]@users.noreply.github.com> Co-authored-by: Tony --- .changes/tray-icon-0.22.md | 5 +++++ Cargo.lock | 43 +++++++++++++++++++++++++------------- crates/tauri/Cargo.toml | 2 +- 3 files changed, 34 insertions(+), 16 deletions(-) create mode 100644 .changes/tray-icon-0.22.md diff --git a/.changes/tray-icon-0.22.md b/.changes/tray-icon-0.22.md new file mode 100644 index 000000000000..e91e419abd0a --- /dev/null +++ b/.changes/tray-icon-0.22.md @@ -0,0 +1,5 @@ +--- +tauri: minor:deps +--- + +Updated `tray-icon` to v0.22 diff --git a/Cargo.lock b/Cargo.lock index 4f857d95cedc..3f2544cd1385 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -2021,7 +2021,7 @@ dependencies = [ "libc", "option-ext", "redox_users 0.5.0", - "windows-sys 0.60.2", + "windows-sys 0.59.0", ] [[package]] @@ -3561,7 +3561,7 @@ source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "3e795dff5605e0f04bff85ca41b51a96b83e80b281e96231bcaaf1ac35103371" dependencies = [ "byteorder", - "png", + "png 0.17.16", ] [[package]] @@ -3747,7 +3747,7 @@ dependencies = [ "gif", "image-webp", "num-traits", - "png", + "png 0.17.16", "qoi", "ravif", "rayon", @@ -4738,9 +4738,9 @@ dependencies = [ [[package]] name = "muda" -version = "0.17.1" +version = "0.17.2" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "01c1738382f66ed56b3b9c8119e794a2e23148ac8ea214eda86622d4cb9d415a" +checksum = "7c9fec5a4e89860383d778d10563a605838f8f0b2f9303868937e5ff32e86177" dependencies = [ "crossbeam-channel", "dpi", @@ -4752,7 +4752,7 @@ dependencies = [ "objc2-core-foundation", "objc2-foundation 0.3.0", "once_cell", - "png", + "png 0.17.16", "serde", "thiserror 2.0.12", "windows-sys 0.60.2", @@ -5520,7 +5520,7 @@ source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "7d8fae84b431384b68627d0f9b3b1245fcf9f46f6c0e3dc902e9dce64edd1967" dependencies = [ "libc", - "windows-sys 0.60.2", + "windows-sys 0.45.0", ] [[package]] @@ -6278,6 +6278,19 @@ dependencies = [ "miniz_oxide", ] +[[package]] +name = "png" +version = "0.18.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "60769b8b31b2a9f263dae2776c37b1b28ae246943cf719eb6946a1db05128a61" +dependencies = [ + "bitflags 2.7.0", + "crc32fast", + "fdeflate", + "flate2", + "miniz_oxide", +] + [[package]] name = "polyval" version = "0.6.2" @@ -7369,7 +7382,7 @@ dependencies = [ "security-framework 3.5.1", "security-framework-sys", "webpki-root-certs", - "windows-sys 0.60.2", + "windows-sys 0.52.0", ] [[package]] @@ -8957,7 +8970,7 @@ dependencies = [ "ico", "json-patch", "plist", - "png", + "png 0.17.16", "proc-macro2", "quote", "semver", @@ -9011,7 +9024,7 @@ source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "03b7eb4d0d43724ba9ba6a6717420ee68aee377816a3edbb45db8c18862b1431" dependencies = [ "byteorder", - "png", + "png 0.17.16", ] [[package]] @@ -9396,7 +9409,7 @@ dependencies = [ "bytemuck", "cfg-if", "log", - "png", + "png 0.17.16", "tiny-skia-path", ] @@ -9775,9 +9788,9 @@ dependencies = [ [[package]] name = "tray-icon" -version = "0.21.0" +version = "0.22.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "2da75ec677957aa21f6e0b361df0daab972f13a5bee3606de0638fd4ee1c666a" +checksum = "7f9eb1da86bd0ab8931fad00650d2ba7473260c5bab06d6f24d04339edb88faa" dependencies = [ "crossbeam-channel", "dirs 6.0.0", @@ -9789,10 +9802,10 @@ dependencies = [ "objc2-core-graphics", "objc2-foundation 0.3.0", "once_cell", - "png", + "png 0.18.1", "serde", "thiserror 2.0.12", - "windows-sys 0.59.0", + "windows-sys 0.60.2", ] [[package]] diff --git a/crates/tauri/Cargo.toml b/crates/tauri/Cargo.toml index 874b986aaac1..0c9a9665c597 100644 --- a/crates/tauri/Cargo.toml +++ b/crates/tauri/Cargo.toml @@ -90,7 +90,7 @@ muda = { version = "0.17", default-features = false, features = [ "serde", "gtk", ] } -tray-icon = { version = "0.21", default-features = false, features = [ +tray-icon = { version = "0.22", default-features = false, features = [ "serde", ], optional = true } From 4a146b368213428139e26f1b4dfec33a437a77a5 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Pascal=20Andr=C3=A9?= Date: Thu, 23 Apr 2026 18:40:59 +0200 Subject: [PATCH 79/95] fix(tauri-build): set Windows FileVersion/ProductVersion strings from tauri config (#15288) --- .changes/windows-versioninfo-strings.md | 5 +++++ crates/tauri-build/src/lib.rs | 2 ++ 2 files changed, 7 insertions(+) create mode 100644 .changes/windows-versioninfo-strings.md diff --git a/.changes/windows-versioninfo-strings.md b/.changes/windows-versioninfo-strings.md new file mode 100644 index 000000000000..ea0e772b0df6 --- /dev/null +++ b/.changes/windows-versioninfo-strings.md @@ -0,0 +1,5 @@ +--- +"tauri-build": "patch:bug" +--- + +Set the correct Windows `FileVersion` and `ProductVersion` string values using the version from the Tauri config. diff --git a/crates/tauri-build/src/lib.rs b/crates/tauri-build/src/lib.rs index cdf44f50edc3..7ce48744f0b6 100644 --- a/crates/tauri-build/src/lib.rs +++ b/crates/tauri-build/src/lib.rs @@ -634,6 +634,8 @@ pub fn try_build(attributes: Attributes) -> Result<()> { let version = (v.major << 48) | (v.minor << 32) | (v.patch << 16); res.set_version_info(VersionInfo::FILEVERSION, version); res.set_version_info(VersionInfo::PRODUCTVERSION, version); + res.set("FileVersion", version_str); + res.set("ProductVersion", version_str); } } From 1a486fa58ed3c30c051af64893c16fc3c4726e16 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Pascal=20Andr=C3=A9?= Date: Mon, 27 Apr 2026 09:20:47 +0200 Subject: [PATCH 80/95] fix(tauri-build): preserve numeric semver build metadata in Windows FILEVERSION (#15289) * fix(tauri-build): preserve numeric semver build metadata in Windows FILEVERSION * refactor(tauri-build): clarify PRODUCTVERSION naming * refactor(tauri-build): align fixed Windows version fields * refactor(tauri-build): rename Windows version helper * style(tauri-build): move winres helper near tests --- .../windows-fileversion-build-metadata.md | 5 ++ crates/tauri-build/src/lib.rs | 53 ++++++++++++++++++- 2 files changed, 57 insertions(+), 1 deletion(-) create mode 100644 .changes/windows-fileversion-build-metadata.md diff --git a/.changes/windows-fileversion-build-metadata.md b/.changes/windows-fileversion-build-metadata.md new file mode 100644 index 000000000000..a3fdc2007f08 --- /dev/null +++ b/.changes/windows-fileversion-build-metadata.md @@ -0,0 +1,5 @@ +--- +"tauri-build": "patch:enhance" +--- + +Preserve a numeric semver build identifier such as `1.2.3+42` in the 4th segment of the Windows `FILEVERSION` fixed field when it fits in the Windows version format. diff --git a/crates/tauri-build/src/lib.rs b/crates/tauri-build/src/lib.rs index 7ce48744f0b6..6c171a3005f9 100644 --- a/crates/tauri-build/src/lib.rs +++ b/crates/tauri-build/src/lib.rs @@ -631,7 +631,7 @@ pub fn try_build(attributes: Attributes) -> Result<()> { if let Some(version_str) = &config.version { if let Ok(v) = Version::parse(version_str) { - let version = (v.major << 48) | (v.minor << 32) | (v.patch << 16); + let version = to_winres_version(&v); res.set_version_info(VersionInfo::FILEVERSION, version); res.set_version_info(VersionInfo::PRODUCTVERSION, version); res.set("FileVersion", version_str); @@ -719,3 +719,54 @@ pub fn try_build(attributes: Attributes) -> Result<()> { Ok(()) } + +fn to_winres_version(v: &semver::Version) -> u64 { + let build = v.build.parse::().map(u64::from).unwrap_or(0); + + (v.major << 48) | (v.minor << 32) | (v.patch << 16) | build +} + +#[cfg(test)] +mod tests { + use semver::Version; + + #[test] + fn version_uses_numeric_build_metadata() { + let version = Version::parse("1.2.3+42").unwrap(); + + assert_eq!( + crate::to_winres_version(&version), + (1 << 48) | (2 << 32) | (3 << 16) | 42 + ); + } + + #[test] + fn version_ignores_non_numeric_composite_build_metadata() { + let version = Version::parse("1.2.3+42.sha").unwrap(); + + assert_eq!( + crate::to_winres_version(&version), + (1 << 48) | (2 << 32) | (3 << 16) + ); + } + + #[test] + fn version_ignores_non_numeric_build_metadata() { + let version = Version::parse("1.2.3+abc").unwrap(); + + assert_eq!( + crate::to_winres_version(&version), + (1 << 48) | (2 << 32) | (3 << 16) + ); + } + + #[test] + fn version_ignores_build_metadata_that_does_not_fit_in_u16() { + let version = Version::parse("1.2.3+70000").unwrap(); + + assert_eq!( + crate::to_winres_version(&version), + (1 << 48) | (2 << 32) | (3 << 16) + ); + } +} From c9842f5ede821053ca217ae4a854aa1bbdc0238f Mon Sep 17 00:00:00 2001 From: "renovate[bot]" <29139614+renovate[bot]@users.noreply.github.com> Date: Wed, 29 Apr 2026 12:28:01 +0800 Subject: [PATCH 81/95] chore(deps): update dependency rollup to v4.60.2 (#15192) * chore(deps): update dependency rollup to v4.60.2 * fix audit --- packages/api/package.json | 2 +- pnpm-lock.yaml | 240 +++++++++++++++++++------------------- 2 files changed, 121 insertions(+), 121 deletions(-) diff --git a/packages/api/package.json b/packages/api/package.json index fe0273f36493..9018a79bf4cf 100644 --- a/packages/api/package.json +++ b/packages/api/package.json @@ -55,7 +55,7 @@ "eslint-plugin-security": "4.0.0", "fast-glob": "3.3.3", "globals": "^17.4.0", - "rollup": "4.60.0", + "rollup": "4.60.2", "tslib": "^2.8.1", "typescript": "^6.0.0", "typescript-eslint": "^8.58.2" diff --git a/pnpm-lock.yaml b/pnpm-lock.yaml index 248ebe420e15..a8e4b4fb205c 100644 --- a/pnpm-lock.yaml +++ b/pnpm-lock.yaml @@ -57,10 +57,10 @@ importers: version: 10.0.1(eslint@10.0.2(jiti@2.6.1)) '@rollup/plugin-terser': specifier: 1.0.0 - version: 1.0.0(rollup@4.60.0) + version: 1.0.0(rollup@4.60.2) '@rollup/plugin-typescript': specifier: 12.3.0 - version: 12.3.0(rollup@4.60.0)(tslib@2.8.1)(typescript@6.0.2) + version: 12.3.0(rollup@4.60.2)(tslib@2.8.1)(typescript@6.0.2) '@types/eslint': specifier: ^9.6.1 version: 9.6.1 @@ -83,8 +83,8 @@ importers: specifier: ^17.4.0 version: 17.4.0 rollup: - specifier: 4.60.0 - version: 4.60.0 + specifier: 4.60.2 + version: 4.60.2 tslib: specifier: ^2.8.1 version: 2.8.1 @@ -1400,141 +1400,141 @@ packages: rollup: optional: true - '@rollup/rollup-android-arm-eabi@4.60.0': - resolution: {integrity: sha512-WOhNW9K8bR3kf4zLxbfg6Pxu2ybOUbB2AjMDHSQx86LIF4rH4Ft7vmMwNt0loO0eonglSNy4cpD3MKXXKQu0/A==} + '@rollup/rollup-android-arm-eabi@4.60.2': + resolution: {integrity: sha512-dnlp69efPPg6Uaw2dVqzWRfAWRnYVb1XJ8CyyhIbZeaq4CA5/mLeZ1IEt9QqQxmbdvagjLIm2ZL8BxXv5lH4Yw==} cpu: [arm] os: [android] - '@rollup/rollup-android-arm64@4.60.0': - resolution: {integrity: sha512-u6JHLll5QKRvjciE78bQXDmqRqNs5M/3GVqZeMwvmjaNODJih/WIrJlFVEihvV0MiYFmd+ZyPr9wxOVbPAG2Iw==} + '@rollup/rollup-android-arm64@4.60.2': + resolution: {integrity: sha512-OqZTwDRDchGRHHm/hwLOL7uVPB9aUvI0am/eQuWMNyFHf5PSEQmyEeYYheA0EPPKUO/l0uigCp+iaTjoLjVoHg==} cpu: [arm64] os: [android] - '@rollup/rollup-darwin-arm64@4.60.0': - resolution: {integrity: sha512-qEF7CsKKzSRc20Ciu2Zw1wRrBz4g56F7r/vRwY430UPp/nt1x21Q/fpJ9N5l47WWvJlkNCPJz3QRVw008fi7yA==} + '@rollup/rollup-darwin-arm64@4.60.2': + resolution: {integrity: sha512-UwRE7CGpvSVEQS8gUMBe1uADWjNnVgP3Iusyda1nSRwNDCsRjnGc7w6El6WLQsXmZTbLZx9cecegumcitNfpmA==} cpu: [arm64] os: [darwin] - '@rollup/rollup-darwin-x64@4.60.0': - resolution: {integrity: sha512-WADYozJ4QCnXCH4wPB+3FuGmDPoFseVCUrANmA5LWwGmC6FL14BWC7pcq+FstOZv3baGX65tZ378uT6WG8ynTw==} + '@rollup/rollup-darwin-x64@4.60.2': + resolution: {integrity: sha512-gjEtURKLCC5VXm1I+2i1u9OhxFsKAQJKTVB8WvDAHF+oZlq0GTVFOlTlO1q3AlCTE/DF32c16ESvfgqR7343/g==} cpu: [x64] os: [darwin] - '@rollup/rollup-freebsd-arm64@4.60.0': - resolution: {integrity: sha512-6b8wGHJlDrGeSE3aH5mGNHBjA0TTkxdoNHik5EkvPHCt351XnigA4pS7Wsj/Eo9Y8RBU6f35cjN9SYmCFBtzxw==} + '@rollup/rollup-freebsd-arm64@4.60.2': + resolution: {integrity: sha512-Bcl6CYDeAgE70cqZaMojOi/eK63h5Me97ZqAQoh77VPjMysA/4ORQBRGo3rRy45x4MzVlU9uZxs8Uwy7ZaKnBw==} cpu: [arm64] os: [freebsd] - '@rollup/rollup-freebsd-x64@4.60.0': - resolution: {integrity: sha512-h25Ga0t4jaylMB8M/JKAyrvvfxGRjnPQIR8lnCayyzEjEOx2EJIlIiMbhpWxDRKGKF8jbNH01NnN663dH638mA==} + '@rollup/rollup-freebsd-x64@4.60.2': + resolution: {integrity: sha512-LU+TPda3mAE2QB0/Hp5VyeKJivpC6+tlOXd1VMoXV/YFMvk/MNk5iXeBfB4MQGRWyOYVJ01625vjkr0Az98OJQ==} cpu: [x64] os: [freebsd] - '@rollup/rollup-linux-arm-gnueabihf@4.60.0': - resolution: {integrity: sha512-RzeBwv0B3qtVBWtcuABtSuCzToo2IEAIQrcyB/b2zMvBWVbjo8bZDjACUpnaafaxhTw2W+imQbP2BD1usasK4g==} + '@rollup/rollup-linux-arm-gnueabihf@4.60.2': + resolution: {integrity: sha512-2QxQrM+KQ7DAW4o22j+XZ6RKdxjLD7BOWTP0Bv0tmjdyhXSsr2Ul1oJDQqh9Zf5qOwTuTc7Ek83mOFaKnodPjg==} cpu: [arm] os: [linux] libc: [glibc] - '@rollup/rollup-linux-arm-musleabihf@4.60.0': - resolution: {integrity: sha512-Sf7zusNI2CIU1HLzuu9Tc5YGAHEZs5Lu7N1ssJG4Tkw6e0MEsN7NdjUDDfGNHy2IU+ENyWT+L2obgWiguWibWQ==} + '@rollup/rollup-linux-arm-musleabihf@4.60.2': + resolution: {integrity: sha512-TbziEu2DVsTEOPif2mKWkMeDMLoYjx95oESa9fkQQK7r/Orta0gnkcDpzwufEcAO2BLBsD7mZkXGFqEdMRRwfw==} cpu: [arm] os: [linux] libc: [musl] - '@rollup/rollup-linux-arm64-gnu@4.60.0': - resolution: {integrity: sha512-DX2x7CMcrJzsE91q7/O02IJQ5/aLkVtYFryqCjduJhUfGKG6yJV8hxaw8pZa93lLEpPTP/ohdN4wFz7yp/ry9A==} + '@rollup/rollup-linux-arm64-gnu@4.60.2': + resolution: {integrity: sha512-bO/rVDiDUuM2YfuCUwZ1t1cP+/yqjqz+Xf2VtkdppefuOFS2OSeAfgafaHNkFn0t02hEyXngZkxtGqXcXwO8Rg==} cpu: [arm64] os: [linux] libc: [glibc] - '@rollup/rollup-linux-arm64-musl@4.60.0': - resolution: {integrity: sha512-09EL+yFVbJZlhcQfShpswwRZ0Rg+z/CsSELFCnPt3iK+iqwGsI4zht3secj5vLEs957QvFFXnzAT0FFPIxSrkQ==} + '@rollup/rollup-linux-arm64-musl@4.60.2': + resolution: {integrity: sha512-hr26p7e93Rl0Za+JwW7EAnwAvKkehh12BU1Llm9Ykiibg4uIr2rbpxG9WCf56GuvidlTG9KiiQT/TXT1yAWxTA==} cpu: [arm64] os: [linux] libc: [musl] - '@rollup/rollup-linux-loong64-gnu@4.60.0': - resolution: {integrity: sha512-i9IcCMPr3EXm8EQg5jnja0Zyc1iFxJjZWlb4wr7U2Wx/GrddOuEafxRdMPRYVaXjgbhvqalp6np07hN1w9kAKw==} + '@rollup/rollup-linux-loong64-gnu@4.60.2': + resolution: {integrity: sha512-pOjB/uSIyDt+ow3k/RcLvUAOGpysT2phDn7TTUB3n75SlIgZzM6NKAqlErPhoFU+npgY3/n+2HYIQVbF70P9/A==} cpu: [loong64] os: [linux] libc: [glibc] - '@rollup/rollup-linux-loong64-musl@4.60.0': - resolution: {integrity: sha512-DGzdJK9kyJ+B78MCkWeGnpXJ91tK/iKA6HwHxF4TAlPIY7GXEvMe8hBFRgdrR9Ly4qebR/7gfUs9y2IoaVEyog==} + '@rollup/rollup-linux-loong64-musl@4.60.2': + resolution: {integrity: sha512-2/w+q8jszv9Ww1c+6uJT3OwqhdmGP2/4T17cu8WuwyUuuaCDDJ2ojdyYwZzCxx0GcsZBhzi3HmH+J5pZNXnd+Q==} cpu: [loong64] os: [linux] libc: [musl] - '@rollup/rollup-linux-ppc64-gnu@4.60.0': - resolution: {integrity: sha512-RwpnLsqC8qbS8z1H1AxBA1H6qknR4YpPR9w2XX0vo2Sz10miu57PkNcnHVaZkbqyw/kUWfKMI73jhmfi9BRMUQ==} + '@rollup/rollup-linux-ppc64-gnu@4.60.2': + resolution: {integrity: sha512-11+aL5vKheYgczxtPVVRhdptAM2H7fcDR5Gw4/bTcteuZBlH4oP9f5s9zYO9aGZvoGeBpqXI/9TZZihZ609wKw==} cpu: [ppc64] os: [linux] libc: [glibc] - '@rollup/rollup-linux-ppc64-musl@4.60.0': - resolution: {integrity: sha512-Z8pPf54Ly3aqtdWC3G4rFigZgNvd+qJlOE52fmko3KST9SoGfAdSRCwyoyG05q1HrrAblLbk1/PSIV+80/pxLg==} + '@rollup/rollup-linux-ppc64-musl@4.60.2': + resolution: {integrity: sha512-i16fokAGK46IVZuV8LIIwMdtqhin9hfYkCh8pf8iC3QU3LpwL+1FSFGej+O7l3E/AoknL6Dclh2oTdnRMpTzFQ==} cpu: [ppc64] os: [linux] libc: [musl] - '@rollup/rollup-linux-riscv64-gnu@4.60.0': - resolution: {integrity: sha512-3a3qQustp3COCGvnP4SvrMHnPQ9d1vzCakQVRTliaz8cIp/wULGjiGpbcqrkv0WrHTEp8bQD/B3HBjzujVWLOA==} + '@rollup/rollup-linux-riscv64-gnu@4.60.2': + resolution: {integrity: sha512-49FkKS6RGQoriDSK/6E2GkAsAuU5kETFCh7pG4yD/ylj9rKhTmO3elsnmBvRD4PgJPds5W2PkhC82aVwmUcJ7A==} cpu: [riscv64] os: [linux] libc: [glibc] - '@rollup/rollup-linux-riscv64-musl@4.60.0': - resolution: {integrity: sha512-pjZDsVH/1VsghMJ2/kAaxt6dL0psT6ZexQVrijczOf+PeP2BUqTHYejk3l6TlPRydggINOeNRhvpLa0AYpCWSQ==} + '@rollup/rollup-linux-riscv64-musl@4.60.2': + resolution: {integrity: sha512-mjYNkHPfGpUR00DuM1ZZIgs64Hpf4bWcz9Z41+4Q+pgDx73UwWdAYyf6EG/lRFldmdHHzgrYyge5akFUW0D3mQ==} cpu: [riscv64] os: [linux] libc: [musl] - '@rollup/rollup-linux-s390x-gnu@4.60.0': - resolution: {integrity: sha512-3ObQs0BhvPgiUVZrN7gqCSvmFuMWvWvsjG5ayJ3Lraqv+2KhOsp+pUbigqbeWqueGIsnn+09HBw27rJ+gYK4VQ==} + '@rollup/rollup-linux-s390x-gnu@4.60.2': + resolution: {integrity: sha512-ALyvJz965BQk8E9Al/JDKKDLH2kfKFLTGMlgkAbbYtZuJt9LU8DW3ZoDMCtQpXAltZxwBHevXz5u+gf0yA0YoA==} cpu: [s390x] os: [linux] libc: [glibc] - '@rollup/rollup-linux-x64-gnu@4.60.0': - resolution: {integrity: sha512-EtylprDtQPdS5rXvAayrNDYoJhIz1/vzN2fEubo3yLE7tfAw+948dO0g4M0vkTVFhKojnF+n6C8bDNe+gDRdTg==} + '@rollup/rollup-linux-x64-gnu@4.60.2': + resolution: {integrity: sha512-UQjrkIdWrKI626Du8lCQ6MJp/6V1LAo2bOK9OTu4mSn8GGXIkPXk/Vsp4bLHCd9Z9Iz2OTEaokUE90VweJgIYQ==} cpu: [x64] os: [linux] libc: [glibc] - '@rollup/rollup-linux-x64-musl@4.60.0': - resolution: {integrity: sha512-k09oiRCi/bHU9UVFqD17r3eJR9bn03TyKraCrlz5ULFJGdJGi7VOmm9jl44vOJvRJ6P7WuBi/s2A97LxxHGIdw==} + '@rollup/rollup-linux-x64-musl@4.60.2': + resolution: {integrity: sha512-bTsRGj6VlSdn/XD4CGyzMnzaBs9bsRxy79eTqTCBsA8TMIEky7qg48aPkvJvFe1HyzQ5oMZdg7AnVlWQSKLTnw==} cpu: [x64] os: [linux] libc: [musl] - '@rollup/rollup-openbsd-x64@4.60.0': - resolution: {integrity: sha512-1o/0/pIhozoSaDJoDcec+IVLbnRtQmHwPV730+AOD29lHEEo4F5BEUB24H0OBdhbBBDwIOSuf7vgg0Ywxdfiiw==} + '@rollup/rollup-openbsd-x64@4.60.2': + resolution: {integrity: sha512-6d4Z3534xitaA1FcMWP7mQPq5zGwBmGbhphh2DwaA1aNIXUu3KTOfwrWpbwI4/Gr0uANo7NTtaykFyO2hPuFLg==} cpu: [x64] os: [openbsd] - '@rollup/rollup-openharmony-arm64@4.60.0': - resolution: {integrity: sha512-pESDkos/PDzYwtyzB5p/UoNU/8fJo68vcXM9ZW2V0kjYayj1KaaUfi1NmTUTUpMn4UhU4gTuK8gIaFO4UGuMbA==} + '@rollup/rollup-openharmony-arm64@4.60.2': + resolution: {integrity: sha512-NetAg5iO2uN7eB8zE5qrZ3CSil+7IJt4WDFLcC75Ymywq1VZVD6qJ6EvNLjZ3rEm6gB7XW5JdT60c6MN35Z85Q==} cpu: [arm64] os: [openharmony] - '@rollup/rollup-win32-arm64-msvc@4.60.0': - resolution: {integrity: sha512-hj1wFStD7B1YBeYmvY+lWXZ7ey73YGPcViMShYikqKT1GtstIKQAtfUI6yrzPjAy/O7pO0VLXGmUVWXQMaYgTQ==} + '@rollup/rollup-win32-arm64-msvc@4.60.2': + resolution: {integrity: sha512-NCYhOotpgWZ5kdxCZsv6Iudx0wX8980Q/oW4pNFNihpBKsDbEA1zpkfxJGC0yugsUuyDZ7gL37dbzwhR0VI7pQ==} cpu: [arm64] os: [win32] - '@rollup/rollup-win32-ia32-msvc@4.60.0': - resolution: {integrity: sha512-SyaIPFoxmUPlNDq5EHkTbiKzmSEmq/gOYFI/3HHJ8iS/v1mbugVa7dXUzcJGQfoytp9DJFLhHH4U3/eTy2Bq4w==} + '@rollup/rollup-win32-ia32-msvc@4.60.2': + resolution: {integrity: sha512-RXsaOqXxfoUBQoOgvmmijVxJnW2IGB0eoMO7F8FAjaj0UTywUO/luSqimWBJn04WNgUkeNhh7fs7pESXajWmkg==} cpu: [ia32] os: [win32] - '@rollup/rollup-win32-x64-gnu@4.60.0': - resolution: {integrity: sha512-RdcryEfzZr+lAr5kRm2ucN9aVlCCa2QNq4hXelZxb8GG0NJSazq44Z3PCCc8wISRuCVnGs0lQJVX5Vp6fKA+IA==} + '@rollup/rollup-win32-x64-gnu@4.60.2': + resolution: {integrity: sha512-qdAzEULD+/hzObedtmV6iBpdL5TIbKVztGiK7O3/KYSf+HIzU257+MX1EXJcyIiDbMAqmbwaufcYPvyRryeZtA==} cpu: [x64] os: [win32] - '@rollup/rollup-win32-x64-msvc@4.60.0': - resolution: {integrity: sha512-PrsWNQ8BuE00O3Xsx3ALh2Df8fAj9+cvvX9AIA6o4KpATR98c9mud4XtDWVvsEuyia5U4tVSTKygawyJkjm60w==} + '@rollup/rollup-win32-x64-msvc@4.60.2': + resolution: {integrity: sha512-Nd/SgG27WoA9e+/TdK74KnHz852TLa94ovOYySo/yMPuTmpckK/jIF2jSwS3g7ELSKXK13/cVdmg1Z/DaCWKxA==} cpu: [x64] os: [win32] @@ -2329,8 +2329,8 @@ packages: pkg-types@1.3.1: resolution: {integrity: sha512-/Jm5M4RvtBFVkKWRu2BLUTNP8/M2a+UwuAX+ae4770q1qVGtfjG+WTCupoZixokjmHiry8uI+dlY8KXYV5HVVQ==} - postcss@8.5.8: - resolution: {integrity: sha512-OW/rX8O/jXnm82Ey1k44pObPtdblfiuWnrd8X7GJ7emImCOstunGbXUpp7HdBrFQX6rJzn3sPT397Wp5aCwCHg==} + postcss@8.5.12: + resolution: {integrity: sha512-W62t/Se6rA0Az3DfCL0AqJwXuKwBeYg6nOaIgzP+xZ7N5BFCI7DYi1qs6ygUYT6rvfi6t9k65UMLJC+PHZpDAA==} engines: {node: ^10 || ^12 || >=14} prelude-ls@1.2.1: @@ -2374,8 +2374,8 @@ packages: engines: {node: ^20.19.0 || >=22.12.0} hasBin: true - rollup@4.60.0: - resolution: {integrity: sha512-yqjxruMGBQJ2gG4HtjZtAfXArHomazDHoFwFFmZZl0r7Pdo7qCIXKqKHZc8yeoMgzJJ+pO6pEEHa+V7uzWlrAQ==} + rollup@4.60.2: + resolution: {integrity: sha512-J9qZyW++QK/09NyN/zeO0dG/1GdGfyp9lV8ajHnRVLfo/uFsbji5mHnDgn/qYdUHyCkM2N+8VyspgZclfAh0eQ==} engines: {node: '>=18.0.0', npm: '>=8.0.0'} hasBin: true @@ -3657,104 +3657,104 @@ snapshots: '@rolldown/pluginutils@1.0.0-rc.12': {} - '@rollup/plugin-terser@1.0.0(rollup@4.60.0)': + '@rollup/plugin-terser@1.0.0(rollup@4.60.2)': dependencies: serialize-javascript: 7.0.5 smob: 1.6.1 terser: 5.46.0 optionalDependencies: - rollup: 4.60.0 + rollup: 4.60.2 - '@rollup/plugin-typescript@12.3.0(rollup@4.60.0)(tslib@2.8.1)(typescript@6.0.2)': + '@rollup/plugin-typescript@12.3.0(rollup@4.60.2)(tslib@2.8.1)(typescript@6.0.2)': dependencies: - '@rollup/pluginutils': 5.3.0(rollup@4.60.0) + '@rollup/pluginutils': 5.3.0(rollup@4.60.2) resolve: 1.22.11 typescript: 6.0.2 optionalDependencies: - rollup: 4.60.0 + rollup: 4.60.2 tslib: 2.8.1 - '@rollup/pluginutils@5.3.0(rollup@4.60.0)': + '@rollup/pluginutils@5.3.0(rollup@4.60.2)': dependencies: '@types/estree': 1.0.8 estree-walker: 2.0.2 picomatch: 4.0.4 optionalDependencies: - rollup: 4.60.0 + rollup: 4.60.2 - '@rollup/rollup-android-arm-eabi@4.60.0': + '@rollup/rollup-android-arm-eabi@4.60.2': optional: true - '@rollup/rollup-android-arm64@4.60.0': + '@rollup/rollup-android-arm64@4.60.2': optional: true - '@rollup/rollup-darwin-arm64@4.60.0': + '@rollup/rollup-darwin-arm64@4.60.2': optional: true - '@rollup/rollup-darwin-x64@4.60.0': + '@rollup/rollup-darwin-x64@4.60.2': optional: true - '@rollup/rollup-freebsd-arm64@4.60.0': + '@rollup/rollup-freebsd-arm64@4.60.2': optional: true - '@rollup/rollup-freebsd-x64@4.60.0': + '@rollup/rollup-freebsd-x64@4.60.2': optional: true - '@rollup/rollup-linux-arm-gnueabihf@4.60.0': + '@rollup/rollup-linux-arm-gnueabihf@4.60.2': optional: true - '@rollup/rollup-linux-arm-musleabihf@4.60.0': + '@rollup/rollup-linux-arm-musleabihf@4.60.2': optional: true - '@rollup/rollup-linux-arm64-gnu@4.60.0': + '@rollup/rollup-linux-arm64-gnu@4.60.2': optional: true - '@rollup/rollup-linux-arm64-musl@4.60.0': + '@rollup/rollup-linux-arm64-musl@4.60.2': optional: true - '@rollup/rollup-linux-loong64-gnu@4.60.0': + '@rollup/rollup-linux-loong64-gnu@4.60.2': optional: true - '@rollup/rollup-linux-loong64-musl@4.60.0': + '@rollup/rollup-linux-loong64-musl@4.60.2': optional: true - '@rollup/rollup-linux-ppc64-gnu@4.60.0': + '@rollup/rollup-linux-ppc64-gnu@4.60.2': optional: true - '@rollup/rollup-linux-ppc64-musl@4.60.0': + '@rollup/rollup-linux-ppc64-musl@4.60.2': optional: true - '@rollup/rollup-linux-riscv64-gnu@4.60.0': + '@rollup/rollup-linux-riscv64-gnu@4.60.2': optional: true - '@rollup/rollup-linux-riscv64-musl@4.60.0': + '@rollup/rollup-linux-riscv64-musl@4.60.2': optional: true - '@rollup/rollup-linux-s390x-gnu@4.60.0': + '@rollup/rollup-linux-s390x-gnu@4.60.2': optional: true - '@rollup/rollup-linux-x64-gnu@4.60.0': + '@rollup/rollup-linux-x64-gnu@4.60.2': optional: true - '@rollup/rollup-linux-x64-musl@4.60.0': + '@rollup/rollup-linux-x64-musl@4.60.2': optional: true - '@rollup/rollup-openbsd-x64@4.60.0': + '@rollup/rollup-openbsd-x64@4.60.2': optional: true - '@rollup/rollup-openharmony-arm64@4.60.0': + '@rollup/rollup-openharmony-arm64@4.60.2': optional: true - '@rollup/rollup-win32-arm64-msvc@4.60.0': + '@rollup/rollup-win32-arm64-msvc@4.60.2': optional: true - '@rollup/rollup-win32-ia32-msvc@4.60.0': + '@rollup/rollup-win32-ia32-msvc@4.60.2': optional: true - '@rollup/rollup-win32-x64-gnu@4.60.0': + '@rollup/rollup-win32-x64-gnu@4.60.2': optional: true - '@rollup/rollup-win32-x64-msvc@4.60.0': + '@rollup/rollup-win32-x64-msvc@4.60.2': optional: true '@sindresorhus/is@7.2.0': {} @@ -4622,7 +4622,7 @@ snapshots: mlly: 1.8.0 pathe: 2.0.3 - postcss@8.5.8: + postcss@8.5.12: dependencies: nanoid: 3.3.11 picocolors: 1.1.1 @@ -4674,35 +4674,35 @@ snapshots: - '@emnapi/core' - '@emnapi/runtime' - rollup@4.60.0: + rollup@4.60.2: dependencies: '@types/estree': 1.0.8 optionalDependencies: - '@rollup/rollup-android-arm-eabi': 4.60.0 - '@rollup/rollup-android-arm64': 4.60.0 - '@rollup/rollup-darwin-arm64': 4.60.0 - '@rollup/rollup-darwin-x64': 4.60.0 - '@rollup/rollup-freebsd-arm64': 4.60.0 - '@rollup/rollup-freebsd-x64': 4.60.0 - '@rollup/rollup-linux-arm-gnueabihf': 4.60.0 - '@rollup/rollup-linux-arm-musleabihf': 4.60.0 - '@rollup/rollup-linux-arm64-gnu': 4.60.0 - '@rollup/rollup-linux-arm64-musl': 4.60.0 - '@rollup/rollup-linux-loong64-gnu': 4.60.0 - '@rollup/rollup-linux-loong64-musl': 4.60.0 - '@rollup/rollup-linux-ppc64-gnu': 4.60.0 - '@rollup/rollup-linux-ppc64-musl': 4.60.0 - '@rollup/rollup-linux-riscv64-gnu': 4.60.0 - '@rollup/rollup-linux-riscv64-musl': 4.60.0 - '@rollup/rollup-linux-s390x-gnu': 4.60.0 - '@rollup/rollup-linux-x64-gnu': 4.60.0 - '@rollup/rollup-linux-x64-musl': 4.60.0 - '@rollup/rollup-openbsd-x64': 4.60.0 - '@rollup/rollup-openharmony-arm64': 4.60.0 - '@rollup/rollup-win32-arm64-msvc': 4.60.0 - '@rollup/rollup-win32-ia32-msvc': 4.60.0 - '@rollup/rollup-win32-x64-gnu': 4.60.0 - '@rollup/rollup-win32-x64-msvc': 4.60.0 + '@rollup/rollup-android-arm-eabi': 4.60.2 + '@rollup/rollup-android-arm64': 4.60.2 + '@rollup/rollup-darwin-arm64': 4.60.2 + '@rollup/rollup-darwin-x64': 4.60.2 + '@rollup/rollup-freebsd-arm64': 4.60.2 + '@rollup/rollup-freebsd-x64': 4.60.2 + '@rollup/rollup-linux-arm-gnueabihf': 4.60.2 + '@rollup/rollup-linux-arm-musleabihf': 4.60.2 + '@rollup/rollup-linux-arm64-gnu': 4.60.2 + '@rollup/rollup-linux-arm64-musl': 4.60.2 + '@rollup/rollup-linux-loong64-gnu': 4.60.2 + '@rollup/rollup-linux-loong64-musl': 4.60.2 + '@rollup/rollup-linux-ppc64-gnu': 4.60.2 + '@rollup/rollup-linux-ppc64-musl': 4.60.2 + '@rollup/rollup-linux-riscv64-gnu': 4.60.2 + '@rollup/rollup-linux-riscv64-musl': 4.60.2 + '@rollup/rollup-linux-s390x-gnu': 4.60.2 + '@rollup/rollup-linux-x64-gnu': 4.60.2 + '@rollup/rollup-linux-x64-musl': 4.60.2 + '@rollup/rollup-openbsd-x64': 4.60.2 + '@rollup/rollup-openharmony-arm64': 4.60.2 + '@rollup/rollup-win32-arm64-msvc': 4.60.2 + '@rollup/rollup-win32-ia32-msvc': 4.60.2 + '@rollup/rollup-win32-x64-gnu': 4.60.2 + '@rollup/rollup-win32-x64-msvc': 4.60.2 fsevents: 2.3.3 run-parallel@1.2.0: @@ -4925,8 +4925,8 @@ snapshots: esbuild: 0.27.3 fdir: 6.5.0(picomatch@4.0.4) picomatch: 4.0.4 - postcss: 8.5.8 - rollup: 4.60.0 + postcss: 8.5.12 + rollup: 4.60.2 tinyglobby: 0.2.16 optionalDependencies: '@types/node': 24.11.0 @@ -4939,7 +4939,7 @@ snapshots: dependencies: lightningcss: 1.32.0 picomatch: 4.0.4 - postcss: 8.5.8 + postcss: 8.5.12 rolldown: 1.0.0-rc.12(@emnapi/core@1.8.1)(@emnapi/runtime@1.8.1) tinyglobby: 0.2.16 optionalDependencies: From 9782f53a1315a819d2a27f04dcca5a976d359415 Mon Sep 17 00:00:00 2001 From: KietNT <113796420+TanNhatCMS@users.noreply.github.com> Date: Wed, 29 Apr 2026 16:58:37 +0700 Subject: [PATCH 82/95] feat(nsis): add Vietnamese language support for installer. (#15218) * Create Vietnamese * Add Vietnamese language support for NSIS bundler * chore rename * Merge branch 'dev' into patch-1 * Add Vietnamese language support for NSIS installer * Merge branch 'dev' into patch-1 * Add Vietnamese language support Added support for the Vietnamese language in the project. * Update change-pr-15218.md * Merge branch 'dev' into patch-1 * Added Vietnamese translations for the NSIS installer * Merge branch 'dev' into patch-1 --- .changes/change-pr-15218.md | 7 +++++ .../windows/nsis/languages/Vietnamese.nsh | 27 +++++++++++++++++++ .../src/bundle/windows/nsis/mod.rs | 1 + 3 files changed, 35 insertions(+) create mode 100644 .changes/change-pr-15218.md create mode 100644 crates/tauri-bundler/src/bundle/windows/nsis/languages/Vietnamese.nsh diff --git a/.changes/change-pr-15218.md b/.changes/change-pr-15218.md new file mode 100644 index 000000000000..ab3b50d0dc29 --- /dev/null +++ b/.changes/change-pr-15218.md @@ -0,0 +1,7 @@ +--- +"tauri-bundler": patch:enhance +"@tauri-apps/cli": patch:enhance +"tauri-cli": patch:enhance +--- + +Added Vietnamese translations for the NSIS installer diff --git a/crates/tauri-bundler/src/bundle/windows/nsis/languages/Vietnamese.nsh b/crates/tauri-bundler/src/bundle/windows/nsis/languages/Vietnamese.nsh new file mode 100644 index 000000000000..00bd156ccf79 --- /dev/null +++ b/crates/tauri-bundler/src/bundle/windows/nsis/languages/Vietnamese.nsh @@ -0,0 +1,27 @@ +LangString addOrReinstall ${LANG_VIETNAMESE} "Thêm/Cài đặt lại các thành phần" +LangString alreadyInstalled ${LANG_VIETNAMESE} "Đã được cài đặt" +LangString alreadyInstalledLong ${LANG_VIETNAMESE} "${PRODUCTNAME} ${VERSION} đã được cài đặt. Hãy chọn thao tác bạn muốn thực hiện và nhấn Next để tiếp tục." +LangString appRunning ${LANG_VIETNAMESE} "{{product_name}} đang chạy! Vui lòng đóng ứng dụng trước rồi thử lại." +LangString appRunningOkKill ${LANG_VIETNAMESE} "{{product_name}} đang chạy!$\nNhấn OK để tắt ứng dụng" +LangString chooseMaintenanceOption ${LANG_VIETNAMESE} "Chọn thao tác bảo trì bạn muốn thực hiện." +LangString choowHowToInstall ${LANG_VIETNAMESE} "Chọn cách bạn muốn cài đặt ${PRODUCTNAME}." +LangString createDesktop ${LANG_VIETNAMESE} "Tạo biểu tượng ngoài màn hình" +LangString dontUninstall ${LANG_VIETNAMESE} "Không gỡ cài đặt" +LangString dontUninstallDowngrade ${LANG_VIETNAMESE} "Không gỡ cài đặt (Không hỗ trợ hạ cấp mà không gỡ cài đặt trong bộ cài này)" +LangString failedToKillApp ${LANG_VIETNAMESE} "Không thể tắt {{product_name}}. Vui lòng đóng ứng dụng trước rồi thử lại" +LangString installingWebview2 ${LANG_VIETNAMESE} "Đang cài đặt WebView2..." +LangString newerVersionInstalled ${LANG_VIETNAMESE} "Một phiên bản mới hơn của ${PRODUCTNAME} đã được cài đặt! Không khuyến nghị cài đặt phiên bản cũ hơn. Nếu bạn vẫn muốn cài phiên bản này, hãy gỡ phiên bản hiện tại trước. Chọn thao tác bạn muốn thực hiện và nhấn Next để tiếp tục." +LangString older ${LANG_VIETNAMESE} "cũ hơn" +LangString olderOrUnknownVersionInstalled ${LANG_VIETNAMESE} "Một phiên bản $R4 của ${PRODUCTNAME} đã được cài trên hệ thống. Khuyến nghị gỡ phiên bản hiện tại trước khi cài đặt. Chọn thao tác bạn muốn thực hiện và nhấn Next để tiếp tục." +LangString silentDowngrades ${LANG_VIETNAMESE} "Không hỗ trợ hạ cấp trong chế độ cài đặt im lặng, không thể tiếp tục. Vui lòng sử dụng trình cài đặt giao diện đồ họa.$\n" +LangString unableToUninstall ${LANG_VIETNAMESE} "Không thể gỡ cài đặt!" +LangString uninstallApp ${LANG_VIETNAMESE} "Gỡ cài đặt ${PRODUCTNAME}" +LangString uninstallBeforeInstalling ${LANG_VIETNAMESE} "Gỡ cài đặt trước khi cài đặt" +LangString unknown ${LANG_VIETNAMESE} "không xác định" +LangString webview2AbortError ${LANG_VIETNAMESE} "Cài đặt WebView2 thất bại! Ứng dụng không thể chạy nếu thiếu thành phần này. Hãy thử khởi động lại trình cài đặt." +LangString webview2DownloadError ${LANG_VIETNAMESE} "Lỗi: Tải WebView2 thất bại - $0" +LangString webview2DownloadSuccess ${LANG_VIETNAMESE} "Tải trình cài đặt WebView2 thành công" +LangString webview2Downloading ${LANG_VIETNAMESE} "Đang tải trình cài đặt WebView2..." +LangString webview2InstallError ${LANG_VIETNAMESE} "Lỗi: Cài đặt WebView2 thất bại với mã lỗi $1" +LangString webview2InstallSuccess ${LANG_VIETNAMESE} "Cài đặt WebView2 thành công" +LangString deleteAppData ${LANG_VIETNAMESE} "Xóa dữ liệu ứng dụng" diff --git a/crates/tauri-bundler/src/bundle/windows/nsis/mod.rs b/crates/tauri-bundler/src/bundle/windows/nsis/mod.rs index 85370834f80c..0ad87c188cab 100644 --- a/crates/tauri-bundler/src/bundle/windows/nsis/mod.rs +++ b/crates/tauri-bundler/src/bundle/windows/nsis/mod.rs @@ -887,6 +887,7 @@ fn get_lang_data(lang: &str) -> Option<(String, &[u8])> { "portuguese" => include_bytes!("./languages/Portuguese.nsh"), "ukrainian" => include_bytes!("./languages/Ukrainian.nsh"), "norwegian" => include_bytes!("./languages/Norwegian.nsh"), + "vietnamese" => include_bytes!("./languages/Vietnamese.nsh"), _ => return None, }; Some((path, content)) From e6ccf078d967d5bef724c972ef38062ffb771bc9 Mon Sep 17 00:00:00 2001 From: Tunglies Date: Wed, 29 Apr 2026 05:57:57 -0700 Subject: [PATCH 83/95] feat(async_runtime): enable track_caller attribute for async_runtime (#14905) * feat(async_runtime): enable track_caller attribute for async_runtime under tracing feature * fix: `track_caller` enable by default for async_runtime --------- Co-authored-by: Tony <68118705+Legend-Master@users.noreply.github.com> --- .changes/feat-async_runtime-track.md | 5 +++++ crates/tauri/src/async_runtime.rs | 13 +++++++++++++ 2 files changed, 18 insertions(+) create mode 100644 .changes/feat-async_runtime-track.md diff --git a/.changes/feat-async_runtime-track.md b/.changes/feat-async_runtime-track.md new file mode 100644 index 000000000000..7a761ccbe09d --- /dev/null +++ b/.changes/feat-async_runtime-track.md @@ -0,0 +1,5 @@ +--- +"tauri": minor:feat +--- + +Enable track_caller attribute for async_runtime to provide better location information in logs and panics. diff --git a/crates/tauri/src/async_runtime.rs b/crates/tauri/src/async_runtime.rs index 4925878ce99e..3ccc2c3bf68c 100644 --- a/crates/tauri/src/async_runtime.rs +++ b/crates/tauri/src/async_runtime.rs @@ -42,6 +42,7 @@ impl GlobalRuntime { } } + #[track_caller] fn spawn(&self, task: F) -> JoinHandle where F: Future + Send + 'static, @@ -54,6 +55,7 @@ impl GlobalRuntime { } } + #[track_caller] pub fn spawn_blocking(&self, func: F) -> JoinHandle where F: FnOnce() -> R + Send + 'static, @@ -66,6 +68,7 @@ impl GlobalRuntime { } } + #[track_caller] fn block_on(&self, task: F) -> F::Output { if let Some(r) = &self.runtime { r.block_on(task) @@ -95,6 +98,7 @@ impl Runtime { } } + #[track_caller] /// Spawns a future onto the runtime. pub fn spawn(&self, task: F) -> JoinHandle where @@ -109,6 +113,7 @@ impl Runtime { } } + #[track_caller] /// Runs the provided function on an executor dedicated to blocking operations. pub fn spawn_blocking(&self, func: F) -> JoinHandle where @@ -120,6 +125,7 @@ impl Runtime { } } + #[track_caller] /// Runs a future to completion on runtime. pub fn block_on(&self, task: F) -> F::Output { match self { @@ -177,6 +183,7 @@ impl RuntimeHandle { h } + #[track_caller] /// Runs the provided function on an executor dedicated to blocking operations. pub fn spawn_blocking(&self, func: F) -> JoinHandle where @@ -188,6 +195,7 @@ impl RuntimeHandle { } } + #[track_caller] /// Spawns a future onto the runtime. pub fn spawn(&self, task: F) -> JoinHandle where @@ -202,6 +210,7 @@ impl RuntimeHandle { } } + #[track_caller] /// Runs a future to completion on runtime. pub fn block_on(&self, task: F) -> F::Output { match self { @@ -258,12 +267,14 @@ pub fn handle() -> RuntimeHandle { runtime.handle() } +#[track_caller] /// Runs a future to completion on runtime. pub fn block_on(task: F) -> F::Output { let runtime = RUNTIME.get_or_init(default_runtime); runtime.block_on(task) } +#[track_caller] /// Spawns a future onto the runtime. pub fn spawn(task: F) -> JoinHandle where @@ -274,6 +285,7 @@ where runtime.spawn(task) } +#[track_caller] /// Runs the provided function on an executor dedicated to blocking operations. pub fn spawn_blocking(func: F) -> JoinHandle where @@ -284,6 +296,7 @@ where runtime.spawn_blocking(func) } +#[track_caller] #[allow(dead_code)] pub(crate) fn safe_block_on(task: F) -> F::Output where From 2316afcf88f2f13f253bedced7ff25a22cdc62a3 Mon Sep 17 00:00:00 2001 From: Yonatan <145396871+ykogan-discord@users.noreply.github.com> Date: Wed, 29 Apr 2026 05:58:31 -0700 Subject: [PATCH 84/95] feat: Add support for setting icon & template at same time (#14357) * [macos] Add support for setting icon & template at same time Calling set_icon and then set_icon_as_template in sequence cause a flicker as they both run on the main thread and update the UI. This exposes a single function to do both at once, preventing the flicker. * Format * Update changed.md --------- Co-authored-by: Fabian-Lars <30730186+FabianLars@users.noreply.github.com> --- .changes/changed.md | 6 ++++ crates/tauri/build.rs | 1 + .../tray/autogenerated/reference.md | 27 ++++++++++++++++ crates/tauri/scripts/bundle.global.js | 2 +- crates/tauri/src/tray/mod.rs | 32 +++++++++++++++++++ crates/tauri/src/tray/plugin.rs | 19 +++++++++++ packages/api/src/tray.ts | 25 +++++++++++++++ 7 files changed, 111 insertions(+), 1 deletion(-) create mode 100644 .changes/changed.md diff --git a/.changes/changed.md b/.changes/changed.md new file mode 100644 index 000000000000..df4743908869 --- /dev/null +++ b/.changes/changed.md @@ -0,0 +1,6 @@ +--- +'tauri': 'minor:feat' +'@tauri-apps/api': 'minor:feat' +--- + +Add macos support for setting the icon and icon template state in the same step of the main thread, to prevent flickering. diff --git a/crates/tauri/build.rs b/crates/tauri/build.rs index f2efb35cf1e2..9c21776ee48d 100644 --- a/crates/tauri/build.rs +++ b/crates/tauri/build.rs @@ -222,6 +222,7 @@ const PLUGINS: &[(&str, &[(&str, bool)])] = &[ ("set_visible", true), ("set_temp_dir_path", true), ("set_icon_as_template", true), + ("set_icon_with_as_template", true), ("set_show_menu_on_left_click", true), ], ), diff --git a/crates/tauri/permissions/tray/autogenerated/reference.md b/crates/tauri/permissions/tray/autogenerated/reference.md index 6ea38e1c9af4..341858892145 100644 --- a/crates/tauri/permissions/tray/autogenerated/reference.md +++ b/crates/tauri/permissions/tray/autogenerated/reference.md @@ -14,6 +14,7 @@ Default permissions for the plugin, which enables all commands. - `allow-set-visible` - `allow-set-temp-dir-path` - `allow-set-icon-as-template` +- `allow-set-icon-with-as-template` - `allow-set-show-menu-on-left-click` ## Permission Table @@ -158,6 +159,32 @@ Denies the set_icon_as_template command without any pre-configured scope. +`core:tray:allow-set-icon-with-as-template` + + + + +Enables the set_icon_with_as_template command without any pre-configured scope. + + + + + + + +`core:tray:deny-set-icon-with-as-template` + + + + +Denies the set_icon_with_as_template command without any pre-configured scope. + + + + + + + `core:tray:allow-set-menu` diff --git a/crates/tauri/scripts/bundle.global.js b/crates/tauri/scripts/bundle.global.js index 33d685365b4d..c56bb9c63ca7 100644 --- a/crates/tauri/scripts/bundle.global.js +++ b/crates/tauri/scripts/bundle.global.js @@ -1 +1 @@ -var __TAURI_IIFE__=function(e){"use strict";function n(e,n,t,i){if("a"===t&&!i)throw new TypeError("Private accessor was defined without a getter");if("function"==typeof n?e!==n||!i:!n.has(e))throw new TypeError("Cannot read private member from an object whose class did not declare it");return"m"===t?i:"a"===t?i.call(e):i?i.value:n.get(e)}function t(e,n,t,i,r){if("m"===i)throw new TypeError("Private method is not writable");if("a"===i&&!r)throw new TypeError("Private accessor was defined without a setter");if("function"==typeof n?e!==n||!r:!n.has(e))throw new TypeError("Cannot write private member to an object whose class did not declare it");return"a"===i?r.call(e,t):r?r.value=t:n.set(e,t),t}var i,r,s,a,l;"function"==typeof SuppressedError&&SuppressedError;const o="__TAURI_TO_IPC_KEY__";function u(e,n=!1){return window.__TAURI_INTERNALS__.transformCallback(e,n)}class c{constructor(e){i.set(this,void 0),r.set(this,0),s.set(this,[]),a.set(this,void 0),t(this,i,e||(()=>{}),"f"),this.id=u(e=>{const l=e.index;if("end"in e)return void(l==n(this,r,"f")?this.cleanupCallback():t(this,a,l,"f"));const o=e.message;if(l==n(this,r,"f")){for(n(this,i,"f").call(this,o),t(this,r,n(this,r,"f")+1,"f");n(this,r,"f")in n(this,s,"f");){const e=n(this,s,"f")[n(this,r,"f")];n(this,i,"f").call(this,e),delete n(this,s,"f")[n(this,r,"f")],t(this,r,n(this,r,"f")+1,"f")}n(this,r,"f")===n(this,a,"f")&&this.cleanupCallback()}else n(this,s,"f")[l]=o})}cleanupCallback(){window.__TAURI_INTERNALS__.unregisterCallback(this.id)}set onmessage(e){t(this,i,e,"f")}get onmessage(){return n(this,i,"f")}[(i=new WeakMap,r=new WeakMap,s=new WeakMap,a=new WeakMap,o)](){return`__CHANNEL__:${this.id}`}toJSON(){return this[o]()}}class d{constructor(e,n,t){this.plugin=e,this.event=n,this.channelId=t}async unregister(){return h(`plugin:${this.plugin}|remove_listener`,{event:this.event,channelId:this.channelId})}}async function p(e,n,t){const i=new c(t);try{return await h(`plugin:${e}|register_listener`,{event:n,handler:i}),new d(e,n,i.id)}catch{return await h(`plugin:${e}|registerListener`,{event:n,handler:i}),new d(e,n,i.id)}}async function h(e,n={},t){return window.__TAURI_INTERNALS__.invoke(e,n,t)}class w{get rid(){return n(this,l,"f")}constructor(e){l.set(this,void 0),t(this,l,e,"f")}async close(){return h("plugin:resources|close",{rid:this.rid})}}l=new WeakMap;var _=Object.freeze({__proto__:null,Channel:c,PluginListener:d,Resource:w,SERIALIZE_TO_IPC_FN:o,addPluginListener:p,checkPermissions:async function(e){return h(`plugin:${e}|check_permissions`)},convertFileSrc:function(e,n="asset"){return window.__TAURI_INTERNALS__.convertFileSrc(e,n)},invoke:h,isTauri:function(){return!!(globalThis||window).isTauri},requestPermissions:async function(e){return h(`plugin:${e}|request_permissions`)},transformCallback:u});class y extends w{constructor(e){super(e)}static async new(e,n,t){return h("plugin:image|new",{rgba:g(e),width:n,height:t}).then(e=>new y(e))}static async fromBytes(e){return h("plugin:image|from_bytes",{bytes:g(e)}).then(e=>new y(e))}static async fromPath(e){return h("plugin:image|from_path",{path:e}).then(e=>new y(e))}async rgba(){return h("plugin:image|rgba",{rid:this.rid}).then(e=>new Uint8Array(e))}async size(){return h("plugin:image|size",{rid:this.rid})}}function g(e){return null==e?null:"string"==typeof e?e:e instanceof y?e.rid:e}var b,m=Object.freeze({__proto__:null,Image:y,transformImage:g});!function(e){e.Nsis="nsis",e.Msi="msi",e.Deb="deb",e.Rpm="rpm",e.AppImage="appimage",e.App="app"}(b||(b={}));var f=Object.freeze({__proto__:null,get BundleType(){return b},defaultWindowIcon:async function(){return h("plugin:app|default_window_icon").then(e=>e?new y(e):null)},fetchDataStoreIdentifiers:async function(){return h("plugin:app|fetch_data_store_identifiers")},getBundleType:async function(){return h("plugin:app|bundle_type")},getIdentifier:async function(){return h("plugin:app|identifier")},getName:async function(){return h("plugin:app|name")},getTauriVersion:async function(){return h("plugin:app|tauri_version")},getVersion:async function(){return h("plugin:app|version")},hide:async function(){return h("plugin:app|app_hide")},onBackButtonPress:async function(e){return p("app","back-button",e)},removeDataStore:async function(e){return h("plugin:app|remove_data_store",{uuid:e})},setDockVisibility:async function(e){return h("plugin:app|set_dock_visibility",{visible:e})},setTheme:async function(e){return h("plugin:app|set_app_theme",{theme:e})},show:async function(){return h("plugin:app|app_show")},supportsMultipleWindows:async function(){return h("plugin:app|supports_multiple_windows")}});class v{constructor(...e){this.type="Logical",1===e.length?"Logical"in e[0]?(this.width=e[0].Logical.width,this.height=e[0].Logical.height):(this.width=e[0].width,this.height=e[0].height):(this.width=e[0],this.height=e[1])}toPhysical(e){return new k(this.width*e,this.height*e)}[o](){return{width:this.width,height:this.height}}toJSON(){return this[o]()}}class k{constructor(...e){this.type="Physical",1===e.length?"Physical"in e[0]?(this.width=e[0].Physical.width,this.height=e[0].Physical.height):(this.width=e[0].width,this.height=e[0].height):(this.width=e[0],this.height=e[1])}toLogical(e){return new v(this.width/e,this.height/e)}[o](){return{width:this.width,height:this.height}}toJSON(){return this[o]()}}class A{constructor(e){this.size=e}toLogical(e){return this.size instanceof v?this.size:this.size.toLogical(e)}toPhysical(e){return this.size instanceof k?this.size:this.size.toPhysical(e)}[o](){return{[`${this.size.type}`]:{width:this.size.width,height:this.size.height}}}toJSON(){return this[o]()}}class T{constructor(...e){this.type="Logical",1===e.length?"Logical"in e[0]?(this.x=e[0].Logical.x,this.y=e[0].Logical.y):(this.x=e[0].x,this.y=e[0].y):(this.x=e[0],this.y=e[1])}toPhysical(e){return new I(this.x*e,this.y*e)}[o](){return{x:this.x,y:this.y}}toJSON(){return this[o]()}}class I{constructor(...e){this.type="Physical",1===e.length?"Physical"in e[0]?(this.x=e[0].Physical.x,this.y=e[0].Physical.y):(this.x=e[0].x,this.y=e[0].y):(this.x=e[0],this.y=e[1])}toLogical(e){return new T(this.x/e,this.y/e)}[o](){return{x:this.x,y:this.y}}toJSON(){return this[o]()}}class E{constructor(e){this.position=e}toLogical(e){return this.position instanceof T?this.position:this.position.toLogical(e)}toPhysical(e){return this.position instanceof I?this.position:this.position.toPhysical(e)}[o](){return{[`${this.position.type}`]:{x:this.position.x,y:this.position.y}}}toJSON(){return this[o]()}}var R,D=Object.freeze({__proto__:null,LogicalPosition:T,LogicalSize:v,PhysicalPosition:I,PhysicalSize:k,Position:E,Size:A});async function S(e,n){window.__TAURI_EVENT_PLUGIN_INTERNALS__.unregisterListener(e,n),await h("plugin:event|unlisten",{event:e,eventId:n})}async function N(e,n,t){var i;const r="string"==typeof(null==t?void 0:t.target)?{kind:"AnyLabel",label:t.target}:null!==(i=null==t?void 0:t.target)&&void 0!==i?i:{kind:"Any"};return h("plugin:event|listen",{event:e,target:r,handler:u(n)}).then(n=>async()=>S(e,n))}async function L(e,n,t){return N(e,t=>{S(e,t.id),n(t)},t)}async function C(e,n){await h("plugin:event|emit",{event:e,payload:n})}async function x(e,n,t){const i="string"==typeof e?{kind:"AnyLabel",label:e}:e;await h("plugin:event|emit_to",{target:i,event:n,payload:t})}!function(e){e.WINDOW_RESIZED="tauri://resize",e.WINDOW_MOVED="tauri://move",e.WINDOW_CLOSE_REQUESTED="tauri://close-requested",e.WINDOW_DESTROYED="tauri://destroyed",e.WINDOW_FOCUS="tauri://focus",e.WINDOW_BLUR="tauri://blur",e.WINDOW_SCALE_FACTOR_CHANGED="tauri://scale-change",e.WINDOW_THEME_CHANGED="tauri://theme-changed",e.WINDOW_CREATED="tauri://window-created",e.WEBVIEW_CREATED="tauri://webview-created",e.DRAG_ENTER="tauri://drag-enter",e.DRAG_OVER="tauri://drag-over",e.DRAG_DROP="tauri://drag-drop",e.DRAG_LEAVE="tauri://drag-leave"}(R||(R={}));var P,z,W,O=Object.freeze({__proto__:null,get TauriEvent(){return R},emit:C,emitTo:x,listen:N,once:L});function U(e){var n;if("items"in e)e.items=null===(n=e.items)||void 0===n?void 0:n.map(e=>"rid"in e?e:U(e));else if("action"in e&&e.action){const n=new c;return n.onmessage=e.action,delete e.action,{...e,handler:n}}return e}async function F(e,n){const t=new c;if(n&&"object"==typeof n&&("action"in n&&n.action&&(t.onmessage=n.action,delete n.action),"item"in n&&n.item&&"object"==typeof n.item&&"About"in n.item&&n.item.About&&"object"==typeof n.item.About&&"icon"in n.item.About&&n.item.About.icon&&(n.item.About.icon=g(n.item.About.icon)),"icon"in n&&n.icon&&(n.icon=g(n.icon)),"items"in n&&n.items)){function i(e){var n;return"rid"in e?[e.rid,e.kind]:("item"in e&&"object"==typeof e.item&&(null===(n=e.item.About)||void 0===n?void 0:n.icon)&&(e.item.About.icon=g(e.item.About.icon)),"icon"in e&&e.icon&&(e.icon=g(e.icon)),"items"in e&&e.items&&(e.items=e.items.map(i)),U(e))}n.items=n.items.map(i)}return h("plugin:menu|new",{kind:e,options:n,handler:t})}class M extends w{get id(){return n(this,P,"f")}get kind(){return n(this,z,"f")}constructor(e,n,i){super(e),P.set(this,void 0),z.set(this,void 0),t(this,P,n,"f"),t(this,z,i,"f")}}P=new WeakMap,z=new WeakMap;class B extends M{constructor(e,n){super(e,n,"MenuItem")}static async new(e){return F("MenuItem",e).then(([e,n])=>new B(e,n))}async text(){return h("plugin:menu|text",{rid:this.rid,kind:this.kind})}async setText(e){return h("plugin:menu|set_text",{rid:this.rid,kind:this.kind,text:e})}async isEnabled(){return h("plugin:menu|is_enabled",{rid:this.rid,kind:this.kind})}async setEnabled(e){return h("plugin:menu|set_enabled",{rid:this.rid,kind:this.kind,enabled:e})}async setAccelerator(e){return h("plugin:menu|set_accelerator",{rid:this.rid,kind:this.kind,accelerator:e})}}class V extends M{constructor(e,n){super(e,n,"Check")}static async new(e){return F("Check",e).then(([e,n])=>new V(e,n))}async text(){return h("plugin:menu|text",{rid:this.rid,kind:this.kind})}async setText(e){return h("plugin:menu|set_text",{rid:this.rid,kind:this.kind,text:e})}async isEnabled(){return h("plugin:menu|is_enabled",{rid:this.rid,kind:this.kind})}async setEnabled(e){return h("plugin:menu|set_enabled",{rid:this.rid,kind:this.kind,enabled:e})}async setAccelerator(e){return h("plugin:menu|set_accelerator",{rid:this.rid,kind:this.kind,accelerator:e})}async isChecked(){return h("plugin:menu|is_checked",{rid:this.rid})}async setChecked(e){return h("plugin:menu|set_checked",{rid:this.rid,checked:e})}}!function(e){e.Add="Add",e.Advanced="Advanced",e.Bluetooth="Bluetooth",e.Bookmarks="Bookmarks",e.Caution="Caution",e.ColorPanel="ColorPanel",e.ColumnView="ColumnView",e.Computer="Computer",e.EnterFullScreen="EnterFullScreen",e.Everyone="Everyone",e.ExitFullScreen="ExitFullScreen",e.FlowView="FlowView",e.Folder="Folder",e.FolderBurnable="FolderBurnable",e.FolderSmart="FolderSmart",e.FollowLinkFreestanding="FollowLinkFreestanding",e.FontPanel="FontPanel",e.GoLeft="GoLeft",e.GoRight="GoRight",e.Home="Home",e.IChatTheater="IChatTheater",e.IconView="IconView",e.Info="Info",e.InvalidDataFreestanding="InvalidDataFreestanding",e.LeftFacingTriangle="LeftFacingTriangle",e.ListView="ListView",e.LockLocked="LockLocked",e.LockUnlocked="LockUnlocked",e.MenuMixedState="MenuMixedState",e.MenuOnState="MenuOnState",e.MobileMe="MobileMe",e.MultipleDocuments="MultipleDocuments",e.Network="Network",e.Path="Path",e.PreferencesGeneral="PreferencesGeneral",e.QuickLook="QuickLook",e.RefreshFreestanding="RefreshFreestanding",e.Refresh="Refresh",e.Remove="Remove",e.RevealFreestanding="RevealFreestanding",e.RightFacingTriangle="RightFacingTriangle",e.Share="Share",e.Slideshow="Slideshow",e.SmartBadge="SmartBadge",e.StatusAvailable="StatusAvailable",e.StatusNone="StatusNone",e.StatusPartiallyAvailable="StatusPartiallyAvailable",e.StatusUnavailable="StatusUnavailable",e.StopProgressFreestanding="StopProgressFreestanding",e.StopProgress="StopProgress",e.TrashEmpty="TrashEmpty",e.TrashFull="TrashFull",e.User="User",e.UserAccounts="UserAccounts",e.UserGroup="UserGroup",e.UserGuest="UserGuest"}(W||(W={}));class G extends M{constructor(e,n){super(e,n,"Icon")}static async new(e){return F("Icon",e).then(([e,n])=>new G(e,n))}async text(){return h("plugin:menu|text",{rid:this.rid,kind:this.kind})}async setText(e){return h("plugin:menu|set_text",{rid:this.rid,kind:this.kind,text:e})}async isEnabled(){return h("plugin:menu|is_enabled",{rid:this.rid,kind:this.kind})}async setEnabled(e){return h("plugin:menu|set_enabled",{rid:this.rid,kind:this.kind,enabled:e})}async setAccelerator(e){return h("plugin:menu|set_accelerator",{rid:this.rid,kind:this.kind,accelerator:e})}async setIcon(e){return h("plugin:menu|set_icon",{rid:this.rid,kind:this.kind,icon:g(e)})}}class j extends M{constructor(e,n){super(e,n,"Predefined")}static async new(e){return F("Predefined",e).then(([e,n])=>new j(e,n))}async text(){return h("plugin:menu|text",{rid:this.rid,kind:this.kind})}async setText(e){return h("plugin:menu|set_text",{rid:this.rid,kind:this.kind,text:e})}}function H([e,n,t]){switch(t){case"Submenu":return new $(e,n);case"Predefined":return new j(e,n);case"Check":return new V(e,n);case"Icon":return new G(e,n);default:return new B(e,n)}}class $ extends M{constructor(e,n){super(e,n,"Submenu")}static async new(e){return F("Submenu",e).then(([e,n])=>new $(e,n))}async text(){return h("plugin:menu|text",{rid:this.rid,kind:this.kind})}async setText(e){return h("plugin:menu|set_text",{rid:this.rid,kind:this.kind,text:e})}async isEnabled(){return h("plugin:menu|is_enabled",{rid:this.rid,kind:this.kind})}async setEnabled(e){return h("plugin:menu|set_enabled",{rid:this.rid,kind:this.kind,enabled:e})}async append(e){return h("plugin:menu|append",{rid:this.rid,kind:this.kind,items:(Array.isArray(e)?e:[e]).map(e=>"rid"in e?[e.rid,e.kind]:e)})}async prepend(e){return h("plugin:menu|prepend",{rid:this.rid,kind:this.kind,items:(Array.isArray(e)?e:[e]).map(e=>"rid"in e?[e.rid,e.kind]:e)})}async insert(e,n){return h("plugin:menu|insert",{rid:this.rid,kind:this.kind,items:(Array.isArray(e)?e:[e]).map(e=>"rid"in e?[e.rid,e.kind]:e),position:n})}async remove(e){return h("plugin:menu|remove",{rid:this.rid,kind:this.kind,item:[e.rid,e.kind]})}async removeAt(e){return h("plugin:menu|remove_at",{rid:this.rid,kind:this.kind,position:e}).then(H)}async items(){return h("plugin:menu|items",{rid:this.rid,kind:this.kind}).then(e=>e.map(H))}async get(e){return h("plugin:menu|get",{rid:this.rid,kind:this.kind,id:e}).then(e=>e?H(e):null)}async popup(e,n){var t;return h("plugin:menu|popup",{rid:this.rid,kind:this.kind,window:null!==(t=null==n?void 0:n.label)&&void 0!==t?t:null,at:e instanceof E?e:e?new E(e):null})}async setAsWindowsMenuForNSApp(){return h("plugin:menu|set_as_windows_menu_for_nsapp",{rid:this.rid})}async setAsHelpMenuForNSApp(){return h("plugin:menu|set_as_help_menu_for_nsapp",{rid:this.rid})}async setIcon(e){return h("plugin:menu|set_icon",{rid:this.rid,kind:this.kind,icon:g(e)})}}class q extends M{constructor(e,n){super(e,n,"Menu")}static async new(e){return F("Menu",e).then(([e,n])=>new q(e,n))}static async default(){return h("plugin:menu|create_default").then(([e,n])=>new q(e,n))}async append(e){return h("plugin:menu|append",{rid:this.rid,kind:this.kind,items:(Array.isArray(e)?e:[e]).map(e=>"rid"in e?[e.rid,e.kind]:e)})}async prepend(e){return h("plugin:menu|prepend",{rid:this.rid,kind:this.kind,items:(Array.isArray(e)?e:[e]).map(e=>"rid"in e?[e.rid,e.kind]:e)})}async insert(e,n){return h("plugin:menu|insert",{rid:this.rid,kind:this.kind,items:(Array.isArray(e)?e:[e]).map(e=>"rid"in e?[e.rid,e.kind]:e),position:n})}async remove(e){return h("plugin:menu|remove",{rid:this.rid,kind:this.kind,item:[e.rid,e.kind]})}async removeAt(e){return h("plugin:menu|remove_at",{rid:this.rid,kind:this.kind,position:e}).then(H)}async items(){return h("plugin:menu|items",{rid:this.rid,kind:this.kind}).then(e=>e.map(H))}async get(e){return h("plugin:menu|get",{rid:this.rid,kind:this.kind,id:e}).then(e=>e?H(e):null)}async popup(e,n){var t;return h("plugin:menu|popup",{rid:this.rid,kind:this.kind,window:null!==(t=null==n?void 0:n.label)&&void 0!==t?t:null,at:e instanceof E?e:e?new E(e):null})}async setAsAppMenu(){return h("plugin:menu|set_as_app_menu",{rid:this.rid}).then(e=>e?new q(e[0],e[1]):null)}async setAsWindowMenu(e){var n;return h("plugin:menu|set_as_window_menu",{rid:this.rid,window:null!==(n=null==e?void 0:e.label)&&void 0!==n?n:null}).then(e=>e?new q(e[0],e[1]):null)}}var J=Object.freeze({__proto__:null,CheckMenuItem:V,IconMenuItem:G,Menu:q,MenuItem:B,get NativeIcon(){return W},PredefinedMenuItem:j,Submenu:$,itemFromKind:H});function Q(){var e,n;window.__TAURI_INTERNALS__=null!==(e=window.__TAURI_INTERNALS__)&&void 0!==e?e:{},window.__TAURI_EVENT_PLUGIN_INTERNALS__=null!==(n=window.__TAURI_EVENT_PLUGIN_INTERNALS__)&&void 0!==n?n:{}}var Z,K=Object.freeze({__proto__:null,clearMocks:function(){"object"==typeof window.__TAURI_INTERNALS__&&(delete window.__TAURI_INTERNALS__.invoke,delete window.__TAURI_INTERNALS__.transformCallback,delete window.__TAURI_INTERNALS__.unregisterCallback,delete window.__TAURI_INTERNALS__.runCallback,delete window.__TAURI_INTERNALS__.callbacks,delete window.__TAURI_INTERNALS__.convertFileSrc,delete window.__TAURI_INTERNALS__.metadata,"object"==typeof window.__TAURI_EVENT_PLUGIN_INTERNALS__&&delete window.__TAURI_EVENT_PLUGIN_INTERNALS__.unregisterListener)},mockConvertFileSrc:function(e){Q(),window.__TAURI_INTERNALS__.convertFileSrc=function(n,t="asset"){const i=encodeURIComponent(n);return"windows"===e?`http://${t}.localhost/${i}`:`${t}://localhost/${i}`}},mockIPC:function(e,n){function t(e,n){switch(e){case"plugin:event|listen":return function(e){i.has(e.event)||i.set(e.event,[]);return i.get(e.event).push(e.handler),e.handler}(n);case"plugin:event|emit":return function(e){const n=i.get(e.event)||[];for(const t of n)a(t,e);return null}(n);case"plugin:event|unlisten":return function(e){const n=i.get(e.event);if(n){const t=n.indexOf(e.id);-1!==t&&n.splice(t,1)}}(n)}}Q();const i=new Map,r=new Map;function s(e){r.delete(e)}function a(e,n){const t=r.get(e);t?t(n):console.warn(`[TAURI] Couldn't find callback id ${e}. This might happen when the app is reloaded while Rust is running an asynchronous operation.`)}window.__TAURI_INTERNALS__.invoke=async function(i,r,s){return(null==n?void 0:n.shouldMockEvents)&&function(e){return e.startsWith("plugin:event|")}(i)?t(i,r):e(i,r)},window.__TAURI_INTERNALS__.transformCallback=function(e,n=!1){const t=window.crypto.getRandomValues(new Uint32Array(1))[0];return r.set(t,i=>(n&&s(t),e&&e(i))),t},window.__TAURI_INTERNALS__.unregisterCallback=s,window.__TAURI_INTERNALS__.runCallback=a,window.__TAURI_INTERNALS__.callbacks=r,window.__TAURI_EVENT_PLUGIN_INTERNALS__.unregisterListener=function(e,n){s(n)}},mockWindows:function(e,...n){Q(),window.__TAURI_INTERNALS__.metadata={currentWindow:{label:e},currentWebview:{windowLabel:e,label:e}}}});!function(e){e[e.Audio=1]="Audio",e[e.Cache=2]="Cache",e[e.Config=3]="Config",e[e.Data=4]="Data",e[e.LocalData=5]="LocalData",e[e.Document=6]="Document",e[e.Download=7]="Download",e[e.Picture=8]="Picture",e[e.Public=9]="Public",e[e.Video=10]="Video",e[e.Resource=11]="Resource",e[e.Temp=12]="Temp",e[e.AppConfig=13]="AppConfig",e[e.AppData=14]="AppData",e[e.AppLocalData=15]="AppLocalData",e[e.AppCache=16]="AppCache",e[e.AppLog=17]="AppLog",e[e.Desktop=18]="Desktop",e[e.Executable=19]="Executable",e[e.Font=20]="Font",e[e.Home=21]="Home",e[e.Runtime=22]="Runtime",e[e.Template=23]="Template"}(Z||(Z={}));var Y=Object.freeze({__proto__:null,get BaseDirectory(){return Z},appCacheDir:async function(){return h("plugin:path|resolve_directory",{directory:Z.AppCache})},appConfigDir:async function(){return h("plugin:path|resolve_directory",{directory:Z.AppConfig})},appDataDir:async function(){return h("plugin:path|resolve_directory",{directory:Z.AppData})},appLocalDataDir:async function(){return h("plugin:path|resolve_directory",{directory:Z.AppLocalData})},appLogDir:async function(){return h("plugin:path|resolve_directory",{directory:Z.AppLog})},audioDir:async function(){return h("plugin:path|resolve_directory",{directory:Z.Audio})},basename:async function(e,n){return h("plugin:path|basename",{path:e,ext:n})},cacheDir:async function(){return h("plugin:path|resolve_directory",{directory:Z.Cache})},configDir:async function(){return h("plugin:path|resolve_directory",{directory:Z.Config})},dataDir:async function(){return h("plugin:path|resolve_directory",{directory:Z.Data})},delimiter:function(){return window.__TAURI_INTERNALS__.plugins.path.delimiter},desktopDir:async function(){return h("plugin:path|resolve_directory",{directory:Z.Desktop})},dirname:async function(e){return h("plugin:path|dirname",{path:e})},documentDir:async function(){return h("plugin:path|resolve_directory",{directory:Z.Document})},downloadDir:async function(){return h("plugin:path|resolve_directory",{directory:Z.Download})},executableDir:async function(){return h("plugin:path|resolve_directory",{directory:Z.Executable})},extname:async function(e){return h("plugin:path|extname",{path:e})},fontDir:async function(){return h("plugin:path|resolve_directory",{directory:Z.Font})},homeDir:async function(){return h("plugin:path|resolve_directory",{directory:Z.Home})},isAbsolute:async function(e){return h("plugin:path|is_absolute",{path:e})},join:async function(...e){return h("plugin:path|join",{paths:e})},localDataDir:async function(){return h("plugin:path|resolve_directory",{directory:Z.LocalData})},normalize:async function(e){return h("plugin:path|normalize",{path:e})},pictureDir:async function(){return h("plugin:path|resolve_directory",{directory:Z.Picture})},publicDir:async function(){return h("plugin:path|resolve_directory",{directory:Z.Public})},resolve:async function(...e){return h("plugin:path|resolve",{paths:e})},resolveResource:async function(e){return h("plugin:path|resolve_directory",{directory:Z.Resource,path:e})},resourceDir:async function(){return h("plugin:path|resolve_directory",{directory:Z.Resource})},runtimeDir:async function(){return h("plugin:path|resolve_directory",{directory:Z.Runtime})},sep:function(){return window.__TAURI_INTERNALS__.plugins.path.sep},tempDir:async function(){return h("plugin:path|resolve_directory",{directory:Z.Temp})},templateDir:async function(){return h("plugin:path|resolve_directory",{directory:Z.Template})},videoDir:async function(){return h("plugin:path|resolve_directory",{directory:Z.Video})}});class X extends w{constructor(e,n){super(e),this.id=n}static async getById(e){return h("plugin:tray|get_by_id",{id:e}).then(n=>n?new X(n,e):null)}static async removeById(e){return h("plugin:tray|remove_by_id",{id:e})}static async new(e){(null==e?void 0:e.menu)&&(e.menu=[e.menu.rid,e.menu.kind]),(null==e?void 0:e.icon)&&(e.icon=g(e.icon));const n=new c;if(null==e?void 0:e.action){const t=e.action;n.onmessage=e=>t(function(e){const n=e;return n.position=new I(e.position),n.rect.position=new I(e.rect.position),n.rect.size=new k(e.rect.size),n}(e)),delete e.action}return h("plugin:tray|new",{options:null!=e?e:{},handler:n}).then(([e,n])=>new X(e,n))}async setIcon(e){let n=null;return e&&(n=g(e)),h("plugin:tray|set_icon",{rid:this.rid,icon:n})}async setMenu(e){return e&&(e=[e.rid,e.kind]),h("plugin:tray|set_menu",{rid:this.rid,menu:e})}async setTooltip(e){return h("plugin:tray|set_tooltip",{rid:this.rid,tooltip:e})}async setTitle(e){return h("plugin:tray|set_title",{rid:this.rid,title:e})}async setVisible(e){return h("plugin:tray|set_visible",{rid:this.rid,visible:e})}async setTempDirPath(e){return h("plugin:tray|set_temp_dir_path",{rid:this.rid,path:e})}async setIconAsTemplate(e){return h("plugin:tray|set_icon_as_template",{rid:this.rid,asTemplate:e})}async setMenuOnLeftClick(e){return h("plugin:tray|set_show_menu_on_left_click",{rid:this.rid,onLeft:e})}async setShowMenuOnLeftClick(e){return h("plugin:tray|set_show_menu_on_left_click",{rid:this.rid,onLeft:e})}}var ee,ne,te=Object.freeze({__proto__:null,TrayIcon:X});!function(e){e[e.Critical=1]="Critical",e[e.Informational=2]="Informational"}(ee||(ee={}));class ie{constructor(e){this._preventDefault=!1,this.event=e.event,this.id=e.id}preventDefault(){this._preventDefault=!0}isPreventDefault(){return this._preventDefault}}function re(){return new le(window.__TAURI_INTERNALS__.metadata.currentWindow.label,{skip:!0})}async function se(){return h("plugin:window|get_all_windows").then(e=>e.map(e=>new le(e,{skip:!0})))}!function(e){e.None="none",e.Normal="normal",e.Indeterminate="indeterminate",e.Paused="paused",e.Error="error"}(ne||(ne={}));const ae=["tauri://created","tauri://error"];class le{constructor(e,n={}){var t;this.label=e,this.listeners=Object.create(null),(null==n?void 0:n.skip)||h("plugin:window|create",{options:{...n,parent:"string"==typeof n.parent?n.parent:null===(t=n.parent)||void 0===t?void 0:t.label,label:e}}).then(async()=>this.emit("tauri://created")).catch(async e=>this.emit("tauri://error",e))}static async getByLabel(e){var n;return null!==(n=(await se()).find(n=>n.label===e))&&void 0!==n?n:null}static getCurrent(){return re()}static async getAll(){return se()}static async getFocusedWindow(){for(const e of await se())if(await e.isFocused())return e;return null}async listen(e,n){return this._handleTauriEvent(e,n)?()=>{const t=this.listeners[e];t.splice(t.indexOf(n),1)}:N(e,n,{target:{kind:"Window",label:this.label}})}async once(e,n){return this._handleTauriEvent(e,n)?()=>{const t=this.listeners[e];t.splice(t.indexOf(n),1)}:L(e,n,{target:{kind:"Window",label:this.label}})}async emit(e,n){if(!ae.includes(e))return C(e,n);for(const t of this.listeners[e]||[])t({event:e,id:-1,payload:n})}async emitTo(e,n,t){if(!ae.includes(n))return x(e,n,t);for(const e of this.listeners[n]||[])e({event:n,id:-1,payload:t})}_handleTauriEvent(e,n){return!!ae.includes(e)&&(e in this.listeners?this.listeners[e].push(n):this.listeners[e]=[n],!0)}async scaleFactor(){return h("plugin:window|scale_factor",{label:this.label})}async innerPosition(){return h("plugin:window|inner_position",{label:this.label}).then(e=>new I(e))}async outerPosition(){return h("plugin:window|outer_position",{label:this.label}).then(e=>new I(e))}async innerSize(){return h("plugin:window|inner_size",{label:this.label}).then(e=>new k(e))}async outerSize(){return h("plugin:window|outer_size",{label:this.label}).then(e=>new k(e))}async isFullscreen(){return h("plugin:window|is_fullscreen",{label:this.label})}async isMinimized(){return h("plugin:window|is_minimized",{label:this.label})}async isMaximized(){return h("plugin:window|is_maximized",{label:this.label})}async isFocused(){return h("plugin:window|is_focused",{label:this.label})}async isDecorated(){return h("plugin:window|is_decorated",{label:this.label})}async isResizable(){return h("plugin:window|is_resizable",{label:this.label})}async isMaximizable(){return h("plugin:window|is_maximizable",{label:this.label})}async isMinimizable(){return h("plugin:window|is_minimizable",{label:this.label})}async isClosable(){return h("plugin:window|is_closable",{label:this.label})}async isVisible(){return h("plugin:window|is_visible",{label:this.label})}async title(){return h("plugin:window|title",{label:this.label})}async theme(){return h("plugin:window|theme",{label:this.label})}async isAlwaysOnTop(){return h("plugin:window|is_always_on_top",{label:this.label})}async activityName(){return h("plugin:window|activity_name",{label:this.label})}async sceneIdentifier(){return h("plugin:window|scene_identifier",{label:this.label})}async center(){return h("plugin:window|center",{label:this.label})}async requestUserAttention(e){let n=null;return e&&(n=e===ee.Critical?{type:"Critical"}:{type:"Informational"}),h("plugin:window|request_user_attention",{label:this.label,value:n})}async setResizable(e){return h("plugin:window|set_resizable",{label:this.label,value:e})}async setEnabled(e){return h("plugin:window|set_enabled",{label:this.label,value:e})}async isEnabled(){return h("plugin:window|is_enabled",{label:this.label})}async setMaximizable(e){return h("plugin:window|set_maximizable",{label:this.label,value:e})}async setMinimizable(e){return h("plugin:window|set_minimizable",{label:this.label,value:e})}async setClosable(e){return h("plugin:window|set_closable",{label:this.label,value:e})}async setTitle(e){return h("plugin:window|set_title",{label:this.label,value:e})}async maximize(){return h("plugin:window|maximize",{label:this.label})}async unmaximize(){return h("plugin:window|unmaximize",{label:this.label})}async toggleMaximize(){return h("plugin:window|toggle_maximize",{label:this.label})}async minimize(){return h("plugin:window|minimize",{label:this.label})}async unminimize(){return h("plugin:window|unminimize",{label:this.label})}async show(){return h("plugin:window|show",{label:this.label})}async hide(){return h("plugin:window|hide",{label:this.label})}async close(){return h("plugin:window|close",{label:this.label})}async destroy(){return h("plugin:window|destroy",{label:this.label})}async setDecorations(e){return h("plugin:window|set_decorations",{label:this.label,value:e})}async setShadow(e){return h("plugin:window|set_shadow",{label:this.label,value:e})}async setEffects(e){return h("plugin:window|set_effects",{label:this.label,value:e})}async clearEffects(){return h("plugin:window|set_effects",{label:this.label,value:null})}async setAlwaysOnTop(e){return h("plugin:window|set_always_on_top",{label:this.label,value:e})}async setAlwaysOnBottom(e){return h("plugin:window|set_always_on_bottom",{label:this.label,value:e})}async setContentProtected(e){return h("plugin:window|set_content_protected",{label:this.label,value:e})}async setSize(e){return h("plugin:window|set_size",{label:this.label,value:e instanceof A?e:new A(e)})}async setMinSize(e){return h("plugin:window|set_min_size",{label:this.label,value:e instanceof A?e:e?new A(e):null})}async setMaxSize(e){return h("plugin:window|set_max_size",{label:this.label,value:e instanceof A?e:e?new A(e):null})}async setSizeConstraints(e){function n(e){return e?{Logical:e}:null}return h("plugin:window|set_size_constraints",{label:this.label,value:{minWidth:n(null==e?void 0:e.minWidth),minHeight:n(null==e?void 0:e.minHeight),maxWidth:n(null==e?void 0:e.maxWidth),maxHeight:n(null==e?void 0:e.maxHeight)}})}async setPosition(e){return h("plugin:window|set_position",{label:this.label,value:e instanceof E?e:new E(e)})}async setFullscreen(e){return h("plugin:window|set_fullscreen",{label:this.label,value:e})}async setSimpleFullscreen(e){return h("plugin:window|set_simple_fullscreen",{label:this.label,value:e})}async setFocus(){return h("plugin:window|set_focus",{label:this.label})}async setFocusable(e){return h("plugin:window|set_focusable",{label:this.label,value:e})}async setIcon(e){return h("plugin:window|set_icon",{label:this.label,value:g(e)})}async setSkipTaskbar(e){return h("plugin:window|set_skip_taskbar",{label:this.label,value:e})}async setCursorGrab(e){return h("plugin:window|set_cursor_grab",{label:this.label,value:e})}async setCursorVisible(e){return h("plugin:window|set_cursor_visible",{label:this.label,value:e})}async setCursorIcon(e){return h("plugin:window|set_cursor_icon",{label:this.label,value:e})}async setBackgroundColor(e){return h("plugin:window|set_background_color",{color:e})}async setCursorPosition(e){return h("plugin:window|set_cursor_position",{label:this.label,value:e instanceof E?e:new E(e)})}async setIgnoreCursorEvents(e){return h("plugin:window|set_ignore_cursor_events",{label:this.label,value:e})}async startDragging(){return h("plugin:window|start_dragging",{label:this.label})}async startResizeDragging(e){return h("plugin:window|start_resize_dragging",{label:this.label,value:e})}async setBadgeCount(e){return h("plugin:window|set_badge_count",{label:this.label,value:e})}async setBadgeLabel(e){return h("plugin:window|set_badge_label",{label:this.label,value:e})}async setOverlayIcon(e){return h("plugin:window|set_overlay_icon",{label:this.label,value:e?g(e):void 0})}async setProgressBar(e){return h("plugin:window|set_progress_bar",{label:this.label,value:e})}async setVisibleOnAllWorkspaces(e){return h("plugin:window|set_visible_on_all_workspaces",{label:this.label,value:e})}async setTitleBarStyle(e){return h("plugin:window|set_title_bar_style",{label:this.label,value:e})}async setTheme(e){return h("plugin:window|set_theme",{label:this.label,value:e})}async onResized(e){return this.listen(R.WINDOW_RESIZED,n=>{n.payload=new k(n.payload),e(n)})}async onMoved(e){return this.listen(R.WINDOW_MOVED,n=>{n.payload=new I(n.payload),e(n)})}async onCloseRequested(e){return this.listen(R.WINDOW_CLOSE_REQUESTED,async n=>{const t=new ie(n);await e(t),t.isPreventDefault()||await this.destroy()})}async onDragDropEvent(e){const n=await this.listen(R.DRAG_ENTER,n=>{e({...n,payload:{type:"enter",paths:n.payload.paths,position:new I(n.payload.position)}})}),t=await this.listen(R.DRAG_OVER,n=>{e({...n,payload:{type:"over",position:new I(n.payload.position)}})}),i=await this.listen(R.DRAG_DROP,n=>{e({...n,payload:{type:"drop",paths:n.payload.paths,position:new I(n.payload.position)}})}),r=await this.listen(R.DRAG_LEAVE,n=>{e({...n,payload:{type:"leave"}})});return()=>{n(),i(),t(),r()}}async onFocusChanged(e){const n=await this.listen(R.WINDOW_FOCUS,n=>{e({...n,payload:!0})}),t=await this.listen(R.WINDOW_BLUR,n=>{e({...n,payload:!1})});return()=>{n(),t()}}async onScaleChanged(e){return this.listen(R.WINDOW_SCALE_FACTOR_CHANGED,e)}async onThemeChanged(e){return this.listen(R.WINDOW_THEME_CHANGED,e)}}var oe,ue,ce,de;function pe(e){return null===e?null:{name:e.name,scaleFactor:e.scaleFactor,position:new I(e.position),size:new k(e.size),workArea:{position:new I(e.workArea.position),size:new k(e.workArea.size)}}}!function(e){e.Disabled="disabled",e.Throttle="throttle",e.Suspend="suspend"}(oe||(oe={})),function(e){e.Default="default",e.FluentOverlay="fluentOverlay"}(ue||(ue={})),function(e){e.AppearanceBased="appearanceBased",e.Light="light",e.Dark="dark",e.MediumLight="mediumLight",e.UltraDark="ultraDark",e.Titlebar="titlebar",e.Selection="selection",e.Menu="menu",e.Popover="popover",e.Sidebar="sidebar",e.HeaderView="headerView",e.Sheet="sheet",e.WindowBackground="windowBackground",e.HudWindow="hudWindow",e.FullScreenUI="fullScreenUI",e.Tooltip="tooltip",e.ContentBackground="contentBackground",e.UnderWindowBackground="underWindowBackground",e.UnderPageBackground="underPageBackground",e.Mica="mica",e.Blur="blur",e.Acrylic="acrylic",e.Tabbed="tabbed",e.TabbedDark="tabbedDark",e.TabbedLight="tabbedLight"}(ce||(ce={})),function(e){e.FollowsWindowActiveState="followsWindowActiveState",e.Active="active",e.Inactive="inactive"}(de||(de={}));var he=Object.freeze({__proto__:null,CloseRequestedEvent:ie,get Effect(){return ce},get EffectState(){return de},LogicalPosition:T,LogicalSize:v,PhysicalPosition:I,PhysicalSize:k,get ProgressBarStatus(){return ne},get UserAttentionType(){return ee},Window:le,availableMonitors:async function(){return h("plugin:window|available_monitors").then(e=>e.map(pe))},currentMonitor:async function(){return h("plugin:window|current_monitor").then(pe)},cursorPosition:async function(){return h("plugin:window|cursor_position").then(e=>new I(e))},getAllWindows:se,getCurrentWindow:re,monitorFromPoint:async function(e,n){return h("plugin:window|monitor_from_point",{x:e,y:n}).then(pe)},primaryMonitor:async function(){return h("plugin:window|primary_monitor").then(pe)}});function we(){return new ge(re(),window.__TAURI_INTERNALS__.metadata.currentWebview.label,{skip:!0})}async function _e(){return h("plugin:webview|get_all_webviews").then(e=>e.map(e=>new ge(new le(e.windowLabel,{skip:!0}),e.label,{skip:!0})))}const ye=["tauri://created","tauri://error"];class ge{constructor(e,n,t){this.window=e,this.label=n,this.listeners=Object.create(null),(null==t?void 0:t.skip)||h("plugin:webview|create_webview",{windowLabel:e.label,options:{...t,label:n}}).then(async()=>this.emit("tauri://created")).catch(async e=>this.emit("tauri://error",e))}static async getByLabel(e){var n;return null!==(n=(await _e()).find(n=>n.label===e))&&void 0!==n?n:null}static getCurrent(){return we()}static async getAll(){return _e()}async listen(e,n){return this._handleTauriEvent(e,n)?()=>{const t=this.listeners[e];t.splice(t.indexOf(n),1)}:N(e,n,{target:{kind:"Webview",label:this.label}})}async once(e,n){return this._handleTauriEvent(e,n)?()=>{const t=this.listeners[e];t.splice(t.indexOf(n),1)}:L(e,n,{target:{kind:"Webview",label:this.label}})}async emit(e,n){if(!ye.includes(e))return C(e,n);for(const t of this.listeners[e]||[])t({event:e,id:-1,payload:n})}async emitTo(e,n,t){if(!ye.includes(n))return x(e,n,t);for(const e of this.listeners[n]||[])e({event:n,id:-1,payload:t})}_handleTauriEvent(e,n){return!!ye.includes(e)&&(e in this.listeners?this.listeners[e].push(n):this.listeners[e]=[n],!0)}async position(){return h("plugin:webview|webview_position",{label:this.label}).then(e=>new I(e))}async size(){return h("plugin:webview|webview_size",{label:this.label}).then(e=>new k(e))}async close(){return h("plugin:webview|webview_close",{label:this.label})}async setSize(e){return h("plugin:webview|set_webview_size",{label:this.label,value:e instanceof A?e:new A(e)})}async setPosition(e){return h("plugin:webview|set_webview_position",{label:this.label,value:e instanceof E?e:new E(e)})}async setFocus(){return h("plugin:webview|set_webview_focus",{label:this.label})}async setAutoResize(e){return h("plugin:webview|set_webview_auto_resize",{label:this.label,value:e})}async hide(){return h("plugin:webview|webview_hide",{label:this.label})}async show(){return h("plugin:webview|webview_show",{label:this.label})}async setZoom(e){return h("plugin:webview|set_webview_zoom",{label:this.label,value:e})}async reparent(e){return h("plugin:webview|reparent",{label:this.label,window:"string"==typeof e?e:e.label})}async clearAllBrowsingData(){return h("plugin:webview|clear_all_browsing_data")}async setBackgroundColor(e){return h("plugin:webview|set_webview_background_color",{color:e})}async onDragDropEvent(e){const n=await this.listen(R.DRAG_ENTER,n=>{e({...n,payload:{type:"enter",paths:n.payload.paths,position:new I(n.payload.position)}})}),t=await this.listen(R.DRAG_OVER,n=>{e({...n,payload:{type:"over",position:new I(n.payload.position)}})}),i=await this.listen(R.DRAG_DROP,n=>{e({...n,payload:{type:"drop",paths:n.payload.paths,position:new I(n.payload.position)}})}),r=await this.listen(R.DRAG_LEAVE,n=>{e({...n,payload:{type:"leave"}})});return()=>{n(),i(),t(),r()}}}var be,me,fe=Object.freeze({__proto__:null,Webview:ge,getAllWebviews:_e,getCurrentWebview:we});function ve(){const e=we();return new Ae(e.label,{skip:!0})}async function ke(){return h("plugin:window|get_all_windows").then(e=>e.map(e=>new Ae(e,{skip:!0})))}class Ae{constructor(e,n={}){var t;this.label=e,this.listeners=Object.create(null),(null==n?void 0:n.skip)||h("plugin:webview|create_webview_window",{options:{...n,parent:"string"==typeof n.parent?n.parent:null===(t=n.parent)||void 0===t?void 0:t.label,label:e}}).then(async()=>this.emit("tauri://created")).catch(async e=>this.emit("tauri://error",e))}static async getByLabel(e){var n;const t=null!==(n=(await ke()).find(n=>n.label===e))&&void 0!==n?n:null;return t?new Ae(t.label,{skip:!0}):null}static getCurrent(){return ve()}static async getAll(){return ke()}async listen(e,n){return this._handleTauriEvent(e,n)?()=>{const t=this.listeners[e];t.splice(t.indexOf(n),1)}:N(e,n,{target:{kind:"WebviewWindow",label:this.label}})}async once(e,n){return this._handleTauriEvent(e,n)?()=>{const t=this.listeners[e];t.splice(t.indexOf(n),1)}:L(e,n,{target:{kind:"WebviewWindow",label:this.label}})}async setBackgroundColor(e){return h("plugin:window|set_background_color",{color:e}).then(()=>h("plugin:webview|set_webview_background_color",{color:e}))}}be=Ae,me=[le,ge],(Array.isArray(me)?me:[me]).forEach(e=>{Object.getOwnPropertyNames(e.prototype).forEach(n=>{var t;"object"==typeof be.prototype&&be.prototype&&n in be.prototype||Object.defineProperty(be.prototype,n,null!==(t=Object.getOwnPropertyDescriptor(e.prototype,n))&&void 0!==t?t:Object.create(null))})});var Te=Object.freeze({__proto__:null,WebviewWindow:Ae,getAllWebviewWindows:ke,getCurrentWebviewWindow:ve});return e.app=f,e.core=_,e.dpi=D,e.event=O,e.image=m,e.menu=J,e.mocks=K,e.path=Y,e.tray=te,e.webview=fe,e.webviewWindow=Te,e.window=he,e}({});window.__TAURI__=__TAURI_IIFE__; +var __TAURI_IIFE__=function(e){"use strict";function n(e,n,t,i){if("a"===t&&!i)throw new TypeError("Private accessor was defined without a getter");if("function"==typeof n?e!==n||!i:!n.has(e))throw new TypeError("Cannot read private member from an object whose class did not declare it");return"m"===t?i:"a"===t?i.call(e):i?i.value:n.get(e)}function t(e,n,t,i,r){if("m"===i)throw new TypeError("Private method is not writable");if("a"===i&&!r)throw new TypeError("Private accessor was defined without a setter");if("function"==typeof n?e!==n||!r:!n.has(e))throw new TypeError("Cannot write private member to an object whose class did not declare it");return"a"===i?r.call(e,t):r?r.value=t:n.set(e,t),t}var i,r,s,a,l;"function"==typeof SuppressedError&&SuppressedError;const o="__TAURI_TO_IPC_KEY__";function u(e,n=!1){return window.__TAURI_INTERNALS__.transformCallback(e,n)}class c{constructor(e){i.set(this,void 0),r.set(this,0),s.set(this,[]),a.set(this,void 0),t(this,i,e||(()=>{}),"f"),this.id=u(e=>{const l=e.index;if("end"in e)return void(l==n(this,r,"f")?this.cleanupCallback():t(this,a,l,"f"));const o=e.message;if(l==n(this,r,"f")){for(n(this,i,"f").call(this,o),t(this,r,n(this,r,"f")+1,"f");n(this,r,"f")in n(this,s,"f");){const e=n(this,s,"f")[n(this,r,"f")];n(this,i,"f").call(this,e),delete n(this,s,"f")[n(this,r,"f")],t(this,r,n(this,r,"f")+1,"f")}n(this,r,"f")===n(this,a,"f")&&this.cleanupCallback()}else n(this,s,"f")[l]=o})}cleanupCallback(){window.__TAURI_INTERNALS__.unregisterCallback(this.id)}set onmessage(e){t(this,i,e,"f")}get onmessage(){return n(this,i,"f")}[(i=new WeakMap,r=new WeakMap,s=new WeakMap,a=new WeakMap,o)](){return`__CHANNEL__:${this.id}`}toJSON(){return this[o]()}}class d{constructor(e,n,t){this.plugin=e,this.event=n,this.channelId=t}async unregister(){return h(`plugin:${this.plugin}|remove_listener`,{event:this.event,channelId:this.channelId})}}async function p(e,n,t){const i=new c(t);try{return await h(`plugin:${e}|register_listener`,{event:n,handler:i}),new d(e,n,i.id)}catch{return await h(`plugin:${e}|registerListener`,{event:n,handler:i}),new d(e,n,i.id)}}async function h(e,n={},t){return window.__TAURI_INTERNALS__.invoke(e,n,t)}class w{get rid(){return n(this,l,"f")}constructor(e){l.set(this,void 0),t(this,l,e,"f")}async close(){return h("plugin:resources|close",{rid:this.rid})}}l=new WeakMap;var _=Object.freeze({__proto__:null,Channel:c,PluginListener:d,Resource:w,SERIALIZE_TO_IPC_FN:o,addPluginListener:p,checkPermissions:async function(e){return h(`plugin:${e}|check_permissions`)},convertFileSrc:function(e,n="asset"){return window.__TAURI_INTERNALS__.convertFileSrc(e,n)},invoke:h,isTauri:function(){return!!(globalThis||window).isTauri},requestPermissions:async function(e){return h(`plugin:${e}|request_permissions`)},transformCallback:u});class y extends w{constructor(e){super(e)}static async new(e,n,t){return h("plugin:image|new",{rgba:g(e),width:n,height:t}).then(e=>new y(e))}static async fromBytes(e){return h("plugin:image|from_bytes",{bytes:g(e)}).then(e=>new y(e))}static async fromPath(e){return h("plugin:image|from_path",{path:e}).then(e=>new y(e))}async rgba(){return h("plugin:image|rgba",{rid:this.rid}).then(e=>new Uint8Array(e))}async size(){return h("plugin:image|size",{rid:this.rid})}}function g(e){return null==e?null:"string"==typeof e?e:e instanceof y?e.rid:e}var b,m=Object.freeze({__proto__:null,Image:y,transformImage:g});!function(e){e.Nsis="nsis",e.Msi="msi",e.Deb="deb",e.Rpm="rpm",e.AppImage="appimage",e.App="app"}(b||(b={}));var f=Object.freeze({__proto__:null,get BundleType(){return b},defaultWindowIcon:async function(){return h("plugin:app|default_window_icon").then(e=>e?new y(e):null)},fetchDataStoreIdentifiers:async function(){return h("plugin:app|fetch_data_store_identifiers")},getBundleType:async function(){return h("plugin:app|bundle_type")},getIdentifier:async function(){return h("plugin:app|identifier")},getName:async function(){return h("plugin:app|name")},getTauriVersion:async function(){return h("plugin:app|tauri_version")},getVersion:async function(){return h("plugin:app|version")},hide:async function(){return h("plugin:app|app_hide")},onBackButtonPress:async function(e){return p("app","back-button",e)},removeDataStore:async function(e){return h("plugin:app|remove_data_store",{uuid:e})},setDockVisibility:async function(e){return h("plugin:app|set_dock_visibility",{visible:e})},setTheme:async function(e){return h("plugin:app|set_app_theme",{theme:e})},show:async function(){return h("plugin:app|app_show")},supportsMultipleWindows:async function(){return h("plugin:app|supports_multiple_windows")}});class v{constructor(...e){this.type="Logical",1===e.length?"Logical"in e[0]?(this.width=e[0].Logical.width,this.height=e[0].Logical.height):(this.width=e[0].width,this.height=e[0].height):(this.width=e[0],this.height=e[1])}toPhysical(e){return new k(this.width*e,this.height*e)}[o](){return{width:this.width,height:this.height}}toJSON(){return this[o]()}}class k{constructor(...e){this.type="Physical",1===e.length?"Physical"in e[0]?(this.width=e[0].Physical.width,this.height=e[0].Physical.height):(this.width=e[0].width,this.height=e[0].height):(this.width=e[0],this.height=e[1])}toLogical(e){return new v(this.width/e,this.height/e)}[o](){return{width:this.width,height:this.height}}toJSON(){return this[o]()}}class A{constructor(e){this.size=e}toLogical(e){return this.size instanceof v?this.size:this.size.toLogical(e)}toPhysical(e){return this.size instanceof k?this.size:this.size.toPhysical(e)}[o](){return{[`${this.size.type}`]:{width:this.size.width,height:this.size.height}}}toJSON(){return this[o]()}}class T{constructor(...e){this.type="Logical",1===e.length?"Logical"in e[0]?(this.x=e[0].Logical.x,this.y=e[0].Logical.y):(this.x=e[0].x,this.y=e[0].y):(this.x=e[0],this.y=e[1])}toPhysical(e){return new I(this.x*e,this.y*e)}[o](){return{x:this.x,y:this.y}}toJSON(){return this[o]()}}class I{constructor(...e){this.type="Physical",1===e.length?"Physical"in e[0]?(this.x=e[0].Physical.x,this.y=e[0].Physical.y):(this.x=e[0].x,this.y=e[0].y):(this.x=e[0],this.y=e[1])}toLogical(e){return new T(this.x/e,this.y/e)}[o](){return{x:this.x,y:this.y}}toJSON(){return this[o]()}}class E{constructor(e){this.position=e}toLogical(e){return this.position instanceof T?this.position:this.position.toLogical(e)}toPhysical(e){return this.position instanceof I?this.position:this.position.toPhysical(e)}[o](){return{[`${this.position.type}`]:{x:this.position.x,y:this.position.y}}}toJSON(){return this[o]()}}var R,D=Object.freeze({__proto__:null,LogicalPosition:T,LogicalSize:v,PhysicalPosition:I,PhysicalSize:k,Position:E,Size:A});async function S(e,n){window.__TAURI_EVENT_PLUGIN_INTERNALS__.unregisterListener(e,n),await h("plugin:event|unlisten",{event:e,eventId:n})}async function N(e,n,t){var i;const r="string"==typeof(null==t?void 0:t.target)?{kind:"AnyLabel",label:t.target}:null!==(i=null==t?void 0:t.target)&&void 0!==i?i:{kind:"Any"};return h("plugin:event|listen",{event:e,target:r,handler:u(n)}).then(n=>async()=>S(e,n))}async function L(e,n,t){return N(e,t=>{S(e,t.id),n(t)},t)}async function C(e,n){await h("plugin:event|emit",{event:e,payload:n})}async function x(e,n,t){const i="string"==typeof e?{kind:"AnyLabel",label:e}:e;await h("plugin:event|emit_to",{target:i,event:n,payload:t})}!function(e){e.WINDOW_RESIZED="tauri://resize",e.WINDOW_MOVED="tauri://move",e.WINDOW_CLOSE_REQUESTED="tauri://close-requested",e.WINDOW_DESTROYED="tauri://destroyed",e.WINDOW_FOCUS="tauri://focus",e.WINDOW_BLUR="tauri://blur",e.WINDOW_SCALE_FACTOR_CHANGED="tauri://scale-change",e.WINDOW_THEME_CHANGED="tauri://theme-changed",e.WINDOW_CREATED="tauri://window-created",e.WEBVIEW_CREATED="tauri://webview-created",e.DRAG_ENTER="tauri://drag-enter",e.DRAG_OVER="tauri://drag-over",e.DRAG_DROP="tauri://drag-drop",e.DRAG_LEAVE="tauri://drag-leave"}(R||(R={}));var P,z,W,O=Object.freeze({__proto__:null,get TauriEvent(){return R},emit:C,emitTo:x,listen:N,once:L});function U(e){var n;if("items"in e)e.items=null===(n=e.items)||void 0===n?void 0:n.map(e=>"rid"in e?e:U(e));else if("action"in e&&e.action){const n=new c;return n.onmessage=e.action,delete e.action,{...e,handler:n}}return e}async function F(e,n){const t=new c;if(n&&"object"==typeof n&&("action"in n&&n.action&&(t.onmessage=n.action,delete n.action),"item"in n&&n.item&&"object"==typeof n.item&&"About"in n.item&&n.item.About&&"object"==typeof n.item.About&&"icon"in n.item.About&&n.item.About.icon&&(n.item.About.icon=g(n.item.About.icon)),"icon"in n&&n.icon&&(n.icon=g(n.icon)),"items"in n&&n.items)){function i(e){var n;return"rid"in e?[e.rid,e.kind]:("item"in e&&"object"==typeof e.item&&(null===(n=e.item.About)||void 0===n?void 0:n.icon)&&(e.item.About.icon=g(e.item.About.icon)),"icon"in e&&e.icon&&(e.icon=g(e.icon)),"items"in e&&e.items&&(e.items=e.items.map(i)),U(e))}n.items=n.items.map(i)}return h("plugin:menu|new",{kind:e,options:n,handler:t})}class M extends w{get id(){return n(this,P,"f")}get kind(){return n(this,z,"f")}constructor(e,n,i){super(e),P.set(this,void 0),z.set(this,void 0),t(this,P,n,"f"),t(this,z,i,"f")}}P=new WeakMap,z=new WeakMap;class B extends M{constructor(e,n){super(e,n,"MenuItem")}static async new(e){return F("MenuItem",e).then(([e,n])=>new B(e,n))}async text(){return h("plugin:menu|text",{rid:this.rid,kind:this.kind})}async setText(e){return h("plugin:menu|set_text",{rid:this.rid,kind:this.kind,text:e})}async isEnabled(){return h("plugin:menu|is_enabled",{rid:this.rid,kind:this.kind})}async setEnabled(e){return h("plugin:menu|set_enabled",{rid:this.rid,kind:this.kind,enabled:e})}async setAccelerator(e){return h("plugin:menu|set_accelerator",{rid:this.rid,kind:this.kind,accelerator:e})}}class V extends M{constructor(e,n){super(e,n,"Check")}static async new(e){return F("Check",e).then(([e,n])=>new V(e,n))}async text(){return h("plugin:menu|text",{rid:this.rid,kind:this.kind})}async setText(e){return h("plugin:menu|set_text",{rid:this.rid,kind:this.kind,text:e})}async isEnabled(){return h("plugin:menu|is_enabled",{rid:this.rid,kind:this.kind})}async setEnabled(e){return h("plugin:menu|set_enabled",{rid:this.rid,kind:this.kind,enabled:e})}async setAccelerator(e){return h("plugin:menu|set_accelerator",{rid:this.rid,kind:this.kind,accelerator:e})}async isChecked(){return h("plugin:menu|is_checked",{rid:this.rid})}async setChecked(e){return h("plugin:menu|set_checked",{rid:this.rid,checked:e})}}!function(e){e.Add="Add",e.Advanced="Advanced",e.Bluetooth="Bluetooth",e.Bookmarks="Bookmarks",e.Caution="Caution",e.ColorPanel="ColorPanel",e.ColumnView="ColumnView",e.Computer="Computer",e.EnterFullScreen="EnterFullScreen",e.Everyone="Everyone",e.ExitFullScreen="ExitFullScreen",e.FlowView="FlowView",e.Folder="Folder",e.FolderBurnable="FolderBurnable",e.FolderSmart="FolderSmart",e.FollowLinkFreestanding="FollowLinkFreestanding",e.FontPanel="FontPanel",e.GoLeft="GoLeft",e.GoRight="GoRight",e.Home="Home",e.IChatTheater="IChatTheater",e.IconView="IconView",e.Info="Info",e.InvalidDataFreestanding="InvalidDataFreestanding",e.LeftFacingTriangle="LeftFacingTriangle",e.ListView="ListView",e.LockLocked="LockLocked",e.LockUnlocked="LockUnlocked",e.MenuMixedState="MenuMixedState",e.MenuOnState="MenuOnState",e.MobileMe="MobileMe",e.MultipleDocuments="MultipleDocuments",e.Network="Network",e.Path="Path",e.PreferencesGeneral="PreferencesGeneral",e.QuickLook="QuickLook",e.RefreshFreestanding="RefreshFreestanding",e.Refresh="Refresh",e.Remove="Remove",e.RevealFreestanding="RevealFreestanding",e.RightFacingTriangle="RightFacingTriangle",e.Share="Share",e.Slideshow="Slideshow",e.SmartBadge="SmartBadge",e.StatusAvailable="StatusAvailable",e.StatusNone="StatusNone",e.StatusPartiallyAvailable="StatusPartiallyAvailable",e.StatusUnavailable="StatusUnavailable",e.StopProgressFreestanding="StopProgressFreestanding",e.StopProgress="StopProgress",e.TrashEmpty="TrashEmpty",e.TrashFull="TrashFull",e.User="User",e.UserAccounts="UserAccounts",e.UserGroup="UserGroup",e.UserGuest="UserGuest"}(W||(W={}));class G extends M{constructor(e,n){super(e,n,"Icon")}static async new(e){return F("Icon",e).then(([e,n])=>new G(e,n))}async text(){return h("plugin:menu|text",{rid:this.rid,kind:this.kind})}async setText(e){return h("plugin:menu|set_text",{rid:this.rid,kind:this.kind,text:e})}async isEnabled(){return h("plugin:menu|is_enabled",{rid:this.rid,kind:this.kind})}async setEnabled(e){return h("plugin:menu|set_enabled",{rid:this.rid,kind:this.kind,enabled:e})}async setAccelerator(e){return h("plugin:menu|set_accelerator",{rid:this.rid,kind:this.kind,accelerator:e})}async setIcon(e){return h("plugin:menu|set_icon",{rid:this.rid,kind:this.kind,icon:g(e)})}}class j extends M{constructor(e,n){super(e,n,"Predefined")}static async new(e){return F("Predefined",e).then(([e,n])=>new j(e,n))}async text(){return h("plugin:menu|text",{rid:this.rid,kind:this.kind})}async setText(e){return h("plugin:menu|set_text",{rid:this.rid,kind:this.kind,text:e})}}function H([e,n,t]){switch(t){case"Submenu":return new $(e,n);case"Predefined":return new j(e,n);case"Check":return new V(e,n);case"Icon":return new G(e,n);default:return new B(e,n)}}class $ extends M{constructor(e,n){super(e,n,"Submenu")}static async new(e){return F("Submenu",e).then(([e,n])=>new $(e,n))}async text(){return h("plugin:menu|text",{rid:this.rid,kind:this.kind})}async setText(e){return h("plugin:menu|set_text",{rid:this.rid,kind:this.kind,text:e})}async isEnabled(){return h("plugin:menu|is_enabled",{rid:this.rid,kind:this.kind})}async setEnabled(e){return h("plugin:menu|set_enabled",{rid:this.rid,kind:this.kind,enabled:e})}async append(e){return h("plugin:menu|append",{rid:this.rid,kind:this.kind,items:(Array.isArray(e)?e:[e]).map(e=>"rid"in e?[e.rid,e.kind]:e)})}async prepend(e){return h("plugin:menu|prepend",{rid:this.rid,kind:this.kind,items:(Array.isArray(e)?e:[e]).map(e=>"rid"in e?[e.rid,e.kind]:e)})}async insert(e,n){return h("plugin:menu|insert",{rid:this.rid,kind:this.kind,items:(Array.isArray(e)?e:[e]).map(e=>"rid"in e?[e.rid,e.kind]:e),position:n})}async remove(e){return h("plugin:menu|remove",{rid:this.rid,kind:this.kind,item:[e.rid,e.kind]})}async removeAt(e){return h("plugin:menu|remove_at",{rid:this.rid,kind:this.kind,position:e}).then(H)}async items(){return h("plugin:menu|items",{rid:this.rid,kind:this.kind}).then(e=>e.map(H))}async get(e){return h("plugin:menu|get",{rid:this.rid,kind:this.kind,id:e}).then(e=>e?H(e):null)}async popup(e,n){var t;return h("plugin:menu|popup",{rid:this.rid,kind:this.kind,window:null!==(t=null==n?void 0:n.label)&&void 0!==t?t:null,at:e instanceof E?e:e?new E(e):null})}async setAsWindowsMenuForNSApp(){return h("plugin:menu|set_as_windows_menu_for_nsapp",{rid:this.rid})}async setAsHelpMenuForNSApp(){return h("plugin:menu|set_as_help_menu_for_nsapp",{rid:this.rid})}async setIcon(e){return h("plugin:menu|set_icon",{rid:this.rid,kind:this.kind,icon:g(e)})}}class q extends M{constructor(e,n){super(e,n,"Menu")}static async new(e){return F("Menu",e).then(([e,n])=>new q(e,n))}static async default(){return h("plugin:menu|create_default").then(([e,n])=>new q(e,n))}async append(e){return h("plugin:menu|append",{rid:this.rid,kind:this.kind,items:(Array.isArray(e)?e:[e]).map(e=>"rid"in e?[e.rid,e.kind]:e)})}async prepend(e){return h("plugin:menu|prepend",{rid:this.rid,kind:this.kind,items:(Array.isArray(e)?e:[e]).map(e=>"rid"in e?[e.rid,e.kind]:e)})}async insert(e,n){return h("plugin:menu|insert",{rid:this.rid,kind:this.kind,items:(Array.isArray(e)?e:[e]).map(e=>"rid"in e?[e.rid,e.kind]:e),position:n})}async remove(e){return h("plugin:menu|remove",{rid:this.rid,kind:this.kind,item:[e.rid,e.kind]})}async removeAt(e){return h("plugin:menu|remove_at",{rid:this.rid,kind:this.kind,position:e}).then(H)}async items(){return h("plugin:menu|items",{rid:this.rid,kind:this.kind}).then(e=>e.map(H))}async get(e){return h("plugin:menu|get",{rid:this.rid,kind:this.kind,id:e}).then(e=>e?H(e):null)}async popup(e,n){var t;return h("plugin:menu|popup",{rid:this.rid,kind:this.kind,window:null!==(t=null==n?void 0:n.label)&&void 0!==t?t:null,at:e instanceof E?e:e?new E(e):null})}async setAsAppMenu(){return h("plugin:menu|set_as_app_menu",{rid:this.rid}).then(e=>e?new q(e[0],e[1]):null)}async setAsWindowMenu(e){var n;return h("plugin:menu|set_as_window_menu",{rid:this.rid,window:null!==(n=null==e?void 0:e.label)&&void 0!==n?n:null}).then(e=>e?new q(e[0],e[1]):null)}}var J=Object.freeze({__proto__:null,CheckMenuItem:V,IconMenuItem:G,Menu:q,MenuItem:B,get NativeIcon(){return W},PredefinedMenuItem:j,Submenu:$,itemFromKind:H});function Q(){var e,n;window.__TAURI_INTERNALS__=null!==(e=window.__TAURI_INTERNALS__)&&void 0!==e?e:{},window.__TAURI_EVENT_PLUGIN_INTERNALS__=null!==(n=window.__TAURI_EVENT_PLUGIN_INTERNALS__)&&void 0!==n?n:{}}var Z,K=Object.freeze({__proto__:null,clearMocks:function(){"object"==typeof window.__TAURI_INTERNALS__&&(delete window.__TAURI_INTERNALS__.invoke,delete window.__TAURI_INTERNALS__.transformCallback,delete window.__TAURI_INTERNALS__.unregisterCallback,delete window.__TAURI_INTERNALS__.runCallback,delete window.__TAURI_INTERNALS__.callbacks,delete window.__TAURI_INTERNALS__.convertFileSrc,delete window.__TAURI_INTERNALS__.metadata,"object"==typeof window.__TAURI_EVENT_PLUGIN_INTERNALS__&&delete window.__TAURI_EVENT_PLUGIN_INTERNALS__.unregisterListener)},mockConvertFileSrc:function(e){Q(),window.__TAURI_INTERNALS__.convertFileSrc=function(n,t="asset"){const i=encodeURIComponent(n);return"windows"===e?`http://${t}.localhost/${i}`:`${t}://localhost/${i}`}},mockIPC:function(e,n){function t(e,n){switch(e){case"plugin:event|listen":return function(e){i.has(e.event)||i.set(e.event,[]);return i.get(e.event).push(e.handler),e.handler}(n);case"plugin:event|emit":return function(e){const n=i.get(e.event)||[];for(const t of n)a(t,e);return null}(n);case"plugin:event|unlisten":return function(e){const n=i.get(e.event);if(n){const t=n.indexOf(e.id);-1!==t&&n.splice(t,1)}}(n)}}Q();const i=new Map,r=new Map;function s(e){r.delete(e)}function a(e,n){const t=r.get(e);t?t(n):console.warn(`[TAURI] Couldn't find callback id ${e}. This might happen when the app is reloaded while Rust is running an asynchronous operation.`)}window.__TAURI_INTERNALS__.invoke=async function(i,r,s){return(null==n?void 0:n.shouldMockEvents)&&function(e){return e.startsWith("plugin:event|")}(i)?t(i,r):e(i,r)},window.__TAURI_INTERNALS__.transformCallback=function(e,n=!1){const t=window.crypto.getRandomValues(new Uint32Array(1))[0];return r.set(t,i=>(n&&s(t),e&&e(i))),t},window.__TAURI_INTERNALS__.unregisterCallback=s,window.__TAURI_INTERNALS__.runCallback=a,window.__TAURI_INTERNALS__.callbacks=r,window.__TAURI_EVENT_PLUGIN_INTERNALS__.unregisterListener=function(e,n){s(n)}},mockWindows:function(e,...n){Q(),window.__TAURI_INTERNALS__.metadata={currentWindow:{label:e},currentWebview:{windowLabel:e,label:e}}}});!function(e){e[e.Audio=1]="Audio",e[e.Cache=2]="Cache",e[e.Config=3]="Config",e[e.Data=4]="Data",e[e.LocalData=5]="LocalData",e[e.Document=6]="Document",e[e.Download=7]="Download",e[e.Picture=8]="Picture",e[e.Public=9]="Public",e[e.Video=10]="Video",e[e.Resource=11]="Resource",e[e.Temp=12]="Temp",e[e.AppConfig=13]="AppConfig",e[e.AppData=14]="AppData",e[e.AppLocalData=15]="AppLocalData",e[e.AppCache=16]="AppCache",e[e.AppLog=17]="AppLog",e[e.Desktop=18]="Desktop",e[e.Executable=19]="Executable",e[e.Font=20]="Font",e[e.Home=21]="Home",e[e.Runtime=22]="Runtime",e[e.Template=23]="Template"}(Z||(Z={}));var Y=Object.freeze({__proto__:null,get BaseDirectory(){return Z},appCacheDir:async function(){return h("plugin:path|resolve_directory",{directory:Z.AppCache})},appConfigDir:async function(){return h("plugin:path|resolve_directory",{directory:Z.AppConfig})},appDataDir:async function(){return h("plugin:path|resolve_directory",{directory:Z.AppData})},appLocalDataDir:async function(){return h("plugin:path|resolve_directory",{directory:Z.AppLocalData})},appLogDir:async function(){return h("plugin:path|resolve_directory",{directory:Z.AppLog})},audioDir:async function(){return h("plugin:path|resolve_directory",{directory:Z.Audio})},basename:async function(e,n){return h("plugin:path|basename",{path:e,ext:n})},cacheDir:async function(){return h("plugin:path|resolve_directory",{directory:Z.Cache})},configDir:async function(){return h("plugin:path|resolve_directory",{directory:Z.Config})},dataDir:async function(){return h("plugin:path|resolve_directory",{directory:Z.Data})},delimiter:function(){return window.__TAURI_INTERNALS__.plugins.path.delimiter},desktopDir:async function(){return h("plugin:path|resolve_directory",{directory:Z.Desktop})},dirname:async function(e){return h("plugin:path|dirname",{path:e})},documentDir:async function(){return h("plugin:path|resolve_directory",{directory:Z.Document})},downloadDir:async function(){return h("plugin:path|resolve_directory",{directory:Z.Download})},executableDir:async function(){return h("plugin:path|resolve_directory",{directory:Z.Executable})},extname:async function(e){return h("plugin:path|extname",{path:e})},fontDir:async function(){return h("plugin:path|resolve_directory",{directory:Z.Font})},homeDir:async function(){return h("plugin:path|resolve_directory",{directory:Z.Home})},isAbsolute:async function(e){return h("plugin:path|is_absolute",{path:e})},join:async function(...e){return h("plugin:path|join",{paths:e})},localDataDir:async function(){return h("plugin:path|resolve_directory",{directory:Z.LocalData})},normalize:async function(e){return h("plugin:path|normalize",{path:e})},pictureDir:async function(){return h("plugin:path|resolve_directory",{directory:Z.Picture})},publicDir:async function(){return h("plugin:path|resolve_directory",{directory:Z.Public})},resolve:async function(...e){return h("plugin:path|resolve",{paths:e})},resolveResource:async function(e){return h("plugin:path|resolve_directory",{directory:Z.Resource,path:e})},resourceDir:async function(){return h("plugin:path|resolve_directory",{directory:Z.Resource})},runtimeDir:async function(){return h("plugin:path|resolve_directory",{directory:Z.Runtime})},sep:function(){return window.__TAURI_INTERNALS__.plugins.path.sep},tempDir:async function(){return h("plugin:path|resolve_directory",{directory:Z.Temp})},templateDir:async function(){return h("plugin:path|resolve_directory",{directory:Z.Template})},videoDir:async function(){return h("plugin:path|resolve_directory",{directory:Z.Video})}});class X extends w{constructor(e,n){super(e),this.id=n}static async getById(e){return h("plugin:tray|get_by_id",{id:e}).then(n=>n?new X(n,e):null)}static async removeById(e){return h("plugin:tray|remove_by_id",{id:e})}static async new(e){(null==e?void 0:e.menu)&&(e.menu=[e.menu.rid,e.menu.kind]),(null==e?void 0:e.icon)&&(e.icon=g(e.icon));const n=new c;if(null==e?void 0:e.action){const t=e.action;n.onmessage=e=>t(function(e){const n=e;return n.position=new I(e.position),n.rect.position=new I(e.rect.position),n.rect.size=new k(e.rect.size),n}(e)),delete e.action}return h("plugin:tray|new",{options:null!=e?e:{},handler:n}).then(([e,n])=>new X(e,n))}async setIcon(e){let n=null;return e&&(n=g(e)),h("plugin:tray|set_icon",{rid:this.rid,icon:n})}async setMenu(e){return e&&(e=[e.rid,e.kind]),h("plugin:tray|set_menu",{rid:this.rid,menu:e})}async setTooltip(e){return h("plugin:tray|set_tooltip",{rid:this.rid,tooltip:e})}async setTitle(e){return h("plugin:tray|set_title",{rid:this.rid,title:e})}async setVisible(e){return h("plugin:tray|set_visible",{rid:this.rid,visible:e})}async setTempDirPath(e){return h("plugin:tray|set_temp_dir_path",{rid:this.rid,path:e})}async setIconAsTemplate(e){return h("plugin:tray|set_icon_as_template",{rid:this.rid,asTemplate:e})}async setIconWithAsTemplate(e,n){let t=null;return e&&(t=g(e)),h("plugin:tray|set_icon_with_as_template",{rid:this.rid,icon:t,asTemplate:n})}async setMenuOnLeftClick(e){return h("plugin:tray|set_show_menu_on_left_click",{rid:this.rid,onLeft:e})}async setShowMenuOnLeftClick(e){return h("plugin:tray|set_show_menu_on_left_click",{rid:this.rid,onLeft:e})}}var ee,ne,te=Object.freeze({__proto__:null,TrayIcon:X});!function(e){e[e.Critical=1]="Critical",e[e.Informational=2]="Informational"}(ee||(ee={}));class ie{constructor(e){this._preventDefault=!1,this.event=e.event,this.id=e.id}preventDefault(){this._preventDefault=!0}isPreventDefault(){return this._preventDefault}}function re(){return new le(window.__TAURI_INTERNALS__.metadata.currentWindow.label,{skip:!0})}async function se(){return h("plugin:window|get_all_windows").then(e=>e.map(e=>new le(e,{skip:!0})))}!function(e){e.None="none",e.Normal="normal",e.Indeterminate="indeterminate",e.Paused="paused",e.Error="error"}(ne||(ne={}));const ae=["tauri://created","tauri://error"];class le{constructor(e,n={}){var t;this.label=e,this.listeners=Object.create(null),(null==n?void 0:n.skip)||h("plugin:window|create",{options:{...n,parent:"string"==typeof n.parent?n.parent:null===(t=n.parent)||void 0===t?void 0:t.label,label:e}}).then(async()=>this.emit("tauri://created")).catch(async e=>this.emit("tauri://error",e))}static async getByLabel(e){var n;return null!==(n=(await se()).find(n=>n.label===e))&&void 0!==n?n:null}static getCurrent(){return re()}static async getAll(){return se()}static async getFocusedWindow(){for(const e of await se())if(await e.isFocused())return e;return null}async listen(e,n){return this._handleTauriEvent(e,n)?()=>{const t=this.listeners[e];t.splice(t.indexOf(n),1)}:N(e,n,{target:{kind:"Window",label:this.label}})}async once(e,n){return this._handleTauriEvent(e,n)?()=>{const t=this.listeners[e];t.splice(t.indexOf(n),1)}:L(e,n,{target:{kind:"Window",label:this.label}})}async emit(e,n){if(!ae.includes(e))return C(e,n);for(const t of this.listeners[e]||[])t({event:e,id:-1,payload:n})}async emitTo(e,n,t){if(!ae.includes(n))return x(e,n,t);for(const e of this.listeners[n]||[])e({event:n,id:-1,payload:t})}_handleTauriEvent(e,n){return!!ae.includes(e)&&(e in this.listeners?this.listeners[e].push(n):this.listeners[e]=[n],!0)}async scaleFactor(){return h("plugin:window|scale_factor",{label:this.label})}async innerPosition(){return h("plugin:window|inner_position",{label:this.label}).then(e=>new I(e))}async outerPosition(){return h("plugin:window|outer_position",{label:this.label}).then(e=>new I(e))}async innerSize(){return h("plugin:window|inner_size",{label:this.label}).then(e=>new k(e))}async outerSize(){return h("plugin:window|outer_size",{label:this.label}).then(e=>new k(e))}async isFullscreen(){return h("plugin:window|is_fullscreen",{label:this.label})}async isMinimized(){return h("plugin:window|is_minimized",{label:this.label})}async isMaximized(){return h("plugin:window|is_maximized",{label:this.label})}async isFocused(){return h("plugin:window|is_focused",{label:this.label})}async isDecorated(){return h("plugin:window|is_decorated",{label:this.label})}async isResizable(){return h("plugin:window|is_resizable",{label:this.label})}async isMaximizable(){return h("plugin:window|is_maximizable",{label:this.label})}async isMinimizable(){return h("plugin:window|is_minimizable",{label:this.label})}async isClosable(){return h("plugin:window|is_closable",{label:this.label})}async isVisible(){return h("plugin:window|is_visible",{label:this.label})}async title(){return h("plugin:window|title",{label:this.label})}async theme(){return h("plugin:window|theme",{label:this.label})}async isAlwaysOnTop(){return h("plugin:window|is_always_on_top",{label:this.label})}async activityName(){return h("plugin:window|activity_name",{label:this.label})}async sceneIdentifier(){return h("plugin:window|scene_identifier",{label:this.label})}async center(){return h("plugin:window|center",{label:this.label})}async requestUserAttention(e){let n=null;return e&&(n=e===ee.Critical?{type:"Critical"}:{type:"Informational"}),h("plugin:window|request_user_attention",{label:this.label,value:n})}async setResizable(e){return h("plugin:window|set_resizable",{label:this.label,value:e})}async setEnabled(e){return h("plugin:window|set_enabled",{label:this.label,value:e})}async isEnabled(){return h("plugin:window|is_enabled",{label:this.label})}async setMaximizable(e){return h("plugin:window|set_maximizable",{label:this.label,value:e})}async setMinimizable(e){return h("plugin:window|set_minimizable",{label:this.label,value:e})}async setClosable(e){return h("plugin:window|set_closable",{label:this.label,value:e})}async setTitle(e){return h("plugin:window|set_title",{label:this.label,value:e})}async maximize(){return h("plugin:window|maximize",{label:this.label})}async unmaximize(){return h("plugin:window|unmaximize",{label:this.label})}async toggleMaximize(){return h("plugin:window|toggle_maximize",{label:this.label})}async minimize(){return h("plugin:window|minimize",{label:this.label})}async unminimize(){return h("plugin:window|unminimize",{label:this.label})}async show(){return h("plugin:window|show",{label:this.label})}async hide(){return h("plugin:window|hide",{label:this.label})}async close(){return h("plugin:window|close",{label:this.label})}async destroy(){return h("plugin:window|destroy",{label:this.label})}async setDecorations(e){return h("plugin:window|set_decorations",{label:this.label,value:e})}async setShadow(e){return h("plugin:window|set_shadow",{label:this.label,value:e})}async setEffects(e){return h("plugin:window|set_effects",{label:this.label,value:e})}async clearEffects(){return h("plugin:window|set_effects",{label:this.label,value:null})}async setAlwaysOnTop(e){return h("plugin:window|set_always_on_top",{label:this.label,value:e})}async setAlwaysOnBottom(e){return h("plugin:window|set_always_on_bottom",{label:this.label,value:e})}async setContentProtected(e){return h("plugin:window|set_content_protected",{label:this.label,value:e})}async setSize(e){return h("plugin:window|set_size",{label:this.label,value:e instanceof A?e:new A(e)})}async setMinSize(e){return h("plugin:window|set_min_size",{label:this.label,value:e instanceof A?e:e?new A(e):null})}async setMaxSize(e){return h("plugin:window|set_max_size",{label:this.label,value:e instanceof A?e:e?new A(e):null})}async setSizeConstraints(e){function n(e){return e?{Logical:e}:null}return h("plugin:window|set_size_constraints",{label:this.label,value:{minWidth:n(null==e?void 0:e.minWidth),minHeight:n(null==e?void 0:e.minHeight),maxWidth:n(null==e?void 0:e.maxWidth),maxHeight:n(null==e?void 0:e.maxHeight)}})}async setPosition(e){return h("plugin:window|set_position",{label:this.label,value:e instanceof E?e:new E(e)})}async setFullscreen(e){return h("plugin:window|set_fullscreen",{label:this.label,value:e})}async setSimpleFullscreen(e){return h("plugin:window|set_simple_fullscreen",{label:this.label,value:e})}async setFocus(){return h("plugin:window|set_focus",{label:this.label})}async setFocusable(e){return h("plugin:window|set_focusable",{label:this.label,value:e})}async setIcon(e){return h("plugin:window|set_icon",{label:this.label,value:g(e)})}async setSkipTaskbar(e){return h("plugin:window|set_skip_taskbar",{label:this.label,value:e})}async setCursorGrab(e){return h("plugin:window|set_cursor_grab",{label:this.label,value:e})}async setCursorVisible(e){return h("plugin:window|set_cursor_visible",{label:this.label,value:e})}async setCursorIcon(e){return h("plugin:window|set_cursor_icon",{label:this.label,value:e})}async setBackgroundColor(e){return h("plugin:window|set_background_color",{color:e})}async setCursorPosition(e){return h("plugin:window|set_cursor_position",{label:this.label,value:e instanceof E?e:new E(e)})}async setIgnoreCursorEvents(e){return h("plugin:window|set_ignore_cursor_events",{label:this.label,value:e})}async startDragging(){return h("plugin:window|start_dragging",{label:this.label})}async startResizeDragging(e){return h("plugin:window|start_resize_dragging",{label:this.label,value:e})}async setBadgeCount(e){return h("plugin:window|set_badge_count",{label:this.label,value:e})}async setBadgeLabel(e){return h("plugin:window|set_badge_label",{label:this.label,value:e})}async setOverlayIcon(e){return h("plugin:window|set_overlay_icon",{label:this.label,value:e?g(e):void 0})}async setProgressBar(e){return h("plugin:window|set_progress_bar",{label:this.label,value:e})}async setVisibleOnAllWorkspaces(e){return h("plugin:window|set_visible_on_all_workspaces",{label:this.label,value:e})}async setTitleBarStyle(e){return h("plugin:window|set_title_bar_style",{label:this.label,value:e})}async setTheme(e){return h("plugin:window|set_theme",{label:this.label,value:e})}async onResized(e){return this.listen(R.WINDOW_RESIZED,n=>{n.payload=new k(n.payload),e(n)})}async onMoved(e){return this.listen(R.WINDOW_MOVED,n=>{n.payload=new I(n.payload),e(n)})}async onCloseRequested(e){return this.listen(R.WINDOW_CLOSE_REQUESTED,async n=>{const t=new ie(n);await e(t),t.isPreventDefault()||await this.destroy()})}async onDragDropEvent(e){const n=await this.listen(R.DRAG_ENTER,n=>{e({...n,payload:{type:"enter",paths:n.payload.paths,position:new I(n.payload.position)}})}),t=await this.listen(R.DRAG_OVER,n=>{e({...n,payload:{type:"over",position:new I(n.payload.position)}})}),i=await this.listen(R.DRAG_DROP,n=>{e({...n,payload:{type:"drop",paths:n.payload.paths,position:new I(n.payload.position)}})}),r=await this.listen(R.DRAG_LEAVE,n=>{e({...n,payload:{type:"leave"}})});return()=>{n(),i(),t(),r()}}async onFocusChanged(e){const n=await this.listen(R.WINDOW_FOCUS,n=>{e({...n,payload:!0})}),t=await this.listen(R.WINDOW_BLUR,n=>{e({...n,payload:!1})});return()=>{n(),t()}}async onScaleChanged(e){return this.listen(R.WINDOW_SCALE_FACTOR_CHANGED,e)}async onThemeChanged(e){return this.listen(R.WINDOW_THEME_CHANGED,e)}}var oe,ue,ce,de;function pe(e){return null===e?null:{name:e.name,scaleFactor:e.scaleFactor,position:new I(e.position),size:new k(e.size),workArea:{position:new I(e.workArea.position),size:new k(e.workArea.size)}}}!function(e){e.Disabled="disabled",e.Throttle="throttle",e.Suspend="suspend"}(oe||(oe={})),function(e){e.Default="default",e.FluentOverlay="fluentOverlay"}(ue||(ue={})),function(e){e.AppearanceBased="appearanceBased",e.Light="light",e.Dark="dark",e.MediumLight="mediumLight",e.UltraDark="ultraDark",e.Titlebar="titlebar",e.Selection="selection",e.Menu="menu",e.Popover="popover",e.Sidebar="sidebar",e.HeaderView="headerView",e.Sheet="sheet",e.WindowBackground="windowBackground",e.HudWindow="hudWindow",e.FullScreenUI="fullScreenUI",e.Tooltip="tooltip",e.ContentBackground="contentBackground",e.UnderWindowBackground="underWindowBackground",e.UnderPageBackground="underPageBackground",e.Mica="mica",e.Blur="blur",e.Acrylic="acrylic",e.Tabbed="tabbed",e.TabbedDark="tabbedDark",e.TabbedLight="tabbedLight"}(ce||(ce={})),function(e){e.FollowsWindowActiveState="followsWindowActiveState",e.Active="active",e.Inactive="inactive"}(de||(de={}));var he=Object.freeze({__proto__:null,CloseRequestedEvent:ie,get Effect(){return ce},get EffectState(){return de},LogicalPosition:T,LogicalSize:v,PhysicalPosition:I,PhysicalSize:k,get ProgressBarStatus(){return ne},get UserAttentionType(){return ee},Window:le,availableMonitors:async function(){return h("plugin:window|available_monitors").then(e=>e.map(pe))},currentMonitor:async function(){return h("plugin:window|current_monitor").then(pe)},cursorPosition:async function(){return h("plugin:window|cursor_position").then(e=>new I(e))},getAllWindows:se,getCurrentWindow:re,monitorFromPoint:async function(e,n){return h("plugin:window|monitor_from_point",{x:e,y:n}).then(pe)},primaryMonitor:async function(){return h("plugin:window|primary_monitor").then(pe)}});function we(){return new ge(re(),window.__TAURI_INTERNALS__.metadata.currentWebview.label,{skip:!0})}async function _e(){return h("plugin:webview|get_all_webviews").then(e=>e.map(e=>new ge(new le(e.windowLabel,{skip:!0}),e.label,{skip:!0})))}const ye=["tauri://created","tauri://error"];class ge{constructor(e,n,t){this.window=e,this.label=n,this.listeners=Object.create(null),(null==t?void 0:t.skip)||h("plugin:webview|create_webview",{windowLabel:e.label,options:{...t,label:n}}).then(async()=>this.emit("tauri://created")).catch(async e=>this.emit("tauri://error",e))}static async getByLabel(e){var n;return null!==(n=(await _e()).find(n=>n.label===e))&&void 0!==n?n:null}static getCurrent(){return we()}static async getAll(){return _e()}async listen(e,n){return this._handleTauriEvent(e,n)?()=>{const t=this.listeners[e];t.splice(t.indexOf(n),1)}:N(e,n,{target:{kind:"Webview",label:this.label}})}async once(e,n){return this._handleTauriEvent(e,n)?()=>{const t=this.listeners[e];t.splice(t.indexOf(n),1)}:L(e,n,{target:{kind:"Webview",label:this.label}})}async emit(e,n){if(!ye.includes(e))return C(e,n);for(const t of this.listeners[e]||[])t({event:e,id:-1,payload:n})}async emitTo(e,n,t){if(!ye.includes(n))return x(e,n,t);for(const e of this.listeners[n]||[])e({event:n,id:-1,payload:t})}_handleTauriEvent(e,n){return!!ye.includes(e)&&(e in this.listeners?this.listeners[e].push(n):this.listeners[e]=[n],!0)}async position(){return h("plugin:webview|webview_position",{label:this.label}).then(e=>new I(e))}async size(){return h("plugin:webview|webview_size",{label:this.label}).then(e=>new k(e))}async close(){return h("plugin:webview|webview_close",{label:this.label})}async setSize(e){return h("plugin:webview|set_webview_size",{label:this.label,value:e instanceof A?e:new A(e)})}async setPosition(e){return h("plugin:webview|set_webview_position",{label:this.label,value:e instanceof E?e:new E(e)})}async setFocus(){return h("plugin:webview|set_webview_focus",{label:this.label})}async setAutoResize(e){return h("plugin:webview|set_webview_auto_resize",{label:this.label,value:e})}async hide(){return h("plugin:webview|webview_hide",{label:this.label})}async show(){return h("plugin:webview|webview_show",{label:this.label})}async setZoom(e){return h("plugin:webview|set_webview_zoom",{label:this.label,value:e})}async reparent(e){return h("plugin:webview|reparent",{label:this.label,window:"string"==typeof e?e:e.label})}async clearAllBrowsingData(){return h("plugin:webview|clear_all_browsing_data")}async setBackgroundColor(e){return h("plugin:webview|set_webview_background_color",{color:e})}async onDragDropEvent(e){const n=await this.listen(R.DRAG_ENTER,n=>{e({...n,payload:{type:"enter",paths:n.payload.paths,position:new I(n.payload.position)}})}),t=await this.listen(R.DRAG_OVER,n=>{e({...n,payload:{type:"over",position:new I(n.payload.position)}})}),i=await this.listen(R.DRAG_DROP,n=>{e({...n,payload:{type:"drop",paths:n.payload.paths,position:new I(n.payload.position)}})}),r=await this.listen(R.DRAG_LEAVE,n=>{e({...n,payload:{type:"leave"}})});return()=>{n(),i(),t(),r()}}}var be,me,fe=Object.freeze({__proto__:null,Webview:ge,getAllWebviews:_e,getCurrentWebview:we});function ve(){const e=we();return new Ae(e.label,{skip:!0})}async function ke(){return h("plugin:window|get_all_windows").then(e=>e.map(e=>new Ae(e,{skip:!0})))}class Ae{constructor(e,n={}){var t;this.label=e,this.listeners=Object.create(null),(null==n?void 0:n.skip)||h("plugin:webview|create_webview_window",{options:{...n,parent:"string"==typeof n.parent?n.parent:null===(t=n.parent)||void 0===t?void 0:t.label,label:e}}).then(async()=>this.emit("tauri://created")).catch(async e=>this.emit("tauri://error",e))}static async getByLabel(e){var n;const t=null!==(n=(await ke()).find(n=>n.label===e))&&void 0!==n?n:null;return t?new Ae(t.label,{skip:!0}):null}static getCurrent(){return ve()}static async getAll(){return ke()}async listen(e,n){return this._handleTauriEvent(e,n)?()=>{const t=this.listeners[e];t.splice(t.indexOf(n),1)}:N(e,n,{target:{kind:"WebviewWindow",label:this.label}})}async once(e,n){return this._handleTauriEvent(e,n)?()=>{const t=this.listeners[e];t.splice(t.indexOf(n),1)}:L(e,n,{target:{kind:"WebviewWindow",label:this.label}})}async setBackgroundColor(e){return h("plugin:window|set_background_color",{color:e}).then(()=>h("plugin:webview|set_webview_background_color",{color:e}))}}be=Ae,me=[le,ge],(Array.isArray(me)?me:[me]).forEach(e=>{Object.getOwnPropertyNames(e.prototype).forEach(n=>{var t;"object"==typeof be.prototype&&be.prototype&&n in be.prototype||Object.defineProperty(be.prototype,n,null!==(t=Object.getOwnPropertyDescriptor(e.prototype,n))&&void 0!==t?t:Object.create(null))})});var Te=Object.freeze({__proto__:null,WebviewWindow:Ae,getAllWebviewWindows:ke,getCurrentWebviewWindow:ve});return e.app=f,e.core=_,e.dpi=D,e.event=O,e.image=m,e.menu=J,e.mocks=K,e.path=Y,e.tray=te,e.webview=fe,e.webviewWindow=Te,e.window=he,e}({});window.__TAURI__=__TAURI_IIFE__; diff --git a/crates/tauri/src/tray/mod.rs b/crates/tauri/src/tray/mod.rs index 5ecef674a709..a10f74386726 100644 --- a/crates/tauri/src/tray/mod.rs +++ b/crates/tauri/src/tray/mod.rs @@ -566,6 +566,38 @@ impl TrayIcon { Ok(()) } + /// Sets the tray icon and template status atomically. **macOS only**. + /// + /// On macOS, calling `set_icon` followed by `set_icon_as_template` causes a visible + /// flicker as the icon is rendered twice. This method sets both atomically to prevent that. + /// + /// ## Platform-specific: + /// + /// - **Linux / Windows:** Falls back to calling `set_icon`. + pub fn set_icon_with_as_template( + &self, + icon: Option>, + #[allow(unused)] is_template: bool, + ) -> crate::Result<()> { + #[cfg(target_os = "macos")] + { + let tray_icon = match icon { + Some(i) => Some(i.try_into()?), + None => None, + }; + run_item_main_thread!(self, |self_: Self| { + self_ + .inner + .set_icon_with_as_template(tray_icon, is_template) + })??; + } + #[cfg(not(target_os = "macos"))] + { + self.set_icon(icon)?; + } + Ok(()) + } + /// Disable or enable showing the tray menu on left click. /// /// diff --git a/crates/tauri/src/tray/plugin.rs b/crates/tauri/src/tray/plugin.rs index dfba7743093d..f2d74ca5adda 100644 --- a/crates/tauri/src/tray/plugin.rs +++ b/crates/tauri/src/tray/plugin.rs @@ -203,6 +203,24 @@ fn set_icon_as_template( tray.set_icon_as_template(as_template) } +#[command(root = "crate")] +fn set_icon_with_as_template( + app: AppHandle, + webview: Webview, + rid: ResourceId, + icon: Option, + as_template: bool, +) -> crate::Result<()> { + let resources_table = app.resources_table(); + let tray = resources_table.get::>(rid)?; + let webview_resources_table = webview.resources_table(); + let icon = match icon { + Some(i) => Some(i.into_img(&webview_resources_table)?.as_ref().clone()), + None => None, + }; + tray.set_icon_with_as_template(icon, as_template) +} + #[command(root = "crate")] fn set_show_menu_on_left_click( app: AppHandle, @@ -228,6 +246,7 @@ pub(crate) fn init() -> TauriPlugin { set_visible, set_temp_dir_path, set_icon_as_template, + set_icon_with_as_template, set_show_menu_on_left_click, ]) .build() diff --git a/packages/api/src/tray.ts b/packages/api/src/tray.ts index fabe3e3567bf..c7bce20abb65 100644 --- a/packages/api/src/tray.ts +++ b/packages/api/src/tray.ts @@ -296,6 +296,31 @@ export class TrayIcon extends Resource { }) } + /** + * Sets a new tray icon and template status atomically. **macOS only**. + * + * Note that you may need the `image-ico` or `image-png` Cargo features to use this API. + * To enable it, change your Cargo.toml file: + * ```toml + * [dependencies] + * tauri = { version = "...", features = ["...", "image-png"] } + * ``` + */ + async setIconWithAsTemplate( + icon: string | Image | Uint8Array | ArrayBuffer | number[] | null, + asTemplate: boolean + ): Promise { + let trayIcon = null + if (icon) { + trayIcon = transformImage(icon) + } + return invoke('plugin:tray|set_icon_with_as_template', { + rid: this.rid, + icon: trayIcon, + asTemplate + }) + } + /** * Disable or enable showing the tray menu on left click. * From 2d8d154947d8f941e53c0e1ebccd2b4376f142ab Mon Sep 17 00:00:00 2001 From: Oscar Beaumont Date: Wed, 29 Apr 2026 22:43:56 +0800 Subject: [PATCH 85/95] Update Specta in lockfile to fix documentation (#15177) * update Specta in lockfile * Create change-pr-15177.md * update sha1 and sha2 dependencies * Update changeset * update changefile * sha1 0.10 --------- Co-authored-by: Lucas Nogueira --- .changes/change-pr-15177.md | 6 ++++++ Cargo.lock | 10 +++++----- 2 files changed, 11 insertions(+), 5 deletions(-) create mode 100644 .changes/change-pr-15177.md diff --git a/.changes/change-pr-15177.md b/.changes/change-pr-15177.md new file mode 100644 index 000000000000..f15e72aca316 --- /dev/null +++ b/.changes/change-pr-15177.md @@ -0,0 +1,6 @@ +--- +"tauri": patch:deps +"tauri-bundler": patch:deps +--- + +Update Specta in lockfile and upgrade dependencies using the removed `doc_auto_cfg` attribute to fix errors building documentation diff --git a/Cargo.lock b/Cargo.lock index 3f2544cd1385..bc10293acf6c 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -2021,7 +2021,7 @@ dependencies = [ "libc", "option-ext", "redox_users 0.5.0", - "windows-sys 0.59.0", + "windows-sys 0.60.2", ] [[package]] @@ -5520,7 +5520,7 @@ source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "7d8fae84b431384b68627d0f9b3b1245fcf9f46f6c0e3dc902e9dce64edd1967" dependencies = [ "libc", - "windows-sys 0.45.0", + "windows-sys 0.60.2", ] [[package]] @@ -7382,7 +7382,7 @@ dependencies = [ "security-framework 3.5.1", "security-framework-sys", "webpki-root-certs", - "windows-sys 0.52.0", + "windows-sys 0.60.2", ] [[package]] @@ -9889,9 +9889,9 @@ checksum = "0e13db2e0ccd5e14a544e8a246ba2312cd25223f616442d7f2cb0e3db614236e" [[package]] name = "typenum" -version = "1.17.0" +version = "1.20.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "42ff0bf0c66b8238c6f3b578df37d0b7848e55df8577b3f74f92a69acceeb825" +checksum = "40ce102ab67701b8526c123c1bab5cbe42d7040ccfd0f64af1a385808d2f43de" [[package]] name = "typewit" From 35f9a7b7a182496a24e7a349044f9c61120c85cb Mon Sep 17 00:00:00 2001 From: Lucas Fernandes Nogueira Date: Wed, 29 Apr 2026 13:24:27 -0300 Subject: [PATCH 86/95] fix: doc links (#15300) --- crates/tauri-cli/config.schema.json | 4 ++-- crates/tauri-plugin/src/lib.rs | 4 ++-- crates/tauri-runtime/src/webview.rs | 8 ++++---- .../schemas/config.schema.json | 4 ++-- crates/tauri-utils/src/config.rs | 4 ++-- crates/tauri/Cargo.toml | 1 + crates/tauri/src/app.rs | 2 +- crates/tauri/src/image/mod.rs | 2 +- crates/tauri/src/lib.rs | 6 +++--- crates/tauri/src/resources/mod.rs | 2 +- crates/tauri/src/webview/mod.rs | 8 ++++---- crates/tauri/src/webview/webview_window.rs | 12 +++++++++--- crates/tauri/src/window/mod.rs | 2 +- 13 files changed, 33 insertions(+), 26 deletions(-) diff --git a/crates/tauri-cli/config.schema.json b/crates/tauri-cli/config.schema.json index f4381d54c1f0..6878c2b2adc8 100644 --- a/crates/tauri-cli/config.schema.json +++ b/crates/tauri-cli/config.schema.json @@ -550,7 +550,7 @@ ] }, "backgroundThrottling": { - "description": "Change the default background throttling behaviour.\n\n By default, browsers use a suspend policy that will throttle timers and even unload\n the whole tab (view) to free resources after roughly 5 minutes when a view became\n minimized or hidden. This will pause all tasks until the documents visibility state\n changes back from hidden to visible by bringing the view back to the foreground.\n\n ## Platform-specific\n\n - **Linux / Windows / Android**: Unsupported. Workarounds like a pending WebLock transaction might suffice.\n - **iOS**: Supported since version 17.0+.\n - **macOS**: Supported since version 14.0+.\n\n see https://github.com/tauri-apps/tauri/issues/5250#issuecomment-2569380578", + "description": "Change the default background throttling behaviour.\n\n By default, browsers use a suspend policy that will throttle timers and even unload\n the whole tab (view) to free resources after roughly 5 minutes when a view became\n minimized or hidden. This will pause all tasks until the documents visibility state\n changes back from hidden to visible by bringing the view back to the foreground.\n\n ## Platform-specific\n\n - **Linux / Windows / Android**: Unsupported. Workarounds like a pending WebLock transaction might suffice.\n - **iOS**: Supported since version 17.0+.\n - **macOS**: Supported since version 14.0+.\n\n see ", "anyOf": [ { "$ref": "#/definitions/BackgroundThrottlingPolicy" @@ -1160,7 +1160,7 @@ ] }, { - "description": "Fluent UI style overlay scrollbars. **Windows Only**\n\n Requires WebView2 Runtime version 125.0.2535.41 or higher, does nothing on older versions,\n see https://learn.microsoft.com/en-us/microsoft-edge/webview2/release-notes/?tabs=dotnetcsharp#10253541", + "description": "Fluent UI style overlay scrollbars. **Windows Only**\n\n Requires WebView2 Runtime version 125.0.2535.41 or higher, does nothing on older versions,\n see ", "type": "string", "enum": [ "fluentOverlay" diff --git a/crates/tauri-plugin/src/lib.rs b/crates/tauri-plugin/src/lib.rs index 74c1fb941ed6..4c21a6af46ba 100644 --- a/crates/tauri-plugin/src/lib.rs +++ b/crates/tauri-plugin/src/lib.rs @@ -16,9 +16,9 @@ mod build; mod runtime; #[cfg(feature = "build")] -#[cfg_attr(docsrs, doc(feature = "build"))] +#[cfg_attr(docsrs, doc(cfg(feature = "build")))] pub use build::*; #[cfg(feature = "runtime")] -#[cfg_attr(docsrs, doc(feature = "runtime"))] +#[cfg_attr(docsrs, doc(cfg(feature = "runtime")))] #[allow(unused)] pub use runtime::*; diff --git a/crates/tauri-runtime/src/webview.rs b/crates/tauri-runtime/src/webview.rs index d4f7e0145313..d7fb9c80f311 100644 --- a/crates/tauri-runtime/src/webview.rs +++ b/crates/tauri-runtime/src/webview.rs @@ -104,7 +104,7 @@ pub struct NewWindowOpener { pub webview: webkit2gtk::WebView, /// The instance of the webview that initiated the new window request. /// - /// The target webview environment **MUST** match the environment of the opener webview. See [`WebviewAttributes::environment`]. + /// The target webview environment **MUST** match the environment of the opener webview. See [`WebviewAttributes::with_environment`]. #[cfg(windows)] pub webview: webview2_com::Microsoft::Web::WebView2::Win32::ICoreWebView2, #[cfg(windows)] @@ -167,7 +167,7 @@ pub enum NewWindowResponse { /// ## Platform-specific: /// /// **Linux**: The webview must be related to the caller webview. See [`WebviewAttributes::related_view`]. - /// **Windows**: The webview must use the same environment as the caller webview. See [`WebviewAttributes::environment`]. + /// **Windows**: The webview must use the same environment as the caller webview. See [`WebviewAttributes::with_environment`]. #[cfg(not(any(target_os = "android", target_os = "ios")))] Create { window_id: WindowId }, /// Deny the window from being opened. @@ -190,7 +190,7 @@ pub enum ScrollBarStyle { /// Fluent UI style overlay scrollbars. **Windows Only** /// /// Requires WebView2 Runtime version 125.0.2535.41 or higher, does nothing on older versions, - /// see https://learn.microsoft.com/en-us/microsoft-edge/webview2/release-notes/?tabs=dotnetcsharp#10253541 + /// see FluentOverlay, } @@ -802,7 +802,7 @@ impl WebviewAttributes { /// - **iOS**: Supported since version 17.0+. /// - **macOS**: Supported since version 14.0+. /// - /// see https://github.com/tauri-apps/tauri/issues/5250#issuecomment-2569380578 + /// see #[must_use] pub fn background_throttling(mut self, policy: Option) -> Self { self.background_throttling = policy; diff --git a/crates/tauri-schema-generator/schemas/config.schema.json b/crates/tauri-schema-generator/schemas/config.schema.json index f4381d54c1f0..6878c2b2adc8 100644 --- a/crates/tauri-schema-generator/schemas/config.schema.json +++ b/crates/tauri-schema-generator/schemas/config.schema.json @@ -550,7 +550,7 @@ ] }, "backgroundThrottling": { - "description": "Change the default background throttling behaviour.\n\n By default, browsers use a suspend policy that will throttle timers and even unload\n the whole tab (view) to free resources after roughly 5 minutes when a view became\n minimized or hidden. This will pause all tasks until the documents visibility state\n changes back from hidden to visible by bringing the view back to the foreground.\n\n ## Platform-specific\n\n - **Linux / Windows / Android**: Unsupported. Workarounds like a pending WebLock transaction might suffice.\n - **iOS**: Supported since version 17.0+.\n - **macOS**: Supported since version 14.0+.\n\n see https://github.com/tauri-apps/tauri/issues/5250#issuecomment-2569380578", + "description": "Change the default background throttling behaviour.\n\n By default, browsers use a suspend policy that will throttle timers and even unload\n the whole tab (view) to free resources after roughly 5 minutes when a view became\n minimized or hidden. This will pause all tasks until the documents visibility state\n changes back from hidden to visible by bringing the view back to the foreground.\n\n ## Platform-specific\n\n - **Linux / Windows / Android**: Unsupported. Workarounds like a pending WebLock transaction might suffice.\n - **iOS**: Supported since version 17.0+.\n - **macOS**: Supported since version 14.0+.\n\n see ", "anyOf": [ { "$ref": "#/definitions/BackgroundThrottlingPolicy" @@ -1160,7 +1160,7 @@ ] }, { - "description": "Fluent UI style overlay scrollbars. **Windows Only**\n\n Requires WebView2 Runtime version 125.0.2535.41 or higher, does nothing on older versions,\n see https://learn.microsoft.com/en-us/microsoft-edge/webview2/release-notes/?tabs=dotnetcsharp#10253541", + "description": "Fluent UI style overlay scrollbars. **Windows Only**\n\n Requires WebView2 Runtime version 125.0.2535.41 or higher, does nothing on older versions,\n see ", "type": "string", "enum": [ "fluentOverlay" diff --git a/crates/tauri-utils/src/config.rs b/crates/tauri-utils/src/config.rs index e4aeee7ea797..78da42a4945d 100644 --- a/crates/tauri-utils/src/config.rs +++ b/crates/tauri-utils/src/config.rs @@ -1903,7 +1903,7 @@ pub enum ScrollBarStyle { /// Fluent UI style overlay scrollbars. **Windows Only** /// /// Requires WebView2 Runtime version 125.0.2535.41 or higher, does nothing on older versions, - /// see https://learn.microsoft.com/en-us/microsoft-edge/webview2/release-notes/?tabs=dotnetcsharp#10253541 + /// see FluentOverlay, } @@ -2195,7 +2195,7 @@ pub struct WindowConfig { /// - **iOS**: Supported since version 17.0+. /// - **macOS**: Supported since version 14.0+. /// - /// see https://github.com/tauri-apps/tauri/issues/5250#issuecomment-2569380578 + /// see #[serde(default, alias = "background-throttling")] pub background_throttling: Option, /// Whether we should disable JavaScript code execution on the webview or not. diff --git a/crates/tauri/Cargo.toml b/crates/tauri/Cargo.toml index 0c9a9665c597..0ab1a954f9ac 100644 --- a/crates/tauri/Cargo.toml +++ b/crates/tauri/Cargo.toml @@ -26,6 +26,7 @@ features = [ "test", "specta", "dynamic-acl", + "isolation", ] default-target = "x86_64-unknown-linux-gnu" targets = [ diff --git a/crates/tauri/src/app.rs b/crates/tauri/src/app.rs index 8bd9df66ee8c..5b5bf5ae2e05 100644 --- a/crates/tauri/src/app.rs +++ b/crates/tauri/src/app.rs @@ -285,7 +285,7 @@ impl From for RunEvent { } } -/// The asset resolver is a helper to access the [`tauri_utils::assets::Assets`] interface. +/// The asset resolver is a helper to access the [`crate::Assets`] interface. #[derive(Debug, Clone)] pub struct AssetResolver { manager: Arc>, diff --git a/crates/tauri/src/image/mod.rs b/crates/tauri/src/image/mod.rs index 9dec4165802b..c25e98de5f29 100644 --- a/crates/tauri/src/image/mod.rs +++ b/crates/tauri/src/image/mod.rs @@ -194,7 +194,7 @@ impl JsImage { /// This will retrieve the image from the passed [`ResourceTable`] if it is [`JsImage::Resource`] /// and will return an error if it doesn't exist in the passed [`ResourceTable`] so make sure /// the passed [`ResourceTable`] is the same one used to store the image, usually this should be - /// the webview [resources table](crate::webview::Webview::resources_table). + /// the webview resources table. pub fn into_img(self, resources_table: &ResourceTable) -> crate::Result>> { match self { Self::Resource(rid) => resources_table.get::>(rid), diff --git a/crates/tauri/src/lib.rs b/crates/tauri/src/lib.rs index 38cbbc3a58ec..261f7e887de0 100644 --- a/crates/tauri/src/lib.rs +++ b/crates/tauri/src/lib.rs @@ -33,10 +33,10 @@ //! - **compression** *(enabled by default): Enables asset compression. You should only disable this if you want faster compile times in release builds - it produces larger binaries. //! - **config-json5**: Adds support to JSON5 format for `tauri.conf.json`. //! - **config-toml**: Adds support to TOML format for the configuration `Tauri.toml`. -//! - **image-ico**: Adds support to parse `.ico` image, see [`Image`]. -//! - **image-png**: Adds support to parse `.png` image, see [`Image`]. +//! - **image-ico**: Adds support to parse `.ico` image, see [`image::Image`]. +//! - **image-png**: Adds support to parse `.png` image, see [`image::Image`]. //! - **macos-proxy**: Adds support for [`WebviewBuilder::proxy_url`] on macOS. Requires macOS 14+. -//! - **specta**: Add support for [`specta::specta`](https://docs.rs/specta/%5E2.0.0-rc.9/specta/attr.specta.html) with Tauri arguments such as [`State`](crate::State), [`Window`](crate::Window) and [`AppHandle`](crate::AppHandle) +//! - **specta**: Add support for [`specta::specta`](https://docs.rs/specta/%5E2.0.0-rc.9/specta/attr.specta.html) with Tauri arguments such as [`State`], [`Window`] and [`AppHandle`] //! - **dynamic-acl** *(enabled by default)*: Enables you to add ACLs at runtime, notably it enables the [`Manager::add_capability`] function. //! //! ## Cargo allowlist features diff --git a/crates/tauri/src/resources/mod.rs b/crates/tauri/src/resources/mod.rs index d393bca6577a..3a65c3a6fd6f 100644 --- a/crates/tauri/src/resources/mod.rs +++ b/crates/tauri/src/resources/mod.rs @@ -140,7 +140,7 @@ impl ResourceTable { } /// Returns a reference counted pointer to the resource of the given `rid`. - /// If `rid` is not present, this function returns [`Error::BadResourceId`]. + /// If `rid` is not present, this function returns [`crate::Error::BadResourceId`]. pub fn get_any(&self, rid: ResourceId) -> crate::Result> { self .index diff --git a/crates/tauri/src/webview/mod.rs b/crates/tauri/src/webview/mod.rs index b86eb01a223c..c30b8f040563 100644 --- a/crates/tauri/src/webview/mod.rs +++ b/crates/tauri/src/webview/mod.rs @@ -243,8 +243,8 @@ pub enum NewWindowResponse { /// /// ## Platform-specific: /// - /// **Linux**: The webview must be related to the caller webview. See [`WebviewBuilder::related_view`]. - /// **Windows**: The webview must use the same environment as the caller webview. See [`WebviewBuilder::environment`]. + /// **Linux**: The webview must be related to the caller webview. See [`WebviewBuilder::with_related_view`]. + /// **Windows**: The webview must use the same environment as the caller webview. See [`WebviewBuilder::with_environment`]. /// **macOS**: The webview must use the same webview configuration as the caller webview. See [`WebviewBuilder::with_webview_configuration`] and [`NewWindowFeatures::webview_configuration`]. Create { /// Window that was created. @@ -1146,7 +1146,7 @@ fn main() { /// - **iOS**: Supported since version 17.0+. /// - **macOS**: Supported since version 14.0+. /// - /// see https://github.com/tauri-apps/tauri/issues/5250#issuecomment-2569380578 + /// see #[must_use] pub fn background_throttling(mut self, policy: BackgroundThrottlingPolicy) -> Self { self.webview_attributes.background_throttling = Some(policy); @@ -1664,7 +1664,7 @@ tauri::Builder::default() "#### )] #[cfg(feature = "wry")] - #[cfg_attr(docsrs, doc(feature = "wry"))] + #[cfg_attr(docsrs, doc(cfg(feature = "wry")))] pub fn with_webview( &self, f: F, diff --git a/crates/tauri/src/webview/webview_window.rs b/crates/tauri/src/webview/webview_window.rs index 95bf67719399..8db5db27dbd3 100644 --- a/crates/tauri/src/webview/webview_window.rs +++ b/crates/tauri/src/webview/webview_window.rs @@ -938,6 +938,9 @@ impl> WebviewWindowBuilder<'_, R, M> { /// }); /// } /// ``` + /// + /// [addDocumentStartJavaScript]: https://developer.android.com/reference/androidx/webkit/WebViewCompat#addDocumentStartJavaScript(android.webkit.WebView,java.lang.String,java.util.Set%3Cjava.lang.String%3E) + /// [onPageStarted]: https://developer.android.com/reference/android/webkit/WebViewClient#onPageStarted(android.webkit.WebView,%20java.lang.String,%20android.graphics.Bitmap) #[must_use] pub fn initialization_script(mut self, script: impl Into) -> Self { self.webview_builder = self.webview_builder.initialization_script(script); @@ -980,6 +983,9 @@ impl> WebviewWindowBuilder<'_, R, M> { /// }); /// } /// ``` + /// + /// [addDocumentStartJavaScript]: https://developer.android.com/reference/androidx/webkit/WebViewCompat#addDocumentStartJavaScript(android.webkit.WebView,java.lang.String,java.util.Set%3Cjava.lang.String%3E) + /// [onPageStarted]: https://developer.android.com/reference/android/webkit/WebViewClient#onPageStarted(android.webkit.WebView,%20java.lang.String,%20android.graphics.Bitmap) #[must_use] pub fn initialization_script_for_all_frames(mut self, script: impl Into) -> Self { self.webview_builder = self @@ -1193,7 +1199,7 @@ impl> WebviewWindowBuilder<'_, R, M> { /// - **iOS**: Supported since version 17.0+. /// - **macOS**: Supported since version 14.0+. /// - /// see https://github.com/tauri-apps/tauri/issues/5250#issuecomment-2569380578 + /// see #[must_use] pub fn background_throttling(mut self, policy: BackgroundThrottlingPolicy) -> Self { self.webview_builder = self.webview_builder.background_throttling(policy); @@ -2195,7 +2201,7 @@ impl WebviewWindow { self.window.hide() } - /// Closes this window. It emits [`crate::RunEvent::CloseRequested`] first like a user-initiated close request so you can intercept it. + /// Closes this window. It emits [`crate::WindowEvent::CloseRequested`] first like a user-initiated close request so you can intercept it. pub fn close(&self) -> crate::Result<()> { self.window.close() } @@ -2349,7 +2355,7 @@ impl WebviewWindow { /// ``` #[allow(clippy::needless_doctest_main)] // To avoid a large diff #[cfg(feature = "wry")] - #[cfg_attr(docsrs, doc(feature = "wry"))] + #[cfg_attr(docsrs, doc(cfg(feature = "wry")))] pub fn with_webview( &self, f: F, diff --git a/crates/tauri/src/window/mod.rs b/crates/tauri/src/window/mod.rs index faaaca48b006..6be20288bd0c 100644 --- a/crates/tauri/src/window/mod.rs +++ b/crates/tauri/src/window/mod.rs @@ -1778,7 +1778,7 @@ impl Window { self.window.dispatcher.hide().map_err(Into::into) } - /// Closes this window. It emits [`crate::RunEvent::CloseRequested`] first like a user-initiated close request so you can intercept it. + /// Closes this window. It emits [`crate::WindowEvent::CloseRequested`] first like a user-initiated close request so you can intercept it. pub fn close(&self) -> crate::Result<()> { self.window.dispatcher.close().map_err(Into::into) } From ea5a7f5ec8fe1cfb29fcb299afc83550fea868a2 Mon Sep 17 00:00:00 2001 From: Tony <68118705+Legend-Master@users.noreply.github.com> Date: Thu, 30 Apr 2026 00:27:43 +0800 Subject: [PATCH 87/95] fix(schema-worker): return content type json (#15301) * fix(schema-worker): return content type json * Revert "fix(schema-worker): return content type json" This reverts commit 6f80c05c31616404e45812e202ed5133b8f0f5d2. * Use a `into_response` struct instead so we don't have to serde the json --- crates/tauri-schema-worker/src/config.rs | 28 +++++++++++++++++++----- 1 file changed, 23 insertions(+), 5 deletions(-) diff --git a/crates/tauri-schema-worker/src/config.rs b/crates/tauri-schema-worker/src/config.rs index f5daef987c32..a5274b89b781 100644 --- a/crates/tauri-schema-worker/src/config.rs +++ b/crates/tauri-schema-worker/src/config.rs @@ -5,8 +5,8 @@ use anyhow::Context; use axum::{ extract::Path, - http::{header, StatusCode}, - response::Result, + http::{header, HeaderValue, StatusCode}, + response::{IntoResponse, Result}, routing::get, Router, }; @@ -48,23 +48,26 @@ pub fn router() -> Router { .route("/config/{version}", get(schema_for_version)) } -async fn schema_for_version(Path(version): Path) -> Result { +async fn schema_for_version(Path(version): Path) -> Result { try_schema_for_version(version) .await + .map(JsonResponse) .map_err(|e| (StatusCode::INTERNAL_SERVER_ERROR, e.to_string())) .map_err(Into::into) } -async fn stable_schema() -> Result { +async fn stable_schema() -> Result { try_stable_schema() .await + .map(JsonResponse) .map_err(|e| (StatusCode::INTERNAL_SERVER_ERROR, e.to_string())) .map_err(Into::into) } -async fn next_schema() -> Result { +async fn next_schema() -> Result { try_next_schema() .await + .map(JsonResponse) .map_err(|e| (StatusCode::INTERNAL_SERVER_ERROR, e.to_string())) .map_err(Into::into) } @@ -172,3 +175,18 @@ fn fetch_req(url: &str) -> anyhow::Result { ) .map_err(Into::into) } + +struct JsonResponse(String); + +impl IntoResponse for JsonResponse { + fn into_response(self) -> axum::response::Response { + ( + [( + header::CONTENT_TYPE, + HeaderValue::from_static("application/json"), + )], + self.0, + ) + .into_response() + } +} From ea4bf8f1757810e4faff29a35c803152800d653f Mon Sep 17 00:00:00 2001 From: "renovate[bot]" <29139614+renovate[bot]@users.noreply.github.com> Date: Wed, 29 Apr 2026 14:51:24 -0300 Subject: [PATCH 88/95] chore(deps): update rust crate muda to 0.19 (#15259) * chore(deps): update rust crate muda to 0.18 * bumps --------- Co-authored-by: renovate[bot] <29139614+renovate[bot]@users.noreply.github.com> Co-authored-by: Lucas Nogueira --- Cargo.lock | 10 +++++----- crates/tauri/Cargo.toml | 4 ++-- 2 files changed, 7 insertions(+), 7 deletions(-) diff --git a/Cargo.lock b/Cargo.lock index bc10293acf6c..b36d3592a613 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -4738,9 +4738,9 @@ dependencies = [ [[package]] name = "muda" -version = "0.17.2" +version = "0.19.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "7c9fec5a4e89860383d778d10563a605838f8f0b2f9303868937e5ff32e86177" +checksum = "0ae8844f63b5b118e334e205585b8c5c17b984121dbdb179d44aeb087ffad3cb" dependencies = [ "crossbeam-channel", "dpi", @@ -4752,7 +4752,7 @@ dependencies = [ "objc2-core-foundation", "objc2-foundation 0.3.0", "once_cell", - "png 0.17.16", + "png 0.18.1", "serde", "thiserror 2.0.12", "windows-sys 0.60.2", @@ -9788,9 +9788,9 @@ dependencies = [ [[package]] name = "tray-icon" -version = "0.22.1" +version = "0.23.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "7f9eb1da86bd0ab8931fad00650d2ba7473260c5bab06d6f24d04339edb88faa" +checksum = "1064cf4fbfa2c60f453e7a9125bc53add41de2d83d1cba7a497636e6520c345b" dependencies = [ "crossbeam-channel", "dirs 6.0.0", diff --git a/crates/tauri/Cargo.toml b/crates/tauri/Cargo.toml index 0ab1a954f9ac..ba2329abc20c 100644 --- a/crates/tauri/Cargo.toml +++ b/crates/tauri/Cargo.toml @@ -87,11 +87,11 @@ cookie = "0.18" # desktop [target.'cfg(any(target_os = "linux", target_os = "dragonfly", target_os = "freebsd", target_os = "openbsd", target_os = "netbsd", target_os = "windows", target_os = "macos"))'.dependencies] -muda = { version = "0.17", default-features = false, features = [ +muda = { version = "0.19", default-features = false, features = [ "serde", "gtk", ] } -tray-icon = { version = "0.22", default-features = false, features = [ +tray-icon = { version = "0.23", default-features = false, features = [ "serde", ], optional = true } From fb3d0998205d54512d0bbee8b356c00558d47c98 Mon Sep 17 00:00:00 2001 From: "renovate[bot]" <29139614+renovate[bot]@users.noreply.github.com> Date: Thu, 30 Apr 2026 10:19:13 +0800 Subject: [PATCH 89/95] chore(deps): update worker-rs crates to 0.8 (#15233) * chore(deps): update worker-rs crates to 0.8 * dedupe --------- Co-authored-by: renovate[bot] <29139614+renovate[bot]@users.noreply.github.com> Co-authored-by: Tony --- Cargo.lock | 77 +++++++++++++++++---------- crates/tauri-schema-worker/Cargo.toml | 4 +- 2 files changed, 51 insertions(+), 30 deletions(-) diff --git a/Cargo.lock b/Cargo.lock index b36d3592a613..b4d6c8dd625c 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -4054,10 +4054,12 @@ checksum = "f5d4a7da358eff58addd2877a45865158f0d78c911d43a5784ceb7bbf52833b0" [[package]] name = "js-sys" -version = "0.3.83" +version = "0.3.97" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "464a3709c7f55f1f721e5389aa6ea4e3bc6aba669353300af094b29ffbdde1d8" +checksum = "a1840c94c045fbcf8ba2812c95db44499f7c64910a912551aaaa541decebcacf" dependencies = [ + "cfg-if", + "futures-util", "once_cell", "wasm-bindgen", ] @@ -6944,9 +6946,9 @@ dependencies = [ [[package]] name = "reqwest" -version = "0.13.1" +version = "0.13.3" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "04e9018c9d814e5f30cc16a0f03271aeab3571e609612d9fe78c1aa8d11c2f62" +checksum = "62e0021ea2c22aed41653bc7e1419abb2c97e038ff2c33d0e1309e49a97deec0" dependencies = [ "base64 0.22.1", "bytes", @@ -8449,6 +8451,27 @@ version = "0.11.1" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "7da8b5736845d9f2fcb837ea5d9e2628564b3b043a70948a3f0b778838c5fb4f" +[[package]] +name = "strum" +version = "0.27.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "af23d6f6c1a224baef9d3f61e287d2761385a5b88fdab4eb4c6f11aeb54c4bcf" +dependencies = [ + "strum_macros", +] + +[[package]] +name = "strum_macros" +version = "0.27.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "7695ce3845ea4b33927c055a39dc438a45b059f7c1b3d91d38d10355fb8cbca7" +dependencies = [ + "heck 0.5.0", + "proc-macro2", + "quote", + "syn 2.0.117", +] + [[package]] name = "sublime_fuzzy" version = "0.7.0" @@ -8776,7 +8799,7 @@ dependencies = [ "quickcheck", "quickcheck_macros", "raw-window-handle", - "reqwest 0.13.1", + "reqwest 0.13.3", "rustls 0.23.35", "serde", "serde_json", @@ -10364,9 +10387,9 @@ dependencies = [ [[package]] name = "wasm-bindgen" -version = "0.2.106" +version = "0.2.120" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "0d759f433fa64a2d763d1340820e46e111a7a5ab75f993d1852d70b03dbb80fd" +checksum = "df52b6d9b87e0c74c9edfa1eb2d9bf85e5d63515474513aa50fa181b3c4f5db1" dependencies = [ "cfg-if", "once_cell", @@ -10377,22 +10400,19 @@ dependencies = [ [[package]] name = "wasm-bindgen-futures" -version = "0.4.56" +version = "0.4.70" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "836d9622d604feee9e5de25ac10e3ea5f2d65b41eac0d9ce72eb5deae707ce7c" +checksum = "af934872acec734c2d80e6617bbb5ff4f12b052dd8e6332b0817bce889516084" dependencies = [ - "cfg-if", "js-sys", - "once_cell", "wasm-bindgen", - "web-sys", ] [[package]] name = "wasm-bindgen-macro" -version = "0.2.106" +version = "0.2.120" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "48cb0d2638f8baedbc542ed444afc0644a29166f1595371af4fecf8ce1e7eeb3" +checksum = "78b1041f495fb322e64aca85f5756b2172e35cd459376e67f2a6c9dffcedb103" dependencies = [ "quote", "wasm-bindgen-macro-support", @@ -10400,9 +10420,9 @@ dependencies = [ [[package]] name = "wasm-bindgen-macro-support" -version = "0.2.106" +version = "0.2.120" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "cefb59d5cd5f92d9dcf80e4683949f15ca4b511f4ac0a6e14d4e1ac60c6ecd40" +checksum = "9dcd0ff20416988a18ac686d4d4d0f6aae9ebf08a389ff5d29012b05af2a1b41" dependencies = [ "bumpalo", "proc-macro2", @@ -10413,18 +10433,18 @@ dependencies = [ [[package]] name = "wasm-bindgen-shared" -version = "0.2.106" +version = "0.2.120" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "cbc538057e648b67f72a982e708d485b2efa771e1ac05fec311f9f63e5800db4" +checksum = "49757b3c82ebf16c57d69365a142940b384176c24df52a087fb748e2085359ea" dependencies = [ "unicode-ident", ] [[package]] name = "wasm-streams" -version = "0.4.2" +version = "0.5.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "15053d8d85c7eccdbefef60f06769760a563c7f0a9d6902a13d35c7800b0ad65" +checksum = "9d1ec4f6517c9e11ae630e200b2b65d193279042e28edd4a2cda233e46670bbb" dependencies = [ "futures-util", "js-sys", @@ -10435,9 +10455,9 @@ dependencies = [ [[package]] name = "web-sys" -version = "0.3.83" +version = "0.3.97" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "9b32828d774c412041098d182a8b38b16ea816958e07cf40eec2bc080ae137ac" +checksum = "2eadbac71025cd7b0834f20d1fe8472e8495821b4e9801eb0a60bd1f19827602" dependencies = [ "js-sys", "wasm-bindgen", @@ -11135,9 +11155,9 @@ dependencies = [ [[package]] name = "worker" -version = "0.7.1" +version = "0.8.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "42c76c5889873a2c309365ad4503810c007d3c25fbb4e9fa9e4e23c4ceb3c7f2" +checksum = "4afd7ae4f7fcc11e0e5e64b964890b3dda90f1290b0612f7cd821b381cc18826" dependencies = [ "async-trait", "axum", @@ -11166,13 +11186,14 @@ dependencies = [ [[package]] name = "worker-macros" -version = "0.7.1" +version = "0.8.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "62c62584d037bad33789a6a5d605b3fccea1c52de9251d06f9d44054170dc612" +checksum = "6371f41ac538c9f6dbe4d40cf7db58ed451eb0529a66f3e29ab8726217fc8a05" dependencies = [ "async-trait", "proc-macro2", "quote", + "strum", "syn 2.0.117", "wasm-bindgen", "wasm-bindgen-futures", @@ -11182,9 +11203,9 @@ dependencies = [ [[package]] name = "worker-sys" -version = "0.7.1" +version = "0.8.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "72ddd412fd62c6eeffc1dd85e6ae5960a33b534f44a733df75b6e7519972bc74" +checksum = "4c8de95c532944cee89d63fa8d7945f3db6260ca75ee3da42f7acfeebf538e4c" dependencies = [ "cfg-if", "js-sys", diff --git a/crates/tauri-schema-worker/Cargo.toml b/crates/tauri-schema-worker/Cargo.toml index 34da45cc7258..64e319fba85d 100644 --- a/crates/tauri-schema-worker/Cargo.toml +++ b/crates/tauri-schema-worker/Cargo.toml @@ -8,8 +8,8 @@ publish = false crate-type = ["cdylib"] [dependencies] -worker = { version = "0.7", features = ['http', 'axum'] } -worker-macros = { version = "0.7", features = ['http'] } +worker = { version = "0.8", features = ['http', 'axum'] } +worker-macros = { version = "0.8", features = ['http'] } console_error_panic_hook = { version = "0.1" } axum = { version = "0.8", default-features = false } tower-service = "0.3" From 65d11fd08da697da57b2df2438e2003d1d3ee076 Mon Sep 17 00:00:00 2001 From: Tony <68118705+Legend-Master@users.noreply.github.com> Date: Thu, 30 Apr 2026 10:35:43 +0800 Subject: [PATCH 90/95] fix(deps): update worker-build to 0.8 (#15304) --- crates/tauri-schema-worker/wrangler.toml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/crates/tauri-schema-worker/wrangler.toml b/crates/tauri-schema-worker/wrangler.toml index 661b6059ab28..e7e56a635766 100644 --- a/crates/tauri-schema-worker/wrangler.toml +++ b/crates/tauri-schema-worker/wrangler.toml @@ -9,7 +9,7 @@ send_metrics = false # The minor version of worker-build must match worker/worker-macros in Cargo.toml! [build] -command = "cargo install -q worker-build@^0.7 && worker-build --release" +command = "cargo install -q worker-build@^0.8 && worker-build --release" [observability] enabled = true From a15c0397be1c183218516d0d4323a59ff8507477 Mon Sep 17 00:00:00 2001 From: Rohit Singh <27754873+razein97@users.noreply.github.com> Date: Thu, 30 Apr 2026 11:57:18 +0530 Subject: [PATCH 91/95] rename os_bitness to processor_architecture --- .changes/change-pr-14923.md | 18 ------------------ .../tauri-bundler/src/bundle/windows/sign.rs | 2 +- .../tauri-bundler/src/bundle/windows/util.rs | 6 +++--- 3 files changed, 4 insertions(+), 22 deletions(-) delete mode 100644 .changes/change-pr-14923.md diff --git a/.changes/change-pr-14923.md b/.changes/change-pr-14923.md deleted file mode 100644 index d4ab557a9f78..000000000000 --- a/.changes/change-pr-14923.md +++ /dev/null @@ -1,18 +0,0 @@ ---- -"@tauri-apps/api": patch -"tauri-utils": patch -"tauri-macos-sign": patch -"tauri-bundler": patch -"tauri-runtime": patch -"tauri-runtime-wry": patch -"tauri-codegen": patch -"tauri-macros": patch -"tauri-plugin": patch -"tauri-build": patch -"tauri": patch -"@tauri-apps/cli": patch -"tauri-cli": patch -"tauri-driver": patch ---- - -fix(windows): tauri-bundler detect arm system diff --git a/crates/tauri-bundler/src/bundle/windows/sign.rs b/crates/tauri-bundler/src/bundle/windows/sign.rs index f7c7ad1e2122..d9922f58ff69 100644 --- a/crates/tauri-bundler/src/bundle/windows/sign.rs +++ b/crates/tauri-bundler/src/bundle/windows/sign.rs @@ -97,7 +97,7 @@ fn signtool() -> Option { kit_bin_paths.push(kits_root_10_bin_path); // Choose which version of SignTool to use based on OS bitness - let arch_dir = util::os_bitness().ok_or(crate::Error::UnsupportedBitness)?; + let arch_dir = util::processor_architecture().ok_or(crate::Error::UnsupportedBitness)?; /* Iterate through all bin paths, checking for existence of a SignTool executable. */ for kit_bin_path in &kit_bin_paths { diff --git a/crates/tauri-bundler/src/bundle/windows/util.rs b/crates/tauri-bundler/src/bundle/windows/util.rs index 60706976d0d5..e716ad7bbef5 100644 --- a/crates/tauri-bundler/src/bundle/windows/util.rs +++ b/crates/tauri-bundler/src/bundle/windows/util.rs @@ -64,10 +64,10 @@ pub fn download_webview2_offline_installer(base_path: &Path, arch: &str) -> crat } #[cfg(target_os = "windows")] -pub fn os_bitness<'a>() -> Option<&'a str> { +pub fn processor_architecture<'a>() -> Option<&'a str> { use windows_sys::Win32::System::SystemInformation::{ - GetNativeSystemInfo, PROCESSOR_ARCHITECTURE_AMD64, PROCESSOR_ARCHITECTURE_INTEL, SYSTEM_INFO, - PROCESSOR_ARCHITECTURE_ARM, PROCESSOR_ARCHITECTURE_ARM64, + GetNativeSystemInfo, PROCESSOR_ARCHITECTURE_AMD64, PROCESSOR_ARCHITECTURE_ARM, + PROCESSOR_ARCHITECTURE_ARM64, PROCESSOR_ARCHITECTURE_INTEL, SYSTEM_INFO, }; let mut system_info: SYSTEM_INFO = unsafe { std::mem::zeroed() }; From 1fc2b8fa514945f71ce650283b56d8bb7390140f Mon Sep 17 00:00:00 2001 From: Rohit Singh <27754873+razein97@users.noreply.github.com> Date: Thu, 30 Apr 2026 12:00:03 +0530 Subject: [PATCH 92/95] Update windows_arm_signtool_detect.md remove arm32 changes --- .changes/windows_arm_signtool_detect.md | 7 ++++--- 1 file changed, 4 insertions(+), 3 deletions(-) diff --git a/.changes/windows_arm_signtool_detect.md b/.changes/windows_arm_signtool_detect.md index 889255763a88..7d951e7f3dcb 100644 --- a/.changes/windows_arm_signtool_detect.md +++ b/.changes/windows_arm_signtool_detect.md @@ -7,9 +7,10 @@ Signtool path for windows arm systems was not being properly returned which caus This patch addresses it. Previously only the following were supported: + - PROCESSOR_ARCHITECTURE_INTEL - PROCESSOR_ARCHITECTURE_AMD64 -The following were added: -- PROCESSOR_ARCHITECTURE_ARM -- PROCESSOR_ARCHITECTURE_ARM64 \ No newline at end of file +The following were added: + +- PROCESSOR_ARCHITECTURE_ARM64 From 57945e439d8e30524787213b212b10737b874071 Mon Sep 17 00:00:00 2001 From: Lucas Fernandes Nogueira Date: Thu, 30 Apr 2026 07:13:11 -0300 Subject: [PATCH 93/95] update change file --- .changes/windows_arm_signtool_detect.md | 1 + 1 file changed, 1 insertion(+) diff --git a/.changes/windows_arm_signtool_detect.md b/.changes/windows_arm_signtool_detect.md index 7d951e7f3dcb..afff5dc2b395 100644 --- a/.changes/windows_arm_signtool_detect.md +++ b/.changes/windows_arm_signtool_detect.md @@ -13,4 +13,5 @@ Previously only the following were supported: The following were added: +- PROCESSOR_ARCHITECTURE_ARM - PROCESSOR_ARCHITECTURE_ARM64 From 763cd6e452f0da993e74b94121601e6fb35a7122 Mon Sep 17 00:00:00 2001 From: Tony <68118705+Legend-Master@users.noreply.github.com> Date: Thu, 30 Apr 2026 17:06:17 +0800 Subject: [PATCH 94/95] fix(deps): update specta in lockfile (#15303) Co-authored-by: Oscar Beaumont --- Cargo.lock | 10 +++++----- 1 file changed, 5 insertions(+), 5 deletions(-) diff --git a/Cargo.lock b/Cargo.lock index b4d6c8dd625c..80f882b31ec7 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -8325,20 +8325,20 @@ dependencies = [ [[package]] name = "specta" -version = "2.0.0-rc.20" +version = "2.0.0-rc.24" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "4ccbb212565d2dc177bc15ecb7b039d66c4490da892436a4eee5b394d620c9bc" +checksum = "f320c7dd82008b6958f43f6257c95319c407d1c17ade43686e50ea520c28bb26" dependencies = [ "paste", + "rustc_version", "specta-macros", - "thiserror 1.0.69", ] [[package]] name = "specta-macros" -version = "2.0.0-rc.17" +version = "2.0.0-rc.24" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "68999d29816965eb9e5201f60aec02a76512139811661a7e8e653abc810b8f72" +checksum = "153f185d0051a64d81977bab5012809d5c9d9db8792406a0997352e05494f711" dependencies = [ "Inflector", "proc-macro2", From cb11bd9c47c51aae15f4e1b256cd459a792b3fc3 Mon Sep 17 00:00:00 2001 From: Andrew de Waal Date: Thu, 30 Apr 2026 02:55:06 -0700 Subject: [PATCH 95/95] feat: Add support for Android build variants (feat #14777) (#14886) * feat: Add support for Android build variants (feat #14777) * synchronize with build.gradle.kts * update cargo-mobile2 * change to a applicationIdSuffix map to support more variants * Revert "change to a applicationIdSuffix map to support more variants" This reverts commit d251c31fe629ce5a907b12e46d9e7ff0d6de3140. * do not apply .debug suffix by default for existing projects * kotlin raw string support --------- Co-authored-by: Lucas Nogueira --- Cargo.lock | 4 +- crates/tauri-cli/Cargo.toml | 2 +- crates/tauri-cli/config.schema.json | 7 + crates/tauri-cli/schema.json | 7 + crates/tauri-cli/src/mobile/android/build.rs | 3 +- crates/tauri-cli/src/mobile/android/dev.rs | 29 +- crates/tauri-cli/src/mobile/android/mod.rs | 366 ++++++++++++++++++ crates/tauri-cli/src/mobile/android/run.rs | 22 +- crates/tauri-cli/src/mobile/init.rs | 7 + crates/tauri-cli/tauri.config.schema.json | 9 +- .../mobile/android/app/build.gradle.kts | 3 + crates/tauri-cli/templates/tauri.conf.json | 5 +- .../schemas/config.schema.json | 7 + crates/tauri-utils/src/config.rs | 7 + 14 files changed, 464 insertions(+), 14 deletions(-) diff --git a/Cargo.lock b/Cargo.lock index 80f882b31ec7..11cd62da6e0d 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -1055,9 +1055,9 @@ dependencies = [ [[package]] name = "cargo-mobile2" -version = "0.22.3" +version = "0.22.4" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "4409d8c4087e66ff08bae7497ef311dbdedcf9903049d66228056f99ebd2a19b" +checksum = "caa0060b6b7e1c0f14312c8ccebf28f5713b3045ffaae033a180622122a361dc" dependencies = [ "colored", "core-foundation 0.10.0", diff --git a/crates/tauri-cli/Cargo.toml b/crates/tauri-cli/Cargo.toml index 9e216f6c55a3..fa460e15a68a 100644 --- a/crates/tauri-cli/Cargo.toml +++ b/crates/tauri-cli/Cargo.toml @@ -36,7 +36,7 @@ name = "cargo-tauri" path = "src/main.rs" [target."cfg(any(target_os = \"linux\", target_os = \"dragonfly\", target_os = \"freebsd\", target_os = \"openbsd\", target_os = \"netbsd\", target_os = \"windows\", target_os = \"macos\"))".dependencies] -cargo-mobile2 = { version = "0.22.3", default-features = false } +cargo-mobile2 = { version = "0.22.4", default-features = false } [dependencies] jsonrpsee = { version = "0.24", features = ["server"] } diff --git a/crates/tauri-cli/config.schema.json b/crates/tauri-cli/config.schema.json index 6878c2b2adc8..6b0ec229bd96 100644 --- a/crates/tauri-cli/config.schema.json +++ b/crates/tauri-cli/config.schema.json @@ -3919,6 +3919,13 @@ "description": "Whether to automatically increment the `versionCode` on each build.\n\n - If `true`, the generator will try to read the last `versionCode` from\n `tauri.properties` and increment it by 1 for every build.\n - If `false` or not set, it falls back to `version_code` or semver-derived logic.\n\n Note that to use this feature, you should remove `/tauri.properties` from `src-tauri/gen/android/app/.gitignore` so the current versionCode is committed to the repository.", "default": false, "type": "boolean" + }, + "debugApplicationIdSuffix": { + "description": "Application ID suffix to append for debug builds.\n This allows installing debug and release versions side-by-side on the same device.\n Example: \".debug\" will make debug builds use \"com.example.app.debug\" as the application ID.", + "type": [ + "string", + "null" + ] } }, "additionalProperties": false diff --git a/crates/tauri-cli/schema.json b/crates/tauri-cli/schema.json index 6bd2b3bc87bf..903f05633e63 100644 --- a/crates/tauri-cli/schema.json +++ b/crates/tauri-cli/schema.json @@ -3095,6 +3095,13 @@ "format": "uint32", "maximum": 2100000000.0, "minimum": 1.0 + }, + "debugApplicationIdSuffix": { + "description": "Application ID suffix to append for debug builds.\n This allows installing debug and release versions side-by-side on the same device.\n Example: \".debug\" will make debug builds use \"com.example.app.debug\" as the application ID.", + "type": [ + "string", + "null" + ] } }, "additionalProperties": false diff --git a/crates/tauri-cli/src/mobile/android/build.rs b/crates/tauri-cli/src/mobile/android/build.rs index 3a4369402a8a..7d5f39c8d076 100644 --- a/crates/tauri-cli/src/mobile/android/build.rs +++ b/crates/tauri-cli/src/mobile/android/build.rs @@ -4,7 +4,7 @@ use super::{ configure_cargo, delete_codegen_vars, ensure_init, env, get_app, get_config, inject_resources, - log_finished, open_and_wait, MobileTarget, OptionsHandle, + log_finished, open_and_wait, sync_debug_application_id_suffix, MobileTarget, OptionsHandle, }; use crate::{ build::Options as BuildOptions, @@ -192,6 +192,7 @@ pub fn run( configure_cargo(&mut env, &config)?; generate_tauri_properties(&config, tauri_config, false)?; + sync_debug_application_id_suffix(&config, tauri_config)?; crate::build::setup(&interface, &mut build_options, tauri_config, dirs, true)?; diff --git a/crates/tauri-cli/src/mobile/android/dev.rs b/crates/tauri-cli/src/mobile/android/dev.rs index 93692f6d0454..dec1eea932a7 100644 --- a/crates/tauri-cli/src/mobile/android/dev.rs +++ b/crates/tauri-cli/src/mobile/android/dev.rs @@ -4,7 +4,7 @@ use super::{ configure_cargo, delete_codegen_vars, device_prompt, ensure_init, env, get_app, get_config, - inject_resources, open_and_wait, MobileTarget, + inject_resources, open_and_wait, sync_debug_application_id_suffix, MobileTarget, }; use crate::{ dev::Options as DevOptions, @@ -274,6 +274,7 @@ fn run_dev( configure_cargo(&mut env, config)?; generate_tauri_properties(config, &tauri_config, true)?; + sync_debug_application_id_suffix(config, &tauri_config)?; let installed_targets = crate::interface::rust::installation::installed_targets().unwrap_or_default(); @@ -339,7 +340,15 @@ fn run_dev( if open { open_and_wait(config, &env) } else if let Some(device) = &device { - match run(device, options, config, &env, metadata, noise_level) { + match run( + device, + options, + config, + &env, + metadata, + noise_level, + tauri_config, + ) { Ok(c) => Ok(Box::new(c) as Box), Err(e) => { crate::dev::kill_before_dev_process(); @@ -361,6 +370,7 @@ fn run( env: &Env, metadata: &AndroidMetadata, noise_level: NoiseLevel, + tauri_config: &tauri_utils::config::Config, ) -> crate::Result { let profile = if options.debug { Profile::Debug @@ -370,8 +380,18 @@ fn run( let build_app_bundle = metadata.asset_packs().is_some(); + let application_id_suffix = if profile == Profile::Debug { + tauri_config + .bundle + .android + .debug_application_id_suffix + .clone() + } else { + None + }; + device - .run( + .run_with_application_id_suffix( config, env, noise_level, @@ -383,7 +403,8 @@ fn run( }), build_app_bundle, false, - ".MainActivity".into(), + format!("{}.MainActivity", config.app().identifier()), + application_id_suffix, ) .map(DevChild::new) .context("failed to run Android app") diff --git a/crates/tauri-cli/src/mobile/android/mod.rs b/crates/tauri-cli/src/mobile/android/mod.rs index 8ea6490d02c6..fc7406832660 100644 --- a/crates/tauri-cli/src/mobile/android/mod.rs +++ b/crates/tauri-cli/src/mobile/android/mod.rs @@ -25,6 +25,7 @@ use std::{ io::Cursor, path::{Path, PathBuf}, process::{exit, Command}, + sync::OnceLock, thread::sleep, time::Duration, }; @@ -188,6 +189,247 @@ pub fn get_config( (config, metadata) } +fn sync_debug_application_id_suffix( + config: &AndroidConfig, + tauri_config: &TauriConfig, +) -> Result<()> { + let build_gradle_path = config.project_dir().join("app").join("build.gradle.kts"); + let build_gradle = std::fs::read_to_string(&build_gradle_path).fs_context( + "failed to read Android Gradle build file", + build_gradle_path.clone(), + )?; + let Some(updated_build_gradle) = set_debug_application_id_suffix( + &build_gradle, + tauri_config + .bundle + .android + .debug_application_id_suffix + .as_deref(), + ) else { + crate::error::bail!( + "Could not find the Android debug build type in {}. Add a `getByName(\"debug\")` build type or run `tauri android init` to regenerate the Android project.", + build_gradle_path.display() + ); + }; + + if updated_build_gradle != build_gradle { + write(&build_gradle_path, updated_build_gradle).fs_context( + "failed to write Android Gradle build file", + build_gradle_path, + )?; + } + + Ok(()) +} + +fn set_debug_application_id_suffix(build_gradle: &str, suffix: Option<&str>) -> Option { + static DEBUG_BUILD_TYPE_RE: OnceLock = OnceLock::new(); + + let debug_build_type_re = DEBUG_BUILD_TYPE_RE.get_or_init(|| { + regex::Regex::new(r#"(?m)(?:\bgetByName\(\s*"debug"\s*\)|\bdebug\b)\s*\{"#) + .expect("valid debug build type regex") + }); + + for build_type_match in debug_build_type_re.find_iter(build_gradle) { + let Some(opening_brace) = build_gradle[build_type_match.start()..] + .find('{') + .map(|index| build_type_match.start() + index) + else { + continue; + }; + let Some(closing_brace) = find_matching_brace(build_gradle, opening_brace) else { + continue; + }; + + let debug_block = &build_gradle[opening_brace..closing_brace]; + let updated_debug_block = set_application_id_suffix_in_block(debug_block, suffix); + let mut updated_build_gradle = + String::with_capacity(build_gradle.len() + updated_debug_block.len()); + updated_build_gradle.push_str(&build_gradle[..opening_brace]); + updated_build_gradle.push_str(&updated_debug_block); + updated_build_gradle.push_str(&build_gradle[closing_brace..]); + return Some(updated_build_gradle); + } + + None +} + +fn set_application_id_suffix_in_block(debug_block: &str, suffix: Option<&str>) -> String { + static APPLICATION_ID_SUFFIX_RE: OnceLock = OnceLock::new(); + + let application_id_suffix_re = APPLICATION_ID_SUFFIX_RE.get_or_init(|| { + regex::Regex::new(r#"(?m)^[ \t]*applicationIdSuffix\s*=.*(?:\r?\n)?"#) + .expect("valid applicationIdSuffix regex") + }); + + if let Some(application_id_suffix_match) = application_id_suffix_re.find(debug_block) { + let mut updated_debug_block = String::with_capacity(debug_block.len()); + updated_debug_block.push_str(&debug_block[..application_id_suffix_match.start()]); + if let Some(suffix) = suffix { + let indentation = debug_block + [application_id_suffix_match.start()..application_id_suffix_match.end()] + .chars() + .take_while(|character| *character == ' ' || *character == '\t') + .collect::(); + updated_debug_block.push_str(&format!( + "{indentation}applicationIdSuffix = \"{}\"\n", + escape_kotlin_string(suffix) + )); + } + updated_debug_block.push_str(&debug_block[application_id_suffix_match.end()..]); + return updated_debug_block; + } + + let Some(suffix) = suffix else { + return debug_block.to_string(); + }; + + let indentation = debug_block_indentation(debug_block); + let application_id_suffix = format!( + "{indentation}applicationIdSuffix = \"{}\"\n", + escape_kotlin_string(suffix) + ); + + if let Some(first_newline) = debug_block.find('\n') { + let mut updated_debug_block = + String::with_capacity(debug_block.len() + application_id_suffix.len()); + updated_debug_block.push_str(&debug_block[..=first_newline]); + updated_debug_block.push_str(&application_id_suffix); + updated_debug_block.push_str(&debug_block[first_newline + 1..]); + updated_debug_block + } else { + format!("{{\n{application_id_suffix}") + } +} + +fn debug_block_indentation(debug_block: &str) -> &str { + debug_block + .lines() + .skip(1) + .find_map(|line| { + if line.trim().is_empty() { + None + } else { + Some(line.trim_end().trim_end_matches(line.trim_start())) + } + }) + .unwrap_or(" ") +} + +fn find_matching_brace(content: &str, opening_brace: usize) -> Option { + let mut depth = 0u32; + let mut in_line_comment = false; + let mut in_block_comment = false; + let mut in_string = false; + let mut in_raw_string = false; + let mut string_quote = '\0'; + let mut escaped = false; + let mut previous = '\0'; + let mut chars = content[opening_brace..].char_indices().peekable(); + + while let Some((relative_index, character)) = chars.next() { + let index = opening_brace + relative_index; + + if in_line_comment { + if character == '\n' { + in_line_comment = false; + } + previous = character; + continue; + } + + if in_block_comment { + if previous == '*' && character == '/' { + in_block_comment = false; + } + previous = character; + continue; + } + + if in_raw_string { + if content[index..].starts_with("\"\"\"") { + // Consume the remaining two quotes in the Kotlin raw string delimiter. + let _ = chars.next(); + let _ = chars.next(); + in_raw_string = false; + } + previous = character; + continue; + } + + if in_string { + if escaped { + escaped = false; + } else if character == '\\' { + escaped = true; + } else if character == string_quote { + in_string = false; + } + previous = character; + continue; + } + + if character == '/' && chars.peek().is_some_and(|(_, next)| *next == '/') { + in_line_comment = true; + previous = character; + continue; + } + + if character == '/' && chars.peek().is_some_and(|(_, next)| *next == '*') { + in_block_comment = true; + previous = character; + continue; + } + + if content[index..].starts_with("\"\"\"") { + // Consume the remaining two quotes in the Kotlin raw string delimiter. + let _ = chars.next(); + let _ = chars.next(); + in_raw_string = true; + previous = character; + continue; + } + + if character == '"' || character == '\'' { + in_string = true; + string_quote = character; + previous = character; + continue; + } + + if character == '{' { + depth = depth.saturating_add(1); + } else if character == '}' { + depth = depth.saturating_sub(1); + if depth == 0 { + return Some(index); + } + } + + previous = character; + } + + None +} + +fn escape_kotlin_string(value: &str) -> String { + let mut output = String::with_capacity(value.len()); + + for character in value.chars() { + match character { + '"' => output.push_str("\\\""), + '\\' => output.push_str("\\\\"), + '$' => output.push_str("\\$"), + '\n' => output.push_str("\\n"), + '\r' => output.push_str("\\r"), + '\t' => output.push_str("\\t"), + other => output.push(other), + } + } + + output +} + pub fn env(non_interactive: bool) -> Result { let env = super::env().context("failed to setup Android environment")?; ensure_env(non_interactive).context("failed to ensure Android environment")?; @@ -676,3 +918,127 @@ fn generate_tauri_properties( Ok(()) } + +#[cfg(test)] +mod tests { + use super::{find_matching_brace, set_debug_application_id_suffix}; + + #[test] + fn writes_debug_application_id_suffix() { + let build_gradle = r#" +android { + buildTypes { + getByName("debug") { + manifestPlaceholders["usesCleartextTraffic"] = "true" + } + } +} +"#; + + let updated = set_debug_application_id_suffix(build_gradle, Some(".debug")).unwrap(); + + assert!(updated.contains( + r#" getByName("debug") { + applicationIdSuffix = ".debug" + manifestPlaceholders["usesCleartextTraffic"] = "true""# + )); + } + + #[test] + fn replaces_debug_application_id_suffix() { + let build_gradle = r#" +android { + buildTypes { + getByName("debug") { + applicationIdSuffix = ".old" + manifestPlaceholders["usesCleartextTraffic"] = "true" + } + } +} +"#; + + let updated = set_debug_application_id_suffix(build_gradle, Some(".internal")).unwrap(); + + assert!(updated.contains(r#" applicationIdSuffix = ".internal""#)); + assert!(!updated.contains(r#".old"#)); + } + + #[test] + fn removes_debug_application_id_suffix() { + let build_gradle = r#" +android { + buildTypes { + getByName("debug") { + applicationIdSuffix = ".debug" + } + getByName("release") { + applicationIdSuffix = ".release" + } + } +} +"#; + + let updated = set_debug_application_id_suffix(build_gradle, None).unwrap(); + + assert!(!updated.contains(r#"applicationIdSuffix = ".debug""#)); + assert!(updated.contains(r#"applicationIdSuffix = ".release""#)); + } + + #[test] + fn writes_debug_suffix_before_nested_blocks() { + let build_gradle = r#" +android { + buildTypes { + debug { + packaging { + jniLibs.keepDebugSymbols.add("*/arm64-v8a/*.so") + } + } + } +} +"#; + + let updated = set_debug_application_id_suffix(build_gradle, Some(".internal")).unwrap(); + + assert!(updated.contains( + r#" debug { + applicationIdSuffix = ".internal" + packaging {"# + )); + } + + #[test] + fn ignores_braces_inside_kotlin_raw_strings() { + let build_gradle = r#" +android { + buildTypes { + debug { + val proguardRules = """ + -if class ** { + public *; + } + """ + manifestPlaceholders["usesCleartextTraffic"] = "true" + } + } +} +"#; + + let opening_brace = build_gradle + .find("debug {") + .and_then(|index| build_gradle[index..].find('{').map(|brace| index + brace)) + .unwrap(); + let closing_brace = find_matching_brace(build_gradle, opening_brace).unwrap(); + + assert!(build_gradle[opening_brace..closing_brace] + .contains(r#"manifestPlaceholders["usesCleartextTraffic"] = "true""#)); + + let updated = set_debug_application_id_suffix(build_gradle, Some(".debug")).unwrap(); + + assert!(updated.contains( + r#" debug { + applicationIdSuffix = ".debug" + val proguardRules = """"# + )); + } +} diff --git a/crates/tauri-cli/src/mobile/android/run.rs b/crates/tauri-cli/src/mobile/android/run.rs index 2e6c7ba012fe..f459a88e1297 100644 --- a/crates/tauri-cli/src/mobile/android/run.rs +++ b/crates/tauri-cli/src/mobile/android/run.rs @@ -10,7 +10,7 @@ use cargo_mobile2::{ use clap::{ArgAction, Parser}; use std::path::PathBuf; -use super::{configure_cargo, device_prompt, env}; +use super::{configure_cargo, device_prompt, env, sync_debug_application_id_suffix}; use crate::{ error::Context, helpers::config::ConfigMetadata, @@ -125,9 +125,22 @@ pub fn command(options: Options, noise_level: NoiseLevel) -> Result<()> { if let Some(device) = device { let config = built_application.config.clone(); let release = options.release; - let runner = move |_tauri_config: &ConfigMetadata| { + + let runner = move |tauri_config: &ConfigMetadata| { + sync_debug_application_id_suffix(&config, tauri_config)?; + + let application_id_suffix = if !release { + tauri_config + .bundle + .android + .debug_application_id_suffix + .clone() + } else { + None + }; + device - .run( + .run_with_application_id_suffix( &config, &env, noise_level, @@ -143,7 +156,8 @@ pub fn command(options: Options, noise_level: NoiseLevel) -> Result<()> { }), false, false, - ".MainActivity".into(), + format!("{}.MainActivity", config.app().identifier()), + application_id_suffix, ) .map(|c| Box::new(DevChild::new(c)) as Box) .context("failed to run Android app") diff --git a/crates/tauri-cli/src/mobile/init.rs b/crates/tauri-cli/src/mobile/init.rs index 7ace53b512a4..db7fa52f5d29 100644 --- a/crates/tauri-cli/src/mobile/init.rs +++ b/crates/tauri-cli/src/mobile/init.rs @@ -140,6 +140,13 @@ fn exec( let (config, metadata) = super::android::get_config(&app, &tauri_config, &[], &Default::default()); map.insert("android", &config); + + // Add application_id_suffix to the map for template access + // The template will access it via a helper or we'll modify template to use root context + if let Some(suffix) = &tauri_config.bundle.android.debug_application_id_suffix { + map.insert("android-debug-application-id-suffix", suffix); + } + super::android::project::gen( &config, &metadata, diff --git a/crates/tauri-cli/tauri.config.schema.json b/crates/tauri-cli/tauri.config.schema.json index b6c64b09b99b..ea575a22234f 100644 --- a/crates/tauri-cli/tauri.config.schema.json +++ b/crates/tauri-cli/tauri.config.schema.json @@ -3081,7 +3081,7 @@ "additionalProperties": false }, "AndroidConfig": { - "description": "General configuration for the iOS target.", + "description": "General configuration for the Android target.", "type": "object", "properties": { "minSdkVersion": { @@ -3100,6 +3100,13 @@ "format": "uint32", "maximum": 2100000000.0, "minimum": 1.0 + }, + "debugApplicationIdSuffix": { + "description": "Application ID suffix to append for debug builds.\n This allows installing debug and release versions side-by-side on the same device.\n Example: \".debug\" will make debug builds use \"com.example.app.debug\" as the application ID.", + "type": [ + "string", + "null" + ] } }, "additionalProperties": false diff --git a/crates/tauri-cli/templates/mobile/android/app/build.gradle.kts b/crates/tauri-cli/templates/mobile/android/app/build.gradle.kts index b1485863abf9..0f73195fa008 100644 --- a/crates/tauri-cli/templates/mobile/android/app/build.gradle.kts +++ b/crates/tauri-cli/templates/mobile/android/app/build.gradle.kts @@ -28,6 +28,9 @@ android { } buildTypes { getByName("debug") { + {{#if android-debug-application-id-suffix}} + applicationIdSuffix = "{{android-debug-application-id-suffix}}" + {{/if}} manifestPlaceholders["usesCleartextTraffic"] = "true" isDebuggable = true isJniDebuggable = true diff --git a/crates/tauri-cli/templates/tauri.conf.json b/crates/tauri-cli/templates/tauri.conf.json index 6b8354f78464..048fc0f00d8c 100644 --- a/crates/tauri-cli/templates/tauri.conf.json +++ b/crates/tauri-cli/templates/tauri.conf.json @@ -32,6 +32,9 @@ "icons/128x128@2x.png", "icons/icon.icns", "icons/icon.ico" - ] + ], + "android": { + "debugApplicationIdSuffix": ".debug" + } } } diff --git a/crates/tauri-schema-generator/schemas/config.schema.json b/crates/tauri-schema-generator/schemas/config.schema.json index 6878c2b2adc8..6b0ec229bd96 100644 --- a/crates/tauri-schema-generator/schemas/config.schema.json +++ b/crates/tauri-schema-generator/schemas/config.schema.json @@ -3919,6 +3919,13 @@ "description": "Whether to automatically increment the `versionCode` on each build.\n\n - If `true`, the generator will try to read the last `versionCode` from\n `tauri.properties` and increment it by 1 for every build.\n - If `false` or not set, it falls back to `version_code` or semver-derived logic.\n\n Note that to use this feature, you should remove `/tauri.properties` from `src-tauri/gen/android/app/.gitignore` so the current versionCode is committed to the repository.", "default": false, "type": "boolean" + }, + "debugApplicationIdSuffix": { + "description": "Application ID suffix to append for debug builds.\n This allows installing debug and release versions side-by-side on the same device.\n Example: \".debug\" will make debug builds use \"com.example.app.debug\" as the application ID.", + "type": [ + "string", + "null" + ] } }, "additionalProperties": false diff --git a/crates/tauri-utils/src/config.rs b/crates/tauri-utils/src/config.rs index 78da42a4945d..a54c619e3f6f 100644 --- a/crates/tauri-utils/src/config.rs +++ b/crates/tauri-utils/src/config.rs @@ -3232,6 +3232,12 @@ pub struct AndroidConfig { /// Note that to use this feature, you should remove `/tauri.properties` from `src-tauri/gen/android/app/.gitignore` so the current versionCode is committed to the repository. #[serde(alias = "auto-increment-version-code", default)] pub auto_increment_version_code: bool, + + /// Application ID suffix to append for debug builds. + /// This allows installing debug and release versions side-by-side on the same device. + /// Example: ".debug" will make debug builds use "com.example.app.debug" as the application ID. + #[serde(alias = "debug-application-id-suffix")] + pub debug_application_id_suffix: Option, } impl Default for AndroidConfig { @@ -3240,6 +3246,7 @@ impl Default for AndroidConfig { min_sdk_version: default_min_sdk_version(), version_code: None, auto_increment_version_code: false, + debug_application_id_suffix: None, } } }