NETSCRIPT: Update ScriptDeath to extend Error (#1685)

* Update ScriptDeath to extend Error

- Rename the "name" property to "hostname" so that it doesn't clash with inherited Error.name property.
- Extend Error, this way if a user ends up catching it they can:
  - Test the type of error caught (name) and ignore it if desired
  - Get a stack trace and find out where they went wrong
  - Not require special case error printing logic for catching things that are neither strings, nor Error objects.

It is possible (but unlikely) that this could make killing scripts slower in some circumstances.
This commit is contained in:
Alain Bryden 2024-10-10 01:18:06 -03:00 committed by GitHub
parent cace34d759
commit cd99006c4e
No known key found for this signature in database
GPG Key ID: B5690EEEBB952194

@ -3,6 +3,14 @@ import { WorkerScript } from "./WorkerScript";
/**
* Script death marker.
*
* This is thrown in various places when a script has been killed, as opposed to ending
* normally. It can be thrown from exit() and spawn(), which inherently kill the script,
* or from an await if the script is killed while waiting for a ns function, or directly
* if the script is dead but running code is still trying to execute ns functions. By extending Error,
* users with error handling in their scripts that end up catching this can
* more easily detect this error type and ignore it (if desired) or get a stack
* trace to help them identify the root cause (if the behaviour is unexpected).
*
* IMPORTANT: the game engine should not base any of it's decisions on the data
* carried in a ScriptDeath instance.
*
@ -10,19 +18,27 @@ import { WorkerScript } from "./WorkerScript";
* script is killed. Which grants the player access to the class and the ability
* to construct new instances with arbitrary data.
*/
export class ScriptDeath {
export class ScriptDeath extends Error {
/** Process ID number. */
pid: number;
/** Filename of the script. */
name: string;
filename: string;
/** IP Address on which the script was running */
hostname: string;
constructor(ws: WorkerScript) {
// Invoke the Error constructor with a meaningful message
const message = `NS instance has already been killed (${ws.name} running on ${ws.hostname} with pid ${ws.pid})`;
super(message);
// Setting the base Error.name property is important to facilitate easy
// detection, since prototype.constructor.name might be minified for them.
this.name = "ScriptDeath";
// Set own properties
this.pid = ws.pid;
this.name = ws.name;
this.filename = ws.name;
this.hostname = ws.hostname;
Object.freeze(this);