mirror of
https://github.com/yogstation13/Yogstation.git
synced 2025-02-26 09:04:50 +00:00
* Add the system for managed global variables * Travis ban old globals * So you CAN inline proccall, that's neat * Fix that * master.dm * Remove the hack procs * Move InitGlobals to the proper spot * configuration.dm * Fix the missing pre-slash * clockcult.dm * This is probably for the best * Doy * Fix shit * Rest of the DEFINES tree * Fix * Use global. for access * Update find_references_in_globals Always hated that proc Whoever made it must've bee a r e a l idiot... * __HELPERS tree * Move global initialization to master. Fix the declaration * database.dm * Dat newline * I said DECLARATIVE order! * Here's something you can chew on @Iamgoofball * game_modes.dm * Fix this * genetics.dm * flavor_misc.dm * More stuff * Do it mso's way. Keep the controllers as global * Make master actually see it * Fix * Finish _globalvars/lists * Finish the rest of the _globalvars tree * This is weird * Migrate the controllers * SLOTH -> GLOB * Lighting globals * round_start_time -> ticker * PAI card list -> pai SS * record_id_num -> static * Diseases list -> SSdisease * More disease globals to the SS * More disease stuff * Emote list * Better and better * Bluh * So much stuff * Ahh * Wires * dview * station_areas * Teleportlocs * blood_splatter_icons * Stuff and such * More stuff * RAD IO * More stuff and such * Blob shit * Changeling stuff * Add "Balance" to changelogs * Balance for changelog compiler + Auto Tagging * Update the PR template * hivemind_bank * Bip * sacrificed * Good shit * Better define * More cult shit * Devil shit * Gang shit * > borers Fix shit * Rename the define * Nuke * Objectives * Sandbox * Multiverse sword * Announce systems * Stuff and such * TC con * Airlock * doppllllerrrrrr * holopads * Shut up byond you inconsistent fuck * Sneaky fuck * Burp * Bip * Fixnshit * Port without regard * askdlfjs; * asdfjasoidojfi * Protected globals and more * SO MANY * ajsimkvahsaoisd * akfdsiaopwimfeoiwafaw * gsdfigjosidjfgiosdg * AHHHHHHHHHHHHHHHHHHHHHHH!!!!! * facerolll * ASDFASDFASDF * Removes the unused parts of dmm_suite * WIP * Fix quote * asdfjauwfnkjs * afwlunhskjfda * asfjlaiwuefhaf * SO CLOSE * wwwweeeeeewwwww * agdgmoewranwg * HOLY MOTHER OF FUCK AND THATS JUST HALF THE JOB?!? * Fix syntax errors * 100 errors * Another 100 * So many... * Ugh * More shit * kilme * Stuuuuuufffff * ajrgmrlshio;djfa;sdkl * jkbhkhjbmjvjmh * soi soi soi * butt * TODAY WE LEARNED THAT GLOBAL AND STATIC ARE THE EXACT SAME FUCKING THING * lllllllllllllllllllllllllllllllllllllllllll * afsdijfiawhnflnjhnwsdfs * yugykihlugk,kj * time to go * STUFFF!!! * AAAAAAAAAAAAAAAAAHHHHHHHHHHHHHHHHHHHHHHHHHHH!!!!!!!!!!!!!!!!!!!!!!! * ngoaijdjlfkamsdlkf * Break time * aufjsdklfalsjfi * CONTROL KAY AND PRAY * IT COMPILEELEELELAKLJFKLDAFJLKFDJLADKJHFLJKAJGAHIEJALDFJ!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!! * Goteem * Fix testing mode * This does not belong in this PR * Convert it to a controller * Eh, fuck this option * Revert controllerization Ill do it some other time * Fix * Working controllerization * FOR THE LOVE OF CHRIST PROTECT THE LOGS * Protect admins and deadmins * Use the inbuilt proc
194 lines
6.3 KiB
Plaintext
194 lines
6.3 KiB
Plaintext
// Error viewing datums, responsible for storing error info, notifying admins
|
|
// when errors occur, and showing them to admins on demand.
|
|
|
|
// There are 3 different types used here:
|
|
//
|
|
// - error_cache keeps track of all error sources, as well as all individually
|
|
// logged errors. Only one instance of this datum should ever exist, and it's
|
|
// right here:
|
|
|
|
#ifdef DEBUG
|
|
GLOBAL_DATUM_INIT(error_cache, /datum/error_viewer/error_cache, new)
|
|
#else
|
|
// If debugging is disabled, there's nothing useful to log, so don't bother.
|
|
GLOBAL_DATUM(error_cache, /datum/error_viewer/error_cache)
|
|
#endif
|
|
|
|
// - error_source datums exist for each line (of code) that generates an error,
|
|
// and keep track of all errors generated by that line.
|
|
//
|
|
// - error_entry datums exist for each logged error, and keep track of all
|
|
// relevant info about that error.
|
|
|
|
// Common vars and procs are kept at the error_viewer level
|
|
/datum/error_viewer
|
|
var/name = ""
|
|
|
|
/datum/error_viewer/proc/browse_to(client/user, html)
|
|
var/datum/browser/browser = new(user.mob, "error_viewer", null, 600, 400)
|
|
browser.set_content(html)
|
|
browser.add_head_content({"
|
|
<style>
|
|
.runtime
|
|
{
|
|
background-color: #171717;
|
|
border: solid 1px #202020;
|
|
font-family: "Courier New";
|
|
padding-left: 10px;
|
|
color: #CCCCCC;
|
|
}
|
|
.runtime_line
|
|
{
|
|
margin-bottom: 10px;
|
|
display: inline-block;
|
|
}
|
|
</style>
|
|
"})
|
|
browser.open()
|
|
|
|
/datum/error_viewer/proc/build_header(datum/error_viewer/back_to, linear)
|
|
// Common starter HTML for show_to
|
|
|
|
. = ""
|
|
|
|
if (istype(back_to))
|
|
. += back_to.make_link("<b><<<</b>", null, linear)
|
|
|
|
. += "[make_link("Refresh")]<br><br>"
|
|
|
|
/datum/error_viewer/proc/show_to(user, datum/error_viewer/back_to, linear)
|
|
// Specific to each child type
|
|
return
|
|
|
|
/datum/error_viewer/proc/make_link(linktext, datum/error_viewer/back_to, linear)
|
|
var/back_to_param = ""
|
|
if (!linktext)
|
|
linktext = name
|
|
|
|
if (istype(back_to))
|
|
back_to_param = ";viewruntime_backto=\ref[back_to]"
|
|
|
|
if (linear)
|
|
back_to_param += ";viewruntime_linear=1"
|
|
|
|
return "<a href='?_src_=holder;viewruntime=\ref[src][back_to_param]'>[linktext]</a>"
|
|
|
|
/datum/error_viewer/error_cache
|
|
var/list/errors = list()
|
|
var/list/error_sources = list()
|
|
var/list/errors_silenced = list()
|
|
|
|
/datum/error_viewer/error_cache/show_to(user, datum/error_viewer/back_to, linear)
|
|
var/html = build_header()
|
|
html += "<b>[GLOB.total_runtimes]</b> runtimes, <b>[GLOB.total_runtimes_skipped]</b> skipped<br><br>"
|
|
if (!linear)
|
|
html += "organized | [make_link("linear", null, 1)]<hr>"
|
|
var/datum/error_viewer/error_source/error_source
|
|
for (var/erroruid in error_sources)
|
|
error_source = error_sources[erroruid]
|
|
html += "[error_source.make_link(null, src)]<br>"
|
|
|
|
else
|
|
html += "[make_link("organized", null)] | linear<hr>"
|
|
for (var/datum/error_viewer/error_entry/error_entry in errors)
|
|
html += "[error_entry.make_link(null, src, 1)]<br>"
|
|
|
|
browse_to(user, html)
|
|
|
|
/datum/error_viewer/error_cache/proc/log_error(exception/e, list/desclines, skip_count)
|
|
if (!istype(e))
|
|
return // Abnormal exception, don't even bother
|
|
|
|
var/erroruid = "[e.file][e.line]"
|
|
var/datum/error_viewer/error_source/error_source = error_sources[erroruid]
|
|
if (!error_source)
|
|
error_source = new(e)
|
|
error_sources[erroruid] = error_source
|
|
|
|
var/datum/error_viewer/error_entry/error_entry = new(e, desclines, skip_count)
|
|
error_entry.error_source = error_source
|
|
errors += error_entry
|
|
error_source.errors += error_entry
|
|
if (skip_count)
|
|
return // Skip notifying admins about skipped errors.
|
|
|
|
// Show the error to admins with debug messages turned on, but only if one
|
|
// from the same source hasn't been shown too recently
|
|
if (error_source.next_message_at <= world.time)
|
|
var/const/viewtext = "\[view]" // Nesting these in other brackets went poorly
|
|
//log_debug("Runtime in <b>[e.file]</b>, line <b>[e.line]</b>: <b>[html_encode(e.name)]</b> [error_entry.make_link(viewtext)]")
|
|
var/err_msg_delay
|
|
if(config)
|
|
err_msg_delay = config.error_msg_delay
|
|
else
|
|
err_msg_delay = initial(config.error_msg_delay)
|
|
error_source.next_message_at = world.time + err_msg_delay
|
|
|
|
/datum/error_viewer/error_source
|
|
var/list/errors = list()
|
|
var/next_message_at = 0
|
|
|
|
/datum/error_viewer/error_source/New(exception/e)
|
|
if (!istype(e))
|
|
name = "\[[time_stamp()]] Uncaught exceptions"
|
|
return
|
|
|
|
name = "<b>\[[time_stamp()]]</b> Runtime in <b>[e.file]</b>, line <b>[e.line]</b>: <b>[html_encode(e.name)]</b>"
|
|
|
|
/datum/error_viewer/error_source/show_to(user, datum/error_viewer/back_to, linear)
|
|
if (!istype(back_to))
|
|
back_to = GLOB.error_cache
|
|
|
|
var/html = build_header(back_to)
|
|
for (var/datum/error_viewer/error_entry/error_entry in errors)
|
|
html += "[error_entry.make_link(null, src)]<br>"
|
|
|
|
browse_to(user, html)
|
|
|
|
/datum/error_viewer/error_entry
|
|
var/datum/error_viewer/error_source/error_source
|
|
var/exception/exc
|
|
var/desc = ""
|
|
var/usr_ref
|
|
var/turf/usr_loc
|
|
var/is_skip_count
|
|
|
|
/datum/error_viewer/error_entry/New(exception/e, list/desclines, skip_count)
|
|
if (!istype(e))
|
|
name = "<b>\[[time_stamp()]]</b> Uncaught exception: <b>[html_encode(e.name)]</b>"
|
|
return
|
|
|
|
if(skip_count)
|
|
name = "\[[time_stamp()]] Skipped [skip_count] runtimes in [e.file],[e.line]."
|
|
is_skip_count = TRUE
|
|
return
|
|
|
|
name = "<b>\[[time_stamp()]]</b> Runtime in <b>[e.file]</b>, line <b>[e.line]</b>: <b>[html_encode(e.name)]</b>"
|
|
exc = e
|
|
if (istype(desclines))
|
|
for (var/line in desclines)
|
|
// There's probably a better way to do this than non-breaking spaces...
|
|
desc += "<span class='runtime_line'>[html_encode(line)]</span><br>"
|
|
|
|
if (usr)
|
|
usr_ref = "\ref[usr]"
|
|
usr_loc = get_turf(usr)
|
|
|
|
/datum/error_viewer/error_entry/show_to(user, datum/error_viewer/back_to, linear)
|
|
if (!istype(back_to))
|
|
back_to = error_source
|
|
|
|
var/html = build_header(back_to, linear)
|
|
html += "[name]<div class='runtime'>[desc]</div>"
|
|
if (usr_ref)
|
|
html += "<br><b>usr</b>: <a href='?_src_=vars;Vars=[usr_ref]'>VV</a>"
|
|
html += " <a href='?_src_=holder;adminplayeropts=[usr_ref]'>PP</a>"
|
|
html += " <a href='?_src_=holder;adminplayerobservefollow=[usr_ref]'>Follow</a>"
|
|
if (istype(usr_loc))
|
|
html += "<br><b>usr.loc</b>: <a href='?_src_=vars;Vars=\ref[usr_loc]'>VV</a>"
|
|
html += " <a href='?_src_=holder;adminplayerobservecoodjump=1;X=[usr_loc.x];Y=[usr_loc.y];Z=[usr_loc.z]'>JMP</a>"
|
|
|
|
browse_to(user, html)
|
|
|
|
/datum/error_viewer/error_entry/make_link(linktext, datum/error_viewer/back_to, linear)
|
|
return is_skip_count ? name : ..() |