mirror of
https://framagit.org/veretcle/scootaloo.git
synced 2025-07-21 09:31:19 +02:00
Compare commits
2 Commits
Author | SHA1 | Date | |
---|---|---|---|
![]() |
44ec3edfe2 | ||
![]() |
8673dd7866 |
3
Cargo.lock
generated
3
Cargo.lock
generated
@@ -2016,7 +2016,7 @@ dependencies = [
|
|||||||
|
|
||||||
[[package]]
|
[[package]]
|
||||||
name = "scootaloo"
|
name = "scootaloo"
|
||||||
version = "0.6.0"
|
version = "0.6.1"
|
||||||
dependencies = [
|
dependencies = [
|
||||||
"chrono",
|
"chrono",
|
||||||
"clap",
|
"clap",
|
||||||
@@ -2025,6 +2025,7 @@ dependencies = [
|
|||||||
"futures 0.3.14",
|
"futures 0.3.14",
|
||||||
"html-escape",
|
"html-escape",
|
||||||
"log",
|
"log",
|
||||||
|
"mime",
|
||||||
"reqwest 0.11.3",
|
"reqwest 0.11.3",
|
||||||
"rusqlite",
|
"rusqlite",
|
||||||
"serde",
|
"serde",
|
||||||
|
@@ -1,6 +1,6 @@
|
|||||||
[package]
|
[package]
|
||||||
name = "scootaloo"
|
name = "scootaloo"
|
||||||
version = "0.6.0"
|
version = "0.6.1"
|
||||||
authors = ["VC <veretcle+framagit@mateu.be>"]
|
authors = ["VC <veretcle+framagit@mateu.be>"]
|
||||||
edition = "2021"
|
edition = "2021"
|
||||||
|
|
||||||
@@ -20,6 +20,7 @@ html-escape = "^0.2"
|
|||||||
reqwest = "^0.11"
|
reqwest = "^0.11"
|
||||||
log = "^0.4"
|
log = "^0.4"
|
||||||
simple_logger = "^2.1"
|
simple_logger = "^2.1"
|
||||||
|
mime = "^0.3"
|
||||||
|
|
||||||
[profile.release]
|
[profile.release]
|
||||||
strip = true
|
strip = true
|
||||||
|
148
src/twitter.rs
148
src/twitter.rs
@@ -50,29 +50,137 @@ pub async fn get_user_timeline(
|
|||||||
/// Retrieves a single media from a tweet and store it in a temporary file
|
/// Retrieves a single media from a tweet and store it in a temporary file
|
||||||
pub async fn get_tweet_media(m: &MediaEntity, t: &str) -> Result<String, Box<dyn Error>> {
|
pub async fn get_tweet_media(m: &MediaEntity, t: &str) -> Result<String, Box<dyn Error>> {
|
||||||
match m.media_type {
|
match m.media_type {
|
||||||
MediaType::Photo => {
|
MediaType::Photo => cache_media(&m.media_url_https, t).await,
|
||||||
return cache_media(&m.media_url_https, t).await;
|
|
||||||
}
|
|
||||||
_ => match &m.video_info {
|
_ => match &m.video_info {
|
||||||
Some(v) => {
|
Some(v) => match &v.variants.iter().find(|&x| x.content_type == "video/mp4") {
|
||||||
for variant in &v.variants {
|
Some(u) => cache_media(&u.url, t).await,
|
||||||
if variant.content_type == "video/mp4" {
|
None => Err(ScootalooError::new(&format!(
|
||||||
return cache_media(&variant.url, t).await;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
return Err(ScootalooError::new(&format!(
|
|
||||||
"Media Type for {} is video but no mp4 file URL is available",
|
"Media Type for {} is video but no mp4 file URL is available",
|
||||||
&m.url
|
&m.url
|
||||||
))
|
))
|
||||||
.into());
|
.into()),
|
||||||
}
|
},
|
||||||
None => {
|
None => Err(ScootalooError::new(&format!(
|
||||||
return Err(ScootalooError::new(&format!(
|
"Media Type for {} is video but does not contain any video_info",
|
||||||
"Media Type for {} is video but does not contain any video_info",
|
&m.url
|
||||||
&m.url
|
))
|
||||||
))
|
.into()),
|
||||||
.into());
|
|
||||||
}
|
|
||||||
},
|
},
|
||||||
};
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
#[cfg(test)]
|
||||||
|
mod tests {
|
||||||
|
use super::*;
|
||||||
|
use egg_mode::entities::{
|
||||||
|
MediaSize, MediaSizes,
|
||||||
|
MediaType::{Gif, Photo},
|
||||||
|
ResizeMode::Crop,
|
||||||
|
ResizeMode::Fit,
|
||||||
|
VideoInfo, VideoVariant,
|
||||||
|
};
|
||||||
|
use std::fs::remove_dir_all;
|
||||||
|
|
||||||
|
const TMP_DIR: &'static str = "/tmp/scootaloo_get_tweet_media_test";
|
||||||
|
|
||||||
|
#[tokio::test]
|
||||||
|
async fn test_get_tweet_media() {
|
||||||
|
let m_photo = MediaEntity {
|
||||||
|
display_url: "pic.twitter.com/sHrwmP69Yv".to_string(),
|
||||||
|
expanded_url: "https://twitter.com/NintendojoFR/status/1555473821121056771/photo/1"
|
||||||
|
.to_string(),
|
||||||
|
id: 1555473771280080896,
|
||||||
|
range: (91, 114),
|
||||||
|
media_url: "http://pbs.twimg.com/media/FZYnJ1qWIAAReHt.jpg".to_string(),
|
||||||
|
media_url_https: "https://pbs.twimg.com/media/FZYnJ1qWIAAReHt.jpg"
|
||||||
|
.to_string(),
|
||||||
|
sizes: MediaSizes {
|
||||||
|
thumb: MediaSize {
|
||||||
|
w: 150,
|
||||||
|
h: 150,
|
||||||
|
resize: Crop
|
||||||
|
},
|
||||||
|
small: MediaSize {
|
||||||
|
w: 680,
|
||||||
|
h: 510,
|
||||||
|
resize: Fit
|
||||||
|
},
|
||||||
|
medium: MediaSize {
|
||||||
|
w: 1200,
|
||||||
|
h: 900,
|
||||||
|
resize: Fit
|
||||||
|
},
|
||||||
|
large: MediaSize {
|
||||||
|
w: 1280,
|
||||||
|
h: 960,
|
||||||
|
resize: Fit
|
||||||
|
}
|
||||||
|
},
|
||||||
|
source_status_id: None,
|
||||||
|
media_type: Photo,
|
||||||
|
url: "https://t.co/sHrwmP69Yv".to_string(),
|
||||||
|
video_info: None,
|
||||||
|
ext_alt_text: Some("Le menu «\u{a0}Classes » du jeu vidéo Xenoblade Chronicles 3 (Switch). L’affinité du personnage pour la classe est notée par quatre lettres : C, A, C, A (caca)."
|
||||||
|
.to_string())
|
||||||
|
};
|
||||||
|
let m_video = MediaEntity {
|
||||||
|
display_url: "pic.twitter.com/xDln0RrkjU".to_string(),
|
||||||
|
expanded_url: "https://twitter.com/NintendojoFR/status/1551822196833673218/photo/1"
|
||||||
|
.to_string(),
|
||||||
|
id: 1551822189711790081,
|
||||||
|
range: (275, 298),
|
||||||
|
media_url: "http://pbs.twimg.com/tweet_video_thumb/FYkuD0RXEAE-iDx.jpg".to_string(),
|
||||||
|
media_url_https: "https://pbs.twimg.com/tweet_video_thumb/FYkuD0RXEAE-iDx.jpg"
|
||||||
|
.to_string(),
|
||||||
|
sizes: MediaSizes {
|
||||||
|
thumb: MediaSize {
|
||||||
|
w: 150,
|
||||||
|
h: 150,
|
||||||
|
resize: Crop,
|
||||||
|
},
|
||||||
|
small: MediaSize {
|
||||||
|
w: 320,
|
||||||
|
h: 240,
|
||||||
|
resize: Fit,
|
||||||
|
},
|
||||||
|
medium: MediaSize {
|
||||||
|
w: 320,
|
||||||
|
h: 240,
|
||||||
|
resize: Fit,
|
||||||
|
},
|
||||||
|
large: MediaSize {
|
||||||
|
w: 320,
|
||||||
|
h: 240,
|
||||||
|
resize: Fit,
|
||||||
|
},
|
||||||
|
},
|
||||||
|
source_status_id: None,
|
||||||
|
media_type: Gif,
|
||||||
|
url: "https://t.co/xDln0RrkjU".to_string(),
|
||||||
|
video_info: Some(VideoInfo {
|
||||||
|
aspect_ratio: (4, 3),
|
||||||
|
duration_millis: None,
|
||||||
|
variants: vec![VideoVariant {
|
||||||
|
bitrate: Some(0),
|
||||||
|
content_type: "video/mp4".parse::<mime::Mime>().unwrap(),
|
||||||
|
url: "https://video.twimg.com/tweet_video/FYkuD0RXEAE-iDx.mp4".to_string(),
|
||||||
|
}],
|
||||||
|
}),
|
||||||
|
ext_alt_text: Some("Scared Nintendo GIF".to_string()),
|
||||||
|
};
|
||||||
|
|
||||||
|
let tweet_media_photo = get_tweet_media(&m_photo, TMP_DIR).await.unwrap();
|
||||||
|
let tweet_media_video = get_tweet_media(&m_video, TMP_DIR).await.unwrap();
|
||||||
|
|
||||||
|
assert_eq!(
|
||||||
|
tweet_media_photo,
|
||||||
|
format!("{}/FZYnJ1qWIAAReHt.jpg", TMP_DIR)
|
||||||
|
);
|
||||||
|
assert_eq!(
|
||||||
|
tweet_media_video,
|
||||||
|
format!("{}/FYkuD0RXEAE-iDx.mp4", TMP_DIR)
|
||||||
|
);
|
||||||
|
|
||||||
|
remove_dir_all(TMP_DIR).unwrap();
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
Reference in New Issue
Block a user