Migrating to 2.10.3
This guide covers the stable 2.10.2 to 2.10.3 upgrade. Existing Lavalink v4 applications do not need a second Node class or a new storage configuration. They do need to account for the corrected public types and playlist shape.
Install and Retain a Rollback
npm install [email protected]
Review and retain your dependency lockfile. Reverting to [email protected]
also requires reverting code that uses native NodeLink methods or corrected
2.10.3-specific shapes. Do not publish or upgrade a production bot solely because
the package builds.
Playlist Metadata
Previously, playlistInfo was typed/filled as plugin metadata. It now contains
the actual Lavalink playlist information. Move plugin-field reads to pluginInfo.
if ("playlist" in result) {
const { playlist } = result;
// Core protocol information:
console.log(playlist.playlistInfo.name);
console.log(playlist.playlistInfo.selectedTrack);
// Extensible plugin metadata, validated before use:
const url = playlist.pluginInfo.url;
if (typeof url === "string") {
console.log(url);
}
}
PlaylistInfoData is a single { name, selectedTrack } object, not an array.
A selected index of -1 means no selected track.
Nullable Track Fields
Track URI, artwork URL, and ISRC can be null, even though modern providers
usually set a URI. Keep that protocol contract in application code.
if (track.uri) {
embed.setURL(track.uri);
}
if (track.artworkUrl) {
embed.setThumbnail(track.artworkUrl);
}
const isYouTube = track.uri?.includes("youtube.com") ?? false;
Do not cast away nullability or substitute undefined in the library's protocol
types. Choose application-specific fallbacks when rendering a missing URL.
Raw TrackData.userData is exposed on built tracks as Track.customData.
Search Results and Gateway Messages
Narrow SearchResult by loadType or property checks. Empty/backend-error load
results contain tracks: []; transport failures still reject.
if (result.loadType === "empty" || result.loadType === "error") {
return;
}
await player.queue.add(result.tracks);
Gateway data is now a discriminated union rather than a stats-shaped message.
Read stats only on op: "stats", player state only on op: "playerUpdate",
and event-specific properties only after narrowing the event.
Remote LavaPlayer.track and NodeStats.frameStats may be null. Lyrics,
chapter, and SponsorBlock callback tracks may also be null.
Separate Native Search APIs
Continue using SearchPlatform for shared searches. Use
NodeLinkSearchPlatform, NodeLinkRecommendationPlatform, and
NodeLinkSearchType for native capabilities. Shared string values still permit
either backend; native prefixes/modifiers require a connected eligible NodeLink.
NodeLink Spotify recommendations use sprec:seed_tracks=.... Lavalink's raw
sprec:mix:track:... workaround stays on Lavalink. See
search examples.
Guard Native Actions in Mixed Pools
if (player.node.isNodeLink) {
await player.setNodeLinkLoudnessNormalizer(true);
const chapters = await player.getNodeLinkChapters();
}
Pin native-feature players with nodeIdentifier when creating them.
Recheck after node moves. Do not assume a native search also pins playback.
Mixer layers use 0-1 volume, not the main player's 0-1000 scale.
preloadNextTrack() does not enqueue a track; keep the local next track aligned.
Use explicit NodeLink aliases to make native-only code apparent.
Plugin Filters and Lyrics
Nonempty setPluginFilters() now checks for a matching advertised plugin.
By default it expects LavaDSPX-Plugin aliases; provide the advertised plugin name
for another plugin. Empty calls clear without that requirement.
On NodeLink, use node.getLyrics(track, false, language) and narrow
NodeLinkGetLyrics. The current player.getCurrentLyrics() return type does not
reflect its unnormalized native runtime result. See
lyrics handling.
Sessions and Restores
Wait for node readiness before calling session-scoped REST helpers.
getPlayers() returns an empty array without a session; some other helpers
currently return null at runtime despite their declared signatures.
Autoplay settings and requester data are now preserved through state restoration. Check the first restored autoplay request and wrapper-specific user resolution when testing JSON or Redis state. No new storage setup is required.
Validate the Upgrade
Run your bot's typecheck/tests and the release validation checklist on Lavalink, NodeLink, and a mixed pool before promotion.
Older Migration Guide
🔥 Upgrading to MagmaStream v2.10.0 — Migration Guide
This release contains breaking changes. Review everything below before upgrading.
Lables:
🔴 - Breaking
🟡 - Changes
🟢 - New
🔴 Renamed Options
PlayerOptions:
guild→guildIdvoiceChannel→voiceChannelIdtextChannel→textChannelIdnode→nodeIdentifier
NodeOptions:
secure→useSSLresumeStatus→enableSessionResumeOptionresumeTimeout→sessionTimeoutSecondsretryAmount→maxRetryAttemptsretryDelay→retryDelayMspriority→nodePriority
ManagerOptions:
autoPlay→playNextOnEndusePriority→enablePriorityModereplaceYouTubeCredentials→normalizeYouTubeTitlesplugins→enabledPlugins
🔴 Queue Overhaul
The old Queue class has been removed. You must now pick a storage backend explicitly:
MemoryQueue— in-memory, synchronous methods (closest to old behaviour)JsonQueue— persists to disk, async methodsRedisQueue— persists to Redis, async methods
If you use JsonQueue or RedisQueue, all queue calls need await.
🔴 Filter API
Filters now take an explicit boolean instead of being toggle calls:
Before
player.filters.nightcore()
After
player.filters.nightcore(true)
player.filters.nightcore(false)
bassBoost now takes a stage from -3 to 3 instead of being a toggle:
player.filters.bassBoost(3) = max boost, player.filters.bassBoost(0) = disabled
🟡 Error Handling
All errors are now MagmaStreamError instances with structured codes and context. Replace any TypeError / RangeError catches with MagmaStreamError.
🟢 What's been added
- Library wrappers:
DiscordJSManager,DiscordenoManager,ErisManager,OceanicManager,SeyfertManager - Abstract
Pluginbase class withload()/unload()methods - Redis-backed session and queue storage
- New filters:
demon,earrape,doubletime,chipmunk,daycore,darthvader,electronic,radio,tremolo,pop,party