Skip to content

Commit

Permalink
Refactored middleware system (#153)
Browse files Browse the repository at this point in the history
* alpha: begin refactoring middleware system

* alpha: newer middleware syntax prototype

* alpha: merge `Plugin` into `AlphaMiddlewareBuilderLike`

* alpha: merge gats stuff into existing mw traits

* alpha: shuffle some stuff around

* alpha: add too many args to `map`

* alpha: random stuff

* alpha: checkpoint

* alpha: checkpoint

* alpha: lets try this again

* alpha: put mw onto `MapPlugin`

* alpha: replace `Func` with `Executable`

* alpha: checkpoint

* alpha: checkpoint

* alpha: checkpoint

* alpha:: remove `State` from `Executable`

* alpha: generics go brrrrrrr

* Clone `Layer` into `AlphaLayer`

* `DynLayer`

* Drop failed plugin stuff

* `LayerResult<T>`

* `->  Self::LayerResult<T>`

* poggies

* `type Fut<'a>`

* `fn call<'a>`

* checkpoint

* goated `RequestLayer`

* `append_alpha` & `call` working

* load dem up

* checkpoint

* fuck yeah

* basic resp working

* Drop `mw2` module

* removing unused stuff

* benchmark 0.1.3 vs main

* use `ahash` cause it's probs faster *pending more tests*

* Undo `ahash`

* high level cleanup

* fix breaking changes to legacy syntax

* some clippy

* move to `Stream` everywhere + semi-fix alpha test suite

* fix arg mappers & clean up some bounds

* fix `with_middleware_from_func` unit test

* upgrade workspace

* fix non-alpha build
  • Loading branch information
oscartbeaumont committed Apr 1, 2023
1 parent ab0edc9 commit 4c9d8dd
Show file tree
Hide file tree
Showing 49 changed files with 3,128 additions and 2,408 deletions.
37 changes: 27 additions & 10 deletions Cargo.toml
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
[package]
name = "rspc"
description = "A blazing fast and easy to use TRPC server for Rust."
version = "0.1.3"
version = "0.1.4"
authors = ["Oscar Beaumont <[email protected]>"]
edition = "2021"
license = "MIT"
Expand All @@ -11,6 +11,15 @@ documentation = "https://docs.rs/rspc/latest/rspc"
keywords = ["async", "specta", "rust-to-ts", "typescript", "typesafe"]
categories = ["web-programming", "asynchronous"]

# /bin/sh RUSTDOCFLAGS="--cfg docsrs" cargo +nightly doc --all-features
[package.metadata."docs.rs"]
all-features = true
rustdoc-args = ["--cfg", "docsrs"]

[[bench]]
name = "benchmarks"
harness = false

[features]
default = []
tauri = ["dep:tauri"]
Expand Down Expand Up @@ -48,24 +57,32 @@ bytesize = ["specta/bytesize"]
glam = ["specta/glam"]

[dependencies]
specta = { version = "1.0.1", features = ["serde", "typescript", "tokio"] }
specta = { version = "1.0.2", features = ["serde", "typescript", "tokio"] }
httpz = { version = "0.0.4", optional = true } # TODO: Move back to crates.io release
serde = { version = "1.0.152", features = ["derive"] }
serde_json = "1.0.93"
thiserror = "1.0.38"
futures = "0.3.26"
tokio = { version = "1.26.0", features = ["sync", "rt", "macros"] }
serde = { version = "1.0.159", features = ["derive"] }
serde_json = "1.0.95"
thiserror = "1.0.40"
futures = "0.3.28"
tokio = { version = "1.27.0", features = ["sync", "rt", "macros"] }
tauri = { version = "1.2.4", optional = true }
tracing = { version = "0.1.37", optional = true }
worker = { version = "0.0.12", optional = true }
worker = { version = "0.0.15", optional = true }
anyhow = { version = "1", optional = true }
futures-locks = { git = "https://github.com/oscartbeaumont/futures-locks", rev = "a2e880337e6bfb3140a261932667149607e3ada9", features = ["tokio"] }
futures-channel = "0.3.27"
futures-channel = "0.3.28"
nougat = "0.2.4"
pin-project = "1.0.12" # TODO: Move to `pin-project-lite`

[dev-dependencies]
# Tests
async-stream = "0.3.4"

# Benchmark
criterion = { version = "0.4", features = ["async_tokio", "html_reports"] }
pprof = { version = "0.11.1", features = ["flamegraph", "criterion", "protobuf-codec", "frame-pointer"] }
tokio = { version = "1.27.0", features = ["macros", "rt-multi-thread"] }
rspc_legacy = { package = "rspc", version = "0.1.3"}

[workspace]
members = [
"./create-rspc-app",
Expand All @@ -76,4 +93,4 @@ members = [

[patch.crates-io]
specta = { git = "https://github.com/oscartbeaumont/specta.git", rev = "df67cd18ea7a79819387e4c6a329b0e3929fb79e" }
httpz = { git = "https://github.com/oscartbeaumont/httpz", rev = "be67ead9320095bdecf90cae75fded2411509b0f" } # TODO: Move back to crates.io release
httpz = { git = "https://github.com/oscartbeaumont/httpz", rev = "2afc85de7c05b5d7d9b74c5439baf5a952162b15" } # TODO: Move back to crates.io release
311 changes: 311 additions & 0 deletions benches/benchmarks.rs

Large diffs are not rendered by default.

11 changes: 5 additions & 6 deletions create-rspc-app/Cargo.toml
Original file line number Diff line number Diff line change
Expand Up @@ -17,14 +17,13 @@ requestty = "0.5.0"
strum = { version = "0.24.1", features = ["derive"] }
rustc_version = "0.4.0"
ureq = { version = "2.6.2", features = ["json"] }
serde_json = "1.0.93"
serde_json = "1.0.95"
ctrlc = "3.2.5"
thiserror = "1.0.38"
thiserror = "1.0.40"
walkdir = "2"

[dev-dependencies]
tempdir = "0.3.7"
cargo = "0.67.1"
tokio = { version = "1.25.0", features = ["full", "process"] }
ssh2 = { version = "0.9.3", features = ["vendored-openssl"] } # This is need for M1 support
futures = "0.3.26"
cargo = "0.69.1"
tokio = { version = "1.27.0", features = ["full", "process"] }
futures = "0.3.28"
17 changes: 9 additions & 8 deletions docs/package.json
Original file line number Diff line number Diff line change
Expand Up @@ -8,20 +8,21 @@
"start": "next start"
},
"dependencies": {
"@vercel/og": "^0.3.0",
"next": "^13.2.3",
"nextra": "^2.2.17",
"nextra-theme-docs": "^2.2.17",
"@vercel/og": "^0.5.0",
"next": "^13.2.4",
"nextra": "^2.3.0",
"nextra-theme-docs": "^2.3.0",
"react": "^18.2.0",
"react-dom": "^18.2.0"
},
"devDependencies": {
"@rspc/config": "workspace:*",
"@types/node": "18.14.6",
"autoprefixer": "^10.4.13",
"@types/node": "18.15.11",
"@types/react": "^18.0.31",
"autoprefixer": "^10.4.14",
"postcss": "^8.4.21",
"tailwindcss": "^3.2.7",
"tailwindcss": "^3.3.1",
"tslib": "^2.5.0",
"typescript": "^4.9.5"
"typescript": "^5.0.3"
}
}
10 changes: 5 additions & 5 deletions examples/Cargo.toml
Original file line number Diff line number Diff line change
Expand Up @@ -7,12 +7,12 @@ publish = false
[dependencies]
rspc = { path = "../", features = ["axum"] }
async-stream = "0.3.4"
axum = "0.6.10"
chrono = { version = "0.4.23", features = ["serde"] }
serde = { version = "1.0.152", features = ["derive"] }
axum = "0.6.12"
chrono = { version = "0.4.24", features = ["serde"] }
serde = { version = "1.0.159", features = ["derive"] }
time = "0.3.20"
tokio = { version = "1.26.0", features = ["rt-multi-thread", "macros", "time", "sync"], default-features = false }
tokio = { version = "1.27.0", features = ["rt-multi-thread", "macros", "time", "sync"], default-features = false }
tower-cookies = "0.9.0"
tower-http = { version = "0.4.0", default-features = false, features = ["cors"] }
uuid = { version = "1.3.0", features = ["v4", "serde"] }
serde_json = "1.0.93"
serde_json = "1.0.95"
14 changes: 7 additions & 7 deletions examples/astro/package.json
Original file line number Diff line number Diff line change
Expand Up @@ -13,18 +13,18 @@
"@rspc/client": "workspace:*",
"@rspc/react": "workspace:*",
"@rspc/solid": "workspace:*",
"@tanstack/react-query": "^4.26.0",
"@tanstack/solid-query": "^4.26.0",
"astro": "2.0.17",
"@tanstack/react-query": "^4.28.0",
"@tanstack/solid-query": "^4.27.0",
"astro": "2.1.9",
"react": "^18.2.0",
"react-dom": "^18.2.0",
"solid-js": "^1.6.11"
"solid-js": "^1.7.0"
},
"devDependencies": {
"@astrojs/react": "^2.1.1",
"@astrojs/solid-js": "^2.1.0",
"@rspc/config": "workspace:*",
"@astrojs/react": "^2.0.2",
"@astrojs/solid-js": "^2.0.2",
"@types/react": "^18.0.28"
"@types/react": "^18.0.31"
},
"pnpm": {
"peerDependencyRules": {
Expand Down
6 changes: 3 additions & 3 deletions examples/axum/Cargo.toml
Original file line number Diff line number Diff line change
Expand Up @@ -5,8 +5,8 @@ edition = "2021"
publish = false

[dependencies]
rspc = { path = "../../", features = ["axum"] }
tokio = { version = "1.26.0", features = ["full"] }
rspc = { path = "../../", features = ["axum", "alpha"] }
tokio = { version = "1.27.0", features = ["full"] }
async-stream = "0.3.4"
axum = { version = "0.6.10", features = ["ws"] }
axum = { version = "0.6.12", features = ["ws"] }
tower-http = { version = "0.4.0", default-features = false, features = ["cors"] }
167 changes: 111 additions & 56 deletions examples/axum/src/main.rs
Original file line number Diff line number Diff line change
Expand Up @@ -2,77 +2,132 @@ use std::{path::PathBuf, time::Duration};

use async_stream::stream;
use axum::routing::get;
use rspc::{integrations::httpz::Request, Config};
use rspc::{alpha::Rspc, integrations::httpz::Request, Config};
use tokio::time::sleep;
use tower_http::cors::{Any, CorsLayer};

struct Ctx {
x_demo_header: Option<String>,
}

const R: Rspc<Ctx> = Rspc::new();

#[tokio::main]
async fn main() {
let router =
rspc::Router::<Ctx>::new()
.config(Config::new().export_ts_bindings(
PathBuf::from(env!("CARGO_MANIFEST_DIR")).join("../bindings.ts"),
))
.query("version", |t| t(|_, _: ()| env!("CARGO_PKG_VERSION")))
.query("X-Demo-Header", |t| {
t(|ctx, _: ()| {
ctx.x_demo_header
.clone()
.unwrap_or_else(|| "No header".to_string())
})
let router = R
.router()
.procedure("version", R.query(|_, _: ()| env!("CARGO_PKG_VERSION")))
.procedure(
"version1",
R.with(|mw, ctx| async move {
println!("MW ONE");
mw.next(ctx)
})
.query("echo", |t| t(|_, v: String| v))
.query("error", |t| {
t(|_, _: ()| {
Err(rspc::Error::new(
rspc::ErrorCode::InternalServerError,
"Something went wrong".into(),
)) as Result<String, rspc::Error>
})
.query(|_, _: ()| env!("CARGO_PKG_VERSION")),
)
.procedure(
"version2",
R.with(|mw, ctx| async move {
println!("MW ONE");
mw.next(ctx)
})
.mutation("error", |t| {
t(|_, _: ()| {
Err(rspc::Error::new(
rspc::ErrorCode::InternalServerError,
"Something went wrong".into(),
)) as Result<String, rspc::Error>
})
.with(|mw, ctx| async move {
println!("MW TWO");
mw.next(ctx)
})
.query("transformMe", |t| t(|_, _: ()| "Hello, world!".to_string()))
.mutation("sendMsg", |t| {
t(|_, v: String| {
println!("Client said '{}'", v);
v
})
.query(|_, _: ()| env!("CARGO_PKG_VERSION")),
)
.procedure(
"version3",
R.with(|mw, ctx| async move {
println!("MW ONE");
mw.next(ctx)
})
.subscription("pings", |t| {
t(|_ctx, _args: ()| {
stream! {
println!("Client subscribed to 'pings'");
for i in 0..5 {
println!("Sending ping {}", i);
yield "ping".to_string();
sleep(Duration::from_secs(1)).await;
}
}
.with(|mw, ctx| async move {
println!("MW TWO");
mw.next(ctx)
})
.with(|mw, ctx| async move {
println!("MW THREE");
mw.next(ctx)
})
.query(|_, _: ()| env!("CARGO_PKG_VERSION")),
)
.procedure(
"version4",
R.with(|mw, ctx| async move {
println!("MW ONE");
mw.next(ctx).resp(|result| async move {
println!("MW ONE RESULT: {result:?}");
result
})
})
// TODO: Results being returned from subscriptions
// .subscription("errorPings", |t| t(|_ctx, _args: ()| {
// stream! {
// for i in 0..5 {
// yield Ok("ping".to_string());
// sleep(Duration::from_secs(1)).await;
// }
// yield Err(rspc::Error::new(ErrorCode::InternalServerError, "Something went wrong".into()));
// }
// }))
.build()
.arced(); // This function is a shortcut to wrap the router in an `Arc`.
.query(|_, _: ()| env!("CARGO_PKG_VERSION")),
)
.compat()
.arced();

// let router =
// rspc::Router::<Ctx>::new()
// .config(Config::new().export_ts_bindings(
// PathBuf::from(env!("CARGO_MANIFEST_DIR")).join("../bindings.ts"),
// ))
// .query("version", |t| t(|_, _: ()| env!("CARGO_PKG_VERSION")))
// .query("X-Demo-Header", |t| {
// t(|ctx, _: ()| {
// ctx.x_demo_header
// .clone()
// .unwrap_or_else(|| "No header".to_string())
// })
// })
// .query("echo", |t| t(|_, v: String| v))
// .query("error", |t| {
// t(|_, _: ()| {
// Err(rspc::Error::new(
// rspc::ErrorCode::InternalServerError,
// "Something went wrong".into(),
// )) as Result<String, rspc::Error>
// })
// })
// .mutation("error", |t| {
// t(|_, _: ()| {
// Err(rspc::Error::new(
// rspc::ErrorCode::InternalServerError,
// "Something went wrong".into(),
// )) as Result<String, rspc::Error>
// })
// })
// .query("transformMe", |t| t(|_, _: ()| "Hello, world!".to_string()))
// .mutation("sendMsg", |t| {
// t(|_, v: String| {
// println!("Client said '{}'", v);
// v
// })
// })
// .subscription("pings", |t| {
// t(|_ctx, _args: ()| {
// stream! {
// println!("Client subscribed to 'pings'");
// for i in 0..5 {
// println!("Sending ping {}", i);
// yield "ping".to_string();
// sleep(Duration::from_secs(1)).await;
// }
// }
// })
// })
// // TODO: Results being returned from subscriptions
// // .subscription("errorPings", |t| t(|_ctx, _args: ()| {
// // stream! {
// // for i in 0..5 {
// // yield Ok("ping".to_string());
// // sleep(Duration::from_secs(1)).await;
// // }
// // yield Err(rspc::Error::new(ErrorCode::InternalServerError, "Something went wrong".into()));
// // }
// // }))
// .build()
// .arced(); // This function is a shortcut to wrap the router in an `Arc`.

// We disable CORS because this is just an example. DON'T DO THIS IN PRODUCTION!
let cors = CorsLayer::new()
Expand Down
10 changes: 5 additions & 5 deletions examples/nextjs/package.json
Original file line number Diff line number Diff line change
Expand Up @@ -8,15 +8,15 @@
"dependencies": {
"@rspc/client": "workspace:*",
"@rspc/react": "workspace:*",
"@tanstack/react-query": "^4.26.0",
"next": "^13.2.3",
"@tanstack/react-query": "^4.28.0",
"next": "^13.2.4",
"react": "^18.2.0",
"react-dom": "^18.2.0"
},
"devDependencies": {
"@types/node": "^18.14.6",
"@types/react": "^18.0.28",
"@types/node": "^18.15.11",
"@types/react": "^18.0.31",
"@types/react-dom": "^18.0.11",
"typescript": "^4.9.5"
"typescript": "^5.0.3"
}
}
Loading

0 comments on commit 4c9d8dd

Please sign in to comment.