command.rs 8.5 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296
  1. // Copyright 2019-2023 Tauri Programme within The Commons Conservancy
  2. // SPDX-License-Identifier: Apache-2.0
  3. // SPDX-License-Identifier: MIT
  4. //! The Tauri custom commands types and traits.
  5. //!
  6. //! You usually don't need to create these items yourself. These are created from [command](../attr.command.html)
  7. //! attribute macro along the way and used by [`crate::generate_handler`] macro.
  8. use crate::hooks::InvokeError;
  9. use crate::InvokeMessage;
  10. use crate::Runtime;
  11. use serde::de::Visitor;
  12. use serde::{Deserialize, Deserializer};
  13. /// Represents a custom command.
  14. pub struct CommandItem<'a, R: Runtime> {
  15. /// The name of the command, e.g. `handler` on `#[command] fn handler(value: u64)`
  16. pub name: &'static str,
  17. /// The key of the command item, e.g. `value` on `#[command] fn handler(value: u64)`
  18. pub key: &'static str,
  19. /// The [`InvokeMessage`] that was passed to this command.
  20. pub message: &'a InvokeMessage<R>,
  21. }
  22. /// Trait implemented by command arguments to derive a value from a [`CommandItem`].
  23. ///
  24. /// # Command Arguments
  25. ///
  26. /// A command argument is any type that represents an item parsable from a [`CommandItem`]. Most
  27. /// implementations will use the data stored in [`InvokeMessage`] since [`CommandItem`] is mostly a
  28. /// wrapper around it.
  29. ///
  30. /// # Provided Implementations
  31. ///
  32. /// Tauri implements [`CommandArg`] automatically for a number of types.
  33. /// * [`crate::Window`]
  34. /// * [`crate::State`]
  35. /// * `T where T: serde::Deserialize`
  36. /// * Any type that implements `Deserialize` can automatically be used as a [`CommandArg`].
  37. pub trait CommandArg<'de, R: Runtime>: Sized {
  38. /// Derives an instance of `Self` from the [`CommandItem`].
  39. ///
  40. /// If the derivation fails, the corresponding message will be rejected using [`InvokeMessage#reject`].
  41. fn from_command(command: CommandItem<'de, R>) -> Result<Self, InvokeError>;
  42. }
  43. /// Automatically implement [`CommandArg`] for any type that can be deserialized.
  44. impl<'de, D: Deserialize<'de>, R: Runtime> CommandArg<'de, R> for D {
  45. fn from_command(command: CommandItem<'de, R>) -> Result<D, InvokeError> {
  46. let name = command.name;
  47. let arg = command.key;
  48. Self::deserialize(command).map_err(|e| crate::Error::InvalidArgs(name, arg, e).into())
  49. }
  50. }
  51. /// Pass the result of [`serde_json::Value::get`] into [`serde_json::Value`]'s deserializer.
  52. ///
  53. /// Returns an error if the [`CommandItem`]'s key does not exist in the value.
  54. macro_rules! pass {
  55. ($fn:ident, $($arg:ident: $argt:ty),+) => {
  56. fn $fn<V: Visitor<'de>>(self, $($arg: $argt),*) -> Result<V::Value, Self::Error> {
  57. use serde::de::Error;
  58. if self.key.is_empty() {
  59. return Err(serde_json::Error::custom(format!(
  60. "command {} has an argument with no name with a non-optional value",
  61. self.name
  62. )))
  63. }
  64. match self.message.payload.get(self.key) {
  65. Some(value) => value.$fn($($arg),*),
  66. None => {
  67. Err(serde_json::Error::custom(format!(
  68. "command {} missing required key {}",
  69. self.name, self.key
  70. )))
  71. }
  72. }
  73. }
  74. }
  75. }
  76. /// A [`Deserializer`] wrapper around [`CommandItem`].
  77. ///
  78. /// If the key doesn't exist, an error will be returned if the deserialized type is not expecting
  79. /// an optional item. If the key does exist, the value will be called with
  80. /// [`Value`](serde_json::Value)'s [`Deserializer`] implementation.
  81. impl<'de, R: Runtime> Deserializer<'de> for CommandItem<'de, R> {
  82. type Error = serde_json::Error;
  83. pass!(deserialize_any, visitor: V);
  84. pass!(deserialize_bool, visitor: V);
  85. pass!(deserialize_i8, visitor: V);
  86. pass!(deserialize_i16, visitor: V);
  87. pass!(deserialize_i32, visitor: V);
  88. pass!(deserialize_i64, visitor: V);
  89. pass!(deserialize_u8, visitor: V);
  90. pass!(deserialize_u16, visitor: V);
  91. pass!(deserialize_u32, visitor: V);
  92. pass!(deserialize_u64, visitor: V);
  93. pass!(deserialize_f32, visitor: V);
  94. pass!(deserialize_f64, visitor: V);
  95. pass!(deserialize_char, visitor: V);
  96. pass!(deserialize_str, visitor: V);
  97. pass!(deserialize_string, visitor: V);
  98. pass!(deserialize_bytes, visitor: V);
  99. pass!(deserialize_byte_buf, visitor: V);
  100. fn deserialize_option<V: Visitor<'de>>(self, visitor: V) -> Result<V::Value, Self::Error> {
  101. match self.message.payload.get(self.key) {
  102. Some(value) => value.deserialize_option(visitor),
  103. None => visitor.visit_none(),
  104. }
  105. }
  106. pass!(deserialize_unit, visitor: V);
  107. pass!(deserialize_unit_struct, name: &'static str, visitor: V);
  108. pass!(deserialize_newtype_struct, name: &'static str, visitor: V);
  109. pass!(deserialize_seq, visitor: V);
  110. pass!(deserialize_tuple, len: usize, visitor: V);
  111. pass!(
  112. deserialize_tuple_struct,
  113. name: &'static str,
  114. len: usize,
  115. visitor: V
  116. );
  117. pass!(deserialize_map, visitor: V);
  118. pass!(
  119. deserialize_struct,
  120. name: &'static str,
  121. fields: &'static [&'static str],
  122. visitor: V
  123. );
  124. pass!(
  125. deserialize_enum,
  126. name: &'static str,
  127. fields: &'static [&'static str],
  128. visitor: V
  129. );
  130. pass!(deserialize_identifier, visitor: V);
  131. pass!(deserialize_ignored_any, visitor: V);
  132. }
  133. /// [Autoref-based stable specialization](https://github.com/dtolnay/case-studies/blob/master/autoref-specialization/README.md)
  134. ///
  135. /// Nothing in this module is considered stable.
  136. #[doc(hidden)]
  137. pub mod private {
  138. use crate::{InvokeError, InvokeResolver, Runtime};
  139. use futures_util::{FutureExt, TryFutureExt};
  140. use serde::Serialize;
  141. use serde_json::Value;
  142. use std::future::Future;
  143. // ===== impl Serialize =====
  144. pub struct SerializeTag;
  145. pub trait SerializeKind {
  146. #[inline(always)]
  147. fn blocking_kind(&self) -> SerializeTag {
  148. SerializeTag
  149. }
  150. #[inline(always)]
  151. fn async_kind(&self) -> SerializeTag {
  152. SerializeTag
  153. }
  154. }
  155. impl<T: Serialize> SerializeKind for &T {}
  156. impl SerializeTag {
  157. #[inline(always)]
  158. pub fn block<R, T>(self, value: T, resolver: InvokeResolver<R>)
  159. where
  160. R: Runtime,
  161. T: Serialize,
  162. {
  163. resolver.respond(Ok(value))
  164. }
  165. #[inline(always)]
  166. pub fn future<T>(self, value: T) -> impl Future<Output = Result<Value, InvokeError>>
  167. where
  168. T: Serialize,
  169. {
  170. std::future::ready(serde_json::to_value(value).map_err(InvokeError::from_serde_json))
  171. }
  172. }
  173. // ===== Result<impl Serialize, impl Into<InvokeError>> =====
  174. pub struct ResultTag;
  175. pub trait ResultKind {
  176. #[inline(always)]
  177. fn blocking_kind(&self) -> ResultTag {
  178. ResultTag
  179. }
  180. #[inline(always)]
  181. fn async_kind(&self) -> ResultTag {
  182. ResultTag
  183. }
  184. }
  185. impl<T: Serialize, E: Into<InvokeError>> ResultKind for Result<T, E> {}
  186. impl ResultTag {
  187. #[inline(always)]
  188. pub fn block<R, T, E>(self, value: Result<T, E>, resolver: InvokeResolver<R>)
  189. where
  190. R: Runtime,
  191. T: Serialize,
  192. E: Into<InvokeError>,
  193. {
  194. resolver.respond(value.map_err(Into::into))
  195. }
  196. #[inline(always)]
  197. pub fn future<T, E>(
  198. self,
  199. value: Result<T, E>,
  200. ) -> impl Future<Output = Result<Value, InvokeError>>
  201. where
  202. T: Serialize,
  203. E: Into<InvokeError>,
  204. {
  205. std::future::ready(
  206. value
  207. .map_err(Into::into)
  208. .and_then(|value| serde_json::to_value(value).map_err(InvokeError::from_serde_json)),
  209. )
  210. }
  211. }
  212. // ===== Future<Output = impl Serialize> =====
  213. pub struct FutureTag;
  214. pub trait FutureKind {
  215. #[inline(always)]
  216. fn async_kind(&self) -> FutureTag {
  217. FutureTag
  218. }
  219. }
  220. impl<T: Serialize, F: Future<Output = T>> FutureKind for &F {}
  221. impl FutureTag {
  222. #[inline(always)]
  223. pub fn future<T, F>(self, value: F) -> impl Future<Output = Result<Value, InvokeError>>
  224. where
  225. T: Serialize,
  226. F: Future<Output = T> + Send + 'static,
  227. {
  228. value.map(|value| serde_json::to_value(value).map_err(InvokeError::from_serde_json))
  229. }
  230. }
  231. // ===== Future<Output = Result<impl Serialize, impl Into<InvokeError>>> =====
  232. pub struct ResultFutureTag;
  233. pub trait ResultFutureKind {
  234. #[inline(always)]
  235. fn async_kind(&self) -> ResultFutureTag {
  236. ResultFutureTag
  237. }
  238. }
  239. impl<T: Serialize, E: Into<InvokeError>, F: Future<Output = Result<T, E>>> ResultFutureKind for F {}
  240. impl ResultFutureTag {
  241. #[inline(always)]
  242. pub fn future<T, E, F>(self, value: F) -> impl Future<Output = Result<Value, InvokeError>>
  243. where
  244. T: Serialize,
  245. E: Into<InvokeError>,
  246. F: Future<Output = Result<T, E>> + Send,
  247. {
  248. value.err_into().map(|result| {
  249. result.and_then(|value| serde_json::to_value(value).map_err(InvokeError::from_serde_json))
  250. })
  251. }
  252. }
  253. }