bitwarden_ipc/rpc/
request_message.rs

1use serde::{Deserialize, Serialize};
2
3use crate::{
4    message::PayloadTypeName,
5    rpc::{error::RpcError, request::RpcRequest},
6    serde_utils,
7};
8
9pub const RPC_REQUEST_PAYLOAD_TYPE_NAME: &str = "RpcRequestMessage";
10
11/// Represents the payload of an RPC request.
12/// It encapsulates both the serialized and deserialized form of the request. This
13/// allows for efficient handling of requests without having to implement deserialization
14/// in multiple places.
15pub struct RpcRequestPayload {
16    data: Vec<u8>,
17    partial: PartialRpcRequestMessage,
18}
19
20impl RpcRequestPayload {
21    pub fn from_slice(data: Vec<u8>) -> Result<Self, serde_utils::DeserializeError> {
22        let partial: PartialRpcRequestMessage = serde_utils::from_slice(&data)?;
23
24        Ok(Self { data, partial })
25    }
26
27    pub fn request_id(&self) -> &str {
28        &self.partial.request_id
29    }
30
31    pub fn request_type(&self) -> &str {
32        &self.partial.request_type
33    }
34
35    pub fn deserialize_full<T>(&self) -> Result<RpcRequestMessage<T>, RpcError>
36    where
37        T: RpcRequest,
38    {
39        serde_utils::from_slice(&self.data)
40            .map_err(|e| RpcError::RequestDeserializationError(e.to_string()))
41    }
42}
43
44#[derive(Debug, Clone, Serialize, Deserialize)]
45pub struct RpcRequestMessage<T> {
46    pub request: T,
47    pub request_id: String,
48    pub request_type: String,
49}
50
51#[derive(Debug, Clone, Serialize, Deserialize)]
52struct PartialRpcRequestMessage {
53    pub request_id: String,
54    pub request_type: String,
55}
56
57impl<T> PayloadTypeName for RpcRequestMessage<T> {
58    const PAYLOAD_TYPE_NAME: &str = RPC_REQUEST_PAYLOAD_TYPE_NAME;
59}