From b98a88b7002d82c4515746278e108b2cc93be8e0 Mon Sep 17 00:00:00 2001 From: Sainan <63328889+Sainan@users.noreply.github.com> Date: Sun, 15 Jun 2025 18:52:10 -0700 Subject: [PATCH] chore: retroactively populate vendor to hide that it was just generated (#2168) For example, debt-bonds at ticker always expire in at least 2 hours so visiting him, you'd never see an offer with an expiry less than that. The solution here is simply generating offers for the last few hours. Reviewed-on: https://onlyg.it/OpenWF/SpaceNinjaServer/pulls/2168 Co-authored-by: Sainan <63328889+Sainan@users.noreply.github.com> Co-committed-by: Sainan <63328889+Sainan@users.noreply.github.com> --- src/services/serversideVendorsService.ts | 31 +++++++++++++++++++++--- 1 file changed, 27 insertions(+), 4 deletions(-) diff --git a/src/services/serversideVendorsService.ts b/src/services/serversideVendorsService.ts index 2150e4000..701b85b4f 100644 --- a/src/services/serversideVendorsService.ts +++ b/src/services/serversideVendorsService.ts @@ -216,6 +216,22 @@ const toRange = (value: IRange | number): IRange => { return value; }; +const getCycleDurationRange = (manifest: IVendor): IRange | undefined => { + const res: IRange = { minValue: Number.MAX_SAFE_INTEGER, maxValue: 0 }; + for (const offer of manifest.items) { + if (offer.durationHours) { + const range = toRange(offer.durationHours); + if (res.minValue > range.minValue) { + res.minValue = range.minValue; + } + if (res.maxValue < range.maxValue) { + res.maxValue = range.maxValue; + } + } + } + return res.maxValue != 0 ? res : undefined; +}; + const vendorManifestCache: Record = {}; const generateVendorManifest = (vendorInfo: IGeneratableVendorInfo): IVendorManifest => { @@ -232,10 +248,16 @@ const generateVendorManifest = (vendorInfo: IGeneratableVendorInfo): IVendorMani } const cacheEntry = vendorManifestCache[vendorInfo.TypeName]; const info = cacheEntry.VendorInfo; - if (Date.now() >= parseInt(info.Expiry.$date.$numberLong)) { + const manifest = ExportVendors[vendorInfo.TypeName]; + const cycleDurationRange = getCycleDurationRange(manifest); + let now = Date.now(); + if (cycleDurationRange && cycleDurationRange.minValue != cycleDurationRange.maxValue) { + now -= (cycleDurationRange.maxValue - 1) * unixTimesInMs.hour; + } + while (Date.now() >= parseInt(info.Expiry.$date.$numberLong)) { // Remove expired offers for (let i = 0; i != info.ItemManifest.length; ) { - if (Date.now() >= parseInt(info.ItemManifest[i].Expiry.$date.$numberLong)) { + if (now >= parseInt(info.ItemManifest[i].Expiry.$date.$numberLong)) { info.ItemManifest.splice(i, 1); } else { ++i; @@ -246,9 +268,8 @@ const generateVendorManifest = (vendorInfo: IGeneratableVendorInfo): IVendorMani const vendorSeed = parseInt(vendorInfo._id.$oid.substring(16), 16); const cycleOffset = vendorInfo.cycleOffset ?? 1734307200_000; const cycleDuration = vendorInfo.cycleDuration; - const cycleIndex = Math.trunc((Date.now() - cycleOffset) / cycleDuration); + const cycleIndex = Math.trunc((now - cycleOffset) / cycleDuration); const rng = new SRng(mixSeeds(vendorSeed, cycleIndex)); - const manifest = ExportVendors[vendorInfo.TypeName]; const offersToAdd: IVendorOffer[] = []; if (!manifest.isOneBinPerCycle) { const remainingItemCapacity: Record = {}; @@ -371,6 +392,8 @@ const generateVendorManifest = (vendorInfo: IGeneratableVendorInfo): IVendorMani } } info.Expiry.$date.$numberLong = soonestOfferExpiry.toString(); + + now += unixTimesInMs.hour; } return cacheEntry; };