mirror of
https://github.com/bitburner-official/bitburner-src.git
synced 2024-12-27 00:17:32 +01:00
fix mc
This commit is contained in:
commit
58fa091dd5
@ -113,7 +113,7 @@ The list contains the name of (i.e. the value returned by
|
||||
| | | to any position from i to i+n. |
|
||||
| | | |
|
||||
| | | Assuming you are initially positioned at the start of the array, determine |
|
||||
| | | whether you are able to reach the last index of the array EXACTLY. |
|
||||
| | | whether you are able to reach the last index of the array. |
|
||||
+------------------------------------+------------------------------------------------------------------------------------------+
|
||||
| Merge Overlapping Intervals | | Given an array of intervals, merge all overlapping intervals. An interval |
|
||||
| | | is an array with two numbers, where the first number is always less than |
|
||||
|
@ -17,9 +17,16 @@ says 'Infiltrate Company'.
|
||||
When infiltrating a company you will be presented with short active challenges.
|
||||
None of the challenges use the mouse.
|
||||
|
||||
The difficulty at the top lowers with better combat stats. It is not recommended
|
||||
The difficulty at the top lowers with better combat stats and charisma. It is not recommended
|
||||
to attempt infiltrations above mid-normal.
|
||||
|
||||
The "maximum level" is the number of challenges you will need to pass to receive
|
||||
the infiltration reward.
|
||||
|
||||
Every time you fail an infiltration challenge, you will take damage based on the
|
||||
difficulty of the infiltration. If you are reduced to 0 hp or below, the
|
||||
infiltration will immediately end.
|
||||
|
||||
* Most use spacebar as "action"
|
||||
* Some use WASD or arrows interchangeably.
|
||||
* A few others use the rest of the keyboard.
|
||||
@ -60,4 +67,4 @@ Then move the cursor and press space to mark the mines on the board.
|
||||
** Cut the wires **
|
||||
|
||||
Follow the instructions and press the numbers 1 through 9 to cut the appropriate
|
||||
wires.
|
||||
wires.
|
||||
|
@ -16,7 +16,6 @@ Affects:
|
||||
* Chance to successfully hack a server
|
||||
* Percent money stolen when hacking a server
|
||||
* Success rate of certain crimes
|
||||
* Success rate of Hacking option during Infiltration
|
||||
* Time it takes to create a program
|
||||
* Faction reputation gain when carrying out Hacking Contracts or Field Work
|
||||
* Company reputation gain for certain jobs
|
||||
@ -26,7 +25,6 @@ Gain experience by:
|
||||
* Manually hacking servers through Terminal
|
||||
* Executing hack(), grow(), or weaken() through a script
|
||||
* Committing certain crimes
|
||||
* Infiltration
|
||||
* Carrying out Hacking Contracts or doing Field work for Factions
|
||||
* Working certain jobs at a company
|
||||
* Studying at a university
|
||||
@ -38,14 +36,12 @@ Represents the player's physical offensive power
|
||||
Affects:
|
||||
|
||||
* Success rate of certain crimes
|
||||
* Success rate of Combat options during Infiltration
|
||||
* Faction reputation gain for Security and Field Work
|
||||
* Company reputation gain for certain jobs
|
||||
|
||||
Gain experience by:
|
||||
|
||||
* Committing certain crimes
|
||||
* Infiltration
|
||||
* Working out at a gym
|
||||
* Doing Security/Field Work for a faction
|
||||
* Working certain jobs at a company
|
||||
@ -58,15 +54,12 @@ Affects:
|
||||
|
||||
* Success rate of certain crimes
|
||||
* The player's HP
|
||||
* Success rate of Combat options during Infiltration
|
||||
* How much damage the player takes during Infiltration
|
||||
* Faction reputation gain for Security and Field Work
|
||||
* Company reputation gain for certain jobs
|
||||
|
||||
Gain experience by:
|
||||
|
||||
* Committing certain crimes
|
||||
* Infiltration
|
||||
* Working out at a gym
|
||||
* Doing Security/Field Work for a faction
|
||||
* Working certain jobs at a company
|
||||
@ -78,14 +71,12 @@ Represents the player's skill and adeptness in performing certain tasks
|
||||
Affects:
|
||||
|
||||
* Success rate of certain crimes
|
||||
* Success rate of Combat, Lockpick, and Escape options during Infiltration
|
||||
* Faction reputation gain for Security and Field Work
|
||||
* Company reputation gain for certain jobs
|
||||
|
||||
Gain experience by:
|
||||
|
||||
* Committing certain crimes
|
||||
* Infiltration
|
||||
* Working out at a gym
|
||||
* Doing Security/Field Work for a faction
|
||||
* Working certain jobs at a company
|
||||
@ -97,14 +88,12 @@ Represents the player's speed and ability to move
|
||||
Affects:
|
||||
|
||||
* Success rate of certain crimes
|
||||
* Success rate of Combat, Sneak, and Escape options during Infiltration
|
||||
* Faction reputation gain for Security and Field Work
|
||||
* Company reputation gain for certain jobs
|
||||
|
||||
Gain experience by:
|
||||
|
||||
* Committing certain crimes
|
||||
* Infiltration
|
||||
* Working out at a gym
|
||||
* Doing Security/Field Work for a faction
|
||||
* Working certain jobs at a company
|
||||
@ -116,14 +105,12 @@ Represents the player's social abilities
|
||||
Affects:
|
||||
|
||||
* Success rate of certain crimes
|
||||
* Success rate of Bribe option during Infiltration
|
||||
* Faction reputation gain for Field Work
|
||||
* Company reputation gain for most jobs
|
||||
|
||||
Gain experience by:
|
||||
|
||||
* Committing certain crimes
|
||||
* Infiltration
|
||||
* Studying at a university
|
||||
* Working a relevant job at a company
|
||||
* Doing Field work for a Faction
|
||||
|
@ -200,52 +200,52 @@ Here's what mine showed at the time I made this::
|
||||
--Root Access: YES, Required hacking skill: 1
|
||||
--Number of open ports required to NUKE: 0
|
||||
--RAM: 4.00GB
|
||||
|
||||
|
||||
----zer0
|
||||
------Root Access: NO, Required hacking skill: 75
|
||||
------Number of open ports required to NUKE: 1
|
||||
------RAM: 32.00GB
|
||||
|
||||
|
||||
foodnstuff
|
||||
--Root Access: NO, Required hacking skill: 1
|
||||
--Number of open ports required to NUKE: 0
|
||||
--RAM: 16.00GB
|
||||
|
||||
|
||||
sigma-cosmetics
|
||||
--Root Access: NO, Required hacking skill: 5
|
||||
--Number of open ports required to NUKE: 0
|
||||
--RAM: 16.00GB
|
||||
|
||||
|
||||
joesguns
|
||||
--Root Access: NO, Required hacking skill: 10
|
||||
--Number of open ports required to NUKE: 0
|
||||
--RAM: 16.00GB
|
||||
|
||||
|
||||
----max-hardware
|
||||
------Root Access: NO, Required hacking skill: 80
|
||||
------Number of open ports required to NUKE: 1
|
||||
------RAM: 32.00GB
|
||||
|
||||
|
||||
----CSEC
|
||||
------Root Access: NO, Required hacking skill: 54
|
||||
------Number of open ports required to NUKE: 1
|
||||
------RAM: 8.00GB
|
||||
|
||||
|
||||
hong-fang-tea
|
||||
--Root Access: NO, Required hacking skill: 30
|
||||
--Number of open ports required to NUKE: 0
|
||||
--RAM: 16.00GB
|
||||
|
||||
|
||||
----nectar-net
|
||||
------Root Access: NO, Required hacking skill: 20
|
||||
------Number of open ports required to NUKE: 0
|
||||
------RAM: 16.00GB
|
||||
|
||||
|
||||
harakiri-sushi
|
||||
--Root Access: NO, Required hacking skill: 40
|
||||
--Number of open ports required to NUKE: 0
|
||||
--RAM: 16.00GB
|
||||
|
||||
|
||||
iron-gym
|
||||
--Root Access: NO, Required hacking skill: 100
|
||||
--Number of open ports required to NUKE: 1
|
||||
@ -806,8 +806,7 @@ startup script. Feel free to adjust it to your liking.
|
||||
|
||||
// Array of all servers that don't need any ports opened
|
||||
// to gain root access. These have 16 GB of RAM
|
||||
var servers0Port = ["n00dles",
|
||||
"sigma-cosmetics",
|
||||
var servers0Port = ["sigma-cosmetics",
|
||||
"joesguns",
|
||||
"nectar-net",
|
||||
"hong-fang-tea",
|
||||
|
@ -59,15 +59,14 @@ And the data in port 1 will look like::
|
||||
|
||||
.. warning:: In :ref:`netscriptjs`, do not trying writing base
|
||||
`Promises <https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Promise>`_
|
||||
to a port.
|
||||
to a port.
|
||||
|
||||
**Port Handles**
|
||||
|
||||
WARNING: Port Handles only work in :ref:`netscriptjs`. They do not work in :ref:`netscript1`
|
||||
|
||||
The :js:func:`getPortHandle` Netscript function can be used to get a handle to a Netscript Port.
|
||||
This handle allows you to access several new port-related functions and the
|
||||
port's underlying data structure, which is just a JavaScript array. The functions are:
|
||||
This handle allows you to access several new port-related functions. The functions are:
|
||||
|
||||
.. js:method:: NetscriptPort.writePort(data)
|
||||
|
||||
@ -111,22 +110,11 @@ port's underlying data structure, which is just a JavaScript array. The function
|
||||
|
||||
Clears all data from the port. Works the same as the Netscript function `clear`
|
||||
|
||||
.. js:attribute:: NetscriptPort.data
|
||||
|
||||
The Netscript port underlying data structure, which is just a Javascript array. All
|
||||
valid Javascript Array methods can be called on this.
|
||||
|
||||
Port Handle Example::
|
||||
|
||||
port = getPortHandle(5);
|
||||
back = port.data.pop(); //Get and remove last element in port
|
||||
|
||||
//Remove an element from the port
|
||||
i = port.data.findIndex("foo");
|
||||
if (i != -1) {
|
||||
port.data.slice(i, 1);
|
||||
}
|
||||
|
||||
//Wait for port data before reading
|
||||
while(port.empty()) {
|
||||
sleep(10000);
|
||||
|
@ -18,8 +18,18 @@ import { HacknetNodeConstants } from "./data/Constants";
|
||||
|
||||
import { dialogBoxCreate } from "../ui/React/DialogBox";
|
||||
import { Generic_fromJSON, Generic_toJSON, Reviver } from "../utils/JSONReviver";
|
||||
import { ObjectValidator, minMax } from "../utils/Validator";
|
||||
|
||||
export class HacknetNode implements IHacknetNode {
|
||||
|
||||
static validationData: ObjectValidator<HacknetNode> = {
|
||||
cores: minMax(1, 1, HacknetNodeConstants.MaxCores),
|
||||
level: minMax(1, 1, HacknetNodeConstants.MaxLevel),
|
||||
ram: minMax(1, 1, HacknetNodeConstants.MaxRam),
|
||||
onlineTimeSeconds: minMax(0, 0, Infinity),
|
||||
totalMoneyGenerated: minMax(0, 0, Infinity)
|
||||
}
|
||||
|
||||
// Node's number of cores
|
||||
cores = 1;
|
||||
|
||||
|
185
src/ScriptEditor/NetscriptDefinitions.d.ts
vendored
185
src/ScriptEditor/NetscriptDefinitions.d.ts
vendored
@ -109,32 +109,6 @@ interface RunningScript {
|
||||
threads: number;
|
||||
}
|
||||
|
||||
/**
|
||||
* Interface of a netscript port
|
||||
* @public
|
||||
*/
|
||||
export interface IPort {
|
||||
/** write data to the port and removes and returns first element if full */
|
||||
write: (value: any) => any;
|
||||
/** add data to port if not full.
|
||||
* @returns true if added and false if full and not added */
|
||||
tryWrite: (value: any) => boolean;
|
||||
/** reads and removes first element from port
|
||||
* if no data in port returns "NULL PORT DATA"
|
||||
*/
|
||||
read: () => any;
|
||||
/** reads first element without removing it from port
|
||||
* if no data in port returns "NULL PORT DATA"
|
||||
*/
|
||||
peek: () => any;
|
||||
/** check if port is full */
|
||||
full: () => boolean;
|
||||
/** check if port is empty */
|
||||
empty: () => boolean;
|
||||
/** removes all data from port */
|
||||
clear: () => void;
|
||||
}
|
||||
|
||||
/**
|
||||
* Data representing the internal values of a crime.
|
||||
* @public
|
||||
@ -280,6 +254,24 @@ export interface AugmentPair {
|
||||
cost: number;
|
||||
}
|
||||
|
||||
/**
|
||||
* @public
|
||||
*/
|
||||
export enum PositionTypes {
|
||||
Long = "L",
|
||||
Short = "S",
|
||||
}
|
||||
|
||||
/**
|
||||
* @public
|
||||
*/
|
||||
export enum OrderTypes {
|
||||
LimitBuy = "Limit Buy Order",
|
||||
LimitSell = "Limit Sell Order",
|
||||
StopBuy = "Stop Buy Order",
|
||||
StopSell = "Stop Sell Order",
|
||||
}
|
||||
|
||||
/**
|
||||
* Value in map of {@link StockOrder}
|
||||
* @public
|
||||
@ -290,17 +282,18 @@ export interface StockOrderObject {
|
||||
/** Price per share */
|
||||
price: number;
|
||||
/** Order type */
|
||||
type: string;
|
||||
type: OrderTypes;
|
||||
/** Order position */
|
||||
position: string;
|
||||
position: PositionTypes;
|
||||
}
|
||||
|
||||
/**
|
||||
* Return value of {@link TIX.getOrders | getOrders}
|
||||
*
|
||||
* Keys are stock symbols, properties are arrays of {@link StockOrderObject}
|
||||
* @public
|
||||
*/
|
||||
export interface StockOrder {
|
||||
/** Stock Symbol */
|
||||
[key: string]: StockOrderObject[];
|
||||
}
|
||||
|
||||
@ -488,6 +481,8 @@ export interface BitNodeMultipliers {
|
||||
FourSigmaMarketDataApiCost: number;
|
||||
/** Influences how much it costs to unlock the stock market's 4S Market Data (NOT API) */
|
||||
FourSigmaMarketDataCost: number;
|
||||
/** Influences the respect gain and money gain of your gang. */
|
||||
GangSoftcap: number;
|
||||
/** Influences the experienced gained when hacking a server. */
|
||||
HackExpGain: number;
|
||||
/** Influences how quickly the player's hacking level (not experience) scales */
|
||||
@ -508,10 +503,14 @@ export interface BitNodeMultipliers {
|
||||
PurchasedServerLimit: number;
|
||||
/** Influences the maximum allowed RAM for a purchased server */
|
||||
PurchasedServerMaxRam: number;
|
||||
/** Influences cost of any purchased server at or above 128GB */
|
||||
PurchasedServerSoftCap: number;
|
||||
/** Influences the minimum favor the player must have with a faction before they can donate to gain rep. */
|
||||
RepToDonateToFaction: number;
|
||||
/** Influences how much money can be stolen from a server when a script performs a hack against it. */
|
||||
/** Influences how much the money on a server can be reduced when a script performs a hack against it. */
|
||||
ScriptHackMoney: number;
|
||||
/** Influences how much of the money stolen by a scripted hack will be added to the player's money. */
|
||||
ScriptHackMoneyGain: number;
|
||||
/** Influences the growth percentage per cycle against a server. */
|
||||
ServerGrowthRate: number;
|
||||
/** Influences the maxmimum money that a server can grow to. */
|
||||
@ -524,6 +523,12 @@ export interface BitNodeMultipliers {
|
||||
ServerWeakenRate: number;
|
||||
/** Influences how quickly the player's strength level (not exp) scales */
|
||||
StrengthLevelMultiplier: number;
|
||||
/** Influences the power of the gift */
|
||||
StaneksGiftPowerMultiplier: number;
|
||||
/** Influences the size of the gift */
|
||||
StaneksGiftExtraSize: number;
|
||||
/** Influences the hacking skill required to backdoor the world daemon. */
|
||||
WorldDaemonDifficulty: number;
|
||||
}
|
||||
|
||||
/**
|
||||
@ -535,9 +540,9 @@ export interface NodeStats {
|
||||
name: string;
|
||||
/** Node's level */
|
||||
level: number;
|
||||
/** Node's RAM */
|
||||
/** Node's RAM (GB) */
|
||||
ram: number;
|
||||
/** Node's used RAM */
|
||||
/** Node's used RAM (GB) */
|
||||
ramUsed: number;
|
||||
/** Node's number of cores */
|
||||
cores: number;
|
||||
@ -956,6 +961,78 @@ export interface SleeveTask {
|
||||
factionWorkType: string;
|
||||
}
|
||||
|
||||
/**
|
||||
* Object representing a port. A port is a serialized queue.
|
||||
* @public
|
||||
*/
|
||||
export interface NetscriptPort {
|
||||
/**
|
||||
* Write data to a port.
|
||||
* @remarks
|
||||
* RAM cost: 0 GB
|
||||
*
|
||||
* @returns The data popped off the queue if it was full.
|
||||
*/
|
||||
write(value: string|number): null|string|number;
|
||||
|
||||
/**
|
||||
* Attempt to write data to the port.
|
||||
* @remarks
|
||||
* RAM cost: 0 GB
|
||||
*
|
||||
* @returns True if the data was added to the port, false if the port was full
|
||||
*/
|
||||
tryWrite(value: string|number): boolean;
|
||||
|
||||
/**
|
||||
* Shift an element out of the port.
|
||||
* @remarks
|
||||
* RAM cost: 0 GB
|
||||
*
|
||||
* This function will remove the first element from the port and return it.
|
||||
* If the port is empty, then the string “NULL PORT DATA” will be returned.
|
||||
* @returns the data read.
|
||||
*/
|
||||
read(): string|number;
|
||||
|
||||
/**
|
||||
* Retrieve the first element from the port without removing it.
|
||||
* @remarks
|
||||
* RAM cost: 0 GB
|
||||
*
|
||||
* This function is used to peek at the data from a port. It returns the
|
||||
* first element in the specified port without removing that element. If
|
||||
* the port is empty, the string “NULL PORT DATA” will be returned.
|
||||
* @returns the data read
|
||||
*/
|
||||
peek(): string|number;
|
||||
|
||||
/**
|
||||
* Check if the port is full.
|
||||
* @remarks
|
||||
* RAM cost: 0 GB
|
||||
*
|
||||
* @returns true if the port is full, otherwise false
|
||||
*/
|
||||
full(): boolean;
|
||||
|
||||
/**
|
||||
* Check if the port is empty.
|
||||
* @remarks
|
||||
* RAM cost: 0 GB
|
||||
*
|
||||
* @returns true if the port is empty, otherwise false
|
||||
*/
|
||||
empty(): boolean;
|
||||
|
||||
/**
|
||||
* Empties all data from the port.
|
||||
* @remarks
|
||||
* RAM cost: 0 GB
|
||||
*/
|
||||
clear(): void;
|
||||
}
|
||||
|
||||
/**
|
||||
* Stock market API
|
||||
* @public
|
||||
@ -1213,6 +1290,8 @@ export interface TIX {
|
||||
* @remarks
|
||||
* RAM cost: 2.5 GB
|
||||
* This is an object containing information for all the Limit and Stop Orders you have in the stock market.
|
||||
* For each symbol you have a position in, the returned object will have a key with that symbol's name.
|
||||
* The object's properties are each an array of {@link StockOrderObject}
|
||||
* The object has the following structure:
|
||||
*
|
||||
* ```ts
|
||||
@ -4440,11 +4519,11 @@ export interface NS extends Singularity {
|
||||
* //Get logs from foo.script on the foodnstuff server that was run with the arguments [1, "test"]
|
||||
* ns.tail("foo.script", "foodnstuff", 1, "test");
|
||||
* ```
|
||||
* @param fn - Optional. Filename of the script being tailed. If omitted, the current script is tailed.
|
||||
* @param fn - Optional. Filename or PID of the script being tailed. If omitted, the current script is tailed.
|
||||
* @param host - Optional. Hostname of the script being tailed. Defaults to the server this script is running on. If args are specified, this is not optional.
|
||||
* @param args - Arguments for the script being tailed.
|
||||
*/
|
||||
tail(fn?: string, host?: string, ...args: any[]): void;
|
||||
tail(fn?: FilenameOrPID, host?: string, ...args: any[]): void;
|
||||
|
||||
/**
|
||||
* Get the list of servers connected to a server.
|
||||
@ -5094,7 +5173,7 @@ export interface NS extends Singularity {
|
||||
* const [totalRam, ramUsed] = ns.getServerRam("helios");
|
||||
* ```
|
||||
* @param host - Host of target server.
|
||||
* @returns Array with total and used memory on the specified server.
|
||||
* @returns Array with total and used memory on the specified server, in GB.
|
||||
*/
|
||||
getServerRam(host: string): [number, number];
|
||||
|
||||
@ -5104,7 +5183,7 @@ export interface NS extends Singularity {
|
||||
* RAM cost: 0.05 GB
|
||||
*
|
||||
* @param host - Hostname of the target server.
|
||||
* @returns max ram
|
||||
* @returns max ram (GB)
|
||||
*/
|
||||
getServerMaxRam(host: string): number;
|
||||
/**
|
||||
@ -5113,7 +5192,7 @@ export interface NS extends Singularity {
|
||||
* RAM cost: 0.05 GB
|
||||
*
|
||||
* @param host - Hostname of the target server.
|
||||
* @returns used ram
|
||||
* @returns used ram (GB)
|
||||
*/
|
||||
getServerUsedRam(host: string): number;
|
||||
|
||||
@ -5187,6 +5266,7 @@ export interface NS extends Singularity {
|
||||
* RAM cost: 0.1 GB
|
||||
*
|
||||
* Returns a boolean indicating whether the specified script is running on the target server.
|
||||
* If you use a PID instead of a filename, the hostname and args parameters are unnecessary.
|
||||
* Remember that a script is uniquely identified by both its name and its arguments.
|
||||
*
|
||||
* @example
|
||||
@ -5213,12 +5293,12 @@ export interface NS extends Singularity {
|
||||
* //The function call will return true if there is a script named foo.script running with the arguments 1, 5, and “test” (in that order) on the joesguns server, and false otherwise:
|
||||
* ns.isRunning("foo.script", "joesguns", 1, 5, "test");
|
||||
* ```
|
||||
* @param script - Filename of script to check. This is case-sensitive.
|
||||
* @param script - Filename or PID of script to check. This is case-sensitive.
|
||||
* @param host - Host of target server.
|
||||
* @param args - Arguments to specify/identify which scripts to search for.
|
||||
* @returns True if specified script is running on the target server, and false otherwise.
|
||||
*/
|
||||
isRunning(script: string, host: string, ...args: string[]): boolean;
|
||||
isRunning(script: FilenameOrPID, host: string, ...args: string[]): boolean;
|
||||
|
||||
/**
|
||||
* Get general info about a running script.
|
||||
@ -5226,10 +5306,14 @@ export interface NS extends Singularity {
|
||||
* RAM cost: 0.3 GB
|
||||
*
|
||||
* Running with no args returns curent script.
|
||||
* If you use a PID as the first parameter, the hostname and args parameters are unnecessary.
|
||||
*
|
||||
* @param filename - Optional. Filename or PID of the script.
|
||||
* @param hostname - Optional. Name of host server the script is running on.
|
||||
* @param args - Arguments to identify the script
|
||||
* @returns info about a running script
|
||||
*/
|
||||
getRunningScript(filename?: string | number, hostname?: string, ...args: (string | number)[]): RunningScript;
|
||||
getRunningScript(filename?: FilenameOrPID, hostname?: string, ...args: (string | number)[]): RunningScript;
|
||||
|
||||
/**
|
||||
* Get cost of purchasing a server.
|
||||
@ -5252,7 +5336,7 @@ export interface NS extends Singularity {
|
||||
* ns.tprint(i + " -- " + ns.getPurchasedServerCost(Math.pow(2, i)));
|
||||
* }
|
||||
* ```
|
||||
* @param ram - Amount of RAM of a potential purchased server. Must be a power of 2 (2, 4, 8, 16, etc.). Maximum value of 1048576 (2^20).
|
||||
* @param ram - Amount of RAM of a potential purchased server, in GB. Must be a power of 2 (2, 4, 8, 16, etc.). Maximum value of 1048576 (2^20).
|
||||
* @returns The cost to purchase a server with the specified amount of ram.
|
||||
*/
|
||||
getPurchasedServerCost(ram: number): number;
|
||||
@ -5300,7 +5384,7 @@ export interface NS extends Singularity {
|
||||
* }
|
||||
* ```
|
||||
* @param hostname - Host of the purchased server.
|
||||
* @param ram - Amount of RAM of the purchased server. Must be a power of 2 (2, 4, 8, 16, etc.). Maximum value of 1048576 (2^20).
|
||||
* @param ram - Amount of RAM of the purchased server, in GB. Must be a power of 2 (2, 4, 8, 16, etc.). Maximum value of 1048576 (2^20).
|
||||
* @returns The hostname of the newly purchased server.
|
||||
*/
|
||||
purchaseServer(hostname: string, ram: number): string;
|
||||
@ -5341,7 +5425,7 @@ export interface NS extends Singularity {
|
||||
* Returns the maximum RAM that a purchased server can have.
|
||||
*
|
||||
* @remarks RAM cost: 0.05 GB
|
||||
* @returns Returns the maximum RAM that a purchased server can have.
|
||||
* @returns Returns the maximum RAM (in GB) that a purchased server can have.
|
||||
*/
|
||||
getPurchasedServerMaxRam(): number;
|
||||
|
||||
@ -5350,7 +5434,7 @@ export interface NS extends Singularity {
|
||||
* @remarks
|
||||
* RAM cost: 0 GB
|
||||
*
|
||||
* This function can be used to either write data to a text file (.txt).
|
||||
* This function can be used to write data to a text file (.txt).
|
||||
*
|
||||
* This function will write data to that text file. If the specified text file does not exist,
|
||||
* then it will be created. The third argument mode, defines how the data will be written to
|
||||
@ -5359,7 +5443,7 @@ export interface NS extends Singularity {
|
||||
* then the data will be written in “append” mode which means that the data will be added at the
|
||||
* end of the text file.
|
||||
*
|
||||
* @param handle - Port or text file that will be written to.
|
||||
* @param handle - Filename of the text file that will be written to.
|
||||
* @param data - Data to write.
|
||||
* @param mode - Defines the write mode. Only valid when writing to text files.
|
||||
*/
|
||||
@ -5385,13 +5469,13 @@ export interface NS extends Singularity {
|
||||
* @remarks
|
||||
* RAM cost: 0 GB
|
||||
*
|
||||
* This function is used to read data from a port or from a text file (.txt).
|
||||
* This function is used to read data from a text file (.txt).
|
||||
*
|
||||
* This function will return the data in the specified text
|
||||
* file. If the text file does not exist, an empty string will be returned.
|
||||
*
|
||||
* @param handle - Port or text file to read from.
|
||||
* @returns Data in the specified text file or port.
|
||||
* @param handle - Filename to read from.
|
||||
* @returns Data in the specified text file.
|
||||
*/
|
||||
read(handle: string): any;
|
||||
|
||||
@ -5463,9 +5547,8 @@ export interface NS extends Singularity {
|
||||
*
|
||||
* @see https://bitburner.readthedocs.io/en/latest/netscript/netscriptmisc.html#netscript-ports
|
||||
* @param port - Port number. Must be an integer between 1 and 20.
|
||||
* @returns Data in the specified port.
|
||||
*/
|
||||
getPortHandle(port: number): IPort;
|
||||
getPortHandle(port: number): NetscriptPort;
|
||||
|
||||
/**
|
||||
* Delete a file.
|
||||
@ -5548,7 +5631,7 @@ export interface NS extends Singularity {
|
||||
*
|
||||
* @param script - Filename of script. This is case-sensitive.
|
||||
* @param host - Host of target server the script is located on. This is optional, If it is not specified then the function will se the current server as the target server.
|
||||
* @returns Amount of RAM required to run the specified script on the target server, and 0 if the script does not exist.
|
||||
* @returns Amount of RAM (in GB) required to run the specified script on the target server, and 0 if the script does not exist.
|
||||
*/
|
||||
getScriptRam(script: string, host?: string): number;
|
||||
|
||||
|
@ -1,9 +1,13 @@
|
||||
import { Theme } from "@mui/material/styles";
|
||||
import createStyles from "@mui/styles/createStyles";
|
||||
import makeStyles from "@mui/styles/makeStyles";
|
||||
import { toString } from "lodash";
|
||||
import React from "react";
|
||||
import { ITerminal } from "../ITerminal";
|
||||
import { IRouter } from "../../ui/Router";
|
||||
import { IPlayer } from "../../PersonObjects/IPlayer";
|
||||
import { BaseServer } from "../../Server/BaseServer";
|
||||
import { getFirstParentDirectory, isValidDirectoryPath, evaluateDirectoryPath } from "../../Terminal/DirectoryHelpers";
|
||||
import { evaluateDirectoryPath, getFirstParentDirectory, isValidDirectoryPath } from "../../Terminal/DirectoryHelpers";
|
||||
import { IRouter } from "../../ui/Router";
|
||||
import { ITerminal } from "../ITerminal";
|
||||
|
||||
export function ls(
|
||||
terminal: ITerminal,
|
||||
@ -113,7 +117,55 @@ export function ls(
|
||||
allMessages.sort();
|
||||
folders.sort();
|
||||
|
||||
function postSegments(segments: string[], style?: any): void {
|
||||
interface ClickableScriptRowProps {
|
||||
row: string;
|
||||
prefix: string;
|
||||
hostname: string;
|
||||
}
|
||||
|
||||
function ClickableScriptRow({ row, prefix, hostname }: ClickableScriptRowProps): React.ReactElement {
|
||||
const classes = makeStyles((theme: Theme) =>
|
||||
createStyles({
|
||||
scriptLinksWrap: {
|
||||
display: "flex",
|
||||
color: theme.palette.warning.main,
|
||||
},
|
||||
scriptLink: {
|
||||
cursor: "pointer",
|
||||
textDecorationLine: "underline",
|
||||
paddingRight: "1.15em",
|
||||
"&:last-child": { padding: 0 },
|
||||
},
|
||||
}),
|
||||
)();
|
||||
|
||||
const rowSplit = row
|
||||
.split(" ")
|
||||
.map((x) => x.trim())
|
||||
.filter((x) => !!x);
|
||||
|
||||
function onScriptLinkClick(filename: string): void {
|
||||
if (player.getCurrentServer().hostname !== hostname) {
|
||||
return terminal.error(`File is not on this server, connect to ${hostname} and try again`);
|
||||
}
|
||||
if (filename.startsWith("/")) filename = filename.slice(1);
|
||||
const filepath = terminal.getFilepath(`${prefix}${filename}`);
|
||||
const code = toString(terminal.getScript(player, filepath)?.code);
|
||||
router.toScriptEditor({ [filepath]: code });
|
||||
}
|
||||
|
||||
return (
|
||||
<span className={classes.scriptLinksWrap}>
|
||||
{rowSplit.map((rowItem) => (
|
||||
<span key={rowItem} className={classes.scriptLink} onClick={() => onScriptLinkClick(rowItem)}>
|
||||
{rowItem}
|
||||
</span>
|
||||
))}
|
||||
</span>
|
||||
);
|
||||
}
|
||||
|
||||
function postSegments(segments: string[], style?: any, linked?: boolean): void {
|
||||
const maxLength = Math.max(...segments.map((s) => s.length)) + 1;
|
||||
const filesPerRow = Math.floor(80 / maxLength);
|
||||
for (let i = 0; i < segments.length; i++) {
|
||||
@ -128,7 +180,11 @@ export function ls(
|
||||
if (!style) {
|
||||
terminal.print(row);
|
||||
} else {
|
||||
terminal.printRaw(<span style={style}>{row}</span>);
|
||||
if (linked) {
|
||||
terminal.printRaw(<ClickableScriptRow row={row} prefix={prefix} hostname={server.hostname} />);
|
||||
} else {
|
||||
terminal.printRaw(<span style={style}>{row}</span>);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
@ -139,9 +195,9 @@ export function ls(
|
||||
{ segments: allTextFiles },
|
||||
{ segments: allPrograms },
|
||||
{ segments: allContracts },
|
||||
{ segments: allScripts, style: { color: "yellow", fontStyle: "bold" } },
|
||||
{ segments: allScripts, style: { color: "yellow", fontStyle: "bold" }, linked: true },
|
||||
].filter((g) => g.segments.length > 0);
|
||||
for (let i = 0; i < groups.length; i++) {
|
||||
postSegments(groups[i].segments, groups[i].style);
|
||||
postSegments(groups[i].segments, groups[i].style, groups[i].linked);
|
||||
}
|
||||
}
|
||||
|
@ -279,7 +279,7 @@ export const codingContractTypesMetadata: ICodingContractTypeMetadata[] = [
|
||||
"i to i+n.",
|
||||
"\n\nAssuming you are initially positioned",
|
||||
"at the start of the array, determine whether you are",
|
||||
"able to reach the last index exactly.\n\n",
|
||||
"able to reach the last index.\n\n",
|
||||
"Your answer should be submitted as 1 or 0, representing true and false respectively",
|
||||
].join(" ");
|
||||
},
|
||||
|
@ -1,5 +1,7 @@
|
||||
/* Generic Reviver, toJSON, and fromJSON functions used for saving and loading objects */
|
||||
|
||||
import { validateObject } from "./Validator";
|
||||
|
||||
interface IReviverValue {
|
||||
ctor: string;
|
||||
data: any;
|
||||
@ -26,7 +28,11 @@ export function Reviver(key: string, value: IReviverValue | null): any {
|
||||
const ctor = Reviver.constructors[value.ctor];
|
||||
|
||||
if (typeof ctor === "function" && typeof ctor.fromJSON === "function") {
|
||||
return ctor.fromJSON(value);
|
||||
const obj = ctor.fromJSON(value);
|
||||
if (ctor.validationData !== undefined) {
|
||||
validateObject(obj, ctor.validationData);
|
||||
}
|
||||
return obj;
|
||||
}
|
||||
}
|
||||
return value;
|
||||
|
78
src/utils/Validator.ts
Normal file
78
src/utils/Validator.ts
Normal file
@ -0,0 +1,78 @@
|
||||
export type ObjectValidator<T> = {
|
||||
[key in keyof T]?: ParameterValidator<T, keyof T>;
|
||||
}
|
||||
|
||||
interface ParameterValidatorObject<Type, Key extends keyof Type> {
|
||||
default?: any;
|
||||
min?: number;
|
||||
max?: number;
|
||||
func?: (obj: Type, validator: ObjectValidator<Type>, key: Key) => void;
|
||||
}
|
||||
type ParameterValidatorFunction<Type, Key extends keyof Type> = (obj: Type, key: Key) => void;
|
||||
type ParameterValidator<Type, Key extends keyof Type> = ParameterValidatorObject<Type, Key> | ParameterValidatorFunction<Type, Key>
|
||||
|
||||
export function validateObject<Type extends Record<string, unknown>, Key extends keyof Type>(obj: Type, validator: ObjectValidator<Type>): void {
|
||||
for (const key of Object.keys(validator) as Key[]) {
|
||||
const paramValidator = validator[key];
|
||||
if (paramValidator !== undefined) {
|
||||
if (typeof paramValidator === 'function') {
|
||||
paramValidator(obj, key);
|
||||
} else {
|
||||
if (paramValidator.func !== undefined) {
|
||||
paramValidator.func(obj, validator, key);
|
||||
} else {
|
||||
if ((typeof obj[key]) !== (typeof paramValidator.default)) {
|
||||
obj[key] = paramValidator.default
|
||||
}
|
||||
if (typeof obj[key] === 'number' && paramValidator.min !== undefined) {
|
||||
if (obj[key] < paramValidator.min) obj[key] = paramValidator.min as Type[Key];
|
||||
}
|
||||
if (typeof obj[key] === 'number' && paramValidator.max !== undefined) {
|
||||
if (obj[key] > paramValidator.max) obj[key] = paramValidator.max as Type[Key];
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
export function minMax<Type, Key extends keyof Type>(def: number, min: number, max: number): (obj: Type, key: Key & keyof Type) => void {
|
||||
return (obj, key) => {
|
||||
if (typeof obj[key] !== 'number') {
|
||||
obj[key] = def as unknown as Type[Key];
|
||||
return;
|
||||
}
|
||||
if ((obj[key] as unknown as number) < min) {
|
||||
obj[key] = min as unknown as Type[Key];
|
||||
}
|
||||
if ((obj[key] as unknown as number) > max) {
|
||||
obj[key] = max as unknown as Type[Key];
|
||||
}
|
||||
};
|
||||
}
|
||||
|
||||
export function oneOf<Type, Key extends keyof Type, Value>(def: Value, options: Value[]): (obj: Type, key: Key & keyof Type) => void {
|
||||
return (obj, key) => {
|
||||
if (typeof obj[key] !== typeof def) {
|
||||
obj[key] = def as unknown as Type[Key];
|
||||
return;
|
||||
}
|
||||
if (!options.includes(obj[key] as unknown as Value)) {
|
||||
obj[key] = def as unknown as Type[Key];
|
||||
}
|
||||
};
|
||||
}
|
||||
|
||||
export function subsetOf<Type, Key extends keyof Type, Value>(options: Value[]): (obj: Type, key: Key & keyof Type) => void {
|
||||
return (obj, key) => {
|
||||
if (typeof obj[key] !== 'object' || !Array.isArray(obj[key])) {
|
||||
obj[key] = [] as unknown as Type[Key];
|
||||
return;
|
||||
}
|
||||
const validValues: Value[] = [];
|
||||
for (const value of obj[key] as unknown as Value[]) {
|
||||
if (options.includes(value)) validValues.push(value);
|
||||
}
|
||||
obj[key] = validValues as unknown as Type[Key];
|
||||
};
|
||||
}
|
Loading…
Reference in New Issue
Block a user