Refactor code to use API struct deserialization
The deserialization errors have been fixed in 0.18.1
This commit is contained in:
parent
164bd37987
commit
04fdd8908f
@ -1,11 +1,10 @@
|
||||
use lemmy_api_common::{
|
||||
community::GetCommunity,
|
||||
community::{GetCommunity, GetCommunityResponse},
|
||||
lemmy_db_schema::newtypes::CommunityId,
|
||||
person::{Login, LoginResponse},
|
||||
sensitive::Sensitive,
|
||||
};
|
||||
use reqwest::Client;
|
||||
use serde_json::Value;
|
||||
use std::fmt;
|
||||
|
||||
static API_VERSION: i32 = 3;
|
||||
@ -31,17 +30,13 @@ pub fn api_url(suffix: &str) -> String {
|
||||
}
|
||||
|
||||
#[derive(Debug)]
|
||||
pub enum WordleError {
|
||||
ParseFailed,
|
||||
LoginFailed,
|
||||
NoNewPostId,
|
||||
}
|
||||
struct LoginFailedError;
|
||||
|
||||
impl std::error::Error for WordleError {}
|
||||
impl std::error::Error for LoginFailedError {}
|
||||
|
||||
impl fmt::Display for WordleError {
|
||||
impl fmt::Display for LoginFailedError {
|
||||
fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
|
||||
write!(f, "Oh no, something bad went down")
|
||||
write!(f, "Login failed.")
|
||||
}
|
||||
}
|
||||
|
||||
@ -59,19 +54,8 @@ pub async fn get_community_id(
|
||||
.query(¶ms)
|
||||
.send()
|
||||
.await?;
|
||||
let text = response.text().await?;
|
||||
|
||||
// Deserializing from GetCommunityResponse would fail with missing field `followers_url` in Community
|
||||
let data = serde_json::from_str::<Value>(text.as_str())?;
|
||||
|
||||
if let Some(id) = data["community_view"]["community"]
|
||||
.get("id")
|
||||
.and_then(|v| v.as_i64())
|
||||
{
|
||||
return Ok(CommunityId(i32::try_from(id)?));
|
||||
}
|
||||
|
||||
Err(Box::new(WordleError::ParseFailed))
|
||||
let data = response.json::<GetCommunityResponse>().await?;
|
||||
Ok(data.community_view.community.id)
|
||||
}
|
||||
|
||||
pub async fn lemmy_login(client: &Client) -> Result<Sensitive<String>, Box<dyn std::error::Error>> {
|
||||
@ -95,5 +79,5 @@ pub async fn lemmy_login(client: &Client) -> Result<Sensitive<String>, Box<dyn s
|
||||
return Ok(jwt);
|
||||
}
|
||||
|
||||
Err(Box::new(WordleError::LoginFailed))
|
||||
Err(Box::new(LoginFailedError))
|
||||
}
|
||||
|
35
src/main.rs
35
src/main.rs
@ -1,11 +1,10 @@
|
||||
use chrono::{Datelike, Month, Utc};
|
||||
use lemmy_api_common::post::CreatePost;
|
||||
use lemmy_api_common::{post::{CreatePost, PostResponse}, sensitive::Sensitive, lemmy_db_schema::newtypes::PostId};
|
||||
use reqwest::{Client, Url};
|
||||
use serde::Deserialize;
|
||||
use serde_json::Value;
|
||||
|
||||
mod helper;
|
||||
use crate::helper::{get_community_id, lemmy_community, lemmy_login, WordleError};
|
||||
use crate::helper::{get_community_id, lemmy_community, lemmy_login};
|
||||
|
||||
#[derive(Debug, Deserialize, Default)]
|
||||
struct WordleData {
|
||||
@ -21,21 +20,16 @@ async fn get_current_nyt_wordle_data() -> Result<WordleData, Box<dyn std::error:
|
||||
.await?;
|
||||
// Did it work?
|
||||
response.error_for_status_ref()?;
|
||||
let text = response.text().await?;
|
||||
let data: WordleData = serde_json::from_str(&text)?;
|
||||
let data = response.json::<WordleData>().await?;
|
||||
println!("{:?}", data);
|
||||
Ok(data)
|
||||
}
|
||||
|
||||
async fn post_to_lemmy(data: &WordleData) -> Result<(), Box<dyn std::error::Error>> {
|
||||
async fn post_to_lemmy(data: &WordleData, client: &Client, auth: Sensitive<String>) -> Result<PostId, Box<dyn std::error::Error>> {
|
||||
println!("Posting to lemmy: {:?}", data);
|
||||
|
||||
let client = Client::new();
|
||||
|
||||
let auth = lemmy_login(&client).await?;
|
||||
|
||||
// Get the community id
|
||||
let community_id = get_community_id(&client, lemmy_community()).await?;
|
||||
let community_id = get_community_id(client, lemmy_community()).await?;
|
||||
|
||||
let now = Utc::now();
|
||||
|
||||
@ -61,7 +55,7 @@ async fn post_to_lemmy(data: &WordleData) -> Result<(), Box<dyn std::error::Erro
|
||||
community_id,
|
||||
name: title,
|
||||
url: Some(url),
|
||||
body: Some("Post your results and discuss your guesses. Have fun!\nNote: there might be spoilers in the thread.".to_owned()),
|
||||
body: Some("Post your results and discuss your guesses. Have fun! \nNote: there might be spoilers in the thread.".to_owned()),
|
||||
auth,
|
||||
..Default::default()
|
||||
};
|
||||
@ -71,22 +65,19 @@ async fn post_to_lemmy(data: &WordleData) -> Result<(), Box<dyn std::error::Erro
|
||||
.json(¶ms)
|
||||
.send()
|
||||
.await?;
|
||||
let data = response.json::<Value>().await?;
|
||||
|
||||
// Again, deserializing using the api struct did not work due to missing fields
|
||||
if let Some(new_id) = data["post_view"]["post"].get("id") {
|
||||
println!("New post id: {}", new_id);
|
||||
} else {
|
||||
return Err(Box::new(WordleError::NoNewPostId));
|
||||
}
|
||||
Ok(())
|
||||
let data = response.json::<PostResponse>().await?;
|
||||
Ok(data.post_view.post.id)
|
||||
}
|
||||
|
||||
#[tokio::main]
|
||||
async fn main() -> Result<(), Box<dyn std::error::Error>> {
|
||||
println!("A wordle a day keeps the doctor away!");
|
||||
|
||||
let client = Client::new();
|
||||
let auth = lemmy_login(&client).await?;
|
||||
let data = get_current_nyt_wordle_data().await?;
|
||||
post_to_lemmy(&data).await?;
|
||||
let id = post_to_lemmy(&data, &client, auth).await?;
|
||||
println!("New post ID: {}", id);
|
||||
|
||||
Ok(())
|
||||
}
|
||||
|
Loading…
Reference in New Issue
Block a user