diff --git a/src/Netscript/NetscriptHelpers.tsx b/src/Netscript/NetscriptHelpers.tsx index e50917f54..c8c8b6c00 100644 --- a/src/Netscript/NetscriptHelpers.tsx +++ b/src/Netscript/NetscriptHelpers.tsx @@ -26,7 +26,7 @@ import { convertTimeMsToTimeElapsedString } from "../utils/StringHelperFunctions import { currentNodeMults } from "../BitNode/BitNodeMultipliers"; import { CONSTANTS } from "../Constants"; import { influenceStockThroughServerHack } from "../StockMarket/PlayerInfluencing"; -import { PortNumber } from "../NetscriptPort"; +import { type PortNumber, PortHandle } from "../NetscriptPort"; import { FormulaGang } from "../Gang/formulas/formulas"; import { GangMember } from "../Gang/GangMember"; import { GangMemberTask } from "../Gang/GangMemberTask"; @@ -88,7 +88,7 @@ export const helpers = { getServer, scriptIdentifier, hack, - portNumber, + portHandle, person, server, gang, @@ -611,7 +611,7 @@ function hack(ctx: NetscriptContext, hostname: string, manual: boolean, opts: un }); } -function portNumber(ctx: NetscriptContext, _n: unknown): PortNumber { +function portHandle(ctx: NetscriptContext, _n: unknown): PortHandle { const n = positiveInteger(ctx, "portNumber", _n); if (n > CONSTANTS.NumNetscriptPorts) { throw errorMessage( @@ -619,7 +619,7 @@ function portNumber(ctx: NetscriptContext, _n: unknown): PortNumber { `Trying to use an invalid port: ${n}. Must be less or equal to ${CONSTANTS.NumNetscriptPorts}.`, ); } - return n as PortNumber; + return new PortHandle(n as PortNumber); } function person(ctx: NetscriptContext, p: unknown): IPerson { diff --git a/src/NetscriptFunctions.ts b/src/NetscriptFunctions.ts index ea7c0046f..dc7950cf4 100644 --- a/src/NetscriptFunctions.ts +++ b/src/NetscriptFunctions.ts @@ -91,7 +91,6 @@ import { ScriptDeath } from "./Netscript/ScriptDeath"; import { getBitNodeMultipliers } from "./BitNode/BitNode"; import { assert, assertArray, assertString, assertObject } from "./utils/TypeAssertion"; import { escapeRegExp } from "lodash"; -import { clearPort, peekPort, portHandle, readPort, tryWritePort, writePort, nextPortWrite } from "./NetscriptPort"; import { FilePath, resolveFilePath } from "./Paths/FilePath"; import { hasScriptExtension } from "./Paths/ScriptFilePath"; import { hasTextExtension } from "./Paths/TextFilePath"; @@ -1039,8 +1038,8 @@ export const ns: InternalAPI = { return helpers.getRunningScript(ctx, ident) !== null; }, writePort: (ctx) => (_portNumber, data) => { - const portNumber = helpers.portNumber(ctx, _portNumber); - return writePort(portNumber, data); + const portHandle = helpers.portHandle(ctx, _portNumber); + return portHandle.write(data); }, write: (ctx) => (_filename, _data, _mode) => { const filepath = helpers.filePath(ctx, "filename", _filename); @@ -1071,16 +1070,16 @@ export const ns: InternalAPI = { server.writeToTextFile(filepath, mode === "w" ? data : existingText + data); }, tryWritePort: (ctx) => (_portNumber, data) => { - const portNumber = helpers.portNumber(ctx, _portNumber); - return tryWritePort(portNumber, data); + const portHandle = helpers.portHandle(ctx, _portNumber); + return portHandle.tryWrite(data); }, nextPortWrite: (ctx) => (_portNumber) => { - const portNumber = helpers.portNumber(ctx, _portNumber); - return nextPortWrite(portNumber); + const portHandle = helpers.portHandle(ctx, _portNumber); + return portHandle.nextWrite(); }, readPort: (ctx) => (_portNumber) => { - const portNumber = helpers.portNumber(ctx, _portNumber); - return readPort(portNumber); + const portHandle = helpers.portHandle(ctx, _portNumber); + return portHandle.read(); }, read: (ctx) => (_filename) => { const path = helpers.filePath(ctx, "filename", _filename); @@ -1101,8 +1100,8 @@ export const ns: InternalAPI = { return contentFile.metadata.plain(); }, peek: (ctx) => (_portNumber) => { - const portNumber = helpers.portNumber(ctx, _portNumber); - return peekPort(portNumber); + const portHandle = helpers.portHandle(ctx, _portNumber); + return portHandle.peek(); }, clear: (ctx) => (_file) => { const path = helpers.filePath(ctx, "file", _file); @@ -1116,12 +1115,12 @@ export const ns: InternalAPI = { file.content = ""; }, clearPort: (ctx) => (_portNumber) => { - const portNumber = helpers.portNumber(ctx, _portNumber); - return clearPort(portNumber); + const portHandle = helpers.portHandle(ctx, _portNumber); + return portHandle.clear(); }, getPortHandle: (ctx) => (_portNumber) => { - const portNumber = helpers.portNumber(ctx, _portNumber); - return portHandle(portNumber); + const portHandle = helpers.portHandle(ctx, _portNumber); + return portHandle; }, rm: (ctx) => (_fn, _host) => { const filepath = helpers.filePath(ctx, "fn", _fn); diff --git a/src/NetscriptPort.ts b/src/NetscriptPort.ts index 8a4eb710d..ce2684cd6 100644 --- a/src/NetscriptPort.ts +++ b/src/NetscriptPort.ts @@ -23,10 +23,10 @@ export function getPort(n: PortNumber) { } export class Port { - data: any[] = []; + data: unknown[] = []; resolver: Resolver | null = null; promise: Promise | null = null; - add(data: any) { + add(data: unknown) { this.data.push(data); if (!this.resolver) return; this.resolver(); @@ -35,71 +35,66 @@ export class Port { } } -export function portHandle(n: PortNumber): NetscriptPort { - return { - write: (value: unknown) => writePort(n, value), - tryWrite: (value: unknown) => tryWritePort(n, value), - read: () => readPort(n), - peek: () => peekPort(n), - nextWrite: () => nextPortWrite(n), - full: () => isFullPort(n), - empty: () => isEmptyPort(n), - clear: () => clearPort(n), - }; -} +export class PortHandle implements NetscriptPort { + n: PortNumber; -export function writePort(n: PortNumber, value: unknown): unknown { - const port = getPort(n); - // Primitives don't need to be cloned. - port.add(isObjectLike(value) ? structuredClone(value) : value); - if (port.data.length > Settings.MaxPortCapacity) return port.data.shift(); - return null; -} + constructor(n: PortNumber) { + this.n = n; + } -export function tryWritePort(n: PortNumber, value: unknown): boolean { - const port = getPort(n); - if (port.data.length >= Settings.MaxPortCapacity) return false; - // Primitives don't need to be cloned. - port.add(isObjectLike(value) ? structuredClone(value) : value); - return true; -} + write(value: unknown): unknown { + const port = getPort(this.n); + // Primitives don't need to be cloned. + port.add(isObjectLike(value) ? structuredClone(value) : value); + if (port.data.length > Settings.MaxPortCapacity) return port.data.shift(); + return null; + } -export function readPort(n: PortNumber): unknown { - const port = NetscriptPorts.get(n); - if (!port || !port.data.length) return emptyPortData; - const returnVal: unknown = port.data.shift(); - if (!port.data.length && !port.resolver) NetscriptPorts.delete(n); - return returnVal; -} + tryWrite(value: unknown): boolean { + const port = getPort(this.n); + if (port.data.length >= Settings.MaxPortCapacity) return false; + // Primitives don't need to be cloned. + port.add(isObjectLike(value) ? structuredClone(value) : value); + return true; + } -export function peekPort(n: PortNumber): unknown { - const port = NetscriptPorts.get(n); - if (!port || !port.data.length) return emptyPortData; - // Needed to avoid exposing internal objects. - return isObjectLike(port.data[0]) ? structuredClone(port.data[0]) : port.data[0]; -} + read(): unknown { + const port = NetscriptPorts.get(this.n); + if (!port || !port.data.length) return emptyPortData; + const returnVal: unknown = port.data.shift(); + if (!port.data.length && !port.resolver) NetscriptPorts.delete(this.n); + return returnVal; + } -export function nextPortWrite(n: PortNumber) { - const port = getPort(n); - if (!port.promise) port.promise = new Promise((res) => (port.resolver = res)); - return port.promise; -} + peek(): unknown { + const port = NetscriptPorts.get(this.n); + if (!port || !port.data.length) return emptyPortData; + // Needed to avoid exposing internal objects. + return isObjectLike(port.data[0]) ? structuredClone(port.data[0]) : port.data[0]; + } -function isFullPort(n: PortNumber) { - const port = NetscriptPorts.get(n); - if (!port) return false; - return port.data.length >= Settings.MaxPortCapacity; -} + nextWrite(): Promise { + const port = getPort(this.n); + if (!port.promise) port.promise = new Promise((res) => (port.resolver = res)); + return port.promise; + } -function isEmptyPort(n: PortNumber) { - const port = NetscriptPorts.get(n); - if (!port) return true; - return port.data.length === 0; -} + full(): boolean { + const port = NetscriptPorts.get(this.n); + if (!port) return false; + return port.data.length >= Settings.MaxPortCapacity; + } -export function clearPort(n: PortNumber) { - const port = NetscriptPorts.get(n); - if (!port) return; - if (!port.resolver) NetscriptPorts.delete(n); - port.data.length = 0; + empty(): boolean { + const port = NetscriptPorts.get(this.n); + if (!port) return true; + return port.data.length === 0; + } + + clear(): void { + const port = NetscriptPorts.get(this.n); + if (!port) return; + if (!port.resolver) NetscriptPorts.delete(this.n); + port.data.length = 0; + } }