From 8cca057344dad34cf9fb661942da8abc93805fbb Mon Sep 17 00:00:00 2001 From: skull132 Date: Wed, 24 May 2017 20:46:07 +0300 Subject: [PATCH] Feature - Rewriting jobbans! (#2114) Current jobban system: Jobbans stored as plain text and require a for loop to go through and search for specific ones. Fiddly as shit, because, again, stored as plain text and not quickly break-up-able. butts No temporary jobbans on the old file system. No centralized API to handle jobbanning. Jobbans have to be ran through separate procs in case of the MySQL system being used. New jobban system: Associated lists to store bans. This allows key based accessing and validation of a ban. Much faster than for-looping twice to compare text. Associated lists saved to the ban file. Pretty good stuff that this works. Temporary jobbans for file system. Bans which are expired are removed right as they're checked. Binding of the MySQL procs with the old jobban API. More centralized design. (Less, "Oh god, I forgot to save this to the DB!") Instant effect on unbans. As opposed to waiting 1 round for it to take effect. Removal of dormant code. --- code/game/antagonist/antagonist_helpers.dm | 2 +- code/modules/admin/DB ban/functions.dm | 57 +- code/modules/admin/NewBan.dm | 2 +- code/modules/admin/admin.dm | 21 +- code/modules/admin/banjob.dm | 820 ++++++++++++++++++--- code/modules/admin/newbanjob.dm | 274 ------- code/modules/admin/topic.dm | 414 +---------- 7 files changed, 804 insertions(+), 786 deletions(-) delete mode 100644 code/modules/admin/newbanjob.dm diff --git a/code/game/antagonist/antagonist_helpers.dm b/code/game/antagonist/antagonist_helpers.dm index 987afa846bc..d6c08f0d126 100644 --- a/code/game/antagonist/antagonist_helpers.dm +++ b/code/game/antagonist/antagonist_helpers.dm @@ -1,7 +1,7 @@ /datum/antagonist/proc/can_become_antag(var/datum/mind/player, var/ignore_role) if (!player.current) return 0 - if(jobban_isbanned(player.current, bantype) || jobban_isbanned(player.current, "Antagonist")) + if(jobban_isbanned(player.current, bantype)) return 0 if(!ignore_role) if(player.assigned_role in restricted_jobs) diff --git a/code/modules/admin/DB ban/functions.dm b/code/modules/admin/DB ban/functions.dm index 6cc5589a24e..f7c327b6cf0 100644 --- a/code/modules/admin/DB ban/functions.dm +++ b/code/modules/admin/DB ban/functions.dm @@ -1,8 +1,16 @@ //Either pass the mob you wish to ban in the 'banned_mob' attribute, or the banckey, banip and bancid variables. If both are passed, the mob takes priority! If a mob is not passed, banckey is the minimum that needs to be passed! banip and bancid are optional. -datum/admins/proc/DB_ban_record(var/bantype, var/mob/banned_mob, var/duration = -1, var/reason, var/job = "", var/rounds = 0, var/banckey = null, var/banip = null, var/bancid = null) +/proc/DB_ban_record(var/bantype, var/mob/banned_mob, var/duration = -1, var/reason, var/job = "", var/rounds = 0, var/banckey = null, var/banip = null, var/bancid = null) + if(!check_rights(R_MOD,0) && !check_rights(R_BAN)) + return - if(!check_rights(R_MOD,0) && !check_rights(R_BAN)) return + var/datum/admins/holder = null + + if (usr) + holder = usr.client ? usr.client.holder : null + + if (!holder) + return establish_db_connection(dbcon) if(!dbcon.IsConnected()) @@ -63,10 +71,14 @@ datum/admins/proc/DB_ban_record(var/bantype, var/mob/banned_mob, var/duration = var/a_computerid var/a_ip - if(src.owner && istype(src.owner, /client)) - a_ckey = src.owner:ckey - a_computerid = src.owner:computer_id - a_ip = src.owner:address + if(holder && holder.owner && istype(holder.owner, /client)) + a_ckey = holder.owner:ckey + a_computerid = holder.owner:computer_id + a_ip = holder.owner:address + else + a_ckey = "Adminbot" + a_computerid = "" + a_ip = world.address var/who for(var/client/C in clients) @@ -90,9 +102,7 @@ datum/admins/proc/DB_ban_record(var/bantype, var/mob/banned_mob, var/duration = usr << "Ban saved to database." message_admins("[key_name_admin(usr)] has added a [bantype_str] for [ckey] [(job)?"([job])":""] [(duration > 0)?"([duration] minutes)":""] with the reason: \"[reason]\" to the ban database.",1) - - -datum/admins/proc/DB_ban_unban(var/ckey, var/bantype, var/job = "") +/proc/DB_ban_unban(var/ckey, var/bantype, var/job = "") if(!check_rights(R_BAN)) return @@ -156,7 +166,7 @@ datum/admins/proc/DB_ban_unban(var/ckey, var/bantype, var/job = "") DB_ban_unban_by_id(ban_id) -datum/admins/proc/DB_ban_edit(var/banid = null, var/param = null) +/proc/DB_ban_edit(var/banid = null, var/param = null) if(!check_rights(R_BAN)) return @@ -216,17 +226,17 @@ datum/admins/proc/DB_ban_edit(var/banid = null, var/param = null) usr << "Cancelled" return -datum/admins/proc/DB_ban_unban_by_id(var/id) +/proc/DB_ban_unban_by_id(var/id) if(!check_rights(R_BAN)) return - var/sql = "SELECT ckey, bantype FROM ss13_ban WHERE id = [id]" + var/sql = "SELECT ckey, bantype, job FROM ss13_ban WHERE id = [id]" establish_db_connection(dbcon) if(!dbcon.IsConnected()) return - var/reason = input("Please specify an unban reason.", "Unban Reason", "Unbanned as per appear.") + var/reason = input("Please specify an unban reason.", "Unban Reason", "Unbanned as per appeal.") if (!reason) usr << "Invalid reason given. Cancelled." return @@ -235,11 +245,13 @@ datum/admins/proc/DB_ban_unban_by_id(var/id) var/pckey var/ban_type + var/job // This is for integrating the static jobban API into this. var/DBQuery/query = dbcon.NewQuery(sql) query.Execute() while(query.NextRow()) pckey = query.item[1] ban_type = query.item[2] + job = query.item[3] ban_number++; if(ban_number == 0) @@ -250,12 +262,17 @@ datum/admins/proc/DB_ban_unban_by_id(var/id) usr << "Database update failed due to multiple bans having the same ID. Contact the database admin." return - if(!src.owner || !istype(src.owner, /client)) - return + var/datum/admins/holder = null - var/unban_ckey = src.owner:ckey - var/unban_computerid = src.owner:computer_id - var/unban_ip = src.owner:address + if (usr) + holder = usr.client ? usr.client.holder : null + + if (!holder) + return + + var/unban_ckey = holder ? holder.owner.ckey : "Adminbot" + var/unban_computerid = holder ? holder.owner.computer_id : "" + var/unban_ip = holder ? holder.owner.address : world.address var/unban_reason = sanitizeSQL(reason) var/sql_update = "UPDATE ss13_ban SET unbanned = 1, unbanned_datetime = Now(), unbanned_ckey = '[unban_ckey]', unbanned_computerid = '[unban_computerid]', unbanned_ip = '[unban_ip]', unbanned_reason = '[unban_reason]' WHERE id = [id]" @@ -266,6 +283,10 @@ datum/admins/proc/DB_ban_unban_by_id(var/id) notes_add_sql(ckey(pckey), "[ban_type] (#[id]) lifted. Reason for unban: [reason].", usr) + // If we're lifting a jobban, update the local array of bans. + if ((ban_type == "JOB_TEMPBAN" || ban_type == "JOB_PERMABAN") && job) + jobban_unban(pckey, job) + /client/proc/DB_ban_panel() set category = "Admin" set name = "Banning Panel" diff --git a/code/modules/admin/NewBan.dm b/code/modules/admin/NewBan.dm index 25b6dcd1c73..3083c6889fc 100644 --- a/code/modules/admin/NewBan.dm +++ b/code/modules/admin/NewBan.dm @@ -140,7 +140,7 @@ var/savefile/Banlist log_admin("[key_name_admin(usr)] unbanned [key]",admin_key=key_name(usr),ckey=key) message_admins("[key_name_admin(usr)] unbanned: [key]") feedback_inc("ban_unban",1) - usr.client.holder.DB_ban_unban( ckey(key), BANTYPE_ANY_FULLBAN) + DB_ban_unban( ckey(key), BANTYPE_ANY_FULLBAN) for (var/A in Banlist.dir) Banlist.cd = "/base/[A]" if (key == Banlist["key"] /*|| id == Banlist["id"]*/) diff --git a/code/modules/admin/admin.dm b/code/modules/admin/admin.dm index 3d03bc6219f..9accb22e8c0 100644 --- a/code/modules/admin/admin.dm +++ b/code/modules/admin/admin.dm @@ -63,7 +63,7 @@ proc/admin_notice(var/message, var/rights) Warn | Warnings | Ban | - Jobban | + Jobban | Notes "} @@ -575,14 +575,19 @@ proc/admin_notice(var/message, var/rights) /datum/admins/proc/Jobbans() - if(!check_rights(R_BAN)) return + if(!check_rights(R_BAN)) + return + + // RIP whoever uses this panel. It's going to be amazingly painful! + var/dat = "Job Bans!
" + dat += "Search via ckey
" + dat += "" + for (var/ckey in jobban_keylist) + for (var/job in jobban_keylist[ckey]) + var/list/ban = jobban_keylist[ckey][job] + if (!jobban_isexpired(ban, null, job, ckey)) + dat += "" - var/dat = "Job Bans!
[ckey] - [ban[2]] - (unban)
" - for(var/t in jobban_keylist) - var/r = t - if( findtext(r,"##") ) - r = copytext( r, 1, findtext(r,"##") )//removes the description - dat += text("") dat += "
[t] (unban)
" usr << browse(dat, "window=ban;size=400x400") diff --git a/code/modules/admin/banjob.dm b/code/modules/admin/banjob.dm index 7097d74968d..575a65ab4e1 100644 --- a/code/modules/admin/banjob.dm +++ b/code/modules/admin/banjob.dm @@ -1,26 +1,122 @@ -//This file was auto-corrected by findeclaration.exe on 25.5.2012 20:42:32 +#define CKEY_OR_MOB(tgt, ref) \ + if (istext(ref)) { \ + tgt = ckey(ref); \ + var/mob/CKM = locate(ref); \ + if (CKM && istype(CKM)) { \ + if (CKM.ckey) { \ + tgt = CKM.ckey; \ + } else { \ + tgt = null; \ + } \ + } \ + } else if (ismob(ref)) { \ + var/mob/CKM = ref; \ + tgt = CKM.ckey; \ + } -var/jobban_runonce // Updates legacy bans with new info -var/jobban_keylist[0] //to store the keys & ranks +var/list/jobban_keylist = list() // Global jobban list. -/proc/jobban_fullban(mob/M, rank, reason) - if (!M || !M.key) return - jobban_keylist.Add(text("[M.ckey] - [rank] ## [reason]")) - jobban_savebanfile() +/* + * Expected format: + * list("canonckey1" = list("jobname" = list("reason", time), + * "jobname2" = list("reason", time)), + * "canonckey2" = list("jobname" = list("reason", time))) + * + * And yes, this is all actually savefile compatible, as they can load and + * save associated lists quite neatly. Assoc lists remove the stupid amounts + * of for-looping and string searching, and allow you to simply grab a ban with: + * + * jobban_keylist[ckey][job] + * + * If record doesn't exist, he's not banned there. As easy as that. + * + * "time" should be BYOND realtime. For MySQL bans, it's not relevant, so we + * can get away with just using this. For permanent bans, leave 0. + * + * - Skull132, 17APR2017 + */ -/proc/jobban_client_fullban(ckey, rank) - if (!ckey || !rank) return - jobban_keylist.Add(text("[ckey] - [rank]")) - jobban_savebanfile() +/** + * Global hook for loading jobbans. + * + * @return num 1 + */ +/hook/startup/proc/loadJobBans() + if (config.ban_legacy_system) + jobban_loadbanfile() + else + jobban_loaddatabase() -//returns a reason if M is banned from rank, returns 0 otherwise -/proc/jobban_isbanned(mob/M, rank) - if(M && rank) + testing("Database: [json_encode(jobban_keylist)]") + return 1 + +/** + * Logs a new jobban for a user. + * Will save the bans to a save file if we're using the legacy system. Otherwise, + * should be called via DB_ban_record. + * + * @param str|mob player The mob object or ckey of the player we're looking for. + * @param str rank The string name of the rank we want to ban the user from. + * @param str reason The reason for the ban. + * @param num minutes The length of the ban in minutes. -1 for permanent. + * @param datum/admins holder The holder of the admin doing the unbanning. + * required to access the DB ban procs. + */ +/proc/jobban_fullban(player, rank, reason, minutes) + var/key = null + + CKEY_OR_MOB(key, player) + + if (!key) + return + + // Create a new record if the client isn't logged already. + if (!jobban_keylist[key]) + jobban_keylist[key] = list() + + // Sanity catch. This shouldn't happen, but better safe than sorry. + if (jobban_keylist[key][rank] && !jobban_isexpired(jobban_keylist[key][rank], player, rank)) + log_and_message_admins("Attempted to apply a jobban to [key] while they already have an active ban. Job: [rank].") + return + + // Set the expirey time in case of temp bans. + var/unban_time = minutes + if (minutes > -1) + unban_time = world.realtime + (minutes MINUTES) + + // Create the entry. + jobban_keylist[key][rank] = list(reason, unban_time) + + // Log the ban to the appropriate place. + if (config.ban_legacy_system) + jobban_savebanfile() + else + DB_ban_record(minutes < 0 ? BANTYPE_JOB_PERMA : BANTYPE_JOB_TEMP, null, minutes, reason, rank, banckey = key) + +/** + * Checks if the player attached to the given mob M is banned from + * the given rank. Returns 0 if client is not banned, a reason (str) + * if is banned. + * + * If an antagonist role is sent, then the global "Antagonist" ban rank + * is also checked for. + * + * @param str|mob player The mob object or ckey of the player we're looking for. + * @param str rank The rank name that we're looking for a ban on. + * + * @return mixed str containing the ban reason if user is banned. + * null if user is not banned from given role. + */ +/proc/jobban_isbanned(player, rank) + var/ckey = null + CKEY_OR_MOB(ckey, player) + + if (ckey) if (guest_jobbans(rank)) - if(config.guest_jobban && IsGuestKey(M.key)) + if (config.guest_jobban && IsGuestKey(ckey)) return "Guest Job-ban" - if(config.usewhitelist && !check_whitelist(M)) - return "Whitelisted Job" + if (config.usewhitelist && ismob(player) && !check_whitelist(player)) + return "No Whitelist" var/static/list/antag_bantypes @@ -29,7 +125,7 @@ var/jobban_keylist[0] //to store the keys & ranks for (var/antag_type in all_antag_types) var/datum/antagonist/antag = all_antag_types[antag_type] if (antag && antag.bantype) - antag_bantypes |= "[antag.bantype]" + antag_bantypes |= antag.bantype // We manage antagonist bans at this end point. // Alternative is to manage it at each call to jobban_isbanned, however, @@ -38,89 +134,645 @@ var/jobban_keylist[0] //to store the keys & ranks if (rank in antag_bantypes) antag_ban = TRUE - for (var/s in jobban_keylist) - if(findtext(s,"[M.ckey] - [rank]") == 1 || (antag_ban && findtext(s, "[M.ckey] - Antagonist") == 1)) - var/startpos = findtext(s, "## ")+3 - if(startpos && startpos> jobban_keylist - log_admin("Loading jobban_rank") - S["runonce"] >> jobban_runonce + var/savefile/S = new("data/job_full.ban") + S["bans"] >> jobban_keylist + log_admin("Loading jobban_rank") - if (!length(jobban_keylist)) - jobban_keylist=list() - log_admin("jobban_keylist was empty") - else - if(!establish_db_connection(dbcon)) - error("Database connection failed. Reverting to the legacy ban system.") - log_misc("Database connection failed. Reverting to the legacy ban system.") - config.ban_legacy_system = 1 - jobban_loadbanfile() - return + if (!jobban_keylist) + jobban_keylist = list() + log_admin("jobban_keylist was empty") - //Job permabans - var/DBQuery/query = dbcon.NewQuery("SELECT ckey, job FROM ss13_ban WHERE bantype = 'JOB_PERMABAN' AND isnull(unbanned)") - query.Execute() +/** + * Loads all currently active bans from the database. Sets expiration + * times to 0, as the query refreshes records every time it's pulled. + * Unlike the hard file bans. + */ +/proc/jobban_loaddatabase() + // No database. Weee. + if (!establish_db_connection(dbcon)) + error("Database connection failed. Reverting to the legacy ban system.") + log_misc("Database connection failed. Reverting to the legacy ban system.") + config.ban_legacy_system = 1 + jobban_loadbanfile() + return - while(query.NextRow()) - var/ckey = query.item[1] - var/job = query.item[2] + // All jobbans in one query. Because we don't actually care. + var/DBQuery/query = dbcon.NewQuery("SELECT id, ckey, job, reason FROM ss13_ban WHERE isnull(unbanned) AND ((bantype = 'JOB_PERMABAN') OR (bantype = 'JOB_TEMPBAN' AND expiration_time > Now()))") + query.Execute() - jobban_keylist.Add("[ckey] - [job]") + while (query.NextRow()) + var/ckey = ckey(query.item[2]) + var/job = query.item[3] + var/reason = query.item[4] - //Job tempbans - var/DBQuery/query1 = dbcon.NewQuery("SELECT ckey, job FROM ss13_ban WHERE bantype = 'JOB_TEMPBAN' AND isnull(unbanned) AND expiration_time > Now()") - query1.Execute() + if (!jobban_keylist[ckey]) + jobban_keylist[ckey] = list() - while(query1.NextRow()) - var/ckey = query1.item[1] - var/job = query1.item[2] - - jobban_keylist.Add("[ckey] - [job]") + if (!jobban_keylist[ckey][job]) + // Insert it with 0 time because the expiration of a temp jobban for + // MySQL is dependent on the database and query itself. So we can just + // politely not care. + jobban_keylist[ckey][job] = list(reason, -1) + else + // Woups. What happened here...? + log_and_message_admins("JOBBANS: Duplicate jobban entry in MySQL for [ckey]. Ban ID: #[query.item[1]]") +/** + * Saves the current bans into the data/job_full.ban file. + */ /proc/jobban_savebanfile() - var/savefile/S=new("data/job_full.ban") - S["keys[0]"] << jobban_keylist + var/savefile/S = new("data/job_full.ban") + S["bans"] << jobban_keylist -/proc/jobban_unban(mob/M, rank) - jobban_remove("[M.ckey] - [rank]") - jobban_savebanfile() +/** + * Removes a jobban entry from the code and calls the config appropriate + * record removal method. In case of legacy bans, jobban file is updated. + * + * For the DB system, the DB_ban_unban_by_id method calls this to remove the local + * instance of the ban. + * + * @param str|mob player The mob object or ckey of the player we're looking for. + * @param str rank The job from which we want to unban the given player. + */ +/proc/jobban_unban(player, rank) + var/ckey = null + CKEY_OR_MOB(ckey, player) + if (!ckey) + log_debug("JOBBAN: jobban_unban called without a mob and a backup ckey.") + return + + // Check for a player record. + var/list/entry = jobban_keylist[ckey] + if (entry) + // Find the specific ban. + var/list/ban = entry[rank] + if (ban) + // Remove said ban. Lists pass by ref, so this is fine. + entry[rank] = null + entry -= rank + + // If the entry is now empty, remove the entire ckey from the list. + if (!entry.len) + jobban_keylist[ckey] = null + jobban_keylist -= ckey + + // Update appropriate ban files. + if (config.ban_legacy_system) + jobban_savebanfile() + +/** + * Checks whether or not a jobban is expired. If a ban is expired, + * it'll call jobban_unban to lift the ban. This allows for temporary + * jobbans with the old file system. + * + * Does not work on the MySQL system. The bans for that refresh every + * round, as per the queries. + * + * @param list tuple The list containing reason and expiery time to check. + * @param str|mob player The mob object or ckey of the player we're looking for. + * @param str rank The job we're checking. To be passed into jobban_unban in case + * of an expired ban. + * + * @return num TRUE if ban is expired. + * FALSE if ban is not expired. + */ +/proc/jobban_isexpired(var/list/tuple, var/player, var/rank) + if (config.ban_legacy_system && tuple[2] && (tuple[2] > 0) && (tuple[2] < world.realtime)) + // It's expired. Remove it. + jobban_unban(player, rank) + + return TRUE + + return FALSE + +/** + * Updates the ban_unban_log.txt file by appending formatted_log to its + * contents. + * + * @param str formatted_log The new content to be appended to the log file. + */ /proc/ban_unban_log_save(var/formatted_log) - text2file(formatted_log,"data/ban_unban_log.txt") + text2file(formatted_log, "data/ban_unban_log.txt") +/** + * Opens the jobban panel, showing the bans of the passed mob or ckey. + * + * @param str|mob tgt_ref The target we want to view jobbans of. Can be a reference + * to a mob object (gotten with \ref[M]) or an actual mob object. + */ +/datum/admins/proc/jobban_panel(var/tgt_ref = null) + if (!tgt_ref) + return -/proc/jobban_remove(X) - for (var/i = 1; i <= length(jobban_keylist); i++) - if( findtext(jobban_keylist[i], "[X]") ) - jobban_keylist.Remove(jobban_keylist[i]) - jobban_savebanfile() - return 1 - return 0 + // Check against usr's perms. + if (!check_rights(R_ADMIN|R_MOD|R_BAN)) + return + + var/ckey = null + CKEY_OR_MOB(ckey, tgt_ref) + + if (!ckey) + to_chat(src.owner, "This mob has no ckey.") + return + + var/dat = "" + var/header = "Job-Ban Panel: [ckey]" + var/body + var/jobs = "" + + /***********************************WARNING!************************************ + The jobban stuff looks mangled and disgusting + But it looks beautiful in-game + -Nodrak + ************************************WARNING!***********************************/ + var/counter = 0 + //Regular jobs + //Command (Blue) + jobs += "" + jobs += "" + for (var/jobPos in command_positions) + if (!jobPos) + continue + var/datum/job/job = SSjobs.GetJob(jobPos) + if (!job) + continue + + if (jobban_isbanned(ckey, job.title)) + jobs += "" + counter++ + else + jobs += "" + counter++ + + if (counter >= 6) //So things dont get squiiiiished! + jobs += "" + counter = 0 + jobs += "
Command Positions
[replacetext(job.title, " ", " ")][replacetext(job.title, " ", " ")]
" + + //Security (Red) + counter = 0 + jobs += "" + jobs += "" + for (var/jobPos in security_positions) + if (!jobPos) + continue + var/datum/job/job = SSjobs.GetJob(jobPos) + if (!job) + continue + + if (jobban_isbanned(ckey, job.title)) + jobs += "" + counter++ + else + jobs += "" + counter++ + + if (counter >= 5) //So things dont get squiiiiished! + jobs += "" + counter = 0 + jobs += "
Security Positions
[replacetext(job.title, " ", " ")][replacetext(job.title, " ", " ")]
" + + //Engineering (Yellow) + counter = 0 + jobs += "" + jobs += "" + for (var/jobPos in engineering_positions) + if (!jobPos) + continue + var/datum/job/job = SSjobs.GetJob(jobPos) + if (!job) + continue + + if (jobban_isbanned(ckey, job.title)) + jobs += "" + counter++ + else + jobs += "" + counter++ + + if (counter >= 5) //So things dont get squiiiiished! + jobs += "" + counter = 0 + jobs += "
Engineering Positions
[replacetext(job.title, " ", " ")][replacetext(job.title, " ", " ")]
" + + //Medical (White) + counter = 0 + jobs += "" + jobs += "" + for (var/jobPos in medical_positions) + if (!jobPos) + continue + var/datum/job/job = SSjobs.GetJob(jobPos) + if (!job) + continue + + if (jobban_isbanned(ckey, job.title)) + jobs += "" + counter++ + else + jobs += "" + counter++ + + if (counter >= 5) //So things dont get squiiiiished! + jobs += "" + counter = 0 + jobs += "
Medical Positions
[replacetext(job.title, " ", " ")][replacetext(job.title, " ", " ")]
" + + //Science (Purple) + counter = 0 + jobs += "" + jobs += "" + for (var/jobPos in science_positions) + if (!jobPos) + continue + var/datum/job/job = SSjobs.GetJob(jobPos) + if (!job) + continue + + if (jobban_isbanned(ckey, job.title)) + jobs += "" + counter++ + else + jobs += "" + counter++ + + if (counter >= 5) //So things dont get squiiiiished! + jobs += "" + counter = 0 + jobs += "
Science Positions
[replacetext(job.title, " ", " ")][replacetext(job.title, " ", " ")]
" + + //Cargo (Brown ish) + counter = 0 + jobs += "" + jobs += "" + for (var/jobPos in cargo_positions) + if (!jobPos) + continue + var/datum/job/job = SSjobs.GetJob(jobPos) + if (!job) + continue + + if (jobban_isbanned(ckey, job.title)) + jobs += "" + counter++ + else + jobs += "" + counter++ + + if (counter >= 5) + jobs += "" + counter = 0 + + //Civilian (Grey) + counter = 0 + jobs += "
Cargo Positions
[replacetext(job.title, " ", " ")][replacetext(job.title, " ", " ")]
" + jobs += "" + for (var/jobPos in civilian_positions) + if (!jobPos) + continue + var/datum/job/job = SSjobs.GetJob(jobPos) + if (!job) + continue + + if (jobban_isbanned(ckey, job.title)) + jobs += "" + counter++ + else + jobs += "" + counter++ + + if (counter >= 5) //So things dont get squiiiiished! + jobs += "" + counter = 0 + + if (jobban_isbanned(ckey, "Internal Affairs Agent")) + jobs += "" + else + jobs += "" + + jobs += "
Civilian Positions
[replacetext(job.title, " ", " ")][replacetext(job.title, " ", " ")]
Internal Affairs AgentInternal Affairs Agent
" + + //Non-Human (Green) + counter = 0 + jobs += "" + jobs += "" + for (var/jobPos in nonhuman_positions) + if (!jobPos) + continue + var/datum/job/job = SSjobs.GetJob(jobPos) + if (!job) + continue + + if (jobban_isbanned(ckey, job.title)) + jobs += "" + counter++ + else + jobs += "" + counter++ + + if (counter >= 5) //So things dont get squiiiiished! + jobs += "" + counter = 0 + + //pAI isn't technically a job, but it goes in here. + + if (jobban_isbanned(ckey, "pAI")) + jobs += "" + else + jobs += "" + if (jobban_isbanned(ckey, "AntagHUD")) + jobs += "" + else + jobs += "" + jobs += "
Non-human Positions
[replacetext(job.title, " ", " ")][replacetext(job.title, " ", " ")]
pAIpAIAntagHUDAntagHUD
" + + //Antagonist (Orange) + var/isbanned_dept = jobban_isbanned(ckey, "Antagonist") + jobs += "" + jobs += "" + + // Antagonists. + counter = 0 + for (var/antag_type in all_antag_types) + var/datum/antagonist/antag = all_antag_types[antag_type] + if (!antag || !antag.bantype) + continue + if (isbanned_dept || jobban_isbanned(ckey, antag.bantype)) + jobs += "" + else + jobs += "" + + counter++ + + if (counter >= 5) //So things dont get squiiiiished! + jobs += "" + counter = 0 + + jobs += "
Antagonist Positions
[replacetext("[antag.role_text]", " ", " ")][replacetext("[antag.role_text]", " ", " ")]
" + + //Other races (BLUE, because I have no idea what other color to make this) + jobs += "" + jobs += "" + + if (jobban_isbanned(ckey, "Dionaea")) + jobs += "" + else + jobs += "" + jobs += "
Other Races
DionaeaDionaea
" + body = "[jobs]" + dat = "[header][body]" + usr << browse(dat, "window=jobban_panel;size=800x490") + return + +/** + * Handles the insertion of a new job ban. Currently called from /datum/admins/Topic(). + * + * Relays a new ban to jobban_fullban and also manages database insertions where needed. + * + * @param str tgt_ref The \ref[] of the target mob we want to dinbannu. + * @param str job The name of the job we want to ban the target from. + * + * @return num 1 if something was done. + * 0 otherwise. + */ +/datum/admins/proc/jobban_handle(var/tgt_ref, var/job) + if (!check_rights(R_MOD, 0) && !check_rights(R_ADMIN, 0)) + to_chat(usr, "You do not have the appropriate permissions to add job bans!") + return 0 + + if (check_rights(R_MOD, 0) && !check_rights(R_ADMIN, 0) && !config.mods_can_job_tempban) // If mod and tempban disabled + to_chat(usr, "Mod jobbanning is disabled!") + return 0 + + var/ckey = null + CKEY_OR_MOB(ckey, tgt_ref) + + if (!ckey) + to_chat(usr, "No valid target sent. Cancelling.") + return 0 + + if (admin_datums[ckey]) + if (ckey != usr.ckey) //we can jobban ourselves + var/datum/admins/other_holder = admin_datums[ckey] + if(other_holder && (other_holder.rights & R_BAN)) //they can ban too. So we can't ban them + alert("You cannot perform this action. You must be of a higher administrative rank!") + return 0 + + //get jobs for department if specified, otherwise just returnt he one job in a list. + var/list/joblist = list() + switch (job) + if ("commanddept") + for (var/jobPos in command_positions) + if (!jobPos) + continue + var/datum/job/temp = SSjobs.GetJob(jobPos) + if (!temp) + continue + joblist += temp.title + if ("securitydept") + for (var/jobPos in security_positions) + if (!jobPos) + continue + var/datum/job/temp = SSjobs.GetJob(jobPos) + if (!temp) + continue + joblist += temp.title + if ("engineeringdept") + for (var/jobPos in engineering_positions) + if (!jobPos) + continue + var/datum/job/temp = SSjobs.GetJob(jobPos) + if (!temp) + continue + joblist += temp.title + if ("medicaldept") + for (var/jobPos in medical_positions) + if (!jobPos) + continue + var/datum/job/temp = SSjobs.GetJob(jobPos) + if (!temp) + continue + joblist += temp.title + if ("sciencedept") + for (var/jobPos in science_positions) + if (!jobPos) + continue + var/datum/job/temp = SSjobs.GetJob(jobPos) + if (!temp) + continue + joblist += temp.title + if ("civiliandept") + for (var/jobPos in civilian_positions) + if (!jobPos) + continue + var/datum/job/temp = SSjobs.GetJob(jobPos) + if (!temp) + continue + joblist += temp.title + if ("nonhumandept") + joblist += "pAI" + for (var/jobPos in nonhuman_positions) + if (!jobPos) + continue + var/datum/job/temp = SSjobs.GetJob(jobPos) + if (!temp) + continue + joblist += temp.title + if ("cargodept") + for (var/jobPos in cargo_positions) + if (!jobPos) + continue + var/datum/job/temp = SSjobs.GetJob(jobPos) + if (!temp) + continue + joblist += temp.title + else + joblist += job + + //Create a list of unbanned jobs within joblist + var/list/notbannedlist = list() + for (var/R in joblist) + if (!jobban_isbanned(ckey, R)) + notbannedlist += R + + //Banning comes first + if (notbannedlist.len) //at least 1 unbanned job exists in joblist so we have stuff to ban. + switch (alert("Temporary Ban?",,"Yes","No", "Cancel")) + if ("Yes") + if (!check_rights(R_MOD,0) && !check_rights(R_BAN, 0)) + to_chat(usr, "You Cannot issue temporary job-bans!") + return 0 + var/mins = input(usr, "How long (in minutes)?", "Ban time", 1440) as num|null + if (!mins) + return 0 + if (check_rights(R_MOD, 0) && !check_rights(R_BAN, 0) && mins > config.mod_job_tempban_max) + to_chat(usr, "Moderators can only job tempban up to [config.mod_job_tempban_max] minutes!") + return 0 + var/reason = sanitize(input(usr,"Reason?","Please State Reason","") as text|null) + if (!reason) + return 0 + + var/msg + for (var/R in notbannedlist) + ban_unban_log_save("[key_name(usr)] temp-jobbanned [ckey] from [R] for [mins] minutes. reason: [reason]") + log_admin("[key_name(usr)] temp-jobbanned [ckey] from [R] for [mins] minutes",admin_key=key_name(usr)) + feedback_inc("ban_job_tmp", 1) + feedback_add_details("ban_job_tmp","- [R]") + jobban_fullban(ckey, R, reason, mins) + + if (!msg) + msg = R + else + msg += ", [R]" + if (config.ban_legacy_system) + notes_add(ckey, "Banned from [msg] - [reason]", usr) + else + notes_add_sql(ckey, "Banned from [msg] - [reason]", usr) + message_admins("[key_name_admin(usr)] banned [ckey] from [msg] for [mins] minutes.", 1) + if (ismob(tgt_ref)) + var/mob/M = tgt_ref + to_chat(M, "You have been jobbanned by [usr.client.ckey] from: [msg].") + to_chat(M, "The reason is: [reason]") + to_chat(M, "This jobban will be lifted in [mins] minutes.") + jobban_panel(ckey) + return 1 + if ("No") + if (!check_rights(R_BAN)) + return + var/reason = sanitize(input(usr,"Reason?","Please State Reason","") as text|null) + if (reason) + var/msg + for (var/R in notbannedlist) + ban_unban_log_save("[key_name(usr)] perma-jobbanned [ckey] from [R]. reason: [reason]") + log_admin("[key_name(usr)] perma-banned [ckey] from [R]",admin_key=key_name(usr)) + feedback_inc("ban_job", 1) + feedback_add_details("ban_job", "- [R]") + jobban_fullban(ckey, R, reason, -1) + if (!msg) + msg = R + else + msg += ", [R]" + + if (config.ban_legacy_system) + notes_add(ckey, "Banned from [msg] - [reason]", usr) + else + notes_add_sql(ckey, "Banned from [msg] - [reason]", usr) + message_admins("[key_name_admin(usr)] banned [ckey] from [msg]", 1) + if (ismob(tgt_ref)) + var/mob/M = tgt_ref + to_chat(M, "You have been jobbanned by [usr.client.ckey] from: [msg].") + to_chat(M, "The reason is: [reason]") + to_chat(M, "Jobban can be lifted only upon request.") + jobban_panel(ckey) + return 1 + if("Cancel") + return + + //Unbanning joblist + //all jobs in joblist are banned already OR we didn't give a reason (implying they shouldn't be banned) + if (joblist.len) //at least 1 banned job exists in joblist so we have stuff to unban. + if (!config.ban_legacy_system) + // This is important. jobban_unban() can't actually lift DB bans. So the DB unban + // panel must be used instead. + to_chat(usr, "Unfortunately, database based unbanning cannot be done through this panel") + DB_ban_panel(ckey) + return 0 + + var/msg + for (var/R in joblist) + var/reason = jobban_isbanned(ckey, R) + if (!reason) + continue //skip if it isn't jobbanned anyway + switch (alert("Job: '[R]' Reason: '[reason]' Un-jobban?","Please Confirm","Yes","No")) + if ("Yes") + ban_unban_log_save("[key_name(usr)] unjobbanned [ckey] from [R]") + log_admin("[key_name(usr)] unbanned [ckey] from [R]",admin_key=key_name(usr),ckey=ckey) + jobban_unban(ckey, R) // Refer to the jobban API. + feedback_inc("ban_job_unban",1) + feedback_add_details("ban_job_unban","- [R]") + if (!msg) + msg = R + else + msg += ", [R]" + else + continue + if (msg) + message_admins("[key_name_admin(usr)] unbanned [ckey] from [msg]", 1) + if (ismob(tgt_ref)) + var/mob/M = tgt_ref + to_chat(M, "You have been un-jobbanned by [usr.client.ckey] from [msg].") + jobban_panel(ckey) + return 1 + return 0 //we didn't do anything! + +#undef CKEY_OR_MOB diff --git a/code/modules/admin/newbanjob.dm b/code/modules/admin/newbanjob.dm deleted file mode 100644 index 3d537b87bea..00000000000 --- a/code/modules/admin/newbanjob.dm +++ /dev/null @@ -1,274 +0,0 @@ -var/savefile/Banlistjob - - -/proc/_jobban_isbanned(var/client/clientvar, var/rank) - if(!clientvar) return 1 - ClearTempbansjob() - var/id = clientvar.computer_id - var/key = clientvar.ckey - if (guest_jobbans(rank)) - if(config.guest_jobban && IsGuestKey(key)) - return 1 - Banlistjob.cd = "/base" - if (Banlistjob.dir.Find("[key][id][rank]")) - return 1 - - Banlistjob.cd = "/base" - for (var/A in Banlistjob.dir) - Banlistjob.cd = "/base/[A]" - if ((id == Banlistjob["id"] || key == Banlistjob["key"]) && rank == Banlistjob["rank"]) - return 1 - return 0 - -/proc/LoadBansjob() - - Banlistjob = new("data/job_fullnew.bdb") - log_admin("Loading Banlistjob") - - if (!length(Banlistjob.dir)) log_admin("Banlistjob is empty.") - - if (!Banlistjob.dir.Find("base")) - log_admin("Banlistjob missing base dir.") - Banlistjob.dir.Add("base") - Banlistjob.cd = "/base" - else if (Banlistjob.dir.Find("base")) - Banlistjob.cd = "/base" - - ClearTempbansjob() - return 1 - -/proc/ClearTempbansjob() - UpdateTime() - - Banlistjob.cd = "/base" - for (var/A in Banlistjob.dir) - Banlistjob.cd = "/base/[A]" - //if (!Banlistjob["key"] || !Banlistjob["id"]) - // RemoveBanjob(A, "full") - // log_admin("Invalid Ban.") - // message_admins("Invalid Ban.") - // continue - - if (!Banlistjob["temp"]) continue - if (CMinutes >= Banlistjob["minutes"]) RemoveBanjob(A) - - return 1 - - -/proc/AddBanjob(ckey, computerid, reason, bannedby, temp, minutes, rank) - UpdateTime() - var/bantimestamp - if (temp) - UpdateTime() - bantimestamp = CMinutes + minutes - if(rank == "Heads") - AddBanjob(ckey, computerid, reason, bannedby, temp, minutes, "Head of Personnel") - AddBanjob(ckey, computerid, reason, bannedby, temp, minutes, "Captain") - AddBanjob(ckey, computerid, reason, bannedby, temp, minutes, "Head of Security") - AddBanjob(ckey, computerid, reason, bannedby, temp, minutes, "Chief Engineer") - AddBanjob(ckey, computerid, reason, bannedby, temp, minutes, "Research Director") - AddBanjob(ckey, computerid, reason, bannedby, temp, minutes, "Chief Medical Officer") - return 1 - if(rank == "Security") - AddBanjob(ckey, computerid, reason, bannedby, temp, minutes, "Head of Security") - AddBanjob(ckey, computerid, reason, bannedby, temp, minutes, "Warden") - AddBanjob(ckey, computerid, reason, bannedby, temp, minutes, "Detective") - AddBanjob(ckey, computerid, reason, bannedby, temp, minutes, "Security Officer") - AddBanjob(ckey, computerid, reason, bannedby, temp, minutes, "Cyborg") - return 1 - if(rank == "Engineering") - AddBanjob(ckey, computerid, reason, bannedby, temp, minutes, "Station Engineer") - AddBanjob(ckey, computerid, reason, bannedby, temp, minutes, "Atmospheric Technician") - AddBanjob(ckey, computerid, reason, bannedby, temp, minutes, "Chief Engineer") - AddBanjob(ckey, computerid, reason, bannedby, temp, minutes, "Cyborg") - return 1 - if(rank == "Research") - AddBanjob(ckey, computerid, reason, bannedby, temp, minutes, "Scientist") - AddBanjob(ckey, computerid, reason, bannedby, temp, minutes, "Geneticist") - AddBanjob(ckey, computerid, reason, bannedby, temp, minutes, "Chief Medical Officer") - AddBanjob(ckey, computerid, reason, bannedby, temp, minutes, "Research Director") - return 1 - if(rank == "Medical") - AddBanjob(ckey, computerid, reason, bannedby, temp, minutes, "Geneticist") - AddBanjob(ckey, computerid, reason, bannedby, temp, minutes, "Medical Doctor") - AddBanjob(ckey, computerid, reason, bannedby, temp, minutes, "Chief Medical Officer") - AddBanjob(ckey, computerid, reason, bannedby, temp, minutes, "Chemist") - AddBanjob(ckey, computerid, reason, bannedby, temp, minutes, "Cyborg") - return 1 - if(rank == "CE_Station_Engineer") - AddBanjob(ckey, computerid, reason, bannedby, temp, minutes, "Station Engineer") - AddBanjob(ckey, computerid, reason, bannedby, temp, minutes, "Chief Engineer") - return 1 - if(rank == "CE_Atmospheric_Tech") - AddBanjob(ckey, computerid, reason, bannedby, temp, minutes, "Atmospheric Technician") - AddBanjob(ckey, computerid, reason, bannedby, temp, minutes, "Chief Engineer") - return 1 - if(rank == "CE_Shaft_Miner") - AddBanjob(ckey, computerid, reason, bannedby, temp, minutes, "Shaft Miner") - AddBanjob(ckey, computerid, reason, bannedby, temp, minutes, "Chief Engineer") - return 1 - if(rank == "Chemist_RD_CMO") - AddBanjob(ckey, computerid, reason, bannedby, temp, minutes, "Chief Medical Officer") - AddBanjob(ckey, computerid, reason, bannedby, temp, minutes, "Research Director") - AddBanjob(ckey, computerid, reason, bannedby, temp, minutes, "Chemist") - return 1 - if(rank == "Geneticist_RD_CMO") - AddBanjob(ckey, computerid, reason, bannedby, temp, minutes, "Chief Medical Officer") - AddBanjob(ckey, computerid, reason, bannedby, temp, minutes, "Research Director") - AddBanjob(ckey, computerid, reason, bannedby, temp, minutes, "Geneticist") - return 1 - if(rank == "MD_CMO") - AddBanjob(ckey, computerid, reason, bannedby, temp, minutes, "Chief Medical Officer") - AddBanjob(ckey, computerid, reason, bannedby, temp, minutes, "Medical Doctor") - return 1 - if(rank == "Scientist_RD") - AddBanjob(ckey, computerid, reason, bannedby, temp, minutes, "Research Director") - AddBanjob(ckey, computerid, reason, bannedby, temp, minutes, "Scientist") - return 1 - if(rank == "AI_Cyborg") - AddBanjob(ckey, computerid, reason, bannedby, temp, minutes, "Cyborg") - AddBanjob(ckey, computerid, reason, bannedby, temp, minutes, "AI") - return 1 - if(rank == "Detective_HoS") - AddBanjob(ckey, computerid, reason, bannedby, temp, minutes, "Detective") - AddBanjob(ckey, computerid, reason, bannedby, temp, minutes, "Head of Security") - return 1 - if(rank == "Virologist_RD_CMO") - AddBanjob(ckey, computerid, reason, bannedby, temp, minutes, "Chief Medical Officer") - AddBanjob(ckey, computerid, reason, bannedby, temp, minutes, "Research Director") - AddBanjob(ckey, computerid, reason, bannedby, temp, minutes, "Virologist") - return 1 - - Banlistjob.cd = "/base" - if ( Banlistjob.dir.Find("[ckey][computerid][rank]") ) - usr << text("Banjob already exists.") - return 0 - else - Banlistjob.dir.Add("[ckey][computerid][rank]") - Banlistjob.cd = "/base/[ckey][computerid][rank]" - Banlistjob["key"] << ckey - Banlistjob["id"] << computerid - Banlistjob["rank"] << rank - Banlistjob["reason"] << reason - Banlistjob["bannedby"] << bannedby - Banlistjob["temp"] << temp - if (temp) - Banlistjob["minutes"] << bantimestamp - - return 1 - -/proc/RemoveBanjob(foldername) - var/key - var/id - var/rank - Banlistjob.cd = "/base/[foldername]" - Banlistjob["key"] >> key - Banlistjob["id"] >> id - Banlistjob["rank"] >> rank - Banlistjob.cd = "/base" - - if (!Banlistjob.dir.Remove(foldername)) return 0 - - if(!usr) - log_admin("Banjob Expired: [key]",ckey=key) - message_admins("Banjob Expired: [key]") - else - log_admin("[key_name_admin(usr)] unjobbanned [key] from [rank]",admin_key=key_name(usr),ckey=key) - message_admins("[key_name_admin(usr)] unjobbanned:[key] from [rank]") - ban_unban_log_save("[key_name_admin(usr)] unjobbanned [key] from [rank]") - feedback_inc("ban_job_unban",1) - feedback_add_details("ban_job_unban","- [rank]") - - for (var/A in Banlistjob.dir) - Banlistjob.cd = "/base/[A]" - if ((key == Banlistjob["key"] || id == Banlistjob["id"]) && (rank == Banlistjob["rank"])) - Banlistjob.cd = "/base" - Banlistjob.dir.Remove(A) - continue - - return 1 - -/proc/GetBanExpjob(minutes as num) - UpdateTime() - var/exp = minutes - CMinutes - if (exp <= 0) - return 0 - else - var/timeleftstring - if (exp >= 1440) //1440 = 1 day in minutes - timeleftstring = "[round(exp / 1440, 0.1)] Days" - else if (exp >= 60) //60 = 1 hour in minutes - timeleftstring = "[round(exp / 60, 0.1)] Hours" - else - timeleftstring = "[exp] Minutes" - return timeleftstring - -/datum/admins/proc/unjobbanpanel() - var/count = 0 - var/dat - //var/dat = "
Unban Player: \blue(U) = Unban , (E) = Edit Ban\green (Total
" - Banlistjob.cd = "/base" - for (var/A in Banlistjob.dir) - count++ - Banlistjob.cd = "/base/[A]" - dat += text("") - - dat += "
(U) Key: [Banlistjob["key"]] Rank: [Banlistjob["rank"]] ([Banlistjob["temp"] ? "[GetBanExpjob(Banlistjob["minutes"]) ? GetBanExpjob(Banlistjob["minutes"]) : "Removal pending" ]" : "Permaban"])(By: [Banlistjob["bannedby"]])(Reason: [Banlistjob["reason"]])
" - dat = "
Bans: (U) = Unban , - ([count] Bans)
[dat]" - usr << browse(dat, "window=unbanp;size=875x400") - -/*/datum/admins/proc/permjobban(ckey, computerid, reason, bannedby, temp, minutes, rank) - if(AddBanjob(ckey, computerid, reason, usr.ckey, 0, 0, job)) - M << "\redYou have been banned from [job] by [usr.client.ckey].\nReason: [reason]." - M << "\red This is a permanent ban." - if(config.banappeals) - M << "\red To try to resolve this matter head to [config.banappeals]" - else - M << "\red No ban appeals URL has been set." - log_admin("[usr.client.ckey] has banned from [job] [ckey].\nReason: [reason]\nThis is a permanent ban.") - message_admins("\blue[usr.client.ckey] has banned from [job] [ckey].\nReason: [reason]\nThis is a permanent ban.") -/datum/admins/proc/timejobban(ckey, computerid, reason, bannedby, temp, minutes, rank) - if(AddBanjob(ckey, computerid, reason, usr.ckey, 1, mins, job)) - M << "\redYou have been jobbanned from [job] by [usr.client.ckey].\nReason: [reason]." - M << "\red This is a temporary ban, it will be removed in [mins] minutes." - if(config.banappeals) - M << "\red To try to resolve this matter head to [config.banappeals]" - else - M << "\red No ban appeals URL has been set." - log_admin("[usr.client.ckey] has jobbanned from [job] [ckey].\nReason: [reason]\nThis will be removed in [mins] minutes.") - message_admins("\blue[usr.client.ckey] has banned from [job] [ckey].\nReason: [reason]\nThis will be removed in [mins] minutes.")*/ -//////////////////////////////////// DEBUG //////////////////////////////////// - -/proc/CreateBansjob() - - UpdateTime() - - var/i - var/last - - for(i=0, i<1001, i++) - var/a = pick(1,0) - var/b = pick(1,0) - if(b) - Banlistjob.cd = "/base" - Banlistjob.dir.Add("trash[i]trashid[i]") - Banlistjob.cd = "/base/trash[i]trashid[i]" - Banlistjob["key"] << "trash[i]" - else - Banlistjob.cd = "/base" - Banlistjob.dir.Add("[last]trashid[i]") - Banlistjob.cd = "/base/[last]trashid[i]" - Banlistjob["key"] << last - Banlistjob["id"] << "trashid[i]" - Banlistjob["reason"] << "Trashban[i]." - Banlistjob["temp"] << a - Banlistjob["minutes"] << CMinutes + rand(1,2000) - Banlistjob["bannedby"] << "trashmin" - last = "trash[i]" - - Banlistjob.cd = "/base" - -/proc/ClearAllBansjob() - Banlistjob.cd = "/base" - for (var/A in Banlistjob.dir) - RemoveBanjob(A, "full") diff --git a/code/modules/admin/topic.dm b/code/modules/admin/topic.dm index 580ca44339b..a09b920bd49 100644 --- a/code/modules/admin/topic.dm +++ b/code/modules/admin/topic.dm @@ -396,397 +396,26 @@ /////////////////////////////////////new ban stuff - else if(href_list["jobban2"]) -// if(!check_rights(R_BAN)) return - - var/mob/M = locate(href_list["jobban2"]) - if(!ismob(M)) - usr << "This can only be used on instances of type /mob" - return - - if(!M.ckey) //sanity - usr << "This mob has no ckey" - return - - var/dat = "" - var/header = "Job-Ban Panel: [M.name]" - var/body - var/jobs = "" - - /***********************************WARNING!************************************ - The jobban stuff looks mangled and disgusting - But it looks beautiful in-game - -Nodrak - ************************************WARNING!***********************************/ - var/counter = 0 -//Regular jobs - //Command (Blue) - jobs += "
" - jobs += "" - for(var/jobPos in command_positions) - if(!jobPos) continue - var/datum/job/job = SSjobs.GetJob(jobPos) - if(!job) continue - - if(jobban_isbanned(M, job.title)) - jobs += "" - counter++ - else - jobs += "" - counter++ - - if(counter >= 6) //So things dont get squiiiiished! - jobs += "" - counter = 0 - jobs += "
Command Positions
[replacetext(job.title, " ", " ")][replacetext(job.title, " ", " ")]
" - - //Security (Red) - counter = 0 - jobs += "" - jobs += "" - for(var/jobPos in security_positions) - if(!jobPos) continue - var/datum/job/job = SSjobs.GetJob(jobPos) - if(!job) continue - - if(jobban_isbanned(M, job.title)) - jobs += "" - counter++ - else - jobs += "" - counter++ - - if(counter >= 5) //So things dont get squiiiiished! - jobs += "" - counter = 0 - jobs += "
Security Positions
[replacetext(job.title, " ", " ")][replacetext(job.title, " ", " ")]
" - - //Engineering (Yellow) - counter = 0 - jobs += "" - jobs += "" - for(var/jobPos in engineering_positions) - if(!jobPos) continue - var/datum/job/job = SSjobs.GetJob(jobPos) - if(!job) continue - - if(jobban_isbanned(M, job.title)) - jobs += "" - counter++ - else - jobs += "" - counter++ - - if(counter >= 5) //So things dont get squiiiiished! - jobs += "" - counter = 0 - jobs += "
Engineering Positions
[replacetext(job.title, " ", " ")][replacetext(job.title, " ", " ")]
" - - //Medical (White) - counter = 0 - jobs += "" - jobs += "" - for(var/jobPos in medical_positions) - if(!jobPos) continue - var/datum/job/job = SSjobs.GetJob(jobPos) - if(!job) continue - - if(jobban_isbanned(M, job.title)) - jobs += "" - counter++ - else - jobs += "" - counter++ - - if(counter >= 5) //So things dont get squiiiiished! - jobs += "" - counter = 0 - jobs += "
Medical Positions
[replacetext(job.title, " ", " ")][replacetext(job.title, " ", " ")]
" - - //Science (Purple) - counter = 0 - jobs += "" - jobs += "" - for(var/jobPos in science_positions) - if(!jobPos) continue - var/datum/job/job = SSjobs.GetJob(jobPos) - if(!job) continue - - if(jobban_isbanned(M, job.title)) - jobs += "" - counter++ - else - jobs += "" - counter++ - - if(counter >= 5) //So things dont get squiiiiished! - jobs += "" - counter = 0 - jobs += "
Science Positions
[replacetext(job.title, " ", " ")][replacetext(job.title, " ", " ")]
" - - //Civilian (Grey) - counter = 0 - jobs += "" - jobs += "" - for(var/jobPos in civilian_positions) - if(!jobPos) continue - var/datum/job/job = SSjobs.GetJob(jobPos) - if(!job) continue - - if(jobban_isbanned(M, job.title)) - jobs += "" - counter++ - else - jobs += "" - counter++ - - if(counter >= 5) //So things dont get squiiiiished! - jobs += "" - counter = 0 - - if(jobban_isbanned(M, "Internal Affairs Agent")) - jobs += "" - else - jobs += "" - - jobs += "
Civilian Positions
[replacetext(job.title, " ", " ")][replacetext(job.title, " ", " ")]
Internal Affairs AgentInternal Affairs Agent
" - - //Non-Human (Green) - counter = 0 - jobs += "" - jobs += "" - for(var/jobPos in nonhuman_positions) - if(!jobPos) continue - var/datum/job/job = SSjobs.GetJob(jobPos) - if(!job) continue - - if(jobban_isbanned(M, job.title)) - jobs += "" - counter++ - else - jobs += "" - counter++ - - if(counter >= 5) //So things dont get squiiiiished! - jobs += "" - counter = 0 - - //pAI isn't technically a job, but it goes in here. - - if(jobban_isbanned(M, "pAI")) - jobs += "" - else - jobs += "" - if(jobban_isbanned(M, "AntagHUD")) - jobs += "" - else - jobs += "" - jobs += "
Non-human Positions
[replacetext(job.title, " ", " ")][replacetext(job.title, " ", " ")]
pAIpAIAntagHUDAntagHUD
" - - //Antagonist (Orange) - var/isbanned_dept = jobban_isbanned(M, "Antagonist") - jobs += "" - jobs += "" - - // Antagonists. - for(var/antag_type in all_antag_types) - var/datum/antagonist/antag = all_antag_types[antag_type] - if(!antag || !antag.bantype) - continue - if(jobban_isbanned(M, "[antag.bantype]") || isbanned_dept) - jobs += "" - else - jobs += "" - - jobs += "
Antagonist Positions
[replacetext("[antag.role_text]", " ", " ")][replacetext("[antag.role_text]", " ", " ")]
" - - //Other races (BLUE, because I have no idea what other color to make this) - jobs += "" - jobs += "" - - if(jobban_isbanned(M, "Dionaea")) - jobs += "" - else - jobs += "" - jobs += "
Other Races
DionaeaDionaea
" - body = "[jobs]" - dat = "[header][body]" - usr << browse(dat, "window=jobban2;size=800x490") + else if(href_list["jobban_panel"]) + jobban_panel(href_list["jobban_panel"]) return - //JOBBAN'S INNARDS - else if(href_list["jobban3"]) - if(!check_rights(R_MOD,0) && !check_rights(R_ADMIN,0)) - usr << "You do not have the appropriate permissions to add job bans!" + // JOBBAN'S INNARDS + // Are now moved to banjob.dm. For use with the newer system. + else if(href_list["jobban_job"]) + return jobban_handle(href_list["jobban_tgt"], href_list["jobban_job"]) + + else if(href_list["jobban_search"]) + if (!check_rights(R_MOD|R_ADMIN)) return - if(check_rights(R_MOD,0) && !check_rights(R_ADMIN,0) && !config.mods_can_job_tempban) // If mod and tempban disabled - usr << "Mod jobbanning is disabled!" + var/ckey = ckey(input("Please specify the ckey you want to search for:", "ckey")) as text + if (!ckey) + usr << "Cancelled." return - var/mob/M = locate(href_list["jobban4"]) - if(!ismob(M)) - usr << "This can only be used on instances of type /mob" - return - - if(M != usr) //we can jobban ourselves - if(M.client && M.client.holder && (M.client.holder.rights & R_BAN)) //they can ban too. So we can't ban them - alert("You cannot perform this action. You must be of a higher administrative rank!") - return - - //get jobs for department if specified, otherwise just returnt he one job in a list. - var/list/joblist = list() - switch(href_list["jobban3"]) - if("commanddept") - for(var/jobPos in command_positions) - if(!jobPos) continue - var/datum/job/temp = SSjobs.GetJob(jobPos) - if(!temp) continue - joblist += temp.title - if("securitydept") - for(var/jobPos in security_positions) - if(!jobPos) continue - var/datum/job/temp = SSjobs.GetJob(jobPos) - if(!temp) continue - joblist += temp.title - if("engineeringdept") - for(var/jobPos in engineering_positions) - if(!jobPos) continue - var/datum/job/temp = SSjobs.GetJob(jobPos) - if(!temp) continue - joblist += temp.title - if("medicaldept") - for(var/jobPos in medical_positions) - if(!jobPos) continue - var/datum/job/temp = SSjobs.GetJob(jobPos) - if(!temp) continue - joblist += temp.title - if("sciencedept") - for(var/jobPos in science_positions) - if(!jobPos) continue - var/datum/job/temp = SSjobs.GetJob(jobPos) - if(!temp) continue - joblist += temp.title - if("civiliandept") - for(var/jobPos in civilian_positions) - if(!jobPos) continue - var/datum/job/temp = SSjobs.GetJob(jobPos) - if(!temp) continue - joblist += temp.title - if("nonhumandept") - joblist += "pAI" - for(var/jobPos in nonhuman_positions) - if(!jobPos) continue - var/datum/job/temp = SSjobs.GetJob(jobPos) - if(!temp) continue - joblist += temp.title - else - joblist += href_list["jobban3"] - - //Create a list of unbanned jobs within joblist - var/list/notbannedlist = list() - for(var/job in joblist) - if(!jobban_isbanned(M, job)) - notbannedlist += job - - //Banning comes first - if(notbannedlist.len) //at least 1 unbanned job exists in joblist so we have stuff to ban. - switch(alert("Temporary Ban?",,"Yes","No", "Cancel")) - if("Yes") - if(!check_rights(R_MOD,0) && !check_rights(R_BAN, 0)) - usr << "You Cannot issue temporary job-bans!" - return - if(config.ban_legacy_system) - usr << "Your server is using the legacy banning system, which does not support temporary job bans. Consider upgrading. Aborting ban." - return - var/mins = input(usr,"How long (in minutes)?","Ban time",1440) as num|null - if(!mins) - return - if(check_rights(R_MOD, 0) && !check_rights(R_BAN, 0) && mins > config.mod_job_tempban_max) - usr << "Moderators can only job tempban up to [config.mod_job_tempban_max] minutes!" - return - var/reason = sanitize(input(usr,"Reason?","Please State Reason","") as text|null) - if(!reason) - return - - var/msg - for(var/job in notbannedlist) - ban_unban_log_save("[key_name(usr)] temp-jobbanned [key_name(M)] from [job] for [mins] minutes. reason: [reason]") - log_admin("[key_name(usr)] temp-jobbanned [key_name(M)] from [job] for [mins] minutes",admin_key=key_name(usr)) - feedback_inc("ban_job_tmp",1) - DB_ban_record(BANTYPE_JOB_TEMP, M, mins, reason, job) - feedback_add_details("ban_job_tmp","- [job]") - jobban_fullban(M, job, "[reason]; By [usr.ckey] on [time2text(world.realtime)]") //Legacy banning does not support temporary jobbans. - if(!msg) - msg = job - else - msg += ", [job]" - if (config.ban_legacy_system) - notes_add(M.ckey, "Banned from [msg] - [reason]", usr) - else - notes_add_sql(M.ckey, "Banned from [msg] - [reason]", usr, M.lastKnownIP, M.computer_id) - message_admins("[key_name_admin(usr)] banned [key_name_admin(M)] from [msg] for [mins] minutes.", 1) - M << "You have been jobbanned by [usr.client.ckey] from: [msg]." - M << "The reason is: [reason]" - M << "This jobban will be lifted in [mins] minutes." - href_list["jobban2"] = 1 // lets it fall through and refresh - return 1 - if("No") - if(!check_rights(R_BAN)) return - var/reason = sanitize(input(usr,"Reason?","Please State Reason","") as text|null) - if(reason) - var/msg - for(var/job in notbannedlist) - ban_unban_log_save("[key_name(usr)] perma-jobbanned [key_name(M)] from [job]. reason: [reason]") - log_admin("[key_name(usr)] perma-banned [key_name(M)] from [job]",admin_key=key_name(usr)) - feedback_inc("ban_job",1) - DB_ban_record(BANTYPE_JOB_PERMA, M, -1, reason, job) - feedback_add_details("ban_job","- [job]") - jobban_fullban(M, job, "[reason]; By [usr.ckey] on [time2text(world.realtime)]") - if(!msg) msg = job - else msg += ", [job]" - if (config.ban_legacy_system) - notes_add(M.ckey, "Banned from [msg] - [reason]", usr) - else - notes_add_sql(M.ckey, "Banned from [msg] - [reason]", usr, M.lastKnownIP, M.computer_id) - message_admins("[key_name_admin(usr)] banned [key_name_admin(M)] from [msg]", 1) - M << "You have been jobbanned by [usr.client.ckey] from: [msg]." - M << "The reason is: [reason]" - M << "Jobban can be lifted only upon request." - href_list["jobban2"] = 1 // lets it fall through and refresh - return 1 - if("Cancel") - return - - //Unbanning joblist - //all jobs in joblist are banned already OR we didn't give a reason (implying they shouldn't be banned) - if(joblist.len) //at least 1 banned job exists in joblist so we have stuff to unban. - if(!config.ban_legacy_system) - usr << "Unfortunately, database based unbanning cannot be done through this panel" - DB_ban_panel(M.ckey) - return - var/msg - for(var/job in joblist) - var/reason = jobban_isbanned(M, job) - if(!reason) continue //skip if it isn't jobbanned anyway - switch(alert("Job: '[job]' Reason: '[reason]' Un-jobban?","Please Confirm","Yes","No")) - if("Yes") - ban_unban_log_save("[key_name(usr)] unjobbanned [key_name(M)] from [job]") - log_admin("[key_name(usr)] unbanned [key_name(M)] from [job]",admin_key=key_name(usr),ckey=key_name(M)) - DB_ban_unban(M.ckey, BANTYPE_JOB_PERMA, job) - feedback_inc("ban_job_unban",1) - feedback_add_details("ban_job_unban","- [job]") - jobban_unban(M, job) - if(!msg) msg = job - else msg += ", [job]" - else - continue - if(msg) - message_admins("[key_name_admin(usr)] unbanned [key_name_admin(M)] from [msg]", 1) - M << "You have been un-jobbanned by [usr.client.ckey] from [msg]." - href_list["jobban2"] = 1 // lets it fall through and refresh - return 1 - return 0 //we didn't do anything! + jobban_panel(ckey) + return else if(href_list["boot2"]) var/mob/M = locate(href_list["boot2"]) @@ -803,21 +432,6 @@ //M.client = null qdel(M.client) - else if(href_list["removejobban"]) - if(!check_rights(R_BAN)) return - - var/t = href_list["removejobban"] - if(t) - if((alert("Do you want to unjobban [t]?","Unjobban confirmation", "Yes", "No") == "Yes") && t) //No more misclicks! Unless you do it twice. - log_admin("[key_name(usr)] removed [t]",admin_key=key_name(usr)) - message_admins("[key_name_admin(usr)] removed [t]", 1) - jobban_remove(t) - href_list["ban"] = 1 // lets it fall through and refresh - var/t_split = text2list(t, " - ") - var/key = t_split[1] - var/job = t_split[2] - DB_ban_unban(ckey(key), BANTYPE_JOB_PERMA, job) - else if(href_list["newban"]) if(!check_rights(R_MOD,0) && !check_rights(R_BAN, 0)) usr << "You do not have the appropriate permissions to add bans!"