feat: switch to RabbitMQ streams from Redis Pub/Sub
refactor: redo the bonfire client structure
This commit is contained in:
@@ -32,6 +32,7 @@ ulid = "0.4.1"
|
||||
nanoid = "0.4.0"
|
||||
|
||||
# serde
|
||||
rmp-serde = "1.0.0"
|
||||
serde_json = "1.0.57"
|
||||
serde = { version = "1.0.115", features = ["derive"] }
|
||||
validator = { version = "0.16", features = ["derive"] }
|
||||
@@ -65,6 +66,7 @@ revolt_rocket_okapi = { version = "0.10.0", features = ["swagger"] }
|
||||
|
||||
# rabbit
|
||||
amqprs = { version = "1.7.0" }
|
||||
lapin = { version = "3.0.0" }
|
||||
|
||||
# core
|
||||
authifier = "1.0.15"
|
||||
|
||||
@@ -1,12 +1,15 @@
|
||||
use std::collections::HashMap;
|
||||
|
||||
use authifier::{
|
||||
models::{Account, EmailVerification, Session},
|
||||
Authifier,
|
||||
};
|
||||
use futures::StreamExt;
|
||||
use lapin::types::AMQPValue;
|
||||
use rand::Rng;
|
||||
use redis_kiss::redis::aio::PubSub;
|
||||
use revolt_database::{
|
||||
events::client::EventV1, Channel, Database, Member, Message, Server, User, AMQP,
|
||||
events::client::{get_event_stream_channel, EventV1},
|
||||
Channel, Database, Member, Message, Server, User, AMQP,
|
||||
};
|
||||
use revolt_database::{util::idempotency::IdempotencyKey, Role};
|
||||
use revolt_models::v0;
|
||||
@@ -19,7 +22,7 @@ pub struct TestHarness {
|
||||
authifier: Authifier,
|
||||
pub db: Database,
|
||||
pub amqp: AMQP,
|
||||
sub: PubSub,
|
||||
consumer: lapin::Consumer,
|
||||
event_buffer: Vec<(String, EventV1)>,
|
||||
}
|
||||
|
||||
@@ -31,11 +34,17 @@ impl TestHarness {
|
||||
.await
|
||||
.expect("valid rocket instance");
|
||||
|
||||
let mut sub = redis_kiss::open_pubsub_connection()
|
||||
.await
|
||||
.expect("`PubSub`");
|
||||
let tag: String = rand::thread_rng()
|
||||
.sample_iter::<char, _>(&rand::distributions::Standard)
|
||||
.take(32)
|
||||
.collect();
|
||||
|
||||
sub.psubscribe("*").await.unwrap();
|
||||
static QUEUE_NAME: &str = "revolt.events";
|
||||
let consumer = get_event_stream_channel()
|
||||
.await
|
||||
.basic_consume(QUEUE_NAME, &tag, Default::default(), Default::default())
|
||||
.await
|
||||
.unwrap();
|
||||
|
||||
let db = client
|
||||
.rocket()
|
||||
@@ -68,7 +77,7 @@ impl TestHarness {
|
||||
authifier,
|
||||
db,
|
||||
amqp,
|
||||
sub,
|
||||
consumer,
|
||||
event_buffer: vec![],
|
||||
}
|
||||
}
|
||||
@@ -227,16 +236,33 @@ impl TestHarness {
|
||||
}
|
||||
}
|
||||
|
||||
let mut stream = self.sub.on_message();
|
||||
while let Some(item) = stream.next().await {
|
||||
let msg_topic = item.get_channel_name();
|
||||
let payload: EventV1 = redis_kiss::decode_payload(&item).unwrap();
|
||||
while let Some(Ok(delivery)) = self.consumer.next().await {
|
||||
let headers: HashMap<String, AMQPValue> = delivery
|
||||
.properties
|
||||
.headers()
|
||||
.as_ref()
|
||||
.map(|table| {
|
||||
table
|
||||
.into_iter()
|
||||
.map(|(k, v)| (k.to_string(), v.clone()))
|
||||
.collect()
|
||||
})
|
||||
.unwrap_or_default();
|
||||
|
||||
if topic == msg_topic && predicate(&payload) {
|
||||
let filter_value = headers
|
||||
.get("x-stream-filter-value")
|
||||
.expect("`x-stream-filter-value` not present in message!")
|
||||
.as_long_string()
|
||||
.unwrap()
|
||||
.to_string();
|
||||
|
||||
let payload: EventV1 = rmp_serde::from_slice(&delivery.data).unwrap();
|
||||
|
||||
if topic == filter_value && predicate(&payload) {
|
||||
return payload;
|
||||
}
|
||||
|
||||
self.event_buffer.push((msg_topic.to_string(), payload));
|
||||
self.event_buffer.push((filter_value, payload));
|
||||
}
|
||||
|
||||
// WARNING: if predicate is never satisfied, this will never return
|
||||
|
||||
Reference in New Issue
Block a user