gourami

[UNMAINTAINED] Activitypub server in Rust
Log | Files | Refs | README | LICENSE

commit ec22e136bdb3c53221281f6bb7540465de94bcb9
parent 86cbba84c86f6695e52a30366c7cb2c4d46e610e
Author: alex wennerberg <alex@alexwennerberg.com>
Date:   Thu, 16 Apr 2020 22:19:40 -0500

Working database and basic templates

Diffstat:
MCargo.lock | 1+
MCargo.toml | 1+
MTODO | 18+++++++++++++++++-
Mmigrations/2020-04-13-014917_initialize/up.sql | 37++++++++++++++-----------------------
Asrc/db/mod.rs | 2++
Asrc/db/schema.rs | 9+++++++++
Asrc/db/status.rs | 30++++++++++++++++++++++++++++++
Asrc/lib.rs | 2++
Msrc/main.rs | 52+++++++++++++++++++++++++++++++++++++++++-----------
Mtemplates/base.html | 10+++++++---
Mtemplates/timeline.html | 2+-
11 files changed, 125 insertions(+), 39 deletions(-)

diff --git a/Cargo.lock b/Cargo.lock @@ -478,6 +478,7 @@ version = "0.1.0" dependencies = [ "activitystreams", "askama", + "chrono", "diesel", "env_logger", "log 0.4.8", diff --git a/Cargo.toml b/Cargo.toml @@ -13,3 +13,4 @@ env_logger = "0.7" warp = "0.2" reqwest = "0.10" activitystreams = "0.4.0" +chrono = "*" diff --git a/TODO b/TODO @@ -1,5 +1,18 @@ Plain text statuses +marketing tagline: + +"An intentionally small, lightweight activitypub community" + +NOTES-- + +NO DMS -- not really secure in AP +NO IMAGES -- issue described in https://flak.tedunangst.com/post/honk + +mastodon doesnt implement client-to-server + +outbox -? + TODO -- First, client to server protocol, then federation @@ -8,7 +21,7 @@ Person Note Follow/Unfollow Inbox -Outbox +Outbox --> not really strictly necessary? crates-- logging @@ -42,6 +55,9 @@ Audit log -- https://meta.sr.ht/security https://github.com/rustodon/rustodon https://github.com/Plume-org/Plume.git +microblog +honk https://flak.tedunangst.com/post/honk-preview +https://flak.tedunangst.com/post/honk add code of conduct diff --git a/migrations/2020-04-13-014917_initialize/up.sql b/migrations/2020-04-13-014917_initialize/up.sql @@ -1,34 +1,25 @@ -- Your SQL goes here -CREATE TABLE accounts ( +CREATE TABLE user ( id INTEGER NOT NULL PRIMARY KEY AUTOINCREMENT, -username -email -created_at -private_key -public_key -) - --- why separate -CREATE TABLE users( -id INTEGER NOT NULL PRIMARY KEY AUTOINCREMENT, -email -) + username VARCHAR(255), + email VARCHAR(255), + created_at TEXT, + private_key TEXT, + public_key TEXT +); -CREATE TABLE notifications( -id INTEGER NOT NULL PRIMARY KEY AUTOINCREMENT, -) +CREATE TABLE notification ( + id INTEGER NOT NULL PRIMARY KEY AUTOINCREMENT +); -- media_attachments CREATE TABLE status ( -id INTEGER NOT NULL PRIMARY KEY AUTOINCREMENT, -) - -CREATE TABLE IF NOT EXISTS "follows" ( id INTEGER NOT NULL PRIMARY KEY AUTOINCREMENT, - follower_id INTEGER REFERENCES users(id) ON DELETE CASCADE NOT NULL, - following_id INTEGER REFERENCES users(id) ON DELETE CASCADE NOT NULL, - ap_url TEXT NOT NULL default '' UNIQUE + creator_id INTEGER, + parent_id INTEGER, + content TEXT, + published TEXT ); diff --git a/src/db/mod.rs b/src/db/mod.rs @@ -0,0 +1,2 @@ +pub mod status; +pub mod schema; diff --git a/src/db/schema.rs b/src/db/schema.rs @@ -0,0 +1,9 @@ +table! { + status (id) { + id -> Integer, + creator_id -> Integer, + parent_id -> Nullable<Integer>, + content -> Text, + published -> Timestamp, + } +} diff --git a/src/db/status.rs b/src/db/status.rs @@ -0,0 +1,30 @@ +use chrono; +use activitystreams::object::streams::Note; +use diesel::sqlite::SqliteConnection; +use diesel::deserialize::{Queryable}; +use super::schema::status; + +// Statuses are note activitystream object + +#[derive(Queryable)] +pub struct Status { + pub id: i32, + pub creator_id: i32, + pub parent_id: Option<i32>, + pub content: String, + pub published: chrono::NaiveDateTime, +} + +impl Status { + fn get_for_user(&self, conn: &SqliteConnection, user_id: &str) { + } +} +#[derive(Insertable, Clone)] +#[table_name = "status"] +pub struct StatusInput { + pub id: i32, //unsigned? + pub creator_id: i32, + pub parent_id: Option<i32>, + pub content: String, + // pub published: chrono::NaiveDateTime, +} diff --git a/src/lib.rs b/src/lib.rs @@ -0,0 +1,2 @@ + +// TODO move stuff here? diff --git a/src/main.rs b/src/main.rs @@ -1,24 +1,29 @@ +#[macro_use] +extern crate diesel; + +use gourami_social::*; use warp::Filter; use askama::Template; use warp::http::{self, header, StatusCode}; use warp::hyper::Body; use warp::reply::Response; use env_logger; +use db::status::Status; + +mod db; +// TODO split into separate templates. not sure how #[derive(Template)] #[template(path = "timeline.html")] -struct HomeTemplate<'a>{ - name: &'a str, - _parent: BaseTemplate<'a> +struct TimelineTemplate<'a>{ + page: &'a str, + title: &'a str, + username: &'a str, + logged_in: bool, + statuses: Vec<&'a Status> } - -// all the info on every page -#[derive(Template)] -#[template(path = "base.html")] -struct BaseTemplate<'a>{ - title: &'a str, -} +// impl default #[derive(Template)] #[template(path = "notifications.html")] @@ -39,6 +44,26 @@ pub fn reply<T: askama::Template>(t: &T) -> Response { .unwrap() } +fn new_note() { + // create activitypub activity object + // TODO -- micropub? + // generate activitypub object from post request + // send to outbox +} + +// ActivityPub outbox +fn outbox() { + // fetch/store from db. + // db objects need to serialize/deserialize this object + // if get -> fetch from db + // if post -> put to db, send to inbox of followers + // send to inbox of followers +} + +// ActivityPub inbox +fn inbox() { +} + #[tokio::main] async fn main() { env_logger::init(); @@ -48,7 +73,12 @@ async fn main() { // user // default page -- timeline let home = warp::path::end() - .map(|| reply(&HomeTemplate{name: "world", _parent: BaseTemplate { title: "gourami"}})); + .map(|| reply(&TimelineTemplate{ + page: "timeline", + logged_in: true, + statuses: vec![], + username: "alex", + title: "gourami"})); let static_files = warp::path("static") .and(warp::fs::dir("./static")); diff --git a/templates/base.html b/templates/base.html @@ -10,11 +10,15 @@ <div id="header"> <div class="row navbar"> <div class="col-sm"> - <div class="title">gourami/{{page}}</div> + <div class="title">{{title}}/{{page}}</div> </div> - <div class="col-sm text-center">t n d</div> + <div class="col-sm text-center">t n</div> <div class="col-sm text-right"> - logged out + {% if logged_in %} + {{username}} + {% else %} + logged out + {% endif %} </div> </div> </div> diff --git a/templates/timeline.html b/templates/timeline.html @@ -9,7 +9,7 @@ </form> <div class="row"> <div class="status"> - #{{post_id}} | {{user_id}}: + HL->post_id timestamp | user_id: post content delete button </div> </div> </div>