From 75af98415445ab1457f3a2b78759ad286e665697 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Ond=C5=99ej=20Pe=C5=A1ek?= Date: Sat, 1 Apr 2023 14:26:04 +0200 Subject: [PATCH] fix(polls): apply suggestions and fix id parsing --- src/utils.rs | 30 ++++++++++++++++-------------- templates/utils.html | 20 +++++++++++++------- 2 files changed, 29 insertions(+), 21 deletions(-) diff --git a/src/utils.rs b/src/utils.rs index 769aa9d..ad7b913 100644 --- a/src/utils.rs +++ b/src/utils.rs @@ -104,12 +104,12 @@ pub struct Poll { impl Poll { pub fn parse(poll_data: &Value) -> Option { - if poll_data.as_object().is_none() { return None }; + poll_data.as_object()?; let total_vote_count = poll_data["total_vote_count"].as_u64()?; // voting_end_timestamp is in the format of milliseconds let voting_end_timestamp = time(poll_data["voting_end_timestamp"].as_f64()? / 1000.0); - let poll_options = PollOption::parse(&poll_data["options"]); + let poll_options = PollOption::parse(&poll_data["options"])?; Some(Self { poll_options, @@ -119,36 +119,38 @@ impl Poll { } pub fn most_votes(&self) -> u64 { - self.poll_options.iter().map(|o| o.vote_count).max().unwrap_or(0) + self.poll_options.iter().map(|o| o.vote_count).flatten().max().unwrap_or(0) } } pub struct PollOption { pub id: u64, pub text: String, - pub vote_count: u64 + pub vote_count: Option } impl PollOption { - pub fn parse(options: &Value) -> Vec { - options - .as_array() - .unwrap_or(&Vec::new()) + pub fn parse(options: &Value) -> Option> { + Some(options + .as_array()? .iter() .map(|option| { // For each poll option - let id = option["id"].as_u64().unwrap_or_default(); - let text = option["text"].as_str().unwrap_or_default().to_owned(); - let vote_count = option["vote_count"].as_u64().unwrap_or_default(); + + // we can't just use as_u64() because "id": String("...") and serde would parse it as None + let id = option["id"].as_str()?.parse::().ok()?; + let text = option["text"].as_str()?.to_owned(); + let vote_count = option["vote_count"].as_u64(); // Construct PollOption items - Self { + Some(Self { id, text, vote_count - } + }) }) - .collect::>() + .flatten() + .collect::>()) } } diff --git a/templates/utils.html b/templates/utils.html index 4bf7bdf..d5f3f69 100644 --- a/templates/utils.html +++ b/templates/utils.html @@ -315,14 +315,20 @@ {{ poll.voting_end_timestamp.0 }} {% for option in poll.poll_options %}
- {# Posts without vote_count (all open polls) will show up as having 0 votes. + {# Posts without vote_count (all open polls) will show up without votes. This is an issue with Reddit API, it doesn't work on Old Reddit either. #} - {% if option.vote_count == widest %} -
- {% else %} -
- {% endif %} - {{ option.vote_count }} + {% match option.vote_count %} + {% when Some with (vote_count) %} + {% if vote_count.eq(widest) || widest == 0 %} +
+ {% else %} +
+ {% endif %} + {{ vote_count }} + {% when None %} +
+ + {% endmatch %} {{ option.text }}
{% endfor %}