Federate article covers
This commit is contained in:
parent
485aac2e20
commit
95326c09e0
1
Cargo.lock
generated
1
Cargo.lock
generated
@ -1703,6 +1703,7 @@ dependencies = [
|
|||||||
"canapi 0.1.0 (registry+https://github.com/rust-lang/crates.io-index)",
|
"canapi 0.1.0 (registry+https://github.com/rust-lang/crates.io-index)",
|
||||||
"chrono 0.4.6 (registry+https://github.com/rust-lang/crates.io-index)",
|
"chrono 0.4.6 (registry+https://github.com/rust-lang/crates.io-index)",
|
||||||
"diesel 1.3.3 (registry+https://github.com/rust-lang/crates.io-index)",
|
"diesel 1.3.3 (registry+https://github.com/rust-lang/crates.io-index)",
|
||||||
|
"guid-create 0.1.1 (registry+https://github.com/rust-lang/crates.io-index)",
|
||||||
"heck 0.3.0 (registry+https://github.com/rust-lang/crates.io-index)",
|
"heck 0.3.0 (registry+https://github.com/rust-lang/crates.io-index)",
|
||||||
"lazy_static 1.1.0 (registry+https://github.com/rust-lang/crates.io-index)",
|
"lazy_static 1.1.0 (registry+https://github.com/rust-lang/crates.io-index)",
|
||||||
"openssl 0.10.12 (registry+https://github.com/rust-lang/crates.io-index)",
|
"openssl 0.10.12 (registry+https://github.com/rust-lang/crates.io-index)",
|
||||||
|
@ -8,6 +8,7 @@ activitypub = "0.1.1"
|
|||||||
ammonia = "1.2.0"
|
ammonia = "1.2.0"
|
||||||
bcrypt = "0.2"
|
bcrypt = "0.2"
|
||||||
canapi = "0.1"
|
canapi = "0.1"
|
||||||
|
guid-create = "0.1"
|
||||||
heck = "0.3.0"
|
heck = "0.3.0"
|
||||||
lazy_static = "*"
|
lazy_static = "*"
|
||||||
openssl = "0.10.11"
|
openssl = "0.10.11"
|
||||||
|
@ -8,6 +8,7 @@ extern crate canapi;
|
|||||||
extern crate chrono;
|
extern crate chrono;
|
||||||
#[macro_use]
|
#[macro_use]
|
||||||
extern crate diesel;
|
extern crate diesel;
|
||||||
|
extern crate guid_create;
|
||||||
extern crate heck;
|
extern crate heck;
|
||||||
#[macro_use]
|
#[macro_use]
|
||||||
extern crate lazy_static;
|
extern crate lazy_static;
|
||||||
|
@ -1,9 +1,15 @@
|
|||||||
|
use activitypub::object::Image;
|
||||||
use diesel::{self, QueryDsl, ExpressionMethods, RunQueryDsl};
|
use diesel::{self, QueryDsl, ExpressionMethods, RunQueryDsl};
|
||||||
|
use guid_create::GUID;
|
||||||
|
use reqwest;
|
||||||
use serde_json;
|
use serde_json;
|
||||||
use std::fs;
|
use std::{fs, path::Path};
|
||||||
|
|
||||||
|
use plume_common::activity_pub::Id;
|
||||||
|
|
||||||
use {ap_url, Connection};
|
use {ap_url, Connection};
|
||||||
use instance::Instance;
|
use instance::Instance;
|
||||||
|
use users::User;
|
||||||
use schema::medias;
|
use schema::medias;
|
||||||
|
|
||||||
#[derive(Clone, Identifiable, Queryable, Serialize)]
|
#[derive(Clone, Identifiable, Queryable, Serialize)]
|
||||||
@ -94,4 +100,25 @@ impl Media {
|
|||||||
.execute(conn)
|
.execute(conn)
|
||||||
.expect("Media::set_owner: owner update error");
|
.expect("Media::set_owner: owner update error");
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// TODO: merge with save_remote?
|
||||||
|
pub fn from_activity(conn: &Connection, image: Image) -> Option<Media> {
|
||||||
|
let remote_url = image.object_props.url_string().ok()?;
|
||||||
|
let ext = remote_url.rsplit('.').next().map(|ext| ext.to_owned()).unwrap_or("png".to_owned());
|
||||||
|
let path = Path::new("static").join("media").join(format!("{}.{}", GUID::rand().to_string(), ext));
|
||||||
|
|
||||||
|
let mut dest = fs::File::create(path.clone()).ok()?;
|
||||||
|
reqwest::get(remote_url.as_str()).ok()?
|
||||||
|
.copy_to(&mut dest).ok()?;
|
||||||
|
|
||||||
|
Some(Media::insert(conn, NewMedia {
|
||||||
|
file_path: path.to_str()?.to_string(),
|
||||||
|
alt_text: image.object_props.content_string().ok()?,
|
||||||
|
is_remote: true,
|
||||||
|
remote_url: None,
|
||||||
|
sensitive: image.object_props.summary_string().is_ok(),
|
||||||
|
content_warning: image.object_props.summary_string().ok(),
|
||||||
|
owner_id: User::from_url(conn, image.object_props.attributed_to_link_vec::<Id>().ok()?.into_iter().next()?.into())?.id
|
||||||
|
}))
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
@ -1,7 +1,7 @@
|
|||||||
use activitypub::{
|
use activitypub::{
|
||||||
activity::{Create, Delete, Update},
|
activity::{Create, Delete, Update},
|
||||||
link,
|
link,
|
||||||
object::{Article, Tombstone}
|
object::{Article, Image, Tombstone}
|
||||||
};
|
};
|
||||||
use canapi::{Error, Provider};
|
use canapi::{Error, Provider};
|
||||||
use chrono::{NaiveDateTime, TimeZone, Utc};
|
use chrono::{NaiveDateTime, TimeZone, Utc};
|
||||||
@ -22,6 +22,7 @@ use {BASE_URL, ap_url, Connection};
|
|||||||
use blogs::Blog;
|
use blogs::Blog;
|
||||||
use instance::Instance;
|
use instance::Instance;
|
||||||
use likes::Like;
|
use likes::Like;
|
||||||
|
use medias::Media;
|
||||||
use mentions::Mention;
|
use mentions::Mention;
|
||||||
use post_authors::*;
|
use post_authors::*;
|
||||||
use reshares::Reshare;
|
use reshares::Reshare;
|
||||||
@ -358,6 +359,21 @@ impl Post {
|
|||||||
article.object_props.set_published_utctime(Utc.from_utc_datetime(&self.creation_date)).expect("Post::into_activity: published error");
|
article.object_props.set_published_utctime(Utc.from_utc_datetime(&self.creation_date)).expect("Post::into_activity: published error");
|
||||||
article.object_props.set_summary_string(self.subtitle.clone()).expect("Post::into_activity: summary error");
|
article.object_props.set_summary_string(self.subtitle.clone()).expect("Post::into_activity: summary error");
|
||||||
article.object_props.tag = Some(json!(mentions_json));
|
article.object_props.tag = Some(json!(mentions_json));
|
||||||
|
|
||||||
|
if let Some(media_id) = self.cover_id {
|
||||||
|
let media = Media::get(conn, media_id).expect("Post::into_activity: get cover error");
|
||||||
|
let mut cover = Image::default();
|
||||||
|
cover.object_props.set_url_string(media.url(conn)).expect("Post::into_activity: icon.url error");
|
||||||
|
if media.sensitive {
|
||||||
|
cover.object_props.set_summary_string(media.content_warning.unwrap_or(String::new())).expect("Post::into_activity: icon.summary error");
|
||||||
|
}
|
||||||
|
cover.object_props.set_content_string(media.alt_text).expect("Post::into_activity: icon.content error");
|
||||||
|
cover.object_props.set_attributed_to_link_vec(vec![
|
||||||
|
User::get(conn, media.owner_id).expect("Post::into_activity: media owner not found").into_id()
|
||||||
|
]).expect("Post::into_activity: icon.attributedTo error");
|
||||||
|
article.object_props.set_icon_object(cover).expect("Post::into_activity: icon error");
|
||||||
|
}
|
||||||
|
|
||||||
article.object_props.set_url_string(self.ap_url.clone()).expect("Post::into_activity: url error");
|
article.object_props.set_url_string(self.ap_url.clone()).expect("Post::into_activity: url error");
|
||||||
article.object_props.set_to_link_vec::<Id>(to.into_iter().map(Id::new).collect()).expect("Post::into_activity: to error");
|
article.object_props.set_to_link_vec::<Id>(to.into_iter().map(Id::new).collect()).expect("Post::into_activity: to error");
|
||||||
article.object_props.set_cc_link_vec::<Id>(vec![]).expect("Post::into_activity: cc error");
|
article.object_props.set_cc_link_vec::<Id>(vec![]).expect("Post::into_activity: cc error");
|
||||||
@ -538,6 +554,9 @@ impl FromActivity<Article, Connection> for Post {
|
|||||||
}
|
}
|
||||||
});
|
});
|
||||||
|
|
||||||
|
let cover = article.object_props.icon_object::<Image>().ok()
|
||||||
|
.and_then(|img| Media::from_activity(conn, img).map(|m| m.id));
|
||||||
|
|
||||||
let title = article.object_props.name_string().expect("Post::from_activity: title error");
|
let title = article.object_props.name_string().expect("Post::from_activity: title error");
|
||||||
let post = Post::insert(conn, NewPost {
|
let post = Post::insert(conn, NewPost {
|
||||||
blog_id: blog.expect("Post::from_activity: blog not found error").id,
|
blog_id: blog.expect("Post::from_activity: blog not found error").id,
|
||||||
@ -551,7 +570,7 @@ impl FromActivity<Article, Connection> for Post {
|
|||||||
creation_date: Some(article.object_props.published_utctime().expect("Post::from_activity: published error").naive_utc()),
|
creation_date: Some(article.object_props.published_utctime().expect("Post::from_activity: published error").naive_utc()),
|
||||||
subtitle: article.object_props.summary_string().expect("Post::from_activity: summary error"),
|
subtitle: article.object_props.summary_string().expect("Post::from_activity: summary error"),
|
||||||
source: article.ap_object_props.source_object::<Source>().expect("Post::from_activity: source error").content,
|
source: article.ap_object_props.source_object::<Source>().expect("Post::from_activity: source error").content,
|
||||||
cover_id: None, // TODO
|
cover_id: cover,
|
||||||
});
|
});
|
||||||
|
|
||||||
for author in authors.into_iter() {
|
for author in authors.into_iter() {
|
||||||
|
Loading…
Reference in New Issue
Block a user