mirror of https://github.com/tauri-apps/tauri
parent
76b8c214df
commit
d6918efdaf
|
@ -91,7 +91,7 @@ pub fn generate_run_fn(input: DeriveInput) -> TokenStream {
|
|||
|
||||
let expanded = quote! {
|
||||
impl #impl_generics #name #ty_generics #where_clause {
|
||||
pub #maybe_async fn run<R: crate::Runtime>(self, context: crate::endpoints::InvokeContext<R>) -> crate::Result<crate::endpoints::InvokeResponse> {
|
||||
pub #maybe_async fn run<R: crate::Runtime>(self, context: crate::endpoints::InvokeContext<R>) -> super::Result<crate::endpoints::InvokeResponse> {
|
||||
match self {
|
||||
#matcher
|
||||
}
|
||||
|
@ -160,9 +160,7 @@ pub fn command_handler(attributes: HandlerAttributes, function: ItemFn) -> Token
|
|||
#[allow(unused_variables)]
|
||||
#[allow(unused_mut)]
|
||||
#signature {
|
||||
Err(crate::Error::ApiNotAllowlisted(
|
||||
#error_message.to_string(),
|
||||
))
|
||||
Err(anyhow::anyhow!(crate::Error::ApiNotAllowlisted(#error_message.to_string()).to_string()))
|
||||
}
|
||||
)
|
||||
}
|
||||
|
@ -198,8 +196,8 @@ pub fn command_test(attributes: HandlerTestAttributes, function: ItemFn) -> Toke
|
|||
#[cfg(not(#allowlist))]
|
||||
#[quickcheck_macros::quickcheck]
|
||||
#signature {
|
||||
if let Err(crate::Error::ApiNotAllowlisted(e)) = #response {
|
||||
assert_eq!(e, #error_message);
|
||||
if let Err(e) = #response {
|
||||
assert!(e.to_string().contains(#error_message));
|
||||
} else {
|
||||
panic!("unexpected response");
|
||||
}
|
||||
|
|
|
@ -50,6 +50,7 @@ tokio = { version = "1.16", features = [ "rt", "rt-multi-thread", "sync", "fs",
|
|||
futures = "0.3"
|
||||
uuid = { version = "0.8", features = [ "v4" ] }
|
||||
url = { version = "2.2" }
|
||||
anyhow = "1.0"
|
||||
thiserror = "1.0"
|
||||
once_cell = "1.9"
|
||||
tauri-runtime = { version = "0.3.1", path = "../tauri-runtime" }
|
||||
|
|
|
@ -7,6 +7,7 @@ use crate::{
|
|||
runtime::Runtime,
|
||||
Config, Invoke, PackageInfo, Window,
|
||||
};
|
||||
pub use anyhow::Result;
|
||||
use serde::{Deserialize, Serialize};
|
||||
use serde_json::Value as JsonValue;
|
||||
|
||||
|
@ -48,7 +49,7 @@ impl<R: Runtime> Clone for InvokeContext<R> {
|
|||
|
||||
/// The response for a JS `invoke` call.
|
||||
pub struct InvokeResponse {
|
||||
json: crate::Result<JsonValue>,
|
||||
json: Result<JsonValue>,
|
||||
}
|
||||
|
||||
impl<T: Serialize> From<T> for InvokeResponse {
|
||||
|
@ -96,87 +97,87 @@ impl Module {
|
|||
cmd
|
||||
.run(context)
|
||||
.and_then(|r| r.json)
|
||||
.map_err(InvokeError::from)
|
||||
.map_err(InvokeError::from_anyhow)
|
||||
}),
|
||||
Self::Process(cmd) => resolver.respond_async(async move {
|
||||
cmd
|
||||
.run(context)
|
||||
.and_then(|r| r.json)
|
||||
.map_err(InvokeError::from)
|
||||
.map_err(InvokeError::from_anyhow)
|
||||
}),
|
||||
Self::Fs(cmd) => resolver.respond_async(async move {
|
||||
cmd
|
||||
.run(context)
|
||||
.and_then(|r| r.json)
|
||||
.map_err(InvokeError::from)
|
||||
.map_err(InvokeError::from_anyhow)
|
||||
}),
|
||||
Self::Path(cmd) => resolver.respond_async(async move {
|
||||
cmd
|
||||
.run(context)
|
||||
.and_then(|r| r.json)
|
||||
.map_err(InvokeError::from)
|
||||
.map_err(InvokeError::from_anyhow)
|
||||
}),
|
||||
Self::Os(cmd) => resolver.respond_async(async move {
|
||||
cmd
|
||||
.run(context)
|
||||
.and_then(|r| r.json)
|
||||
.map_err(InvokeError::from)
|
||||
.map_err(InvokeError::from_anyhow)
|
||||
}),
|
||||
Self::Window(cmd) => resolver.respond_async(async move {
|
||||
cmd
|
||||
.run(context)
|
||||
.await
|
||||
.and_then(|r| r.json)
|
||||
.map_err(InvokeError::from)
|
||||
.map_err(InvokeError::from_anyhow)
|
||||
}),
|
||||
Self::Shell(cmd) => resolver.respond_async(async move {
|
||||
cmd
|
||||
.run(context)
|
||||
.and_then(|r| r.json)
|
||||
.map_err(InvokeError::from)
|
||||
.map_err(InvokeError::from_anyhow)
|
||||
}),
|
||||
Self::Event(cmd) => resolver.respond_async(async move {
|
||||
cmd
|
||||
.run(context)
|
||||
.and_then(|r| r.json)
|
||||
.map_err(InvokeError::from)
|
||||
.map_err(InvokeError::from_anyhow)
|
||||
}),
|
||||
Self::Dialog(cmd) => resolver.respond_async(async move {
|
||||
cmd
|
||||
.run(context)
|
||||
.and_then(|r| r.json)
|
||||
.map_err(InvokeError::from)
|
||||
.map_err(InvokeError::from_anyhow)
|
||||
}),
|
||||
Self::Cli(cmd) => resolver.respond_async(async move {
|
||||
cmd
|
||||
.run(context)
|
||||
.and_then(|r| r.json)
|
||||
.map_err(InvokeError::from)
|
||||
.map_err(InvokeError::from_anyhow)
|
||||
}),
|
||||
Self::Notification(cmd) => resolver.respond_async(async move {
|
||||
cmd
|
||||
.run(context)
|
||||
.and_then(|r| r.json)
|
||||
.map_err(InvokeError::from)
|
||||
.map_err(InvokeError::from_anyhow)
|
||||
}),
|
||||
Self::Http(cmd) => resolver.respond_async(async move {
|
||||
cmd
|
||||
.run(context)
|
||||
.await
|
||||
.and_then(|r| r.json)
|
||||
.map_err(InvokeError::from)
|
||||
.map_err(InvokeError::from_anyhow)
|
||||
}),
|
||||
Self::GlobalShortcut(cmd) => resolver.respond_async(async move {
|
||||
cmd
|
||||
.run(context)
|
||||
.and_then(|r| r.json)
|
||||
.map_err(InvokeError::from)
|
||||
.map_err(InvokeError::from_anyhow)
|
||||
}),
|
||||
Self::Clipboard(cmd) => resolver.respond_async(async move {
|
||||
cmd
|
||||
.run(context)
|
||||
.and_then(|r| r.json)
|
||||
.map_err(InvokeError::from)
|
||||
.map_err(InvokeError::from_anyhow)
|
||||
}),
|
||||
}
|
||||
}
|
||||
|
|
|
@ -21,15 +21,15 @@ pub enum Cmd {
|
|||
}
|
||||
|
||||
impl Cmd {
|
||||
fn get_app_version<R: Runtime>(context: InvokeContext<R>) -> crate::Result<String> {
|
||||
fn get_app_version<R: Runtime>(context: InvokeContext<R>) -> super::Result<String> {
|
||||
Ok(context.package_info.version)
|
||||
}
|
||||
|
||||
fn get_app_name<R: Runtime>(context: InvokeContext<R>) -> crate::Result<String> {
|
||||
fn get_app_name<R: Runtime>(context: InvokeContext<R>) -> super::Result<String> {
|
||||
Ok(context.package_info.name)
|
||||
}
|
||||
|
||||
fn get_tauri_version<R: Runtime>(_context: InvokeContext<R>) -> crate::Result<&'static str> {
|
||||
fn get_tauri_version<R: Runtime>(_context: InvokeContext<R>) -> super::Result<&'static str> {
|
||||
Ok(env!("CARGO_PKG_VERSION"))
|
||||
}
|
||||
}
|
||||
|
|
|
@ -17,13 +17,13 @@ pub enum Cmd {
|
|||
|
||||
impl Cmd {
|
||||
#[module_command_handler(cli, "CLI definition not set under tauri.conf.json > tauri > cli (https://tauri.studio/docs/api/config#tauri.cli)")]
|
||||
fn cli_matches<R: Runtime>(context: InvokeContext<R>) -> crate::Result<InvokeResponse> {
|
||||
fn cli_matches<R: Runtime>(context: InvokeContext<R>) -> super::Result<InvokeResponse> {
|
||||
if let Some(cli) = &context.config.tauri.cli {
|
||||
crate::api::cli::get_matches(cli, &context.package_info)
|
||||
.map(Into::into)
|
||||
.map_err(Into::into)
|
||||
} else {
|
||||
Err(crate::Error::ApiNotAllowlisted("CLI definition not set under tauri.conf.json > tauri > cli (https://tauri.studio/docs/api/config#tauri.cli)".into()))
|
||||
Err(crate::Error::ApiNotAllowlisted("CLI definition not set under tauri.conf.json > tauri > cli (https://tauri.studio/docs/api/config#tauri.cli)".into()).into_anyhow())
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -34,6 +34,6 @@ mod tests {
|
|||
#[quickcheck_macros::quickcheck]
|
||||
fn cli_matches() {
|
||||
let res = super::Cmd::cli_matches(crate::test::mock_invoke_context());
|
||||
assert!(!matches!(res, Err(crate::Error::ApiNotAllowlisted(_))));
|
||||
crate::test_utils::assert_not_allowlist_error(res);
|
||||
}
|
||||
}
|
||||
|
|
|
@ -21,19 +21,23 @@ pub enum Cmd {
|
|||
|
||||
impl Cmd {
|
||||
#[module_command_handler(clipboard_write_text, "clipboard > writeText")]
|
||||
fn write_text<R: Runtime>(context: InvokeContext<R>, text: String) -> crate::Result<()> {
|
||||
Ok(
|
||||
context
|
||||
.window
|
||||
.app_handle
|
||||
.clipboard_manager()
|
||||
.write_text(text)?,
|
||||
)
|
||||
fn write_text<R: Runtime>(context: InvokeContext<R>, text: String) -> super::Result<()> {
|
||||
context
|
||||
.window
|
||||
.app_handle
|
||||
.clipboard_manager()
|
||||
.write_text(text)
|
||||
.map_err(crate::error::into_anyhow)
|
||||
}
|
||||
|
||||
#[module_command_handler(clipboard_read_text, "clipboard > readText")]
|
||||
fn read_text<R: Runtime>(context: InvokeContext<R>) -> crate::Result<Option<String>> {
|
||||
Ok(context.window.app_handle.clipboard_manager().read_text()?)
|
||||
fn read_text<R: Runtime>(context: InvokeContext<R>) -> super::Result<Option<String>> {
|
||||
context
|
||||
.window
|
||||
.app_handle
|
||||
.clipboard_manager()
|
||||
.read_text()
|
||||
.map_err(crate::error::into_anyhow)
|
||||
}
|
||||
}
|
||||
|
||||
|
|
|
@ -83,7 +83,7 @@ impl Cmd {
|
|||
fn open_dialog<R: Runtime>(
|
||||
context: InvokeContext<R>,
|
||||
options: OpenDialogOptions,
|
||||
) -> crate::Result<InvokeResponse> {
|
||||
) -> super::Result<InvokeResponse> {
|
||||
let mut dialog_builder = FileDialogBuilder::new();
|
||||
#[cfg(any(windows, target_os = "macos"))]
|
||||
{
|
||||
|
@ -113,7 +113,7 @@ impl Cmd {
|
|||
fn save_dialog<R: Runtime>(
|
||||
context: InvokeContext<R>,
|
||||
options: SaveDialogOptions,
|
||||
) -> crate::Result<Option<PathBuf>> {
|
||||
) -> super::Result<Option<PathBuf>> {
|
||||
let mut dialog_builder = FileDialogBuilder::new();
|
||||
#[cfg(any(windows, target_os = "macos"))]
|
||||
{
|
||||
|
@ -131,7 +131,7 @@ impl Cmd {
|
|||
}
|
||||
|
||||
#[module_command_handler(dialog_message, "dialog > message")]
|
||||
fn message_dialog<R: Runtime>(context: InvokeContext<R>, message: String) -> crate::Result<()> {
|
||||
fn message_dialog<R: Runtime>(context: InvokeContext<R>, message: String) -> super::Result<()> {
|
||||
crate::api::dialog::blocking::message(
|
||||
Some(&context.window),
|
||||
&context.window.app_handle.package_info().name,
|
||||
|
@ -145,7 +145,7 @@ impl Cmd {
|
|||
context: InvokeContext<R>,
|
||||
title: Option<String>,
|
||||
message: String,
|
||||
) -> crate::Result<bool> {
|
||||
) -> super::Result<bool> {
|
||||
Ok(crate::api::dialog::blocking::ask(
|
||||
Some(&context.window),
|
||||
title.unwrap_or_else(|| context.window.app_handle.package_info().name.clone()),
|
||||
|
@ -158,7 +158,7 @@ impl Cmd {
|
|||
context: InvokeContext<R>,
|
||||
title: Option<String>,
|
||||
message: String,
|
||||
) -> crate::Result<bool> {
|
||||
) -> super::Result<bool> {
|
||||
Ok(crate::api::dialog::blocking::confirm(
|
||||
Some(&context.window),
|
||||
title.unwrap_or_else(|| context.window.app_handle.package_info().name.clone()),
|
||||
|
|
|
@ -80,18 +80,21 @@ impl Cmd {
|
|||
event: EventId,
|
||||
window_label: Option<WindowLabel>,
|
||||
handler: CallbackFn,
|
||||
) -> crate::Result<u64> {
|
||||
) -> super::Result<u64> {
|
||||
let event_id = rand::random();
|
||||
|
||||
let window_label = window_label.map(|l| l.0);
|
||||
|
||||
context.window.eval(&listen_js(
|
||||
context.window.manager().event_listeners_object_name(),
|
||||
format!("'{}'", event.0),
|
||||
event_id,
|
||||
window_label.clone(),
|
||||
format!("window['_{}']", handler.0),
|
||||
))?;
|
||||
context
|
||||
.window
|
||||
.eval(&listen_js(
|
||||
context.window.manager().event_listeners_object_name(),
|
||||
format!("'{}'", event.0),
|
||||
event_id,
|
||||
window_label.clone(),
|
||||
format!("window['_{}']", handler.0),
|
||||
))
|
||||
.map_err(crate::error::into_anyhow)?;
|
||||
|
||||
context
|
||||
.window
|
||||
|
@ -100,11 +103,14 @@ impl Cmd {
|
|||
Ok(event_id)
|
||||
}
|
||||
|
||||
fn unlisten<R: Runtime>(context: InvokeContext<R>, event_id: u64) -> crate::Result<()> {
|
||||
context.window.eval(&unlisten_js(
|
||||
context.window.manager().event_listeners_object_name(),
|
||||
event_id,
|
||||
))?;
|
||||
fn unlisten<R: Runtime>(context: InvokeContext<R>, event_id: u64) -> super::Result<()> {
|
||||
context
|
||||
.window
|
||||
.eval(&unlisten_js(
|
||||
context.window.manager().event_listeners_object_name(),
|
||||
event_id,
|
||||
))
|
||||
.map_err(crate::error::into_anyhow)?;
|
||||
context.window.unregister_js_listener(event_id);
|
||||
Ok(())
|
||||
}
|
||||
|
@ -114,14 +120,20 @@ impl Cmd {
|
|||
event: EventId,
|
||||
window_label: Option<WindowLabel>,
|
||||
payload: Option<String>,
|
||||
) -> crate::Result<()> {
|
||||
) -> super::Result<()> {
|
||||
// dispatch the event to Rust listeners
|
||||
context.window.trigger(&event.0, payload.clone());
|
||||
|
||||
if let Some(target) = window_label {
|
||||
context.window.emit_to(&target.0, &event.0, payload)?;
|
||||
context
|
||||
.window
|
||||
.emit_to(&target.0, &event.0, payload)
|
||||
.map_err(crate::error::into_anyhow)?;
|
||||
} else {
|
||||
context.window.emit_all(&event.0, payload)?;
|
||||
context
|
||||
.window
|
||||
.emit_all(&event.0, payload)
|
||||
.map_err(crate::error::into_anyhow)?;
|
||||
}
|
||||
Ok(())
|
||||
}
|
||||
|
|
|
@ -127,7 +127,7 @@ impl Cmd {
|
|||
context: InvokeContext<R>,
|
||||
path: SafePathBuf,
|
||||
options: Option<FileOperationOptions>,
|
||||
) -> crate::Result<Vec<u8>> {
|
||||
) -> super::Result<Vec<u8>> {
|
||||
file::read_binary(resolve_path(
|
||||
&context.config,
|
||||
&context.package_info,
|
||||
|
@ -135,7 +135,7 @@ impl Cmd {
|
|||
path,
|
||||
options.and_then(|o| o.dir),
|
||||
)?)
|
||||
.map_err(crate::Error::FailedToExecuteApi)
|
||||
.map_err(Into::into)
|
||||
}
|
||||
|
||||
#[module_command_handler(fs_write_file, "fs > writeFile")]
|
||||
|
@ -144,7 +144,7 @@ impl Cmd {
|
|||
path: SafePathBuf,
|
||||
contents: Vec<u8>,
|
||||
options: Option<FileOperationOptions>,
|
||||
) -> crate::Result<()> {
|
||||
) -> super::Result<()> {
|
||||
File::create(resolve_path(
|
||||
&context.config,
|
||||
&context.package_info,
|
||||
|
@ -161,7 +161,7 @@ impl Cmd {
|
|||
context: InvokeContext<R>,
|
||||
path: SafePathBuf,
|
||||
options: Option<DirOperationOptions>,
|
||||
) -> crate::Result<Vec<dir::DiskEntry>> {
|
||||
) -> super::Result<Vec<dir::DiskEntry>> {
|
||||
let (recursive, dir) = if let Some(options_value) = options {
|
||||
(options_value.recursive, options_value.dir)
|
||||
} else {
|
||||
|
@ -177,7 +177,7 @@ impl Cmd {
|
|||
)?,
|
||||
recursive,
|
||||
)
|
||||
.map_err(crate::Error::FailedToExecuteApi)
|
||||
.map_err(Into::into)
|
||||
}
|
||||
|
||||
#[module_command_handler(fs_copy_file, "fs > copyFile")]
|
||||
|
@ -186,7 +186,7 @@ impl Cmd {
|
|||
source: SafePathBuf,
|
||||
destination: SafePathBuf,
|
||||
options: Option<FileOperationOptions>,
|
||||
) -> crate::Result<()> {
|
||||
) -> super::Result<()> {
|
||||
let (src, dest) = match options.and_then(|o| o.dir) {
|
||||
Some(dir) => (
|
||||
resolve_path(
|
||||
|
@ -215,7 +215,7 @@ impl Cmd {
|
|||
context: InvokeContext<R>,
|
||||
path: SafePathBuf,
|
||||
options: Option<DirOperationOptions>,
|
||||
) -> crate::Result<()> {
|
||||
) -> super::Result<()> {
|
||||
let (recursive, dir) = if let Some(options_value) = options {
|
||||
(options_value.recursive, options_value.dir)
|
||||
} else {
|
||||
|
@ -242,7 +242,7 @@ impl Cmd {
|
|||
context: InvokeContext<R>,
|
||||
path: SafePathBuf,
|
||||
options: Option<DirOperationOptions>,
|
||||
) -> crate::Result<()> {
|
||||
) -> super::Result<()> {
|
||||
let (recursive, dir) = if let Some(options_value) = options {
|
||||
(options_value.recursive, options_value.dir)
|
||||
} else {
|
||||
|
@ -269,7 +269,7 @@ impl Cmd {
|
|||
context: InvokeContext<R>,
|
||||
path: SafePathBuf,
|
||||
options: Option<FileOperationOptions>,
|
||||
) -> crate::Result<()> {
|
||||
) -> super::Result<()> {
|
||||
let resolved_path = resolve_path(
|
||||
&context.config,
|
||||
&context.package_info,
|
||||
|
@ -287,7 +287,7 @@ impl Cmd {
|
|||
old_path: SafePathBuf,
|
||||
new_path: SafePathBuf,
|
||||
options: Option<FileOperationOptions>,
|
||||
) -> crate::Result<()> {
|
||||
) -> super::Result<()> {
|
||||
let (old, new) = match options.and_then(|o| o.dir) {
|
||||
Some(dir) => (
|
||||
resolve_path(
|
||||
|
@ -307,7 +307,7 @@ impl Cmd {
|
|||
),
|
||||
None => (old_path, new_path),
|
||||
};
|
||||
fs::rename(old, new).map_err(crate::Error::Io)
|
||||
fs::rename(old, new).map_err(Into::into)
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -318,14 +318,16 @@ fn resolve_path<R: Runtime>(
|
|||
window: &Window<R>,
|
||||
path: SafePathBuf,
|
||||
dir: Option<BaseDirectory>,
|
||||
) -> crate::Result<SafePathBuf> {
|
||||
) -> super::Result<SafePathBuf> {
|
||||
let env = window.state::<Env>().inner();
|
||||
match crate::api::path::resolve_path(config, package_info, env, path, dir) {
|
||||
Ok(path) => {
|
||||
if window.state::<Scopes>().fs.is_allowed(&path) {
|
||||
Ok(SafePathBuf(path))
|
||||
} else {
|
||||
Err(crate::Error::PathNotAllowed(path))
|
||||
Err(anyhow::anyhow!(
|
||||
crate::Error::PathNotAllowed(path).to_string()
|
||||
))
|
||||
}
|
||||
}
|
||||
Err(e) => Err(e.into()),
|
||||
|
@ -381,21 +383,21 @@ mod tests {
|
|||
#[quickcheck_macros::quickcheck]
|
||||
fn read_file(path: SafePathBuf, options: Option<FileOperationOptions>) {
|
||||
let res = super::Cmd::read_file(crate::test::mock_invoke_context(), path, options);
|
||||
assert!(!matches!(res, Err(crate::Error::ApiNotAllowlisted(_))));
|
||||
crate::test_utils::assert_not_allowlist_error(res);
|
||||
}
|
||||
|
||||
#[tauri_macros::module_command_test(fs_write_file, "fs > writeFile")]
|
||||
#[quickcheck_macros::quickcheck]
|
||||
fn write_file(path: SafePathBuf, contents: Vec<u8>, options: Option<FileOperationOptions>) {
|
||||
let res = super::Cmd::write_file(crate::test::mock_invoke_context(), path, contents, options);
|
||||
assert!(!matches!(res, Err(crate::Error::ApiNotAllowlisted(_))));
|
||||
crate::test_utils::assert_not_allowlist_error(res);
|
||||
}
|
||||
|
||||
#[tauri_macros::module_command_test(fs_read_dir, "fs > readDir")]
|
||||
#[quickcheck_macros::quickcheck]
|
||||
fn read_dir(path: SafePathBuf, options: Option<DirOperationOptions>) {
|
||||
let res = super::Cmd::read_dir(crate::test::mock_invoke_context(), path, options);
|
||||
assert!(!matches!(res, Err(crate::Error::ApiNotAllowlisted(_))));
|
||||
crate::test_utils::assert_not_allowlist_error(res);
|
||||
}
|
||||
|
||||
#[tauri_macros::module_command_test(fs_copy_file, "fs > copyFile")]
|
||||
|
@ -411,28 +413,28 @@ mod tests {
|
|||
destination,
|
||||
options,
|
||||
);
|
||||
assert!(!matches!(res, Err(crate::Error::ApiNotAllowlisted(_))));
|
||||
crate::test_utils::assert_not_allowlist_error(res);
|
||||
}
|
||||
|
||||
#[tauri_macros::module_command_test(fs_create_dir, "fs > createDir")]
|
||||
#[quickcheck_macros::quickcheck]
|
||||
fn create_dir(path: SafePathBuf, options: Option<DirOperationOptions>) {
|
||||
let res = super::Cmd::create_dir(crate::test::mock_invoke_context(), path, options);
|
||||
assert!(!matches!(res, Err(crate::Error::ApiNotAllowlisted(_))));
|
||||
crate::test_utils::assert_not_allowlist_error(res);
|
||||
}
|
||||
|
||||
#[tauri_macros::module_command_test(fs_remove_dir, "fs > removeDir")]
|
||||
#[quickcheck_macros::quickcheck]
|
||||
fn remove_dir(path: SafePathBuf, options: Option<DirOperationOptions>) {
|
||||
let res = super::Cmd::remove_dir(crate::test::mock_invoke_context(), path, options);
|
||||
assert!(!matches!(res, Err(crate::Error::ApiNotAllowlisted(_))));
|
||||
crate::test_utils::assert_not_allowlist_error(res);
|
||||
}
|
||||
|
||||
#[tauri_macros::module_command_test(fs_remove_file, "fs > removeFile")]
|
||||
#[quickcheck_macros::quickcheck]
|
||||
fn remove_file(path: SafePathBuf, options: Option<FileOperationOptions>) {
|
||||
let res = super::Cmd::remove_file(crate::test::mock_invoke_context(), path, options);
|
||||
assert!(!matches!(res, Err(crate::Error::ApiNotAllowlisted(_))));
|
||||
crate::test_utils::assert_not_allowlist_error(res);
|
||||
}
|
||||
|
||||
#[tauri_macros::module_command_test(fs_rename_file, "fs > renameFile")]
|
||||
|
@ -448,6 +450,6 @@ mod tests {
|
|||
new_path,
|
||||
options,
|
||||
);
|
||||
assert!(!matches!(res, Err(crate::Error::ApiNotAllowlisted(_))));
|
||||
crate::test_utils::assert_not_allowlist_error(res);
|
||||
}
|
||||
}
|
||||
|
|
|
@ -38,7 +38,7 @@ impl Cmd {
|
|||
context: InvokeContext<R>,
|
||||
shortcut: String,
|
||||
handler: CallbackFn,
|
||||
) -> crate::Result<()> {
|
||||
) -> super::Result<()> {
|
||||
let mut manager = context.window.app_handle.global_shortcut_manager();
|
||||
register_shortcut(context.window, &mut manager, shortcut, handler)?;
|
||||
Ok(())
|
||||
|
@ -49,7 +49,7 @@ impl Cmd {
|
|||
context: InvokeContext<R>,
|
||||
shortcuts: Vec<String>,
|
||||
handler: CallbackFn,
|
||||
) -> crate::Result<()> {
|
||||
) -> super::Result<()> {
|
||||
let mut manager = context.window.app_handle.global_shortcut_manager();
|
||||
for shortcut in shortcuts {
|
||||
register_shortcut(context.window.clone(), &mut manager, shortcut, handler)?;
|
||||
|
@ -58,34 +58,35 @@ impl Cmd {
|
|||
}
|
||||
|
||||
#[module_command_handler(global_shortcut_all, "globalShortcut > all")]
|
||||
fn unregister<R: Runtime>(context: InvokeContext<R>, shortcut: String) -> crate::Result<()> {
|
||||
fn unregister<R: Runtime>(context: InvokeContext<R>, shortcut: String) -> super::Result<()> {
|
||||
context
|
||||
.window
|
||||
.app_handle
|
||||
.global_shortcut_manager()
|
||||
.unregister(&shortcut)?;
|
||||
.unregister(&shortcut)
|
||||
.map_err(crate::error::into_anyhow)?;
|
||||
Ok(())
|
||||
}
|
||||
|
||||
#[module_command_handler(global_shortcut_all, "globalShortcut > all")]
|
||||
fn unregister_all<R: Runtime>(context: InvokeContext<R>) -> crate::Result<()> {
|
||||
fn unregister_all<R: Runtime>(context: InvokeContext<R>) -> super::Result<()> {
|
||||
context
|
||||
.window
|
||||
.app_handle
|
||||
.global_shortcut_manager()
|
||||
.unregister_all()?;
|
||||
.unregister_all()
|
||||
.map_err(crate::error::into_anyhow)?;
|
||||
Ok(())
|
||||
}
|
||||
|
||||
#[module_command_handler(global_shortcut_all, "globalShortcut > all")]
|
||||
fn is_registered<R: Runtime>(context: InvokeContext<R>, shortcut: String) -> crate::Result<bool> {
|
||||
Ok(
|
||||
context
|
||||
.window
|
||||
.app_handle
|
||||
.global_shortcut_manager()
|
||||
.is_registered(&shortcut)?,
|
||||
)
|
||||
fn is_registered<R: Runtime>(context: InvokeContext<R>, shortcut: String) -> super::Result<bool> {
|
||||
context
|
||||
.window
|
||||
.app_handle
|
||||
.global_shortcut_manager()
|
||||
.is_registered(&shortcut)
|
||||
.map_err(crate::error::into_anyhow)
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -95,13 +96,15 @@ fn register_shortcut<R: Runtime>(
|
|||
manager: &mut R::GlobalShortcutManager,
|
||||
shortcut: String,
|
||||
handler: CallbackFn,
|
||||
) -> crate::Result<()> {
|
||||
) -> super::Result<()> {
|
||||
let accelerator = shortcut.clone();
|
||||
manager.register(&shortcut, move || {
|
||||
let callback_string = crate::api::ipc::format_callback(handler, &accelerator)
|
||||
.expect("unable to serialize shortcut string to json");
|
||||
let _ = window.eval(callback_string.as_str());
|
||||
})?;
|
||||
manager
|
||||
.register(&shortcut, move || {
|
||||
let callback_string = crate::api::ipc::format_callback(handler, &accelerator)
|
||||
.expect("unable to serialize shortcut string to json");
|
||||
let _ = window.eval(callback_string.as_str());
|
||||
})
|
||||
.map_err(crate::error::into_anyhow)?;
|
||||
Ok(())
|
||||
}
|
||||
|
||||
|
|
|
@ -54,7 +54,7 @@ impl Cmd {
|
|||
async fn create_client<R: Runtime>(
|
||||
_context: InvokeContext<R>,
|
||||
options: Option<ClientBuilder>,
|
||||
) -> crate::Result<ClientId> {
|
||||
) -> super::Result<ClientId> {
|
||||
let client = options.unwrap_or_default().build()?;
|
||||
let mut store = clients().lock().unwrap();
|
||||
let id = rand::random::<ClientId>();
|
||||
|
@ -66,7 +66,7 @@ impl Cmd {
|
|||
async fn drop_client<R: Runtime>(
|
||||
_context: InvokeContext<R>,
|
||||
client: ClientId,
|
||||
) -> crate::Result<()> {
|
||||
) -> super::Result<()> {
|
||||
let mut store = clients().lock().unwrap();
|
||||
store.remove(&client);
|
||||
Ok(())
|
||||
|
@ -77,7 +77,7 @@ impl Cmd {
|
|||
context: InvokeContext<R>,
|
||||
client_id: ClientId,
|
||||
options: Box<HttpRequestBuilder>,
|
||||
) -> crate::Result<ResponseData> {
|
||||
) -> super::Result<ResponseData> {
|
||||
use crate::Manager;
|
||||
if context
|
||||
.window
|
||||
|
@ -89,12 +89,12 @@ impl Cmd {
|
|||
.lock()
|
||||
.unwrap()
|
||||
.get(&client_id)
|
||||
.ok_or(crate::Error::HttpClientNotInitialized)?
|
||||
.ok_or_else(|| crate::Error::HttpClientNotInitialized.into_anyhow())?
|
||||
.clone();
|
||||
let response = client.send(*options).await?;
|
||||
Ok(response.read().await?)
|
||||
} else {
|
||||
Err(crate::Error::UrlNotAllowed(options.url))
|
||||
Err(crate::Error::UrlNotAllowed(options.url).into_anyhow())
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
@ -44,13 +44,13 @@ impl Cmd {
|
|||
fn notification<R: Runtime>(
|
||||
context: InvokeContext<R>,
|
||||
options: NotificationOptions,
|
||||
) -> crate::Result<()> {
|
||||
) -> super::Result<()> {
|
||||
let allowed = match is_permission_granted(&context) {
|
||||
Some(p) => p,
|
||||
None => request_permission(&context),
|
||||
};
|
||||
if !allowed {
|
||||
return Err(crate::Error::NotificationNotAllowed);
|
||||
return Err(crate::Error::NotificationNotAllowed.into_anyhow());
|
||||
}
|
||||
let mut notification =
|
||||
Notification::new(context.config.tauri.bundle.identifier.clone()).title(options.title);
|
||||
|
@ -67,7 +67,7 @@ impl Cmd {
|
|||
#[cfg(notification_all)]
|
||||
fn request_notification_permission<R: Runtime>(
|
||||
context: InvokeContext<R>,
|
||||
) -> crate::Result<&'static str> {
|
||||
) -> super::Result<&'static str> {
|
||||
if request_permission(&context) {
|
||||
Ok(PERMISSION_GRANTED)
|
||||
} else {
|
||||
|
@ -78,14 +78,14 @@ impl Cmd {
|
|||
#[cfg(not(notification_all))]
|
||||
fn request_notification_permission<R: Runtime>(
|
||||
_context: InvokeContext<R>,
|
||||
) -> crate::Result<&'static str> {
|
||||
) -> super::Result<&'static str> {
|
||||
Ok(PERMISSION_DENIED)
|
||||
}
|
||||
|
||||
#[cfg(notification_all)]
|
||||
fn is_notification_permission_granted<R: Runtime>(
|
||||
context: InvokeContext<R>,
|
||||
) -> crate::Result<Option<bool>> {
|
||||
) -> super::Result<Option<bool>> {
|
||||
if let Some(allow_notification) = is_permission_granted(&context) {
|
||||
Ok(Some(allow_notification))
|
||||
} else {
|
||||
|
@ -96,7 +96,7 @@ impl Cmd {
|
|||
#[cfg(not(notification_all))]
|
||||
fn is_notification_permission_granted<R: Runtime>(
|
||||
_context: InvokeContext<R>,
|
||||
) -> crate::Result<Option<bool>> {
|
||||
) -> super::Result<Option<bool>> {
|
||||
Ok(Some(false))
|
||||
}
|
||||
}
|
||||
|
|
|
@ -21,27 +21,27 @@ pub enum Cmd {
|
|||
|
||||
impl Cmd {
|
||||
#[module_command_handler(os_all, "os > all")]
|
||||
fn platform<R: Runtime>(_context: InvokeContext<R>) -> crate::Result<&'static str> {
|
||||
fn platform<R: Runtime>(_context: InvokeContext<R>) -> super::Result<&'static str> {
|
||||
Ok(os_platform())
|
||||
}
|
||||
|
||||
#[module_command_handler(os_all, "os > all")]
|
||||
fn version<R: Runtime>(_context: InvokeContext<R>) -> crate::Result<String> {
|
||||
fn version<R: Runtime>(_context: InvokeContext<R>) -> super::Result<String> {
|
||||
Ok(os_info::get().version().to_string())
|
||||
}
|
||||
|
||||
#[module_command_handler(os_all, "os > all")]
|
||||
fn os_type<R: Runtime>(_context: InvokeContext<R>) -> crate::Result<&'static str> {
|
||||
fn os_type<R: Runtime>(_context: InvokeContext<R>) -> super::Result<&'static str> {
|
||||
Ok(os_type())
|
||||
}
|
||||
|
||||
#[module_command_handler(os_all, "os > all")]
|
||||
fn arch<R: Runtime>(_context: InvokeContext<R>) -> crate::Result<&'static str> {
|
||||
fn arch<R: Runtime>(_context: InvokeContext<R>) -> super::Result<&'static str> {
|
||||
Ok(std::env::consts::ARCH)
|
||||
}
|
||||
|
||||
#[module_command_handler(os_all, "os > all")]
|
||||
fn tempdir<R: Runtime>(_context: InvokeContext<R>) -> crate::Result<PathBuf> {
|
||||
fn tempdir<R: Runtime>(_context: InvokeContext<R>) -> super::Result<PathBuf> {
|
||||
Ok(std::env::temp_dir())
|
||||
}
|
||||
}
|
||||
|
|
|
@ -51,7 +51,7 @@ impl Cmd {
|
|||
context: InvokeContext<R>,
|
||||
path: String,
|
||||
directory: Option<BaseDirectory>,
|
||||
) -> crate::Result<PathBuf> {
|
||||
) -> super::Result<PathBuf> {
|
||||
crate::api::path::resolve_path(
|
||||
&context.config,
|
||||
&context.package_info,
|
||||
|
@ -63,7 +63,7 @@ impl Cmd {
|
|||
}
|
||||
|
||||
#[module_command_handler(path_all, "path > all")]
|
||||
fn resolve<R: Runtime>(_context: InvokeContext<R>, paths: Vec<String>) -> crate::Result<PathBuf> {
|
||||
fn resolve<R: Runtime>(_context: InvokeContext<R>, paths: Vec<String>) -> super::Result<PathBuf> {
|
||||
// Start with current directory then start adding paths from the vector one by one using `PathBuf.push()` which
|
||||
// will ensure that if an absolute path is encountered in the iteration, it will be used as the current full path.
|
||||
//
|
||||
|
@ -78,7 +78,7 @@ impl Cmd {
|
|||
}
|
||||
|
||||
#[module_command_handler(path_all, "path > all")]
|
||||
fn normalize<R: Runtime>(_context: InvokeContext<R>, path: String) -> crate::Result<String> {
|
||||
fn normalize<R: Runtime>(_context: InvokeContext<R>, path: String) -> super::Result<String> {
|
||||
let mut p = normalize_path_no_absolute(Path::new(&path))
|
||||
.to_string_lossy()
|
||||
.to_string();
|
||||
|
@ -102,7 +102,7 @@ impl Cmd {
|
|||
}
|
||||
|
||||
#[module_command_handler(path_all, "path > all")]
|
||||
fn join<R: Runtime>(_context: InvokeContext<R>, mut paths: Vec<String>) -> crate::Result<String> {
|
||||
fn join<R: Runtime>(_context: InvokeContext<R>, mut paths: Vec<String>) -> super::Result<String> {
|
||||
let path = PathBuf::from(
|
||||
paths
|
||||
.iter_mut()
|
||||
|
@ -126,23 +126,23 @@ impl Cmd {
|
|||
}
|
||||
|
||||
#[module_command_handler(path_all, "path > all")]
|
||||
fn dirname<R: Runtime>(_context: InvokeContext<R>, path: String) -> crate::Result<PathBuf> {
|
||||
fn dirname<R: Runtime>(_context: InvokeContext<R>, path: String) -> super::Result<PathBuf> {
|
||||
match Path::new(&path).parent() {
|
||||
Some(p) => Ok(p.to_path_buf()),
|
||||
None => Err(crate::Error::FailedToExecuteApi(crate::api::Error::Path(
|
||||
None => Err(crate::error::into_anyhow(crate::api::Error::Path(
|
||||
"Couldn't get the parent directory".into(),
|
||||
))),
|
||||
}
|
||||
}
|
||||
|
||||
#[module_command_handler(path_all, "path > all")]
|
||||
fn extname<R: Runtime>(_context: InvokeContext<R>, path: String) -> crate::Result<String> {
|
||||
fn extname<R: Runtime>(_context: InvokeContext<R>, path: String) -> super::Result<String> {
|
||||
match Path::new(&path)
|
||||
.extension()
|
||||
.and_then(std::ffi::OsStr::to_str)
|
||||
{
|
||||
Some(p) => Ok(p.to_string()),
|
||||
None => Err(crate::Error::FailedToExecuteApi(crate::api::Error::Path(
|
||||
None => Err(crate::error::into_anyhow(crate::api::Error::Path(
|
||||
"Couldn't get the extension of the file".into(),
|
||||
))),
|
||||
}
|
||||
|
@ -153,7 +153,7 @@ impl Cmd {
|
|||
_context: InvokeContext<R>,
|
||||
path: String,
|
||||
ext: Option<String>,
|
||||
) -> crate::Result<String> {
|
||||
) -> super::Result<String> {
|
||||
match Path::new(&path)
|
||||
.file_name()
|
||||
.and_then(std::ffi::OsStr::to_str)
|
||||
|
@ -163,14 +163,14 @@ impl Cmd {
|
|||
} else {
|
||||
p.to_string()
|
||||
}),
|
||||
None => Err(crate::Error::FailedToExecuteApi(crate::api::Error::Path(
|
||||
None => Err(crate::error::into_anyhow(crate::api::Error::Path(
|
||||
"Couldn't get the basename".into(),
|
||||
))),
|
||||
}
|
||||
}
|
||||
|
||||
#[module_command_handler(path_all, "path > all")]
|
||||
fn is_absolute<R: Runtime>(_context: InvokeContext<R>, path: String) -> crate::Result<bool> {
|
||||
fn is_absolute<R: Runtime>(_context: InvokeContext<R>, path: String) -> super::Result<bool> {
|
||||
Ok(Path::new(&path).is_absolute())
|
||||
}
|
||||
}
|
||||
|
|
|
@ -22,13 +22,13 @@ pub enum Cmd {
|
|||
|
||||
impl Cmd {
|
||||
#[module_command_handler(process_relaunch, "process > relaunch")]
|
||||
fn relaunch<R: Runtime>(context: InvokeContext<R>) -> crate::Result<()> {
|
||||
fn relaunch<R: Runtime>(context: InvokeContext<R>) -> super::Result<()> {
|
||||
crate::api::process::restart(&context.window.state());
|
||||
Ok(())
|
||||
}
|
||||
|
||||
#[module_command_handler(process_exit, "process > exit")]
|
||||
fn exit<R: Runtime>(_context: InvokeContext<R>, exit_code: i32) -> crate::Result<()> {
|
||||
fn exit<R: Runtime>(_context: InvokeContext<R>, exit_code: i32) -> super::Result<()> {
|
||||
// would be great if we can have a handler inside tauri
|
||||
// who close all window and emit an event that user can catch
|
||||
// if they want to process something before closing the app
|
||||
|
|
|
@ -88,12 +88,10 @@ impl Cmd {
|
|||
args: ExecuteArgs,
|
||||
on_event_fn: CallbackFn,
|
||||
options: CommandOptions,
|
||||
) -> crate::Result<ChildId> {
|
||||
) -> super::Result<ChildId> {
|
||||
let mut command = if options.sidecar {
|
||||
#[cfg(not(shell_sidecar))]
|
||||
return Err(crate::Error::ApiNotAllowlisted(
|
||||
"shell > sidecar".to_string(),
|
||||
));
|
||||
return Err(crate::Error::ApiNotAllowlisted("shell > sidecar".to_string()).into_anyhow());
|
||||
#[cfg(shell_sidecar)]
|
||||
{
|
||||
let program = PathBuf::from(program);
|
||||
|
@ -117,16 +115,14 @@ impl Cmd {
|
|||
.state::<Scopes>()
|
||||
.shell
|
||||
.prepare(&program.to_string_lossy(), args, true)
|
||||
.map_err(Box::new)?
|
||||
.map_err(crate::error::into_anyhow)?
|
||||
} else {
|
||||
return Err(crate::Error::SidecarNotAllowed(program));
|
||||
return Err(crate::Error::SidecarNotAllowed(program).into_anyhow());
|
||||
}
|
||||
}
|
||||
} else {
|
||||
#[cfg(not(shell_execute))]
|
||||
return Err(crate::Error::ApiNotAllowlisted(
|
||||
"shell > execute".to_string(),
|
||||
));
|
||||
return Err(crate::Error::ApiNotAllowlisted("shell > execute".to_string()).into_anyhow());
|
||||
#[cfg(shell_execute)]
|
||||
match context
|
||||
.window
|
||||
|
@ -138,7 +134,7 @@ impl Cmd {
|
|||
Err(e) => {
|
||||
#[cfg(debug_assertions)]
|
||||
eprintln!("{}", e);
|
||||
return Err(crate::Error::ProgramNotAllowed(PathBuf::from(program)));
|
||||
return Err(crate::Error::ProgramNotAllowed(PathBuf::from(program)).into_anyhow());
|
||||
}
|
||||
}
|
||||
};
|
||||
|
@ -178,7 +174,7 @@ impl Cmd {
|
|||
_context: InvokeContext<R>,
|
||||
pid: ChildId,
|
||||
buffer: Buffer,
|
||||
) -> crate::Result<()> {
|
||||
) -> super::Result<()> {
|
||||
if let Some(child) = command_childs().lock().unwrap().get_mut(&pid) {
|
||||
match buffer {
|
||||
Buffer::Text(t) => child.write(t.as_bytes())?,
|
||||
|
@ -193,14 +189,12 @@ impl Cmd {
|
|||
_context: InvokeContext<R>,
|
||||
_pid: ChildId,
|
||||
_buffer: Buffer,
|
||||
) -> crate::Result<()> {
|
||||
Err(crate::Error::ApiNotAllowlisted(
|
||||
"shell > execute or shell > sidecar".into(),
|
||||
))
|
||||
) -> super::Result<()> {
|
||||
Err(crate::Error::ApiNotAllowlisted("shell > execute or shell > sidecar".into()).into_anyhow())
|
||||
}
|
||||
|
||||
#[cfg(any(shell_execute, shell_sidecar))]
|
||||
fn kill_child<R: Runtime>(_context: InvokeContext<R>, pid: ChildId) -> crate::Result<()> {
|
||||
fn kill_child<R: Runtime>(_context: InvokeContext<R>, pid: ChildId) -> super::Result<()> {
|
||||
if let Some(child) = command_childs().lock().unwrap().remove(&pid) {
|
||||
child.kill()?;
|
||||
}
|
||||
|
@ -208,10 +202,8 @@ impl Cmd {
|
|||
}
|
||||
|
||||
#[cfg(not(any(shell_execute, shell_sidecar)))]
|
||||
fn kill_child<R: Runtime>(_context: InvokeContext<R>, _pid: ChildId) -> crate::Result<()> {
|
||||
Err(crate::Error::ApiNotAllowlisted(
|
||||
"shell > execute or shell > sidecar".into(),
|
||||
))
|
||||
fn kill_child<R: Runtime>(_context: InvokeContext<R>, _pid: ChildId) -> super::Result<()> {
|
||||
Err(crate::Error::ApiNotAllowlisted("shell > execute or shell > sidecar".into()).into_anyhow())
|
||||
}
|
||||
|
||||
/// Open a (url) path with a default or specific browser opening program.
|
||||
|
@ -222,7 +214,7 @@ impl Cmd {
|
|||
context: InvokeContext<R>,
|
||||
path: String,
|
||||
with: Option<String>,
|
||||
) -> crate::Result<()> {
|
||||
) -> super::Result<()> {
|
||||
use std::str::FromStr;
|
||||
|
||||
with
|
||||
|
|
|
@ -151,17 +151,19 @@ impl Cmd {
|
|||
async fn create_webview<R: Runtime>(
|
||||
context: InvokeContext<R>,
|
||||
options: Box<WindowConfig>,
|
||||
) -> crate::Result<()> {
|
||||
) -> super::Result<()> {
|
||||
let mut window = context.window;
|
||||
let label = options.label.clone();
|
||||
let url = options.url.clone();
|
||||
|
||||
window.create_window(label, url, |_, webview_attributes| {
|
||||
(
|
||||
<<R::Dispatcher as Dispatch>::WindowBuilder>::with_config(*options),
|
||||
webview_attributes,
|
||||
)
|
||||
})?;
|
||||
window
|
||||
.create_window(label, url, |_, webview_attributes| {
|
||||
(
|
||||
<<R::Dispatcher as Dispatch>::WindowBuilder>::with_config(*options),
|
||||
webview_attributes,
|
||||
)
|
||||
})
|
||||
.map_err(crate::error::into_anyhow)?;
|
||||
|
||||
Ok(())
|
||||
}
|
||||
|
@ -170,6 +172,16 @@ impl Cmd {
|
|||
context: InvokeContext<R>,
|
||||
label: Option<String>,
|
||||
cmd: WindowManagerCmd,
|
||||
) -> super::Result<InvokeResponse> {
|
||||
Self::_manage(context, label, cmd)
|
||||
.await
|
||||
.map_err(crate::error::into_anyhow)
|
||||
}
|
||||
|
||||
async fn _manage<R: Runtime>(
|
||||
context: InvokeContext<R>,
|
||||
label: Option<String>,
|
||||
cmd: WindowManagerCmd,
|
||||
) -> crate::Result<InvokeResponse> {
|
||||
let window = match label {
|
||||
Some(l) if !l.is_empty() => context
|
||||
|
|
|
@ -109,6 +109,16 @@ pub enum Error {
|
|||
InvalidWindowUrl(&'static str),
|
||||
}
|
||||
|
||||
pub(crate) fn into_anyhow<T: std::fmt::Display>(err: T) -> anyhow::Error {
|
||||
anyhow::anyhow!(err.to_string())
|
||||
}
|
||||
|
||||
impl Error {
|
||||
pub(crate) fn into_anyhow(self) -> anyhow::Error {
|
||||
anyhow::anyhow!(self.to_string())
|
||||
}
|
||||
}
|
||||
|
||||
impl From<serde_json::Error> for Error {
|
||||
fn from(error: serde_json::Error) -> Self {
|
||||
if error.to_string().contains("unknown variant") {
|
||||
|
|
|
@ -95,6 +95,12 @@ impl InvokeError {
|
|||
pub fn from_serde_json(error: serde_json::Error) -> Self {
|
||||
Self(JsonValue::String(error.to_string()))
|
||||
}
|
||||
|
||||
/// Create an [`InvokeError`] as a string of the [`anyhow::Error`] message.
|
||||
#[inline(always)]
|
||||
pub fn from_anyhow(error: anyhow::Error) -> Self {
|
||||
Self(JsonValue::String(error.to_string()))
|
||||
}
|
||||
}
|
||||
|
||||
impl<T: Serialize> From<T> for InvokeError {
|
||||
|
|
|
@ -577,6 +577,13 @@ mod test_utils {
|
|||
pub fn assert_send<T: Send>() {}
|
||||
pub fn assert_sync<T: Sync>() {}
|
||||
|
||||
#[allow(dead_code)]
|
||||
pub fn assert_not_allowlist_error<T>(res: anyhow::Result<T>) {
|
||||
if let Err(e) = res {
|
||||
assert!(!e.to_string().contains("not on the allowlist"));
|
||||
}
|
||||
}
|
||||
|
||||
proptest! {
|
||||
#![proptest_config(ProptestConfig::with_cases(10000))]
|
||||
#[test]
|
||||
|
|
Loading…
Reference in New Issue