Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Query history from history server #143

Merged
merged 24 commits into from
Nov 17, 2024

Conversation

progval
Copy link
Collaborator

@progval progval commented Oct 26, 2024

test suite here: progval/irctest#292

@progval
Copy link
Collaborator Author

progval commented Nov 2, 2024

@spb AFAICT, I only need to implement AROUND in the postgresql backend before this PR is ready to be merged. Could you start reviewing?


let mut connection_lock = self.database_connection.lock().await;

let db_channel_id = i64::try_from(channel_id.as_u64()).expect("channel id overflows u64");
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I've been preferring as conversions for this (to be replaced eventually with cast_signed/cast_unsigned), to just store and retrieve the bit pattern on the basis that we don't need the database server to be ordering IDs, just checking equality.

Unless we do need the database to order them, in which case we need to change the existing code (and should probably enforce on creation that an id fits in 63 bits). Either way I think it's better to be consistent.

Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

ok for now, but in the future we should do it explicitly, eg. with bytemuck. Behavior of as depends on compilation profile, so it shouldn't be relied upon.

return HashMap::new();
}
Ok(rows) => {
rows.map(|row| row.expect("Could not deserialize row"))
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Is panicking appropriate here or should we log an error and skip instead? We've got a lot of existing PoC code that panics all over the place but maybe it's time to make more efforts not to.

Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Based on https://docs.rs/diesel/latest/diesel/result/enum.Error.html this happens when:

  • there is a major logic error on our side,
  • the database misbehaved, or
  • the database schema does not match Rust's

It seems reasonable to crash either way.

Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Heh, you're right. I removed the panics.

historic_users::dsl::ident,
historic_users::dsl::vhost,
historic_users::dsl::account_name,
))
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Is it worth packaging this query up into a helper function in the models?

@@ -27,7 +29,7 @@ pub struct HistoryServerConfig {
pub struct HistoryServer {
node: Arc<NetworkNode>,
history_receiver: Mutex<UnboundedReceiver<sable_network::rpc::NetworkHistoryUpdate>>,
database_connection: Mutex<AsyncPgConnection>,
database_connection: Mutex<AsyncPgConnection>, // TODO: use a connection pool
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Yes, definitely

sable_network/Cargo.toml Outdated Show resolved Hide resolved
@@ -20,12 +22,12 @@ fn target_id_for_entry(for_user: UserId, entry: &HistoryLogEntry) -> Option<Targ
}

/// Implementation of [`HistoryService`] backed by [`NetworkNode`]
pub struct LocalHistoryService<'a> {
node: &'a NetworkNode,
pub struct LocalHistoryService<'a, NetworkPolicy: policy::PolicyService> {
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I'm starting to really question whether making Node generic over its policy was a good idea. Not much to do about it in this PR but it wants thought more generally.

sable_network/src/history/mod.rs Outdated Show resolved Hide resolved
))
.filter(messages::dsl::target_channel.eq(db_channel_id));
Ok(match request {
HistoryRequest::Latest { to_ts, limit } => {
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Is there no commonality in these arms that can be broken out? They're quite hard to follow as they are.

Copy link
Collaborator Author

@progval progval Nov 9, 2024

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I can rewrite Latest/Before/After as a Between, I guess

Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I managed to deduplicate most of the code: a8f711b


fn make_historical_event(
channel: &crate::models::Channel,
(id, timestamp, message_type, text, source_nick, source_ident, source_vhost, source_account): (
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This might be more readable as a new Queryable struct (possibly with a helper method in the model to query it) - this ties into the comment further up about a helper query method

Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I don't see what you have in mind

async fn handle_new_message(
&self,
new_message: update::NewMessage,
update_timestamp: i64,
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Why is this not using the ts field from the Message?

Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

To make the @time tag consistent between echo-message and chathistory d56db83

pub sasl_mechanisms: Vec<String>,
}

#[target_type(ServerId)]
struct IntroduceHistoryServer {
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I realise this is matching the services behaviour and it's probably fine for now, but long term the desired behaviour isn't the same - we need a single authoritative services node, but for history we can have multiple active nodes and just send requests to any of them.

Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

ack

@progval progval marked this pull request as ready for review November 10, 2024 18:16
@progval progval changed the title [WIP] Query history from history server Query history from history server Nov 10, 2024
@spb spb merged commit ede3e68 into Libera-Chat:master Nov 17, 2024
2 checks passed
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

2 participants