Updated example 5/13/14/18 to use DatabaseService
This commit is contained in:
parent
6ea6803456
commit
9bbc7d7a25
@ -5,7 +5,6 @@ import { IPreSptLoadMod } from "@spt/models/external/IPreSptLoadMod";
|
|||||||
import { IPostDBLoadMod } from "@spt/models/external/IPostDBLoadMod";
|
import { IPostDBLoadMod } from "@spt/models/external/IPostDBLoadMod";
|
||||||
import { ILogger } from "@spt/models/spt/utils/ILogger";
|
import { ILogger } from "@spt/models/spt/utils/ILogger";
|
||||||
import { PreSptModLoader } from "@spt/loaders/PreSptModLoader";
|
import { PreSptModLoader } from "@spt/loaders/PreSptModLoader";
|
||||||
import { DatabaseServer } from "@spt/servers/DatabaseServer";
|
|
||||||
import { ImageRouter } from "@spt/routers/ImageRouter";
|
import { ImageRouter } from "@spt/routers/ImageRouter";
|
||||||
import { ConfigServer } from "@spt/servers/ConfigServer";
|
import { ConfigServer } from "@spt/servers/ConfigServer";
|
||||||
import { ConfigTypes } from "@spt/models/enums/ConfigTypes";
|
import { ConfigTypes } from "@spt/models/enums/ConfigTypes";
|
||||||
@ -21,6 +20,7 @@ import * as baseJson from "../db/base.json";
|
|||||||
|
|
||||||
import { TraderHelper } from "./traderHelpers";
|
import { TraderHelper } from "./traderHelpers";
|
||||||
import { FluentAssortConstructor as FluentAssortCreator } from "./fluentTraderAssortCreator";
|
import { FluentAssortConstructor as FluentAssortCreator } from "./fluentTraderAssortCreator";
|
||||||
|
import { DatabaseService } from "@spt/services/DatabaseService";
|
||||||
|
|
||||||
class SampleTrader implements IPreSptLoadMod, IPostDBLoadMod
|
class SampleTrader implements IPreSptLoadMod, IPostDBLoadMod
|
||||||
{
|
{
|
||||||
@ -44,7 +44,7 @@ class SampleTrader implements IPreSptLoadMod, IPostDBLoadMod
|
|||||||
this.logger.debug(`[${this.mod}] preSpt Loading... `);
|
this.logger.debug(`[${this.mod}] preSpt Loading... `);
|
||||||
|
|
||||||
// Get SPT code/data we need later
|
// Get SPT code/data we need later
|
||||||
const PreSptModLoader: PreSptModLoader = container.resolve<PreSptModLoader>("PreSptModLoader");
|
const preSptModLoader: PreSptModLoader = container.resolve<PreSptModLoader>("PreSptModLoader");
|
||||||
const imageRouter: ImageRouter = container.resolve<ImageRouter>("ImageRouter");
|
const imageRouter: ImageRouter = container.resolve<ImageRouter>("ImageRouter");
|
||||||
const hashUtil: HashUtil = container.resolve<HashUtil>("HashUtil");
|
const hashUtil: HashUtil = container.resolve<HashUtil>("HashUtil");
|
||||||
const configServer = container.resolve<ConfigServer>("ConfigServer");
|
const configServer = container.resolve<ConfigServer>("ConfigServer");
|
||||||
@ -54,7 +54,7 @@ class SampleTrader implements IPreSptLoadMod, IPostDBLoadMod
|
|||||||
// Create helper class and use it to register our traders image/icon + set its stock refresh time
|
// Create helper class and use it to register our traders image/icon + set its stock refresh time
|
||||||
this.traderHelper = new TraderHelper();
|
this.traderHelper = new TraderHelper();
|
||||||
this.fluentAssortCreator = new FluentAssortCreator(hashUtil, this.logger);
|
this.fluentAssortCreator = new FluentAssortCreator(hashUtil, this.logger);
|
||||||
this.traderHelper.registerProfileImage(baseJson, this.mod, PreSptModLoader, imageRouter, "cat.jpg");
|
this.traderHelper.registerProfileImage(baseJson, this.mod, preSptModLoader, imageRouter, "cat.jpg");
|
||||||
this.traderHelper.setTraderUpdateTime(traderConfig, baseJson, 3600, 4000);
|
this.traderHelper.setTraderUpdateTime(traderConfig, baseJson, 3600, 4000);
|
||||||
|
|
||||||
// Add trader to trader enum
|
// Add trader to trader enum
|
||||||
@ -74,37 +74,38 @@ class SampleTrader implements IPreSptLoadMod, IPostDBLoadMod
|
|||||||
{
|
{
|
||||||
this.logger.debug(`[${this.mod}] postDb Loading... `);
|
this.logger.debug(`[${this.mod}] postDb Loading... `);
|
||||||
|
|
||||||
// Resolve SPT classes we'll use
|
// Resolve SPT classes we'll need
|
||||||
const databaseServer: DatabaseServer = container.resolve<DatabaseServer>("DatabaseServer");
|
const databaseService = container.resolve<DatabaseService>("DatabaseService");
|
||||||
const configServer: ConfigServer = container.resolve<ConfigServer>("ConfigServer");
|
|
||||||
const jsonUtil: JsonUtil = container.resolve<JsonUtil>("JsonUtil");
|
const jsonUtil: JsonUtil = container.resolve<JsonUtil>("JsonUtil");
|
||||||
|
|
||||||
// Get a reference to the database tables
|
// Get references to database data we need
|
||||||
const tables = databaseServer.getTables();
|
const traders = databaseService.getTraders();
|
||||||
|
const globals = databaseService.getGlobals();
|
||||||
|
const locales = databaseService.getLocales();
|
||||||
|
|
||||||
// Add new trader to the trader dictionary in DatabaseServer - has no assorts (items) yet
|
// Add new trader to the trader dictionary in DatabaseServer - has no assorts (items) yet
|
||||||
this.traderHelper.addTraderToDb(baseJson, tables, jsonUtil);
|
this.traderHelper.addTraderToDb(baseJson, traders, jsonUtil);
|
||||||
|
|
||||||
// Add milk
|
// Add milk
|
||||||
const MILK_ID = "575146b724597720a27126d5"; // Can find item ids in `database\templates\items.json` or with https://db.sp-tarkov.com/search
|
const MILK_ID = "575146b724597720a27126d5"; // Can find item ids in: `database\templates\items.json` or with: https://db.sp-tarkov.com/search
|
||||||
this.fluentAssortCreator
|
this.fluentAssortCreator
|
||||||
.createSingleAssortItem(MILK_ID)
|
.createSingleAssortItem(MILK_ID)
|
||||||
.addStackCount(200)
|
.addStackCount(200)
|
||||||
.addBuyRestriction(10)
|
.addBuyRestriction(10)
|
||||||
.addMoneyCost(Money.ROUBLES, 2000)
|
.addMoneyCost(Money.ROUBLES, 2000)
|
||||||
.addLoyaltyLevel(1)
|
.addLoyaltyLevel(1)
|
||||||
.export(tables.traders[baseJson._id]);
|
.export(traders[baseJson._id]);
|
||||||
|
|
||||||
// Add 3x bitcoin + salewa for milk barter
|
// Add 3x bitcoin + salewa for milk barter
|
||||||
const BITCOIN_ID = "59faff1d86f7746c51718c9c";
|
const BITCOIN_ID = "59faff1d86f7746c51718c9c"; // Can find item ids in: `database\templates\items.json` or with: https://db.sp-tarkov.com/search
|
||||||
const SALEWA_ID = "544fb45d4bdc2dee738b4568";
|
const SALEWA_ID = "544fb45d4bdc2dee738b4568"; // Can find item ids in: `database\templates\items.json` or with: https://db.sp-tarkov.com/search
|
||||||
this.fluentAssortCreator
|
this.fluentAssortCreator
|
||||||
.createSingleAssortItem(MILK_ID)
|
.createSingleAssortItem(MILK_ID)
|
||||||
.addStackCount(100)
|
.addStackCount(100)
|
||||||
.addBarterCost(BITCOIN_ID, 3)
|
.addBarterCost(BITCOIN_ID, 3)
|
||||||
.addBarterCost(SALEWA_ID, 1)
|
.addBarterCost(SALEWA_ID, 1)
|
||||||
.addLoyaltyLevel(1)
|
.addLoyaltyLevel(1)
|
||||||
.export(tables.traders[baseJson._id]);
|
.export(traders[baseJson._id]);
|
||||||
|
|
||||||
|
|
||||||
// Add glock as money purchase
|
// Add glock as money purchase
|
||||||
@ -114,20 +115,20 @@ class SampleTrader implements IPreSptLoadMod, IPostDBLoadMod
|
|||||||
.addMoneyCost(Money.ROUBLES, 20000)
|
.addMoneyCost(Money.ROUBLES, 20000)
|
||||||
.addBuyRestriction(3)
|
.addBuyRestriction(3)
|
||||||
.addLoyaltyLevel(1)
|
.addLoyaltyLevel(1)
|
||||||
.export(tables.traders[baseJson._id]);
|
.export(traders[baseJson._id]);
|
||||||
|
|
||||||
// Add mp133 preset as mayo barter
|
// Add mp133 preset as mayo barter
|
||||||
this.fluentAssortCreator
|
this.fluentAssortCreator
|
||||||
.createComplexAssortItem(tables.globals.ItemPresets["584148f2245977598f1ad387"]._items)
|
.createComplexAssortItem(globals.ItemPresets["584148f2245977598f1ad387"]._items)
|
||||||
.addStackCount(200)
|
.addStackCount(200)
|
||||||
.addBarterCost("5bc9b156d4351e00367fbce9", 1)
|
.addBarterCost("5bc9b156d4351e00367fbce9", 1)
|
||||||
.addBuyRestriction(3)
|
.addBuyRestriction(3)
|
||||||
.addLoyaltyLevel(1)
|
.addLoyaltyLevel(1)
|
||||||
.export(tables.traders[baseJson._id]);
|
.export(traders[baseJson._id]);
|
||||||
|
|
||||||
// Add trader to locale file, ensures trader text shows properly on screen
|
// Add trader to locale file, ensures trader text shows properly on screen
|
||||||
// WARNING: adds the same text to ALL locales (e.g. chinese/french/english)
|
// WARNING: adds the same text to ALL locales (e.g. chinese/french/english)
|
||||||
this.traderHelper.addTraderToLocales(baseJson, tables, baseJson.name, "Cat", baseJson.nickname, baseJson.location, "This is the cat shop");
|
this.traderHelper.addTraderToLocales(baseJson, locales, baseJson.name, "Cat", baseJson.nickname, baseJson.location, "This is the cat shop");
|
||||||
|
|
||||||
this.logger.debug(`[${this.mod}] postDb Loaded`);
|
this.logger.debug(`[${this.mod}] postDb Loaded`);
|
||||||
}
|
}
|
||||||
|
@ -1,29 +1,30 @@
|
|||||||
import { PreSptModLoader } from "@spt/loaders/PreSptModLoader";
|
import { PreSptModLoader } from "@spt/loaders/PreSptModLoader";
|
||||||
import { Item } from "@spt/models/eft/common/tables/IItem";
|
import { Item } from "@spt/models/eft/common/tables/IItem";
|
||||||
import { ITraderBase, ITraderAssort } from "@spt/models/eft/common/tables/ITrader";
|
import { ITraderBase, ITraderAssort, ITrader } from "@spt/models/eft/common/tables/ITrader";
|
||||||
import { ITraderConfig, UpdateTime } from "@spt/models/spt/config/ITraderConfig";
|
import { ITraderConfig, UpdateTime } from "@spt/models/spt/config/ITraderConfig";
|
||||||
import { IDatabaseTables } from "@spt/models/spt/server/IDatabaseTables";
|
import { IDatabaseTables } from "@spt/models/spt/server/IDatabaseTables";
|
||||||
|
import { ILocaleBase } from "@spt/models/spt/server/ILocaleBase";
|
||||||
import { ImageRouter } from "@spt/routers/ImageRouter";
|
import { ImageRouter } from "@spt/routers/ImageRouter";
|
||||||
import { JsonUtil } from "@spt/utils/JsonUtil";
|
import { JsonUtil } from "@spt/utils/JsonUtil";
|
||||||
|
|
||||||
export class TraderHelper
|
export class TraderHelper
|
||||||
{
|
{
|
||||||
/**
|
/**
|
||||||
* Add profile picture to our trader
|
* Add profile picture to our trader
|
||||||
* @param baseJson json file for trader (db/base.json)
|
* @param baseJson json file for trader (db/base.json)
|
||||||
* @param modName mod folder name
|
* @param modName mod folder name
|
||||||
* @param PreSptModLoader mod loader class - used to get the mods file path
|
* @param preSptModLoader mod loader class - used to get the mods file path
|
||||||
* @param imageRouter image router class - used to register the trader image path so we see their image on trader page
|
* @param imageRouter image router class - used to register the trader image path so we see their image on trader page
|
||||||
* @param traderImageName Filename of the trader icon to use
|
* @param traderImageName Filename of the trader icon to use
|
||||||
*/
|
*/
|
||||||
public registerProfileImage(baseJson: any, modName: string, PreSptModLoader: PreSptModLoader, imageRouter: ImageRouter, traderImageName: string): void
|
public registerProfileImage(baseJson: any, modName: string, preSptModLoader: PreSptModLoader, imageRouter: ImageRouter, traderImageName: string): void
|
||||||
{
|
{
|
||||||
// Reference the mod "res" folder
|
// Reference the mod "res" folder
|
||||||
const imageFilepath = `./${PreSptModLoader.getModPath(modName)}res`;
|
const imageFilepath = `./${preSptModLoader.getModPath(modName)}res`;
|
||||||
|
|
||||||
// Register a route to point to the profile picture - remember to remove the .jpg from it
|
// Register a route to point to the profile picture - remember to remove the .jpg from it
|
||||||
imageRouter.addRoute(baseJson.avatar.replace(".jpg", ""), `${imageFilepath}/${traderImageName}`);
|
imageRouter.addRoute(baseJson.avatar.replace(".jpg", ""), `${imageFilepath}/${traderImageName}`);
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Add record to trader config to set the refresh time of trader in seconds (default is 60 minutes)
|
* Add record to trader config to set the refresh time of trader in seconds (default is 60 minutes)
|
||||||
@ -39,8 +40,8 @@ export class TraderHelper
|
|||||||
traderId: baseJson._id,
|
traderId: baseJson._id,
|
||||||
seconds: {
|
seconds: {
|
||||||
min: refreshTimeSecondsMin,
|
min: refreshTimeSecondsMin,
|
||||||
max: refreshTimeSecondsMax,
|
max: refreshTimeSecondsMax
|
||||||
},
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
traderConfig.updateTime.push(traderRefreshRecord);
|
traderConfig.updateTime.push(traderRefreshRecord);
|
||||||
@ -49,21 +50,21 @@ export class TraderHelper
|
|||||||
/**
|
/**
|
||||||
* Add our new trader to the database
|
* Add our new trader to the database
|
||||||
* @param traderDetailsToAdd trader details
|
* @param traderDetailsToAdd trader details
|
||||||
* @param tables database
|
* @param traders Traders dictionary (key is traderid, value is trader data)
|
||||||
* @param jsonUtil json utility class
|
* @param jsonUtil json utility class
|
||||||
*/
|
*/
|
||||||
// rome-ignore lint/suspicious/noExplicitAny: traderDetailsToAdd comes from base.json, so no type
|
// rome-ignore lint/suspicious/noExplicitAny: traderDetailsToAdd comes from base.json, so no type
|
||||||
public addTraderToDb(traderDetailsToAdd: any, tables: IDatabaseTables, jsonUtil: JsonUtil): void
|
public addTraderToDb(traderDetailsToAdd: any, traders: Record<string, ITrader>, jsonUtil: JsonUtil): void
|
||||||
{
|
{
|
||||||
// Add trader to trader table, key is the traders id
|
// Add trader to trader table, key is the traders id
|
||||||
tables.traders[traderDetailsToAdd._id] = {
|
traders[traderDetailsToAdd._id] = {
|
||||||
assort: this.createAssortTable(), // assorts are the 'offers' trader sells, can be a single item (e.g. carton of milk) or multiple items as a collection (e.g. a gun)
|
assort: this.createAssortTable(), // assorts are the 'offers' trader sells, can be a single item (e.g. carton of milk) or multiple items as a collection (e.g. a gun)
|
||||||
base: jsonUtil.deserialize(jsonUtil.serialize(traderDetailsToAdd)) as ITraderBase, // Deserialise/serialise creates a copy of the json and allows us to cast it as an ITraderBase
|
base: jsonUtil.deserialize(jsonUtil.serialize(traderDetailsToAdd)) as ITraderBase, // Deserialise/serialise creates a copy of the json and allows us to cast it as an ITraderBase
|
||||||
questassort: {
|
questassort: {
|
||||||
started: {},
|
started: {},
|
||||||
success: {},
|
success: {},
|
||||||
fail: {},
|
fail: {}
|
||||||
}, // questassort is empty as trader has no assorts unlocked by quests
|
} // questassort is empty as trader has no assorts unlocked by quests
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -78,7 +79,7 @@ export class TraderHelper
|
|||||||
nextResupply: 0,
|
nextResupply: 0,
|
||||||
items: [],
|
items: [],
|
||||||
barter_scheme: {},
|
barter_scheme: {},
|
||||||
loyal_level_items: {},
|
loyal_level_items: {}
|
||||||
};
|
};
|
||||||
|
|
||||||
return assortTable;
|
return assortTable;
|
||||||
@ -96,7 +97,7 @@ export class TraderHelper
|
|||||||
// Add the base first
|
// Add the base first
|
||||||
glock.push({ // Add the base weapon first
|
glock.push({ // Add the base weapon first
|
||||||
_id: "glockBase", // Ids dont matter, as long as they are unique (can use hashUtil.generate() if you dont want to type every id by hand)
|
_id: "glockBase", // Ids dont matter, as long as they are unique (can use hashUtil.generate() if you dont want to type every id by hand)
|
||||||
_tpl: "5a7ae0c351dfba0017554310", // This is the weapons tpl, found on: https://db.sp-tarkov.com/search
|
_tpl: "5a7ae0c351dfba0017554310" // This is the weapons tpl, found on: https://db.sp-tarkov.com/search
|
||||||
});
|
});
|
||||||
|
|
||||||
// Add barrel
|
// Add barrel
|
||||||
@ -104,7 +105,7 @@ export class TraderHelper
|
|||||||
_id: "glockbarrel",
|
_id: "glockbarrel",
|
||||||
_tpl: "5a6b60158dc32e000a31138b",
|
_tpl: "5a6b60158dc32e000a31138b",
|
||||||
parentId: "glockBase", // This is a sub item, you need to define its parent its attached to / inserted into
|
parentId: "glockBase", // This is a sub item, you need to define its parent its attached to / inserted into
|
||||||
slotId: "mod_barrel", // Required for mods, you need to define what 'role' they have
|
slotId: "mod_barrel" // Required for mods, you need to define what 'role' they have
|
||||||
});
|
});
|
||||||
|
|
||||||
// Add reciever
|
// Add reciever
|
||||||
@ -112,15 +113,15 @@ export class TraderHelper
|
|||||||
_id: "glockReciever",
|
_id: "glockReciever",
|
||||||
_tpl:"5a9685b1a2750c0032157104",
|
_tpl:"5a9685b1a2750c0032157104",
|
||||||
parentId: "glockBase",
|
parentId: "glockBase",
|
||||||
slotId: "mod_reciever",
|
slotId: "mod_reciever"
|
||||||
});
|
});
|
||||||
|
|
||||||
// Add compensator
|
// Add compensator
|
||||||
glock.push({
|
glock.push({
|
||||||
_id: "glockCompensator",
|
_id: "glockCompensator",
|
||||||
_tpl:"5a7b32a2e899ef00135e345a",
|
_tpl:"5a7b32a2e899ef00135e345a",
|
||||||
parentId: "glockReciever", // The parent of this mod is the reciever NOT weapon, be careful to get the correct parent
|
parentId: "glockReciever", // The parent of this mod is the reciever NOT weapon, be careful to get the correct parent
|
||||||
slotId: "mod_muzzle",
|
slotId: "mod_muzzle"
|
||||||
});
|
});
|
||||||
|
|
||||||
// Add Pistol grip
|
// Add Pistol grip
|
||||||
@ -128,7 +129,7 @@ export class TraderHelper
|
|||||||
_id: "glockPistolGrip",
|
_id: "glockPistolGrip",
|
||||||
_tpl:"5a7b4960e899ef197b331a2d",
|
_tpl:"5a7b4960e899ef197b331a2d",
|
||||||
parentId: "glockBase",
|
parentId: "glockBase",
|
||||||
slotId: "mod_pistol_grip",
|
slotId: "mod_pistol_grip"
|
||||||
});
|
});
|
||||||
|
|
||||||
// Add front sight
|
// Add front sight
|
||||||
@ -136,7 +137,7 @@ export class TraderHelper
|
|||||||
_id: "glockRearSight",
|
_id: "glockRearSight",
|
||||||
_tpl: "5a6f5d528dc32e00094b97d9",
|
_tpl: "5a6f5d528dc32e00094b97d9",
|
||||||
parentId: "glockReciever",
|
parentId: "glockReciever",
|
||||||
slotId: "mod_sight_rear",
|
slotId: "mod_sight_rear"
|
||||||
});
|
});
|
||||||
|
|
||||||
// Add rear sight
|
// Add rear sight
|
||||||
@ -144,7 +145,7 @@ export class TraderHelper
|
|||||||
_id: "glockFrontSight",
|
_id: "glockFrontSight",
|
||||||
_tpl: "5a6f58f68dc32e000a311390",
|
_tpl: "5a6f58f68dc32e000a311390",
|
||||||
parentId: "glockReciever",
|
parentId: "glockReciever",
|
||||||
slotId: "mod_sight_front",
|
slotId: "mod_sight_front"
|
||||||
});
|
});
|
||||||
|
|
||||||
// Add magazine
|
// Add magazine
|
||||||
@ -152,28 +153,29 @@ export class TraderHelper
|
|||||||
_id: "glockMagazine",
|
_id: "glockMagazine",
|
||||||
_tpl: "630769c4962d0247b029dc60",
|
_tpl: "630769c4962d0247b029dc60",
|
||||||
parentId: "glockBase",
|
parentId: "glockBase",
|
||||||
slotId: "mod_magazine",
|
slotId: "mod_magazine"
|
||||||
});
|
});
|
||||||
|
|
||||||
return glock;
|
return glock;
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Add traders name/location/description to the locale table
|
* Add traders name/location/description to the locale table
|
||||||
* @param baseJson json file for trader (db/base.json)
|
* @param baseJson json file for trader (mod/db/base.json)
|
||||||
* @param tables database tables
|
* @param localesDb Locale data from database
|
||||||
* @param fullName Complete name of trader
|
* @param fullName Complete name of trader
|
||||||
* @param firstName First name of trader
|
* @param firstName First name of trader
|
||||||
* @param nickName Nickname of trader
|
* @param nickName Nickname of trader
|
||||||
* @param location Location of trader (e.g. "Here in the cat shop")
|
* @param location Location of trader (e.g. "Here in the cat shop")
|
||||||
* @param description Description of trader
|
* @param description Description of trader
|
||||||
*/
|
*/
|
||||||
public addTraderToLocales(baseJson: any, tables: IDatabaseTables, fullName: string, firstName: string, nickName: string, location: string, description: string)
|
public addTraderToLocales(baseJson: any, localesDb: ILocaleBase, fullName: string, firstName: string, nickName: string, location: string, description: string): void
|
||||||
{
|
{
|
||||||
// For each language, add locale for the new trader
|
// For each language, add locale for the new trader
|
||||||
const locales = Object.values(tables.locales.global);
|
const localeValues = Object.values(localesDb.global);
|
||||||
|
|
||||||
for (const locale of locales) {
|
for (const locale of localeValues)
|
||||||
|
{
|
||||||
locale[`${baseJson._id} FullName`] = fullName;
|
locale[`${baseJson._id} FullName`] = fullName;
|
||||||
locale[`${baseJson._id} FirstName`] = firstName;
|
locale[`${baseJson._id} FirstName`] = firstName;
|
||||||
locale[`${baseJson._id} Nickname`] = nickName;
|
locale[`${baseJson._id} Nickname`] = nickName;
|
||||||
|
@ -4,46 +4,59 @@ import { IPreSptLoadMod } from "@spt/models/external/IPreSptLoadMod";
|
|||||||
import { IPostSptLoadMod } from "@spt/models/external/IPostSptLoadMod";
|
import { IPostSptLoadMod } from "@spt/models/external/IPostSptLoadMod";
|
||||||
import { IPostDBLoadMod } from "@spt/models/external/IPostDBLoadMod";
|
import { IPostDBLoadMod } from "@spt/models/external/IPostDBLoadMod";
|
||||||
import { ILogger } from "@spt/models/spt/utils/ILogger";
|
import { ILogger } from "@spt/models/spt/utils/ILogger";
|
||||||
import { DatabaseServer } from "@spt/servers/DatabaseServer";
|
|
||||||
import { LogTextColor } from "@spt/models/spt/logging/LogTextColor";
|
import { LogTextColor } from "@spt/models/spt/logging/LogTextColor";
|
||||||
import { LogBackgroundColor } from "@spt/models/spt/logging/LogBackgroundColor";
|
import { LogBackgroundColor } from "@spt/models/spt/logging/LogBackgroundColor";
|
||||||
|
import { DatabaseService } from "@spt/services/DatabaseService";
|
||||||
|
import { ItemHelper } from "@spt/helpers/ItemHelper";
|
||||||
|
|
||||||
|
|
||||||
class Mod implements IPreSptLoadMod, IPostSptLoadMod, IPostDBLoadMod
|
class Mod implements IPreSptLoadMod, IPostSptLoadMod, IPostDBLoadMod
|
||||||
{
|
{
|
||||||
public preSptLoad(container: DependencyContainer): void {
|
public preSptLoad(container: DependencyContainer): void
|
||||||
|
{
|
||||||
// Database will be empty in here
|
// Database will be empty in here
|
||||||
const databaseServer = container.resolve<DatabaseServer>("DatabaseServer");
|
const databaseService = container.resolve<DatabaseService>("DatabaseService");
|
||||||
const logger = container.resolve<ILogger>("PrimaryLogger");
|
const logger = container.resolve<ILogger>("PrimaryLogger");
|
||||||
logger.logWithColor(`Database item table state: ${databaseServer.getTables().templates} (<<< should be undefined)`, LogTextColor.RED, LogBackgroundColor.YELLOW);
|
logger.logWithColor(`Database item table state: ${databaseService.getTemplates()} (<<< should be undefined)`, LogTextColor.RED, LogBackgroundColor.YELLOW);
|
||||||
}
|
}
|
||||||
|
|
||||||
public postDBLoad(container: DependencyContainer): void {
|
public postDBLoad(container: DependencyContainer): void
|
||||||
|
{
|
||||||
// Database will be loaded, this is the fresh state of the DB so NOTHING from the SPT
|
// Database will be loaded, this is the fresh state of the DB so NOTHING from the SPT
|
||||||
// logic has modified anything yet. This is the DB loaded straight from the JSON files
|
// logic has modified anything yet. This is the DB loaded straight from the JSON files
|
||||||
const databaseServer = container.resolve<DatabaseServer>("DatabaseServer");
|
const databaseService = container.resolve<DatabaseService>("DatabaseService");
|
||||||
const logger = container.resolve<ILogger>("PrimaryLogger");
|
const logger = container.resolve<ILogger>("PrimaryLogger");
|
||||||
logger.logWithColor(`Database item size: ${Object.entries(databaseServer.getTables().templates.items).length}`, LogTextColor.RED, LogBackgroundColor.YELLOW);
|
logger.logWithColor(`Database item size: ${Object.entries(databaseService.getItems()).length}`, LogTextColor.RED, LogBackgroundColor.YELLOW);
|
||||||
// lets do a quick modification and see how this reflect later on, on the postSptLoad()
|
// lets do a quick modification and see how this reflect later on, on the postSptLoad()
|
||||||
|
|
||||||
// find the nvgs item by its Id
|
// find the nvgs item by its Id
|
||||||
const nvgs = databaseServer.getTables().templates.items["5c0558060db834001b735271"];
|
const nvgs = databaseService.getItems()["5c0558060db834001b735271"];
|
||||||
// Lets log the state before the modification:
|
// Lets log the state before the modification:
|
||||||
logger.logWithColor(`NVGs default CanSellOnRagfair: ${nvgs._props.CanSellOnRagfair}`, LogTextColor.RED, LogBackgroundColor.YELLOW);
|
logger.logWithColor(`NVGs default CanSellOnRagfair: ${nvgs._props.CanSellOnRagfair}`, LogTextColor.RED, LogBackgroundColor.YELLOW);
|
||||||
// update one of its properties to be true
|
// update one of its properties to be true
|
||||||
nvgs._props.CanSellOnRagfair = true;
|
nvgs._props.CanSellOnRagfair = true;
|
||||||
}
|
}
|
||||||
|
|
||||||
public postSptLoad(container: DependencyContainer): void {
|
public postSptLoad(container: DependencyContainer): void
|
||||||
|
{
|
||||||
// The modification we made above would have been processed by now by SPT, so any values we changed had
|
// The modification we made above would have been processed by now by SPT, so any values we changed had
|
||||||
// already been passed through the initial lifecycles (OnLoad) of SPT.
|
// already been passed through the initial lifecycles (OnLoad) of SPT.
|
||||||
const databaseServer = container.resolve<DatabaseServer>("DatabaseServer");
|
const itemHelper = container.resolve<ItemHelper>("ItemHelper");
|
||||||
const logger = container.resolve<ILogger>("PrimaryLogger");
|
const logger = container.resolve<ILogger>("PrimaryLogger");
|
||||||
|
|
||||||
// find the nvgs item again by its Id
|
// Find the nvgs item again by its Id using ItemHelper class (alternate way of getting items that has more saftey checks)
|
||||||
const nvgs = databaseServer.getTables().templates.items["5c0558060db834001b735271"];
|
const nvgs = itemHelper.getItem("5c0558060db834001b735271"); // Returns an array of 2 values, 1st is a bool, true if item is valid, 2nd is the item data
|
||||||
// Lets log the state, this value should be true:
|
if (nvgs[0])
|
||||||
logger.logWithColor(`NVGs modified CanSellOnRagfair: ${nvgs._props.CanSellOnRagfair}`, LogTextColor.RED, LogBackgroundColor.YELLOW);
|
{
|
||||||
|
// item was found in database, hooray
|
||||||
|
|
||||||
|
// Assign a new variable so we can cleanly reference its _props data below
|
||||||
|
const nvgsData = nvgs[1];
|
||||||
|
|
||||||
|
// Lets log the state, this value should be true:
|
||||||
|
logger.logWithColor(`NVGs modified CanSellOnRagfair: ${nvgsData._props.CanSellOnRagfair}`, LogTextColor.RED, LogBackgroundColor.YELLOW);
|
||||||
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -4,18 +4,18 @@ import { IPostDBLoadMod } from "@spt/models/external/IPostDBLoadMod";
|
|||||||
import { CustomItemService } from "@spt/services/mod/CustomItemService";
|
import { CustomItemService } from "@spt/services/mod/CustomItemService";
|
||||||
import { NewItemFromCloneDetails } from "@spt/models/spt/mod/NewItemDetails";
|
import { NewItemFromCloneDetails } from "@spt/models/spt/mod/NewItemDetails";
|
||||||
import { IPostSptLoadMod } from "@spt/models/external/IPostSptLoadMod";
|
import { IPostSptLoadMod } from "@spt/models/external/IPostSptLoadMod";
|
||||||
import { DatabaseServer } from "@spt/servers/DatabaseServer";
|
import { DatabaseService } from "@spt/services/DatabaseService";
|
||||||
|
|
||||||
class Mod implements IPostDBLoadMod, IPostSptLoadMod
|
class Mod implements IPostDBLoadMod, IPostSptLoadMod
|
||||||
{
|
{
|
||||||
public postDBLoad(container: DependencyContainer): void
|
public postDBLoad(container: DependencyContainer): void
|
||||||
{
|
{
|
||||||
// Resolve the CustomItemService container
|
// Resolve the CustomItemService
|
||||||
const CustomItem = container.resolve<CustomItemService>("CustomItemService");
|
const customItemService = container.resolve<CustomItemService>("CustomItemService");
|
||||||
|
|
||||||
//Example of adding new item by cloning existing item using createclonedetails
|
// Clone the mp-18 and adjust its properties slightly
|
||||||
const ExampleCloneItem: NewItemFromCloneDetails = {
|
const exampleCloneItem: NewItemFromCloneDetails = {
|
||||||
itemTplToClone: "61f7c9e189e6fb1a5e3ea78d", //the item we want to clone, in this example i will cloning the MP-18
|
itemTplToClone: "61f7c9e189e6fb1a5e3ea78d", // MP-18 id
|
||||||
overrideProperties: {
|
overrideProperties: {
|
||||||
Chambers: [
|
Chambers: [
|
||||||
{
|
{
|
||||||
@ -41,40 +41,42 @@ class Mod implements IPostDBLoadMod, IPostSptLoadMod
|
|||||||
"5d6e68b3a4b9361bca7e50b5",
|
"5d6e68b3a4b9361bca7e50b5",
|
||||||
"5d6e6891a4b9361bd473feea",
|
"5d6e6891a4b9361bd473feea",
|
||||||
"5d6e689ca4b9361bc8618956",
|
"5d6e689ca4b9361bc8618956",
|
||||||
"5d6e68d1a4b93622fe60e845",
|
"5d6e68d1a4b93622fe60e845"
|
||||||
],
|
]
|
||||||
},
|
}
|
||||||
],
|
]
|
||||||
},
|
},
|
||||||
_required: false,
|
_required: false,
|
||||||
_mergeSlotWithChildren: false,
|
_mergeSlotWithChildren: false,
|
||||||
_proto: "55d4af244bdc2d962f8b4571",
|
_proto: "55d4af244bdc2d962f8b4571"
|
||||||
},
|
}
|
||||||
],
|
]
|
||||||
}, //Overried properties basically tell the server on what data inside _props to be modified from the cloned item, in this example i am modifying the ammo used to be 12G
|
}, // Overried properties basically tell the server on what data inside _props to be modified from the cloned item, in this example i am modifying the ammo used to be 12G
|
||||||
parentId: "5447b6094bdc2dc3278b4567", //ParentId refers to the Node item the gun will be under, you can check it in https://db.sp-tarkov.com/search
|
parentId: "5447b6094bdc2dc3278b4567", // ParentId refers to the Node item the gun will be under. For this example we use `Shotgun`, you can check it in https://db.sp-tarkov.com/search
|
||||||
newId: "CustomMP18", //The new id of our cloned item
|
newId: "CustomMP18", // The new id of our cloned item
|
||||||
fleaPriceRoubles: 50000, //Self explanatary
|
fleaPriceRoubles: 50000, // Average price of item on flea
|
||||||
handbookPriceRoubles: 42500,
|
handbookPriceRoubles: 42500,
|
||||||
handbookParentId: "5b5f78e986f77447ed5636b1", //Handbook Parent Id refers to the category the gun will be under
|
handbookParentId: "5b5f78e986f77447ed5636b1", // Handbook Parent Id refers to the category the gun will be under
|
||||||
//you see those side box tab thing that only select gun under specific icon? Handbook parent can be found in SPT_Data\Server\database\templates.
|
// You see those side box tab thing that only select gun under specific icon? Handbook parent can be found in SPT_Data\Server\database\templates.
|
||||||
locales: {
|
locales: {
|
||||||
en: {
|
en: {
|
||||||
name: "MP-18 12g",
|
name: "MP-18 12g",
|
||||||
shortName: "Custom MP18",
|
shortName: "Custom MP18",
|
||||||
description: "A custom MP18 chambered in 12G",
|
description: "A custom MP18 chambered in 12G"
|
||||||
},
|
}
|
||||||
},
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
CustomItem.createItemFromClone(ExampleCloneItem); //Basically calls the function and tell the server to add our Cloned new item into the server
|
customItemService.createItemFromClone(exampleCloneItem); // Tell the server to add our Cloned item into the server using custom item service
|
||||||
}
|
}
|
||||||
|
|
||||||
//Check if our item is in the server or not
|
//Check if our item is in the server or not
|
||||||
public postSptLoad(container: DependencyContainer): void {
|
public postSptLoad(container: DependencyContainer): void
|
||||||
const db = container.resolve<DatabaseServer>("DatabaseServer");
|
{
|
||||||
const item = db.getTables().templates.items;
|
const databaseService = container.resolve<DatabaseService>("DatabaseService");
|
||||||
|
const item = databaseService.getItems();
|
||||||
|
|
||||||
|
// Log our new guns properties to console
|
||||||
console.log(item["CustomMP18"]._props);
|
console.log(item["CustomMP18"]._props);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -2,10 +2,10 @@ import { DependencyContainer } from "tsyringe";
|
|||||||
|
|
||||||
import { IPreSptLoadMod } from "@spt/models/external/IPreSptLoadMod";
|
import { IPreSptLoadMod } from "@spt/models/external/IPreSptLoadMod";
|
||||||
import { LauncherController } from "@spt/controllers/LauncherController";
|
import { LauncherController } from "@spt/controllers/LauncherController";
|
||||||
import { DatabaseServer } from "@spt/servers/DatabaseServer";
|
|
||||||
import { ILoginRequestData } from "@spt/models/eft/launcher/ILoginRequestData";
|
import { ILoginRequestData } from "@spt/models/eft/launcher/ILoginRequestData";
|
||||||
import { ILogger } from "@spt/models/spt/utils/ILogger";
|
import { ILogger } from "@spt/models/spt/utils/ILogger";
|
||||||
import { SaveServer } from "@spt/servers/SaveServer";
|
import { SaveServer } from "@spt/servers/SaveServer";
|
||||||
|
import { DatabaseService } from "@spt/services/DatabaseService";
|
||||||
|
|
||||||
class Mod implements IPreSptLoadMod
|
class Mod implements IPreSptLoadMod
|
||||||
{
|
{
|
||||||
@ -26,16 +26,16 @@ class Mod implements IPreSptLoadMod
|
|||||||
container.afterResolution("LauncherController", (_t, result: LauncherController) =>
|
container.afterResolution("LauncherController", (_t, result: LauncherController) =>
|
||||||
{
|
{
|
||||||
// We want to replace the original method logic with something different
|
// We want to replace the original method logic with something different
|
||||||
result.login = (info: ILoginRequestData) =>
|
result.login = (info: ILoginRequestData) =>
|
||||||
{
|
{
|
||||||
return this.replacementFunction(info);
|
return this.replacementFunction(info);
|
||||||
}
|
}
|
||||||
// The modifier Always makes sure this replacement method is ALWAYS replaced
|
// The modifier Always makes sure this replacement method is ALWAYS replaced
|
||||||
}, {frequency: "Always"});
|
}, { frequency: "Always" });
|
||||||
}
|
}
|
||||||
|
|
||||||
// our new replacement function, ready to be used
|
// our new replacement function, ready to be used
|
||||||
public replacementFunction(info: ILoginRequestData): string
|
public replacementFunction(info: ILoginRequestData): string
|
||||||
{
|
{
|
||||||
// The original method requires the save server to be loaded
|
// The original method requires the save server to be loaded
|
||||||
const saveServer = Mod.container.resolve<SaveServer>("SaveServer");
|
const saveServer = Mod.container.resolve<SaveServer>("SaveServer");
|
||||||
@ -55,15 +55,16 @@ class Mod implements IPreSptLoadMod
|
|||||||
// This is now extra stuff we want to add
|
// This is now extra stuff we want to add
|
||||||
// We resolve 2 more dependencies: The logger and the DatabaseServer
|
// We resolve 2 more dependencies: The logger and the DatabaseServer
|
||||||
const logger = Mod.container.resolve<ILogger>("PrimaryLogger");
|
const logger = Mod.container.resolve<ILogger>("PrimaryLogger");
|
||||||
const dbServer = Mod.container.resolve<DatabaseServer>("DatabaseServer");
|
const databaseService = Mod.container.resolve<DatabaseService>("DatabaseService");
|
||||||
|
|
||||||
|
// As an example lets count the number of items in the database
|
||||||
|
const loadedItems = Object.entries(databaseService.getItems()).length;
|
||||||
|
|
||||||
// As an example Im counting the amount of loaded items on the DB
|
|
||||||
const loadedItems = Object.entries(dbServer.getTables().templates.items).length;
|
|
||||||
// Lets do a few informational messages
|
// Lets do a few informational messages
|
||||||
logger.success(`User ${info.username} logged in to SPT, there are ${loadedItems} items loaded into the database`);
|
logger.success(`User ${info.username} logged in to SPT, there are ${loadedItems} items loaded into the database`);
|
||||||
logger.success(originalReturn.length > 0 ? `User session ID: ${originalReturn}` : "User not found");
|
logger.success(originalReturn.length > 0 ? `User session ID: ${originalReturn}` : "User not found");
|
||||||
|
|
||||||
// And finally return whatever we were supposed to return through this function
|
// And finally return whatever we were supposed to return originally through this function
|
||||||
return originalReturn;
|
return originalReturn;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
Loading…
x
Reference in New Issue
Block a user