steamcommunity-inventory
Version:
A rate limit and response handler for steamcommunity inventories. - It's functional. - Will appreciate all feedback I can get
150 lines (149 loc) • 6.02 kB
JavaScript
;
var __importDefault = (this && this.__importDefault) || function (mod) {
return (mod && mod.__esModule) ? mod : { "default": mod };
};
Object.defineProperty(exports, "__esModule", { value: true });
exports.Inventory = void 0;
const axios_1 = __importDefault(require("axios"));
const bottleneck_1 = __importDefault(require("bottleneck"));
const Parser_1 = require("./Inventory/Parser");
const getDesiredMoreAmount_1 = require("./Inventory/getDesiredMoreAmount");
const fetchMore_1 = require("./Inventory/fetchMore");
const getNextCount_1 = require("./Inventory/getNextCount");
const constant_1 = require("./Inventory/constant");
const DAY = 24 * 60 * 60 * 1000;
const SECOND = 1000;
/**
* Handles inventory requests to SteamCommunity.
*/
class Inventory {
/**
* @param {Object} options
* @param {string} options.steamID When passed with cookies,
* you don't have to rely on rate limit, steam lets you request your inventory freely
* @param {number} options.minTime @see https://github.com/SGrondin/bottleneck#constructor
* @param {number} options.maxConcurent @see https://github.com/SGrondin/bottleneck#constructor
* @param {number} options.reservoir @see https://github.com/SGrondin/bottleneck#constructor
* @param {number} options.reservoirRefreshAmount @see https://github.com/SGrondin/bottleneck#constructor
* @param {number} options.reservoirRefreshInverval @see https://github.com/SGrondin/bottleneck#constructor
* @param {'new'|'old'} options.method method we use for inventory
* @param {Function} options.formatter modifies econItem before being passed into then
* @param {Object} [options.headers]
*/
constructor(options = {}) {
const { steamID, formatter, headers, cookies, minTime = 3, maxConcurent = SECOND, reservoir = 100000, reservoirRefreshAmount = DAY, reservoirRefreshInverval = 100000, axiosInstance = axios_1.default.create(), } = options;
this.steamID = steamID;
this.formatter = formatter;
this.parser = new Parser_1.Parser(this);
this.headers = headers;
if (cookies)
this.setCookies(cookies);
this.request = axiosInstance;
this.limiter = new bottleneck_1.default({
maxConcurent,
minTime,
reservoir,
reservoirRefreshInverval,
reservoirRefreshAmount,
});
}
/**
* Sets cookies to instance, in key=value format.
* @param {string[]} cookies
*/
setCookies(cookies) {
this.cookies = cookies.join('; ');
}
/**
* Gets inventory from new endpoint that has better rate limit but less data.
* @param {string} steamID
* @param {string} appID
* @param {string} contextID
* @param {string} [start] from which assetID do you want to start
* @param {number} [count=Infinity] If set gets the exact amount of items,
* if `Infinity` gets all recursively,
* if `void` gets only the first 500
* @param {string} [language=english]
* @return {Promise<TItem[]>}
*/
get({ steamID, appID, contextID, lastAssetId, count = Infinity, language = 'english', }) {
return this.fetchInventoryPage({
steamID,
appID,
contextID,
lastAssetId,
count,
language,
});
}
async fetchInventoryPage({ steamID, appID, contextID, lastAssetId, count, language, inventory = [], }) {
const desiredMoreAmount = getDesiredMoreAmount_1.getDesiredMoreAmount(count);
if (desiredMoreAmount) {
count = constant_1.REQUEST_COUNT_THRESHOLD;
}
const url = `https://steamcommunity.com/inventory/${steamID}/${appID}/${contextID}`;
const params = {
count,
l: language
};
if (lastAssetId) {
params.start_assetid = lastAssetId;
}
const { data } = await this.sendRequest({
url,
settings: {
headers: this.getHeaders(),
params: {
start_assetid: lastAssetId,
count,
l: language,
},
},
});
if (data.error) {
return Promise.reject(new Error(`Unsuccessful inventory request, ${data.error}`));
}
if (data.success !== 1) {
return Promise.reject(new Error(`Unsuccessful inventory request, ${data.message}`));
}
if (data.total_inventory_count < 1) {
return inventory;
}
inventory.push(...this.parser.toEconNew({
assets: data.assets,
descriptions: data.descriptions,
}));
if (fetchMore_1.fetchMore({
desiredMoreAmount,
currentAmount: inventory.length,
moreItems: data.more_items,
})) {
return this.fetchInventoryPage({
steamID,
appID,
contextID,
language,
inventory,
lastAssetId: data.last_assetid,
count: getNextCount_1.getNextCount({
desiredMoreAmount,
currentAmount: inventory.length,
totalAmount: data.total_inventory_count,
}),
});
}
return inventory;
}
sendRequest({ url, settings, priority = 3, }) {
return this.limiter.schedule({ priority: priority }, () => this.request.get(url, settings));
}
/**
* Returns cookies in object for iterators.
* @return {Object}
*/
getHeaders() {
const { headers = {}, cookies } = this;
return Object.assign(Object.assign({}, headers), (cookies ? { Cookie: cookies } : {}));
}
}
exports.Inventory = Inventory;