jacquard_api/com_atproto/repo/
create_record.rs1#[allow(unused_imports)]
9use alloc::collections::BTreeMap;
10
11#[allow(unused_imports)]
12use core::marker::PhantomData;
13use jacquard_common::CowStr;
14use jacquard_common::types::ident::AtIdentifier;
15use jacquard_common::types::string::{AtUri, Nsid, Cid, RecordKey, Rkey};
16use jacquard_common::types::value::Data;
17use jacquard_derive::{IntoStatic, lexicon, open_union};
18use serde::{Serialize, Deserialize};
19use crate::com_atproto::repo::CommitMeta;
20
21#[lexicon]
22#[derive(Serialize, Deserialize, Debug, Clone, PartialEq, Eq, IntoStatic)]
23#[serde(rename_all = "camelCase")]
24pub struct CreateRecord<'a> {
25 #[serde(borrow)]
27 pub collection: Nsid<'a>,
28 #[serde(borrow)]
30 pub record: Data<'a>,
31 #[serde(borrow)]
33 pub repo: AtIdentifier<'a>,
34 #[serde(skip_serializing_if = "Option::is_none")]
36 #[serde(borrow)]
37 pub rkey: Option<RecordKey<Rkey<'a>>>,
38 #[serde(skip_serializing_if = "Option::is_none")]
40 #[serde(borrow)]
41 pub swap_commit: Option<Cid<'a>>,
42 #[serde(skip_serializing_if = "Option::is_none")]
44 pub validate: Option<bool>,
45}
46
47
48#[lexicon]
49#[derive(Serialize, Deserialize, Debug, Clone, PartialEq, Eq, IntoStatic)]
50#[serde(rename_all = "camelCase")]
51pub struct CreateRecordOutput<'a> {
52 #[serde(borrow)]
53 pub cid: Cid<'a>,
54 #[serde(skip_serializing_if = "Option::is_none")]
55 #[serde(borrow)]
56 pub commit: Option<CommitMeta<'a>>,
57 #[serde(borrow)]
58 pub uri: AtUri<'a>,
59 #[serde(skip_serializing_if = "Option::is_none")]
60 #[serde(borrow)]
61 pub validation_status: Option<CreateRecordOutputValidationStatus<'a>>,
62}
63
64
65#[derive(Debug, Clone, PartialEq, Eq, Hash)]
66pub enum CreateRecordOutputValidationStatus<'a> {
67 Valid,
68 Unknown,
69 Other(CowStr<'a>),
70}
71
72impl<'a> CreateRecordOutputValidationStatus<'a> {
73 pub fn as_str(&self) -> &str {
74 match self {
75 Self::Valid => "valid",
76 Self::Unknown => "unknown",
77 Self::Other(s) => s.as_ref(),
78 }
79 }
80}
81
82impl<'a> From<&'a str> for CreateRecordOutputValidationStatus<'a> {
83 fn from(s: &'a str) -> Self {
84 match s {
85 "valid" => Self::Valid,
86 "unknown" => Self::Unknown,
87 _ => Self::Other(CowStr::from(s)),
88 }
89 }
90}
91
92impl<'a> From<String> for CreateRecordOutputValidationStatus<'a> {
93 fn from(s: String) -> Self {
94 match s.as_str() {
95 "valid" => Self::Valid,
96 "unknown" => Self::Unknown,
97 _ => Self::Other(CowStr::from(s)),
98 }
99 }
100}
101
102impl<'a> core::fmt::Display for CreateRecordOutputValidationStatus<'a> {
103 fn fmt(&self, f: &mut core::fmt::Formatter<'_>) -> core::fmt::Result {
104 write!(f, "{}", self.as_str())
105 }
106}
107
108impl<'a> AsRef<str> for CreateRecordOutputValidationStatus<'a> {
109 fn as_ref(&self) -> &str {
110 self.as_str()
111 }
112}
113
114impl<'a> serde::Serialize for CreateRecordOutputValidationStatus<'a> {
115 fn serialize<S>(&self, serializer: S) -> Result<S::Ok, S::Error>
116 where
117 S: serde::Serializer,
118 {
119 serializer.serialize_str(self.as_str())
120 }
121}
122
123impl<'de, 'a> serde::Deserialize<'de> for CreateRecordOutputValidationStatus<'a>
124where
125 'de: 'a,
126{
127 fn deserialize<D>(deserializer: D) -> Result<Self, D::Error>
128 where
129 D: serde::Deserializer<'de>,
130 {
131 let s = <&'de str>::deserialize(deserializer)?;
132 Ok(Self::from(s))
133 }
134}
135
136impl<'a> Default for CreateRecordOutputValidationStatus<'a> {
137 fn default() -> Self {
138 Self::Other(Default::default())
139 }
140}
141
142impl jacquard_common::IntoStatic for CreateRecordOutputValidationStatus<'_> {
143 type Output = CreateRecordOutputValidationStatus<'static>;
144 fn into_static(self) -> Self::Output {
145 match self {
146 CreateRecordOutputValidationStatus::Valid => {
147 CreateRecordOutputValidationStatus::Valid
148 }
149 CreateRecordOutputValidationStatus::Unknown => {
150 CreateRecordOutputValidationStatus::Unknown
151 }
152 CreateRecordOutputValidationStatus::Other(v) => {
153 CreateRecordOutputValidationStatus::Other(v.into_static())
154 }
155 }
156 }
157}
158
159
160#[open_union]
161#[derive(
162 Serialize,
163 Deserialize,
164 Debug,
165 Clone,
166 PartialEq,
167 Eq,
168 thiserror::Error,
169 miette::Diagnostic,
170 IntoStatic
171)]
172
173#[serde(tag = "error", content = "message")]
174#[serde(bound(deserialize = "'de: 'a"))]
175pub enum CreateRecordError<'a> {
176 #[serde(rename = "InvalidSwap")]
178 InvalidSwap(Option<CowStr<'a>>),
179}
180
181impl core::fmt::Display for CreateRecordError<'_> {
182 fn fmt(&self, f: &mut core::fmt::Formatter<'_>) -> core::fmt::Result {
183 match self {
184 Self::InvalidSwap(msg) => {
185 write!(f, "InvalidSwap")?;
186 if let Some(msg) = msg {
187 write!(f, ": {}", msg)?;
188 }
189 Ok(())
190 }
191 Self::Unknown(err) => write!(f, "Unknown error: {:?}", err),
192 }
193 }
194}
195
196pub struct CreateRecordResponse;
198impl jacquard_common::xrpc::XrpcResp for CreateRecordResponse {
199 const NSID: &'static str = "com.atproto.repo.createRecord";
200 const ENCODING: &'static str = "application/json";
201 type Output<'de> = CreateRecordOutput<'de>;
202 type Err<'de> = CreateRecordError<'de>;
203}
204
205impl<'a> jacquard_common::xrpc::XrpcRequest for CreateRecord<'a> {
206 const NSID: &'static str = "com.atproto.repo.createRecord";
207 const METHOD: jacquard_common::xrpc::XrpcMethod = jacquard_common::xrpc::XrpcMethod::Procedure(
208 "application/json",
209 );
210 type Response = CreateRecordResponse;
211}
212
213pub struct CreateRecordRequest;
215impl jacquard_common::xrpc::XrpcEndpoint for CreateRecordRequest {
216 const PATH: &'static str = "/xrpc/com.atproto.repo.createRecord";
217 const METHOD: jacquard_common::xrpc::XrpcMethod = jacquard_common::xrpc::XrpcMethod::Procedure(
218 "application/json",
219 );
220 type Request<'de> = CreateRecord<'de>;
221 type Response = CreateRecordResponse;
222}
223
224pub mod create_record_state {
225
226 pub use crate::builder_types::{Set, Unset, IsSet, IsUnset};
227 #[allow(unused)]
228 use ::core::marker::PhantomData;
229 mod sealed {
230 pub trait Sealed {}
231 }
232 pub trait State: sealed::Sealed {
234 type Repo;
235 type Collection;
236 type Record;
237 }
238 pub struct Empty(());
240 impl sealed::Sealed for Empty {}
241 impl State for Empty {
242 type Repo = Unset;
243 type Collection = Unset;
244 type Record = Unset;
245 }
246 pub struct SetRepo<S: State = Empty>(PhantomData<fn() -> S>);
248 impl<S: State> sealed::Sealed for SetRepo<S> {}
249 impl<S: State> State for SetRepo<S> {
250 type Repo = Set<members::repo>;
251 type Collection = S::Collection;
252 type Record = S::Record;
253 }
254 pub struct SetCollection<S: State = Empty>(PhantomData<fn() -> S>);
256 impl<S: State> sealed::Sealed for SetCollection<S> {}
257 impl<S: State> State for SetCollection<S> {
258 type Repo = S::Repo;
259 type Collection = Set<members::collection>;
260 type Record = S::Record;
261 }
262 pub struct SetRecord<S: State = Empty>(PhantomData<fn() -> S>);
264 impl<S: State> sealed::Sealed for SetRecord<S> {}
265 impl<S: State> State for SetRecord<S> {
266 type Repo = S::Repo;
267 type Collection = S::Collection;
268 type Record = Set<members::record>;
269 }
270 #[allow(non_camel_case_types)]
272 pub mod members {
273 pub struct repo(());
275 pub struct collection(());
277 pub struct record(());
279 }
280}
281
282pub struct CreateRecordBuilder<'a, S: create_record_state::State> {
284 _state: PhantomData<fn() -> S>,
285 _fields: (
286 Option<Nsid<'a>>,
287 Option<Data<'a>>,
288 Option<AtIdentifier<'a>>,
289 Option<RecordKey<Rkey<'a>>>,
290 Option<Cid<'a>>,
291 Option<bool>,
292 ),
293 _lifetime: PhantomData<&'a ()>,
294}
295
296impl<'a> CreateRecord<'a> {
297 pub fn new() -> CreateRecordBuilder<'a, create_record_state::Empty> {
299 CreateRecordBuilder::new()
300 }
301}
302
303impl<'a> CreateRecordBuilder<'a, create_record_state::Empty> {
304 pub fn new() -> Self {
306 CreateRecordBuilder {
307 _state: PhantomData,
308 _fields: (None, None, None, None, None, None),
309 _lifetime: PhantomData,
310 }
311 }
312}
313
314impl<'a, S> CreateRecordBuilder<'a, S>
315where
316 S: create_record_state::State,
317 S::Collection: create_record_state::IsUnset,
318{
319 pub fn collection(
321 mut self,
322 value: impl Into<Nsid<'a>>,
323 ) -> CreateRecordBuilder<'a, create_record_state::SetCollection<S>> {
324 self._fields.0 = Option::Some(value.into());
325 CreateRecordBuilder {
326 _state: PhantomData,
327 _fields: self._fields,
328 _lifetime: PhantomData,
329 }
330 }
331}
332
333impl<'a, S> CreateRecordBuilder<'a, S>
334where
335 S: create_record_state::State,
336 S::Record: create_record_state::IsUnset,
337{
338 pub fn record(
340 mut self,
341 value: impl Into<Data<'a>>,
342 ) -> CreateRecordBuilder<'a, create_record_state::SetRecord<S>> {
343 self._fields.1 = Option::Some(value.into());
344 CreateRecordBuilder {
345 _state: PhantomData,
346 _fields: self._fields,
347 _lifetime: PhantomData,
348 }
349 }
350}
351
352impl<'a, S> CreateRecordBuilder<'a, S>
353where
354 S: create_record_state::State,
355 S::Repo: create_record_state::IsUnset,
356{
357 pub fn repo(
359 mut self,
360 value: impl Into<AtIdentifier<'a>>,
361 ) -> CreateRecordBuilder<'a, create_record_state::SetRepo<S>> {
362 self._fields.2 = Option::Some(value.into());
363 CreateRecordBuilder {
364 _state: PhantomData,
365 _fields: self._fields,
366 _lifetime: PhantomData,
367 }
368 }
369}
370
371impl<'a, S: create_record_state::State> CreateRecordBuilder<'a, S> {
372 pub fn rkey(mut self, value: impl Into<Option<RecordKey<Rkey<'a>>>>) -> Self {
374 self._fields.3 = value.into();
375 self
376 }
377 pub fn maybe_rkey(mut self, value: Option<RecordKey<Rkey<'a>>>) -> Self {
379 self._fields.3 = value;
380 self
381 }
382}
383
384impl<'a, S: create_record_state::State> CreateRecordBuilder<'a, S> {
385 pub fn swap_commit(mut self, value: impl Into<Option<Cid<'a>>>) -> Self {
387 self._fields.4 = value.into();
388 self
389 }
390 pub fn maybe_swap_commit(mut self, value: Option<Cid<'a>>) -> Self {
392 self._fields.4 = value;
393 self
394 }
395}
396
397impl<'a, S: create_record_state::State> CreateRecordBuilder<'a, S> {
398 pub fn validate(mut self, value: impl Into<Option<bool>>) -> Self {
400 self._fields.5 = value.into();
401 self
402 }
403 pub fn maybe_validate(mut self, value: Option<bool>) -> Self {
405 self._fields.5 = value;
406 self
407 }
408}
409
410impl<'a, S> CreateRecordBuilder<'a, S>
411where
412 S: create_record_state::State,
413 S::Repo: create_record_state::IsSet,
414 S::Collection: create_record_state::IsSet,
415 S::Record: create_record_state::IsSet,
416{
417 pub fn build(self) -> CreateRecord<'a> {
419 CreateRecord {
420 collection: self._fields.0.unwrap(),
421 record: self._fields.1.unwrap(),
422 repo: self._fields.2.unwrap(),
423 rkey: self._fields.3,
424 swap_commit: self._fields.4,
425 validate: self._fields.5,
426 extra_data: Default::default(),
427 }
428 }
429 pub fn build_with_data(
431 self,
432 extra_data: BTreeMap<jacquard_common::deps::smol_str::SmolStr, Data<'a>>,
433 ) -> CreateRecord<'a> {
434 CreateRecord {
435 collection: self._fields.0.unwrap(),
436 record: self._fields.1.unwrap(),
437 repo: self._fields.2.unwrap(),
438 rkey: self._fields.3,
439 swap_commit: self._fields.4,
440 validate: self._fields.5,
441 extra_data: Some(extra_data),
442 }
443 }
444}