diff --git a/examples/sharding.js b/examples/sharding.js index 2444bc079..07db91fbb 100644 --- a/examples/sharding.js +++ b/examples/sharding.js @@ -4,6 +4,7 @@ const Eris = require("eris"); const bot = new Eris("Bot TOKEN", { firstShardID: 0, lastShardID: 15, + shardIDs: [5, 9, 1, 4], // Overrides firstShardID and lastShardID above maxShards: 16, getAllUsers: false, intents: ["guilds", "guildMembers", "guildPresences"] diff --git a/index.d.ts b/index.d.ts index 1bf3f6b0d..933918d78 100644 --- a/index.d.ts +++ b/index.d.ts @@ -404,6 +404,7 @@ declare namespace Eris { restMode?: boolean; seedVoiceConnections?: boolean; shardConcurrency?: number | "auto"; + shardIDs?: number[]; ws?: unknown; } interface CommandClientOptions { diff --git a/lib/Client.js b/lib/Client.js index ef6c0432d..9030b2101 100644 --- a/lib/Client.js +++ b/lib/Client.js @@ -120,6 +120,7 @@ class Client extends EventEmitter { * @arg {Boolean} [options.restMode=false] Whether to enable getting objects over REST. Even with this option enabled, it is recommended that you check the cache first before using REST * @arg {Boolean} [options.seedVoiceConnections=false] Whether to populate bot.voiceConnections with existing connections the bot account has during startup. Note that this will disconnect connections from other bot sessions * @arg {Number | String} [options.shardConcurrency="auto"] The number of shards that can start simultaneously. If "auto" Eris will use Discord's recommended shard concurrency. + * @arg {Array} [options.shardIDs] An array of shard IDs to run for this client. If this is specified, the firstShardID and lastShardID options are ignored. * @arg {Object} [options.ws] An object of WebSocket options to pass to the shard WebSocket constructors */ constructor(token, options) { @@ -151,6 +152,7 @@ class Client extends EventEmitter { restMode: false, seedVoiceConnections: false, shardConcurrency: "auto", + shardIDs: [], ws: {}, reconnectDelay: (lastDelay, attempts) => Math.pow(attempts + 1, 0.7) * 20000 }, options); @@ -460,8 +462,22 @@ class Client extends EventEmitter { this.shards.setConcurrency(data.session_start_limit.max_concurrency); } - for(let i = this.options.firstShardID; i <= this.options.lastShardID; ++i) { - this.shards.spawn(i); + // ensure we have a valid shardIDs array + let shardIDs = this.options.shardIDs; + if(!Array.isArray(shardIDs)) { + shardIDs = []; + } + + // populate array via first/last shardID if no elements are present + if(shardIDs.length === 0) { + for(let i = this.options.firstShardID; i <= this.options.lastShardID; i++) { + shardIDs.push(i); + } + } + + // spawn the shards + for(const id of shardIDs) { + this.shards.spawn(id); } } catch(err) { if(!this.options.autoreconnect) {