tower_lsp/jsonrpc/
response.rs

1use std::fmt::{self, Debug, Formatter};
2use std::str::FromStr;
3
4use serde::{Deserialize, Serialize};
5use serde_json::Value;
6
7use super::{Error, Id, Result, Version};
8
9#[derive(Clone, PartialEq, Deserialize, Serialize)]
10#[serde(untagged)]
11enum Kind {
12    Ok { result: Value },
13    Err { error: Error },
14}
15
16/// A successful or failed JSON-RPC response.
17#[derive(Clone, PartialEq, Deserialize, Serialize)]
18pub struct Response {
19    jsonrpc: Version,
20    #[serde(flatten)]
21    kind: Kind,
22    id: Id,
23}
24
25impl Response {
26    /// Creates a new successful response from a request ID and `Error` object.
27    pub const fn from_ok(id: Id, result: Value) -> Self {
28        Response {
29            jsonrpc: Version,
30            kind: Kind::Ok { result },
31            id,
32        }
33    }
34
35    /// Creates a new error response from a request ID and `Error` object.
36    pub const fn from_error(id: Id, error: Error) -> Self {
37        Response {
38            jsonrpc: Version,
39            kind: Kind::Err { error },
40            id,
41        }
42    }
43
44    /// Creates a new response from a request ID and either an `Ok(Value)` or `Err(Error)` body.
45    pub fn from_parts(id: Id, body: Result<Value>) -> Self {
46        match body {
47            Ok(result) => Response::from_ok(id, result),
48            Err(error) => Response::from_error(id, error),
49        }
50    }
51
52    /// Splits the response into a request ID paired with either an `Ok(Value)` or `Err(Error)` to
53    /// signify whether the response is a success or failure.
54    pub fn into_parts(self) -> (Id, Result<Value>) {
55        match self.kind {
56            Kind::Ok { result } => (self.id, Ok(result)),
57            Kind::Err { error } => (self.id, Err(error)),
58        }
59    }
60
61    /// Returns `true` if the response indicates success.
62    pub const fn is_ok(&self) -> bool {
63        matches!(self.kind, Kind::Ok { .. })
64    }
65
66    /// Returns `true` if the response indicates failure.
67    pub const fn is_error(&self) -> bool {
68        !self.is_ok()
69    }
70
71    /// Returns the `result` value, if it exists.
72    ///
73    /// This member only exists if the response indicates success.
74    pub const fn result(&self) -> Option<&Value> {
75        match &self.kind {
76            Kind::Ok { result } => Some(result),
77            _ => None,
78        }
79    }
80
81    /// Returns the `error` value, if it exists.
82    ///
83    /// This member only exists if the response indicates failure.
84    pub const fn error(&self) -> Option<&Error> {
85        match &self.kind {
86            Kind::Err { error } => Some(error),
87            _ => None,
88        }
89    }
90
91    /// Returns the corresponding request ID, if known.
92    pub const fn id(&self) -> &Id {
93        &self.id
94    }
95}
96
97impl Debug for Response {
98    fn fmt(&self, f: &mut Formatter) -> fmt::Result {
99        let mut d = f.debug_struct("Response");
100        d.field("jsonrpc", &self.jsonrpc);
101
102        match &self.kind {
103            Kind::Ok { result } => d.field("result", result),
104            Kind::Err { error } => d.field("error", error),
105        };
106
107        d.field("id", &self.id).finish()
108    }
109}
110
111impl FromStr for Response {
112    type Err = serde_json::Error;
113
114    fn from_str(s: &str) -> std::result::Result<Self, Self::Err> {
115        serde_json::from_str(s)
116    }
117}