1#[allow(unused_imports)]
9use alloc::collections::BTreeMap;
10
11#[allow(unused_imports)]
12use core::marker::PhantomData;
13use jacquard_common::CowStr;
14
15#[allow(unused_imports)]
16use jacquard_common::deps::codegen::unicode_segmentation::UnicodeSegmentation;
17use jacquard_common::types::collection::{Collection, RecordError};
18use jacquard_common::types::string::{AtUri, Cid, Datetime};
19use jacquard_common::types::uri::{RecordUri, UriError};
20use jacquard_common::xrpc::XrpcResp;
21use jacquard_derive::{IntoStatic, lexicon};
22use jacquard_lexicon::lexicon::LexiconDoc;
23use jacquard_lexicon::schema::LexiconSchema;
24
25#[allow(unused_imports)]
26use jacquard_lexicon::validation::{ConstraintError, ValidationPath};
27use serde::{Serialize, Deserialize};
28use crate::app_bsky::richtext::facet::Facet;
29use crate::app_bsky::graph::starterpack;
30
31#[lexicon]
32#[derive(Serialize, Deserialize, Debug, Clone, PartialEq, Eq, IntoStatic)]
33#[serde(rename_all = "camelCase")]
34pub struct FeedItem<'a> {
35 #[serde(borrow)]
36 pub uri: AtUri<'a>,
37}
38
39#[lexicon]
42#[derive(Serialize, Deserialize, Debug, Clone, PartialEq, Eq, IntoStatic)]
43#[serde(rename_all = "camelCase", rename = "app.bsky.graph.starterpack", tag = "$type")]
44pub struct Starterpack<'a> {
45 pub created_at: Datetime,
46 #[serde(skip_serializing_if = "Option::is_none")]
47 #[serde(borrow)]
48 pub description: Option<CowStr<'a>>,
49 #[serde(skip_serializing_if = "Option::is_none")]
50 #[serde(borrow)]
51 pub description_facets: Option<Vec<Facet<'a>>>,
52 #[serde(skip_serializing_if = "Option::is_none")]
53 #[serde(borrow)]
54 pub feeds: Option<Vec<starterpack::FeedItem<'a>>>,
55 #[serde(borrow)]
57 pub list: AtUri<'a>,
58 #[serde(borrow)]
60 pub name: CowStr<'a>,
61}
62
63#[derive(Serialize, Deserialize, Debug, Clone, PartialEq, Eq, IntoStatic)]
66#[serde(rename_all = "camelCase")]
67pub struct StarterpackGetRecordOutput<'a> {
68 #[serde(skip_serializing_if = "Option::is_none")]
69 #[serde(borrow)]
70 pub cid: Option<Cid<'a>>,
71 #[serde(borrow)]
72 pub uri: AtUri<'a>,
73 #[serde(borrow)]
74 pub value: Starterpack<'a>,
75}
76
77impl<'a> Starterpack<'a> {
78 pub fn uri(
79 uri: impl Into<CowStr<'a>>,
80 ) -> Result<RecordUri<'a, StarterpackRecord>, UriError> {
81 RecordUri::try_from_uri(AtUri::new_cow(uri.into())?)
82 }
83}
84
85impl<'a> LexiconSchema for FeedItem<'a> {
86 fn nsid() -> &'static str {
87 "app.bsky.graph.starterpack"
88 }
89 fn def_name() -> &'static str {
90 "feedItem"
91 }
92 fn lexicon_doc() -> LexiconDoc<'static> {
93 lexicon_doc_app_bsky_graph_starterpack()
94 }
95 fn validate(&self) -> Result<(), ConstraintError> {
96 Ok(())
97 }
98}
99
100#[derive(Debug, Serialize, Deserialize)]
103pub struct StarterpackRecord;
104impl XrpcResp for StarterpackRecord {
105 const NSID: &'static str = "app.bsky.graph.starterpack";
106 const ENCODING: &'static str = "application/json";
107 type Output<'de> = StarterpackGetRecordOutput<'de>;
108 type Err<'de> = RecordError<'de>;
109}
110
111impl From<StarterpackGetRecordOutput<'_>> for Starterpack<'_> {
112 fn from(output: StarterpackGetRecordOutput<'_>) -> Self {
113 use jacquard_common::IntoStatic;
114 output.value.into_static()
115 }
116}
117
118impl Collection for Starterpack<'_> {
119 const NSID: &'static str = "app.bsky.graph.starterpack";
120 type Record = StarterpackRecord;
121}
122
123impl Collection for StarterpackRecord {
124 const NSID: &'static str = "app.bsky.graph.starterpack";
125 type Record = StarterpackRecord;
126}
127
128impl<'a> LexiconSchema for Starterpack<'a> {
129 fn nsid() -> &'static str {
130 "app.bsky.graph.starterpack"
131 }
132 fn def_name() -> &'static str {
133 "main"
134 }
135 fn lexicon_doc() -> LexiconDoc<'static> {
136 lexicon_doc_app_bsky_graph_starterpack()
137 }
138 fn validate(&self) -> Result<(), ConstraintError> {
139 if let Some(ref value) = self.description {
140 #[allow(unused_comparisons)]
141 if <str>::len(value.as_ref()) > 3000usize {
142 return Err(ConstraintError::MaxLength {
143 path: ValidationPath::from_field("description"),
144 max: 3000usize,
145 actual: <str>::len(value.as_ref()),
146 });
147 }
148 }
149 if let Some(ref value) = self.description {
150 {
151 let count = UnicodeSegmentation::graphemes(value.as_ref(), true).count();
152 if count > 300usize {
153 return Err(ConstraintError::MaxGraphemes {
154 path: ValidationPath::from_field("description"),
155 max: 300usize,
156 actual: count,
157 });
158 }
159 }
160 }
161 if let Some(ref value) = self.feeds {
162 #[allow(unused_comparisons)]
163 if value.len() > 3usize {
164 return Err(ConstraintError::MaxLength {
165 path: ValidationPath::from_field("feeds"),
166 max: 3usize,
167 actual: value.len(),
168 });
169 }
170 }
171 {
172 let value = &self.name;
173 #[allow(unused_comparisons)]
174 if <str>::len(value.as_ref()) > 500usize {
175 return Err(ConstraintError::MaxLength {
176 path: ValidationPath::from_field("name"),
177 max: 500usize,
178 actual: <str>::len(value.as_ref()),
179 });
180 }
181 }
182 {
183 let value = &self.name;
184 #[allow(unused_comparisons)]
185 if <str>::len(value.as_ref()) < 1usize {
186 return Err(ConstraintError::MinLength {
187 path: ValidationPath::from_field("name"),
188 min: 1usize,
189 actual: <str>::len(value.as_ref()),
190 });
191 }
192 }
193 {
194 let value = &self.name;
195 {
196 let count = UnicodeSegmentation::graphemes(value.as_ref(), true).count();
197 if count > 50usize {
198 return Err(ConstraintError::MaxGraphemes {
199 path: ValidationPath::from_field("name"),
200 max: 50usize,
201 actual: count,
202 });
203 }
204 }
205 }
206 Ok(())
207 }
208}
209
210pub mod feed_item_state {
211
212 pub use crate::builder_types::{Set, Unset, IsSet, IsUnset};
213 #[allow(unused)]
214 use ::core::marker::PhantomData;
215 mod sealed {
216 pub trait Sealed {}
217 }
218 pub trait State: sealed::Sealed {
220 type Uri;
221 }
222 pub struct Empty(());
224 impl sealed::Sealed for Empty {}
225 impl State for Empty {
226 type Uri = Unset;
227 }
228 pub struct SetUri<S: State = Empty>(PhantomData<fn() -> S>);
230 impl<S: State> sealed::Sealed for SetUri<S> {}
231 impl<S: State> State for SetUri<S> {
232 type Uri = Set<members::uri>;
233 }
234 #[allow(non_camel_case_types)]
236 pub mod members {
237 pub struct uri(());
239 }
240}
241
242pub struct FeedItemBuilder<'a, S: feed_item_state::State> {
244 _state: PhantomData<fn() -> S>,
245 _fields: (Option<AtUri<'a>>,),
246 _lifetime: PhantomData<&'a ()>,
247}
248
249impl<'a> FeedItem<'a> {
250 pub fn new() -> FeedItemBuilder<'a, feed_item_state::Empty> {
252 FeedItemBuilder::new()
253 }
254}
255
256impl<'a> FeedItemBuilder<'a, feed_item_state::Empty> {
257 pub fn new() -> Self {
259 FeedItemBuilder {
260 _state: PhantomData,
261 _fields: (None,),
262 _lifetime: PhantomData,
263 }
264 }
265}
266
267impl<'a, S> FeedItemBuilder<'a, S>
268where
269 S: feed_item_state::State,
270 S::Uri: feed_item_state::IsUnset,
271{
272 pub fn uri(
274 mut self,
275 value: impl Into<AtUri<'a>>,
276 ) -> FeedItemBuilder<'a, feed_item_state::SetUri<S>> {
277 self._fields.0 = Option::Some(value.into());
278 FeedItemBuilder {
279 _state: PhantomData,
280 _fields: self._fields,
281 _lifetime: PhantomData,
282 }
283 }
284}
285
286impl<'a, S> FeedItemBuilder<'a, S>
287where
288 S: feed_item_state::State,
289 S::Uri: feed_item_state::IsSet,
290{
291 pub fn build(self) -> FeedItem<'a> {
293 FeedItem {
294 uri: self._fields.0.unwrap(),
295 extra_data: Default::default(),
296 }
297 }
298 pub fn build_with_data(
300 self,
301 extra_data: BTreeMap<
302 jacquard_common::deps::smol_str::SmolStr,
303 jacquard_common::types::value::Data<'a>,
304 >,
305 ) -> FeedItem<'a> {
306 FeedItem {
307 uri: self._fields.0.unwrap(),
308 extra_data: Some(extra_data),
309 }
310 }
311}
312
313fn lexicon_doc_app_bsky_graph_starterpack() -> LexiconDoc<'static> {
314 #[allow(unused_imports)]
315 use jacquard_common::{CowStr, deps::smol_str::SmolStr, types::blob::MimeType};
316 use jacquard_lexicon::lexicon::*;
317 use alloc::collections::BTreeMap;
318 LexiconDoc {
319 lexicon: Lexicon::Lexicon1,
320 id: CowStr::new_static("app.bsky.graph.starterpack"),
321 defs: {
322 let mut map = BTreeMap::new();
323 map.insert(
324 SmolStr::new_static("feedItem"),
325 LexUserType::Object(LexObject {
326 required: Some(vec![SmolStr::new_static("uri")]),
327 properties: {
328 #[allow(unused_mut)]
329 let mut map = BTreeMap::new();
330 map.insert(
331 SmolStr::new_static("uri"),
332 LexObjectProperty::String(LexString {
333 format: Some(LexStringFormat::AtUri),
334 ..Default::default()
335 }),
336 );
337 map
338 },
339 ..Default::default()
340 }),
341 );
342 map.insert(
343 SmolStr::new_static("main"),
344 LexUserType::Record(LexRecord {
345 description: Some(
346 CowStr::new_static(
347 "Record defining a starter pack of actors and feeds for new users.",
348 ),
349 ),
350 key: Some(CowStr::new_static("tid")),
351 record: LexRecordRecord::Object(LexObject {
352 required: Some(
353 vec![
354 SmolStr::new_static("name"), SmolStr::new_static("list"),
355 SmolStr::new_static("createdAt")
356 ],
357 ),
358 properties: {
359 #[allow(unused_mut)]
360 let mut map = BTreeMap::new();
361 map.insert(
362 SmolStr::new_static("createdAt"),
363 LexObjectProperty::String(LexString {
364 format: Some(LexStringFormat::Datetime),
365 ..Default::default()
366 }),
367 );
368 map.insert(
369 SmolStr::new_static("description"),
370 LexObjectProperty::String(LexString {
371 max_length: Some(3000usize),
372 max_graphemes: Some(300usize),
373 ..Default::default()
374 }),
375 );
376 map.insert(
377 SmolStr::new_static("descriptionFacets"),
378 LexObjectProperty::Array(LexArray {
379 items: LexArrayItem::Ref(LexRef {
380 r#ref: CowStr::new_static("app.bsky.richtext.facet"),
381 ..Default::default()
382 }),
383 ..Default::default()
384 }),
385 );
386 map.insert(
387 SmolStr::new_static("feeds"),
388 LexObjectProperty::Array(LexArray {
389 items: LexArrayItem::Ref(LexRef {
390 r#ref: CowStr::new_static("#feedItem"),
391 ..Default::default()
392 }),
393 max_length: Some(3usize),
394 ..Default::default()
395 }),
396 );
397 map.insert(
398 SmolStr::new_static("list"),
399 LexObjectProperty::String(LexString {
400 description: Some(
401 CowStr::new_static("Reference (AT-URI) to the list record."),
402 ),
403 format: Some(LexStringFormat::AtUri),
404 ..Default::default()
405 }),
406 );
407 map.insert(
408 SmolStr::new_static("name"),
409 LexObjectProperty::String(LexString {
410 description: Some(
411 CowStr::new_static(
412 "Display name for starter pack; can not be empty.",
413 ),
414 ),
415 min_length: Some(1usize),
416 max_length: Some(500usize),
417 max_graphemes: Some(50usize),
418 ..Default::default()
419 }),
420 );
421 map
422 },
423 ..Default::default()
424 }),
425 ..Default::default()
426 }),
427 );
428 map
429 },
430 ..Default::default()
431 }
432}
433
434pub mod starterpack_state {
435
436 pub use crate::builder_types::{Set, Unset, IsSet, IsUnset};
437 #[allow(unused)]
438 use ::core::marker::PhantomData;
439 mod sealed {
440 pub trait Sealed {}
441 }
442 pub trait State: sealed::Sealed {
444 type Name;
445 type List;
446 type CreatedAt;
447 }
448 pub struct Empty(());
450 impl sealed::Sealed for Empty {}
451 impl State for Empty {
452 type Name = Unset;
453 type List = Unset;
454 type CreatedAt = Unset;
455 }
456 pub struct SetName<S: State = Empty>(PhantomData<fn() -> S>);
458 impl<S: State> sealed::Sealed for SetName<S> {}
459 impl<S: State> State for SetName<S> {
460 type Name = Set<members::name>;
461 type List = S::List;
462 type CreatedAt = S::CreatedAt;
463 }
464 pub struct SetList<S: State = Empty>(PhantomData<fn() -> S>);
466 impl<S: State> sealed::Sealed for SetList<S> {}
467 impl<S: State> State for SetList<S> {
468 type Name = S::Name;
469 type List = Set<members::list>;
470 type CreatedAt = S::CreatedAt;
471 }
472 pub struct SetCreatedAt<S: State = Empty>(PhantomData<fn() -> S>);
474 impl<S: State> sealed::Sealed for SetCreatedAt<S> {}
475 impl<S: State> State for SetCreatedAt<S> {
476 type Name = S::Name;
477 type List = S::List;
478 type CreatedAt = Set<members::created_at>;
479 }
480 #[allow(non_camel_case_types)]
482 pub mod members {
483 pub struct name(());
485 pub struct list(());
487 pub struct created_at(());
489 }
490}
491
492pub struct StarterpackBuilder<'a, S: starterpack_state::State> {
494 _state: PhantomData<fn() -> S>,
495 _fields: (
496 Option<Datetime>,
497 Option<CowStr<'a>>,
498 Option<Vec<Facet<'a>>>,
499 Option<Vec<starterpack::FeedItem<'a>>>,
500 Option<AtUri<'a>>,
501 Option<CowStr<'a>>,
502 ),
503 _lifetime: PhantomData<&'a ()>,
504}
505
506impl<'a> Starterpack<'a> {
507 pub fn new() -> StarterpackBuilder<'a, starterpack_state::Empty> {
509 StarterpackBuilder::new()
510 }
511}
512
513impl<'a> StarterpackBuilder<'a, starterpack_state::Empty> {
514 pub fn new() -> Self {
516 StarterpackBuilder {
517 _state: PhantomData,
518 _fields: (None, None, None, None, None, None),
519 _lifetime: PhantomData,
520 }
521 }
522}
523
524impl<'a, S> StarterpackBuilder<'a, S>
525where
526 S: starterpack_state::State,
527 S::CreatedAt: starterpack_state::IsUnset,
528{
529 pub fn created_at(
531 mut self,
532 value: impl Into<Datetime>,
533 ) -> StarterpackBuilder<'a, starterpack_state::SetCreatedAt<S>> {
534 self._fields.0 = Option::Some(value.into());
535 StarterpackBuilder {
536 _state: PhantomData,
537 _fields: self._fields,
538 _lifetime: PhantomData,
539 }
540 }
541}
542
543impl<'a, S: starterpack_state::State> StarterpackBuilder<'a, S> {
544 pub fn description(mut self, value: impl Into<Option<CowStr<'a>>>) -> Self {
546 self._fields.1 = value.into();
547 self
548 }
549 pub fn maybe_description(mut self, value: Option<CowStr<'a>>) -> Self {
551 self._fields.1 = value;
552 self
553 }
554}
555
556impl<'a, S: starterpack_state::State> StarterpackBuilder<'a, S> {
557 pub fn description_facets(
559 mut self,
560 value: impl Into<Option<Vec<Facet<'a>>>>,
561 ) -> Self {
562 self._fields.2 = value.into();
563 self
564 }
565 pub fn maybe_description_facets(mut self, value: Option<Vec<Facet<'a>>>) -> Self {
567 self._fields.2 = value;
568 self
569 }
570}
571
572impl<'a, S: starterpack_state::State> StarterpackBuilder<'a, S> {
573 pub fn feeds(
575 mut self,
576 value: impl Into<Option<Vec<starterpack::FeedItem<'a>>>>,
577 ) -> Self {
578 self._fields.3 = value.into();
579 self
580 }
581 pub fn maybe_feeds(mut self, value: Option<Vec<starterpack::FeedItem<'a>>>) -> Self {
583 self._fields.3 = value;
584 self
585 }
586}
587
588impl<'a, S> StarterpackBuilder<'a, S>
589where
590 S: starterpack_state::State,
591 S::List: starterpack_state::IsUnset,
592{
593 pub fn list(
595 mut self,
596 value: impl Into<AtUri<'a>>,
597 ) -> StarterpackBuilder<'a, starterpack_state::SetList<S>> {
598 self._fields.4 = Option::Some(value.into());
599 StarterpackBuilder {
600 _state: PhantomData,
601 _fields: self._fields,
602 _lifetime: PhantomData,
603 }
604 }
605}
606
607impl<'a, S> StarterpackBuilder<'a, S>
608where
609 S: starterpack_state::State,
610 S::Name: starterpack_state::IsUnset,
611{
612 pub fn name(
614 mut self,
615 value: impl Into<CowStr<'a>>,
616 ) -> StarterpackBuilder<'a, starterpack_state::SetName<S>> {
617 self._fields.5 = Option::Some(value.into());
618 StarterpackBuilder {
619 _state: PhantomData,
620 _fields: self._fields,
621 _lifetime: PhantomData,
622 }
623 }
624}
625
626impl<'a, S> StarterpackBuilder<'a, S>
627where
628 S: starterpack_state::State,
629 S::Name: starterpack_state::IsSet,
630 S::List: starterpack_state::IsSet,
631 S::CreatedAt: starterpack_state::IsSet,
632{
633 pub fn build(self) -> Starterpack<'a> {
635 Starterpack {
636 created_at: self._fields.0.unwrap(),
637 description: self._fields.1,
638 description_facets: self._fields.2,
639 feeds: self._fields.3,
640 list: self._fields.4.unwrap(),
641 name: self._fields.5.unwrap(),
642 extra_data: Default::default(),
643 }
644 }
645 pub fn build_with_data(
647 self,
648 extra_data: BTreeMap<
649 jacquard_common::deps::smol_str::SmolStr,
650 jacquard_common::types::value::Data<'a>,
651 >,
652 ) -> Starterpack<'a> {
653 Starterpack {
654 created_at: self._fields.0.unwrap(),
655 description: self._fields.1,
656 description_facets: self._fields.2,
657 feeds: self._fields.3,
658 list: self._fields.4.unwrap(),
659 name: self._fields.5.unwrap(),
660 extra_data: Some(extra_data),
661 }
662 }
663}