diff --git a/src/Utils.ts b/src/Utils.ts index 68c3a3a7..9553db3a 100644 --- a/src/Utils.ts +++ b/src/Utils.ts @@ -56,3 +56,22 @@ export function mergeDefault>(def: T, given: T): R export function wait(ms: number): Promise { return new Promise(resolve => setTimeout(resolve, ms)); } + + +export function getCircularReplacer(): (key: string, value: any) => any { + const ancestors: any[] = []; + return function (this: any, key: string, value: any): any { + if (typeof value !== "object" || value === null) { + return value; + } + while (ancestors.length > 0 && ancestors.at(-1) !== this) { + ancestors.pop(); + } + if (ancestors.includes(value)) { + return "[Circular]"; + } + ancestors.push(value); + return value; + }; + } + \ No newline at end of file diff --git a/src/node/Rest.ts b/src/node/Rest.ts index c590d18e..753596c6 100644 --- a/src/node/Rest.ts +++ b/src/node/Rest.ts @@ -2,6 +2,7 @@ import { Versions } from '../Constants'; import { FilterOptions } from '../guild/Player'; import { NodeOption } from '../Shoukaku'; +import { getCircularReplacer } from '../Utils'; import { Node, NodeInfo, Stats } from './Node'; export type Severity = 'common' | 'suspicious' | 'fault'; @@ -204,7 +205,7 @@ export class Rest { public resolve(identifier: string): Promise { const options = { endpoint: '/loadtracks', - options: { params: { identifier }} + options: { params: { identifier } } }; return this.fetch(options); } @@ -217,7 +218,7 @@ export class Rest { public decode(track: string): Promise { const options = { endpoint: '/decodetrack', - options: { params: { track }} + options: { params: { track } } }; return this.fetch(options); } @@ -378,8 +379,8 @@ export class Rest { signal: abortController.signal }; - if (![ 'GET', 'HEAD' ].includes(method) && options.body) - finalFetchOptions.body = JSON.stringify(options.body); + if (!['GET', 'HEAD'].includes(method) && options.body) + finalFetchOptions.body = JSON.stringify(options.body, getCircularReplacer()); const request = await fetch(url.toString(), finalFetchOptions) .finally(() => clearTimeout(timeout));