mirror of https://github.com/mastodon/flodgatt
Remove outdated files and update dependencies
This commit is contained in:
parent
a6a7ebeae1
commit
769af09221
File diff suppressed because it is too large
Load Diff
11
Cargo.toml
11
Cargo.toml
|
@ -2,19 +2,11 @@
|
||||||
name = "ragequit"
|
name = "ragequit"
|
||||||
description = "A blazingly fast drop-in replacement for the Mastodon streaming api server"
|
description = "A blazingly fast drop-in replacement for the Mastodon streaming api server"
|
||||||
version = "0.1.0"
|
version = "0.1.0"
|
||||||
authors = ["Julian Laubstein <contact@julianlaubstein.de>"]
|
authors = ["Daniel Long Sockwell <daniel@codesections.com", "Julian Laubstein <contact@julianlaubstein.de>"]
|
||||||
edition = "2018"
|
edition = "2018"
|
||||||
|
|
||||||
[dependencies]
|
[dependencies]
|
||||||
actix-web = "0.7.18"
|
|
||||||
structopt = "0.2.14"
|
|
||||||
log = "0.4.6"
|
log = "0.4.6"
|
||||||
actix = "0.7.9"
|
|
||||||
actix-redis = "0.5.1"
|
|
||||||
redis-async = "0.4.4"
|
|
||||||
envconfig = "0.5.0"
|
|
||||||
envconfig_derive = "0.5.0"
|
|
||||||
whoami = "0.4.1"
|
|
||||||
futures = "0.1.26"
|
futures = "0.1.26"
|
||||||
tokio = "0.1.19"
|
tokio = "0.1.19"
|
||||||
warp = "0.1.15"
|
warp = "0.1.15"
|
||||||
|
@ -25,6 +17,7 @@ serde = "1.0.90"
|
||||||
pretty_env_logger = "0.3.0"
|
pretty_env_logger = "0.3.0"
|
||||||
postgres = "0.15.2"
|
postgres = "0.15.2"
|
||||||
uuid = { version = "0.7", features = ["v4"] }
|
uuid = { version = "0.7", features = ["v4"] }
|
||||||
|
dotenv = "0.14.0"
|
||||||
|
|
||||||
[features]
|
[features]
|
||||||
default = [ "production" ]
|
default = [ "production" ]
|
||||||
|
|
|
@ -1,6 +0,0 @@
|
||||||
use crate::AppState;
|
|
||||||
use actix_web::{HttpRequest, Responder};
|
|
||||||
|
|
||||||
pub fn index(_req: HttpRequest<AppState>) -> impl Responder {
|
|
||||||
"placeholder response from direct::index"
|
|
||||||
}
|
|
|
@ -1,10 +0,0 @@
|
||||||
use crate::AppState;
|
|
||||||
use actix_web::{HttpRequest, Responder};
|
|
||||||
|
|
||||||
pub fn index(_req: HttpRequest<AppState>) -> impl Responder {
|
|
||||||
"placeholder response from hashtag::index"
|
|
||||||
}
|
|
||||||
|
|
||||||
pub fn local(_req: HttpRequest<AppState>) -> impl Responder {
|
|
||||||
"placeholder response from hashtag::local"
|
|
||||||
}
|
|
|
@ -1,6 +0,0 @@
|
||||||
use crate::AppState;
|
|
||||||
use actix_web::{HttpRequest, Responder};
|
|
||||||
|
|
||||||
pub fn index(_req: HttpRequest<AppState>) -> impl Responder {
|
|
||||||
"placeholder response from list::index"
|
|
||||||
}
|
|
|
@ -1,5 +0,0 @@
|
||||||
pub mod direct;
|
|
||||||
pub mod hashtag;
|
|
||||||
pub mod list;
|
|
||||||
pub mod public;
|
|
||||||
pub mod user;
|
|
|
@ -1,10 +0,0 @@
|
||||||
use crate::AppState;
|
|
||||||
use actix_web::{HttpRequest, Responder};
|
|
||||||
|
|
||||||
pub fn index(_req: HttpRequest<AppState>) -> impl Responder {
|
|
||||||
"placeholder response from public::index"
|
|
||||||
}
|
|
||||||
|
|
||||||
pub fn local(_req: HttpRequest<AppState>) -> impl Responder {
|
|
||||||
"placeholder response from public::local"
|
|
||||||
}
|
|
|
@ -1,6 +0,0 @@
|
||||||
use crate::AppState;
|
|
||||||
use actix_web::{HttpRequest, Responder};
|
|
||||||
|
|
||||||
pub fn index(_req: HttpRequest<AppState>) -> impl Responder {
|
|
||||||
"placeholder response from user::index"
|
|
||||||
}
|
|
|
@ -1,2 +0,0 @@
|
||||||
pub mod http;
|
|
||||||
pub mod ws;
|
|
|
@ -1,46 +0,0 @@
|
||||||
use crate::{common::HEARTBEAT_INTERVAL_SECONDS, AppState};
|
|
||||||
use actix::{Actor, AsyncContext, StreamHandler};
|
|
||||||
use actix_redis::{Command, RespValue};
|
|
||||||
use actix_web::{ws, HttpRequest, Responder};
|
|
||||||
use log::{debug, info};
|
|
||||||
use std::time::Duration;
|
|
||||||
|
|
||||||
/// Define http actor
|
|
||||||
struct WebsocketActor;
|
|
||||||
|
|
||||||
impl Actor for WebsocketActor {
|
|
||||||
type Context = ws::WebsocketContext<Self, AppState>;
|
|
||||||
}
|
|
||||||
|
|
||||||
/// Handler for ws::Message message
|
|
||||||
impl StreamHandler<ws::Message, ws::ProtocolError> for WebsocketActor {
|
|
||||||
fn started(&mut self, ctx: &mut Self::Context) {
|
|
||||||
ctx.run_interval(
|
|
||||||
Duration::from_secs(HEARTBEAT_INTERVAL_SECONDS),
|
|
||||||
|_, inner_ctx| {
|
|
||||||
inner_ctx.ping("Ping from StreamHandler");
|
|
||||||
},
|
|
||||||
);
|
|
||||||
}
|
|
||||||
|
|
||||||
// This appears to be an echo server based on the actix_web documentation
|
|
||||||
// We won't actually need echo functionality in the final server
|
|
||||||
fn handle(&mut self, msg: ws::Message, ctx: &mut Self::Context) {
|
|
||||||
debug!("Message {:?}", msg);
|
|
||||||
|
|
||||||
let red = ctx
|
|
||||||
.state()
|
|
||||||
.redis
|
|
||||||
.send(Command(RespValue::SimpleString("GET".into())));
|
|
||||||
|
|
||||||
match msg {
|
|
||||||
ws::Message::Pong(msg) => debug!("matched: {}", msg),
|
|
||||||
ws::Message::Text(text) => ctx.text(text),
|
|
||||||
_ => (),
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
pub fn index(req: HttpRequest<AppState>) -> impl Responder {
|
|
||||||
ws::start(&req, WebsocketActor)
|
|
||||||
}
|
|
|
@ -1 +0,0 @@
|
||||||
pub const HEARTBEAT_INTERVAL_SECONDS: u64 = 30;
|
|
60
src/env.rs
60
src/env.rs
|
@ -1,60 +0,0 @@
|
||||||
use envconfig::Envconfig;
|
|
||||||
use std::net::IpAddr;
|
|
||||||
|
|
||||||
/// Returns the current users username.
|
|
||||||
/// TODO: Find a way to do this cross-platform
|
|
||||||
pub fn current_user() -> String {
|
|
||||||
whoami::username()
|
|
||||||
}
|
|
||||||
|
|
||||||
#[cfg(feature = "production")]
|
|
||||||
#[derive(Envconfig)]
|
|
||||||
/// Production DB configuration
|
|
||||||
pub struct DbConfig {
|
|
||||||
#[envconfig(from = "DB_USER", default = "mastodon")]
|
|
||||||
user: String,
|
|
||||||
#[envconfig(from = "DB_PASS", default = "")]
|
|
||||||
password: String,
|
|
||||||
#[envconfig(from = "DB_NAME", default = "mastodon_production")]
|
|
||||||
database: String,
|
|
||||||
#[envconfig(from = "DB_HOST", default = "localhost")]
|
|
||||||
host: String,
|
|
||||||
#[envconfig(from = "DB_PORT", default = "5432")]
|
|
||||||
port: u16,
|
|
||||||
}
|
|
||||||
|
|
||||||
#[cfg(not(feature = "production"))]
|
|
||||||
#[derive(Envconfig)]
|
|
||||||
/// Development DB configuration
|
|
||||||
pub struct DbConfig {
|
|
||||||
#[envconfig(from = "DB_USER", default = current_user())]
|
|
||||||
pub user: String,
|
|
||||||
#[envconfig(from = "DB_PASS", default = "")]
|
|
||||||
pub password: String,
|
|
||||||
#[envconfig(from = "DB_NAME", default = "mastodon_development")]
|
|
||||||
pub database: String,
|
|
||||||
#[envconfig(from = "DB_HOST", default = "localhost")]
|
|
||||||
pub host: String,
|
|
||||||
#[envconfig(from = "DB_PORT", default = "5432")]
|
|
||||||
pub port: u16,
|
|
||||||
}
|
|
||||||
|
|
||||||
#[derive(Envconfig)]
|
|
||||||
pub struct ServerConfig {
|
|
||||||
#[envconfig(from = "BIND", default = "0.0.0.0")]
|
|
||||||
pub address: IpAddr,
|
|
||||||
#[envconfig(from = "PORT", default = "4000")]
|
|
||||||
pub port: u16,
|
|
||||||
}
|
|
||||||
|
|
||||||
#[derive(Envconfig)]
|
|
||||||
pub struct RedisConfig {
|
|
||||||
#[envconfig(from = "REDIS_HOST", default = "127.0.0.1")]
|
|
||||||
pub host: IpAddr,
|
|
||||||
#[envconfig(from = "REDIS_PORT", default = "6379")]
|
|
||||||
pub port: u16,
|
|
||||||
#[envconfig(from = "REDIS_DB", default = "0")]
|
|
||||||
pub db: u16,
|
|
||||||
#[envconfig(from = "REDIS_PASSWORD", default = "")]
|
|
||||||
pub password: String,
|
|
||||||
}
|
|
100
src/main.old.rs
100
src/main.old.rs
|
@ -1,100 +0,0 @@
|
||||||
#[macro_use]
|
|
||||||
extern crate envconfig_derive;
|
|
||||||
|
|
||||||
mod api;
|
|
||||||
mod common;
|
|
||||||
mod env;
|
|
||||||
mod middleware;
|
|
||||||
|
|
||||||
use actix::prelude::*;
|
|
||||||
use actix_redis::RedisActor;
|
|
||||||
use actix_web::{http::header, middleware::cors::Cors, server, App, HttpResponse};
|
|
||||||
use env::{RedisConfig, ServerConfig};
|
|
||||||
use env_logger::Builder;
|
|
||||||
use envconfig::Envconfig;
|
|
||||||
use log::info;
|
|
||||||
use std::net::SocketAddr;
|
|
||||||
|
|
||||||
const ENV_LOG_VARIABLE: &str = "STREAMING_API_LOG";
|
|
||||||
|
|
||||||
#[derive(Clone)]
|
|
||||||
pub struct AppState {
|
|
||||||
redis: Addr<RedisActor>,
|
|
||||||
}
|
|
||||||
|
|
||||||
fn main() {
|
|
||||||
Builder::from_env(ENV_LOG_VARIABLE).init();
|
|
||||||
|
|
||||||
info!("starting streaming api server");
|
|
||||||
|
|
||||||
let server_cfg = ServerConfig::init().expect("failed to obtain server environment");
|
|
||||||
let redis_cfg = RedisConfig::init().expect("failed to obtain redis environment");
|
|
||||||
|
|
||||||
let sys = System::new("streaming-api-server");
|
|
||||||
|
|
||||||
let redis_addr = RedisActor::start(format!("{}:{}", redis_cfg.host, redis_cfg.port));
|
|
||||||
|
|
||||||
let app_state = AppState {
|
|
||||||
redis: redis_addr.clone(),
|
|
||||||
};
|
|
||||||
|
|
||||||
server::new(move || endpoints(&app_state))
|
|
||||||
.bind(SocketAddr::new(server_cfg.address, server_cfg.port))
|
|
||||||
.unwrap()
|
|
||||||
.start();
|
|
||||||
|
|
||||||
sys.run();
|
|
||||||
}
|
|
||||||
|
|
||||||
fn endpoints(app_state: &AppState) -> App<AppState> {
|
|
||||||
use api::http;
|
|
||||||
use api::ws;
|
|
||||||
|
|
||||||
App::with_state(app_state.clone())
|
|
||||||
.prefix("/api/v1")
|
|
||||||
.resource("/streaming", |r| r.with(ws::index))
|
|
||||||
.resource("/streaming/health", |r| {
|
|
||||||
r.middleware(cors_middleware());
|
|
||||||
r.get().f(|_| HttpResponse::Ok())
|
|
||||||
})
|
|
||||||
.resource("/streaming/user", |r| {
|
|
||||||
r.middleware(cors_middleware());
|
|
||||||
r.get().with(http::user::index)
|
|
||||||
})
|
|
||||||
.resource("/streaming/public", |r| {
|
|
||||||
r.middleware(cors_middleware());
|
|
||||||
r.get().with(http::public::index)
|
|
||||||
})
|
|
||||||
.resource("/streaming/public/local", |r| {
|
|
||||||
r.middleware(cors_middleware());
|
|
||||||
r.get().with(http::public::local)
|
|
||||||
})
|
|
||||||
.resource("/streaming/direct", |r| {
|
|
||||||
r.middleware(cors_middleware());
|
|
||||||
r.get().with(http::direct::index)
|
|
||||||
})
|
|
||||||
.resource("/streaming/hashtag", |r| {
|
|
||||||
r.middleware(cors_middleware());
|
|
||||||
r.get().with(http::hashtag::index)
|
|
||||||
})
|
|
||||||
.resource("/streaming/hashtag/local", |r| {
|
|
||||||
r.middleware(cors_middleware());
|
|
||||||
r.get().with(http::hashtag::local)
|
|
||||||
})
|
|
||||||
.resource("/streaming/list", |r| {
|
|
||||||
r.middleware(cors_middleware());
|
|
||||||
r.get().with(http::list::index)
|
|
||||||
})
|
|
||||||
}
|
|
||||||
|
|
||||||
fn cors_middleware() -> Cors {
|
|
||||||
Cors::build()
|
|
||||||
.allowed_origin("*")
|
|
||||||
.allowed_methods(vec!["GET", "OPTIONS"])
|
|
||||||
.allowed_headers(vec![
|
|
||||||
header::AUTHORIZATION,
|
|
||||||
header::ACCEPT,
|
|
||||||
header::CACHE_CONTROL,
|
|
||||||
])
|
|
||||||
.finish()
|
|
||||||
}
|
|
|
@ -1,21 +0,0 @@
|
||||||
use crate::AppState;
|
|
||||||
use actix_web::{
|
|
||||||
error::Result,
|
|
||||||
http::header::AUTHORIZATION,
|
|
||||||
middleware::{Middleware, Started},
|
|
||||||
HttpRequest, HttpResponse,
|
|
||||||
};
|
|
||||||
|
|
||||||
pub struct Auth;
|
|
||||||
|
|
||||||
impl Middleware<AppState> for Auth {
|
|
||||||
fn start(&self, req: &HttpRequest<AppState>) -> Result<Started> {
|
|
||||||
let res = req
|
|
||||||
.headers()
|
|
||||||
.get(AUTHORIZATION)
|
|
||||||
.map(|bearer| Started::Done)
|
|
||||||
.unwrap_or_else(|| Started::Response(HttpResponse::Unauthorized().finish()));
|
|
||||||
|
|
||||||
Ok(res)
|
|
||||||
}
|
|
||||||
}
|
|
|
@ -1 +0,0 @@
|
||||||
pub mod auth;
|
|
Loading…
Reference in New Issue