longbridge/content/
context.rs1use std::sync::Arc;
2
3use longbridge_httpcli::{HttpClient, Json, Method};
4use serde::Deserialize;
5
6use super::types::{
7 CreateReplyOptions, CreateTopicOptions, ListTopicRepliesOptions, MyTopicsOptions, NewsItem,
8 OwnedTopic, TopicItem, TopicReply,
9};
10use crate::{Config, Result};
11
12struct InnerContentContext {
13 http_cli: HttpClient,
14}
15
16#[derive(Clone)]
18pub struct ContentContext(Arc<InnerContentContext>);
19
20impl ContentContext {
21 pub fn new(config: Arc<Config>) -> Self {
23 Self(Arc::new(InnerContentContext {
24 http_cli: config.create_http_client(),
25 }))
26 }
27
28 pub async fn my_topics(&self, opts: MyTopicsOptions) -> Result<Vec<OwnedTopic>> {
32 #[derive(Debug, Deserialize)]
33 struct Response {
34 items: Vec<OwnedTopic>,
35 }
36
37 Ok(self
38 .0
39 .http_cli
40 .request(Method::GET, "/v1/content/topics/mine")
41 .query_params(opts)
42 .response::<Json<Response>>()
43 .send()
44 .await?
45 .0
46 .items)
47 }
48
49 pub async fn create_topic(&self, opts: CreateTopicOptions) -> Result<String> {
53 #[derive(Debug, Deserialize)]
54 struct TopicId {
55 id: String,
56 }
57
58 #[derive(Debug, Deserialize)]
59 struct Response {
60 item: TopicId,
61 }
62
63 Ok(self
64 .0
65 .http_cli
66 .request(Method::POST, "/v1/content/topics")
67 .body(Json(opts))
68 .response::<Json<Response>>()
69 .send()
70 .await?
71 .0
72 .item
73 .id)
74 }
75
76 pub async fn topics(&self, symbol: impl Into<String>) -> Result<Vec<TopicItem>> {
78 #[derive(Debug, Deserialize)]
79 struct Response {
80 items: Vec<TopicItem>,
81 }
82
83 let symbol = symbol.into();
84 Ok(self
85 .0
86 .http_cli
87 .request(Method::GET, format!("/v1/content/{symbol}/topics"))
88 .response::<Json<Response>>()
89 .send()
90 .await?
91 .0
92 .items)
93 }
94
95 pub async fn topic_detail(&self, id: impl Into<String>) -> Result<OwnedTopic> {
99 #[derive(Debug, Deserialize)]
100 struct Response {
101 item: OwnedTopic,
102 }
103
104 let id = id.into();
105 Ok(self
106 .0
107 .http_cli
108 .request(Method::GET, format!("/v1/content/topics/{id}"))
109 .response::<Json<Response>>()
110 .send()
111 .await?
112 .0
113 .item)
114 }
115
116 pub async fn list_topic_replies(
120 &self,
121 topic_id: impl Into<String>,
122 opts: ListTopicRepliesOptions,
123 ) -> Result<Vec<TopicReply>> {
124 #[derive(Debug, Deserialize)]
125 struct Response {
126 items: Vec<TopicReply>,
127 }
128
129 let topic_id = topic_id.into();
130 Ok(self
131 .0
132 .http_cli
133 .request(
134 Method::GET,
135 format!("/v1/content/topics/{topic_id}/comments"),
136 )
137 .query_params(opts)
138 .response::<Json<Response>>()
139 .send()
140 .await?
141 .0
142 .items)
143 }
144
145 pub async fn create_topic_reply(
149 &self,
150 topic_id: impl Into<String>,
151 opts: CreateReplyOptions,
152 ) -> Result<TopicReply> {
153 #[derive(Debug, Deserialize)]
154 struct Response {
155 item: TopicReply,
156 }
157
158 let topic_id = topic_id.into();
159 Ok(self
160 .0
161 .http_cli
162 .request(
163 Method::POST,
164 format!("/v1/content/topics/{topic_id}/comments"),
165 )
166 .body(Json(opts))
167 .response::<Json<Response>>()
168 .send()
169 .await?
170 .0
171 .item)
172 }
173
174 pub async fn news(&self, symbol: impl Into<String>) -> Result<Vec<NewsItem>> {
176 #[derive(Debug, Deserialize)]
177 struct Response {
178 items: Vec<NewsItem>,
179 }
180
181 let symbol = symbol.into();
182 Ok(self
183 .0
184 .http_cli
185 .request(Method::GET, format!("/v1/content/{symbol}/news"))
186 .response::<Json<Response>>()
187 .send()
188 .await?
189 .0
190 .items)
191 }
192}