Skip to content

Commit

Permalink
Manual wom sync
Browse files Browse the repository at this point in the history
  • Loading branch information
fatfingers23 committed Apr 20, 2024
1 parent 7750ed2 commit aea0f51
Show file tree
Hide file tree
Showing 11 changed files with 238 additions and 192 deletions.
1 change: 0 additions & 1 deletion docker-compose.yml
Original file line number Diff line number Diff line change
@@ -1,4 +1,3 @@
version: '3.3'
services:
mongo:
image: mongo:5.0.10
Expand Down
16 changes: 2 additions & 14 deletions trackscape-discord-api/src/main.rs
Original file line number Diff line number Diff line change
Expand Up @@ -30,6 +30,7 @@ use crate::controllers::clan_controller::clan_controller;
use crate::controllers::drop_log_controller::drop_log_controller;
use actix_files::{Files, NamedFile};
use log::{error, info};
use trackscape_discord_shared::jobs::get_celery_caller;
use trackscape_discord_shared::wiki_api::wiki_api::{get_quests_and_difficulties, WikiQuest};

/// Connection ID.
Expand Down Expand Up @@ -104,20 +105,7 @@ async fn actix_web(
let (chat_server, server_tx) = ChatServer::new(connected_websockets_counter.clone());

let _ = spawn(chat_server.run());

let celery = celery::app!(
broker = RedisBroker { std::env::var("REDIS_ADDR").unwrap_or_else(|_| "redis://127.0.0.1:6379/".into()) },
tasks = [
],
// This just shows how we can route certain tasks to certain queues based
// on glob matching.
task_routes = [
"*" => "celery",
],
prefetch_count = 2,
heartbeat = Some(10),
).await.expect("Error creating celery job client");

let celery = get_celery_caller().await;
let config = move |cfg: &mut ServiceConfig| {
cfg.service(
web::scope("/api")
Expand Down
4 changes: 2 additions & 2 deletions trackscape-discord-bot/Cargo.toml
Original file line number Diff line number Diff line change
Expand Up @@ -9,7 +9,7 @@ edition = "2021"
anyhow = "1.0.66"
dotenv = "0.15.0"
mongodb = "2.4.0"
xxhash-rust = {version = "0.8.6", features = ["xxh3", "const_xxh3"]}
xxhash-rust = { version = "0.8.6", features = ["xxh3", "const_xxh3"] }
shuttle-serenity = "0.37.0"
shuttle-runtime = "0.37.0"
shuttle-persist = "0.37.0"
Expand All @@ -22,7 +22,7 @@ rand = "0.8.5"
regex = "1.9.4"
urlencoding = "2.1.3"
num-format = "0.4.4"
reqwest = {version = "0.11.20", features = ["json"]}
reqwest = { version = "0.11.20", features = ["json"] }
trackscape-discord-shared = { path = "../trackscape-discord-shared" }
log = "0.4.20"
async-trait = "0.1.77"
Original file line number Diff line number Diff line change
@@ -0,0 +1,30 @@
use crate::database::BotMongoDb;
use serenity::builder::CreateCommand;
use serenity::client::Context;
use serenity::model::prelude::Permissions;
use trackscape_discord_shared::database::guilds_db::RegisteredGuildModel;
use trackscape_discord_shared::jobs::wom_guild_sync_logic::sync_wom_by_guild;

pub fn register() -> CreateCommand {
CreateCommand::new("sync")
.description("If WOM is connected it syncs between Trackscape and WOM.")
.default_member_permissions(Permissions::MANAGE_GUILD)
}

pub async fn run(_ctx: &Context, db: &BotMongoDb, guild_id: u64) -> Option<String> {
match db.guilds.get_by_guild_id(guild_id).await {
Ok(saved_guild) => {
let saved_guild = saved_guild.unwrap_or(RegisteredGuildModel::new(guild_id));
match saved_guild.wom_id {
Some(_) => {
sync_wom_by_guild(&saved_guild, db).await;
None
}
None => Some("Please set your WOM group's id first with /wom ".to_string()),
}
}
Err(_) => {
Some("No saved guild was found. Please try adding and removing the bot".to_string())
}
}
}
3 changes: 2 additions & 1 deletion trackscape-discord-bot/src/commands/mod.rs
Original file line number Diff line number Diff line change
@@ -1,6 +1,7 @@
pub mod expel_clanmate_command;
pub mod get_verification_code;
pub mod info;
pub(crate) mod manually_run_wom_sync_command;
pub mod name_change_command;
pub mod reset_broadcasts_thresholds;
pub mod set_broadcast_channel;
Expand All @@ -11,4 +12,4 @@ pub mod set_quest_min_command;
pub mod set_threshold_command;
pub mod set_wom_id_command;
pub mod toggle_broadcasts_command;
mod trackscape_command_trait;
pub mod trackscape_command_trait;
10 changes: 9 additions & 1 deletion trackscape-discord-bot/src/main.rs
Original file line number Diff line number Diff line change
Expand Up @@ -290,6 +290,14 @@ impl EventHandler for Bot {
)
.await
}
"sync" => {
commands::manually_run_wom_sync_command::run(
&ctx,
&self.mongo_db,
command.guild_id.unwrap().get(),
)
.await
}
_ => {
info!("not implemented :(");
None
Expand Down Expand Up @@ -329,6 +337,7 @@ fn get_commands() -> Vec<CreateCommand> {
commands.push(commands::set_wom_id_command::register());
commands.push(commands::expel_clanmate_command::register());
commands.push(commands::name_change_command::register());
commands.push(commands::manually_run_wom_sync_command::register());
//leagues didnt have any braodcasts this time around and over now
// commands.push(commands::set_leagues_broadcast_channel::register());
commands
Expand Down Expand Up @@ -358,7 +367,6 @@ async fn serenity() -> shuttle_serenity::ShuttleSerenity {
};

let db = BotMongoDb::new_db_instance(mongodb_url).await;

// Set gateway intents, which decides what events the bot will be notified about
let intents =
GatewayIntents::GUILD_MESSAGES | GatewayIntents::MESSAGE_CONTENT | GatewayIntents::GUILDS;
Expand Down
1 change: 0 additions & 1 deletion trackscape-discord-shared/src/jobs/job_helpers.rs
Original file line number Diff line number Diff line change
@@ -1,5 +1,4 @@
use crate::database::{BotMongoDb, MongoDb};

use redis::{Connection, RedisResult};
use std::env;

Expand Down
16 changes: 16 additions & 0 deletions trackscape-discord-shared/src/jobs/mod.rs
Original file line number Diff line number Diff line change
Expand Up @@ -11,6 +11,7 @@ pub mod name_change_job;
pub mod remove_clanmate_job;
pub mod update_create_clanmate_job;
pub mod wom_guild_sync_job;
pub mod wom_guild_sync_logic;

#[async_trait]
pub trait JobQueue {
Expand All @@ -21,6 +22,21 @@ pub struct CeleryJobQueue {
pub celery: Arc<Celery>,
}

pub async fn get_celery_caller() -> Arc<Celery> {
celery::app!(
broker = RedisBroker { std::env::var("REDIS_ADDR").unwrap_or_else(|_| "redis://127.0.0.1:6379/".into()) },
tasks = [
],
// This just shows how we can route certain tasks to certain queues based
// on glob matching.
task_routes = [
"*" => "celery",
],
prefetch_count = 2,
heartbeat = Some(10),
).await.expect("Error creating celery job client")
}

#[async_trait]
impl JobQueue for CeleryJobQueue {
async fn send_task<T: Task>(&self, task_sig: Signature<T>) -> Result<AsyncResult, CeleryError> {
Expand Down
174 changes: 3 additions & 171 deletions trackscape-discord-shared/src/jobs/wom_guild_sync_job.rs
Original file line number Diff line number Diff line change
@@ -1,11 +1,7 @@
use crate::database::clan_mates::{name_compare, ClanMateModel, ClanMates};
use crate::jobs::job_helpers::get_mongodb;
use crate::wom::{get_wom_client, ApiLimiter};
use crate::jobs::wom_guild_sync_logic::sync_wom_by_guild;
use celery::task::TaskResult;
use log::{error, info};

use wom_rs::models::name::NameChangeStatus;
use wom_rs::Pagination;
use log::info;

#[celery::task]
pub async fn wom_guild_sync() -> TaskResult<()> {
Expand All @@ -14,8 +10,6 @@ pub async fn wom_guild_sync() -> TaskResult<()> {
// name changes for in db and combine after the loop and before remove?

let mongodb = get_mongodb().await;
let wom_client = get_wom_client();
let mut limiter = ApiLimiter::new();

let guilds = mongodb
.guilds
Expand All @@ -28,169 +22,7 @@ pub async fn wom_guild_sync() -> TaskResult<()> {
info!("No wom id found for guild: {:?}", guild.clan_name);
continue;
}
info!("Syncing guild: {:?}", guild.clan_name);
let wom_id = guild.wom_id.unwrap();

let wom_group = limiter
.api_limit_request(
|| async { wom_client.group_client.get_group_details(wom_id).await },
None,
)
.await;
let wom_group_name_changes = limiter
.api_limit_request(
|| async {
wom_client
.group_client
.get_group_name_changes(
wom_id,
Some(Pagination {
offset: None,
limit: Some(50),
}),
)
.await
},
None,
)
.await
.expect("Failed to get group name changes");

if wom_group.is_err() {
continue;
}

let guild_clan_mates = mongodb
.clan_mates
.get_clan_mates_by_guild_id(guild.guild_id)
.await
.expect("Failed to get clan mates");

let wom_group = wom_group.unwrap();
for member in wom_group.memberships.clone() {
//Checks to see if the wom player is in the db list
let player_in_db_check = guild_clan_mates
.iter()
.find(|x| name_compare(&x.player_name, &member.player.username));
let mut player_whose_name_is_changing: Option<&ClanMateModel> = None;

if player_in_db_check.is_some() {
info!("Player found: {:?}", member.player.username);
let mut found_player = player_in_db_check.unwrap().clone();
found_player.wom_player_id = Some(member.player.id as u64);
let update_clan_mate = mongodb.clan_mates.update_clan_mate(found_player).await;
if update_clan_mate.is_err() {
error!("Failed to update clan mate: {:?}", update_clan_mate.err());
}
}

//If wom player is not found in db list
if player_in_db_check.is_none() {
//Checks to see if maybe it was a name change
let name_change = wom_group_name_changes
.iter()
.filter(|name_change| {
name_change.status == NameChangeStatus::Approved
&& name_change.resolved_at.is_some()
&& name_compare(&name_change.new_name, &member.player.username)
})
.max_by(|a, b| {
a.resolved_at
.unwrap()
.cmp(&b.resolved_at.unwrap())
.reverse()
});

//If it is a name change
if let Some(name_change) = name_change {
//Get the db player whose name is changing
player_whose_name_is_changing = guild_clan_mates
.iter()
.find(|x| name_compare(&x.player_name, &name_change.old_name.clone()));

//If the db player is not found
if player_whose_name_is_changing.is_none() {
info!(
"Player not found for name change: {:?}",
name_change.old_name
);
} else {
//If the db player already has the new name
if player_whose_name_is_changing
.unwrap()
.previous_names
.contains(&name_change.new_name.replace(" ", "\u{a0}"))
{
info!("Player already has this name: {:?}", name_change.new_name);
continue;
}
info!(
"Changing name: {:?} to: {:?}",
name_change.old_name, member.player.username
);
let name_change = mongodb
.clan_mates
.change_name(
guild.guild_id,
name_change.old_name.clone(),
member.player.display_name.clone(),
)
.await;

if name_change.is_err() {
error!("Failed to change name: {:?}", name_change.err());
}
}
}
}

//If the player is already in the db list or the name change was successful
if player_whose_name_is_changing.is_some() || player_in_db_check.is_some() {
continue;
}
info!("Creating new clan mate: {:?}", member.player.username);

let create_new_clan_mate = mongodb
.clan_mates
.create_new_clan_mate(
guild.guild_id,
member.player.display_name,
Some(member.player.id as u64),
)
.await;
if create_new_clan_mate.is_err() {
error!(
"Failed to create new clan mate: {:?}",
create_new_clan_mate.err()
);
}
}

//Grabs a new list with fresh entries from name chanegs and new clanmates
let fresh_guild_clan_mates = mongodb
.clan_mates
.get_clan_mates_by_guild_id(guild.guild_id)
.await
.expect("Failed to get clan mates");

//checks for who has left the clan
//CHeck that they still have collection log id for them
for db_member in fresh_guild_clan_mates {
let member = wom_group
.memberships
.iter()
.find(|x| name_compare(&x.player.username, &db_member.player_name));
if member.is_none() {
info!("Removing clan mate: {:?}", db_member.player_name);
let remove_clan_mate = mongodb
.clan_mates
.remove_clan_mate(guild.guild_id, db_member.player_name.clone())
.await;
if remove_clan_mate.is_err() {
error!("Failed to remove clan mate: {:?}", remove_clan_mate.err());
}
}
}
sync_wom_by_guild(&guild, &mongodb).await;
}

Ok(())
Expand Down
Loading

0 comments on commit aea0f51

Please sign in to comment.