(async function() {
const username = 'aboveandbeyond';
const minEp = 400, maxEp = 450;
const desiredCount = maxEp - minEp + 1; // 51 episodes inclusive
let episodes = [];
let until = null;
let pageCounter = 0;
console.log(`Starting to collect Group Therapy episodes ${minEp}–${maxEp}…`);
// Step through the feed until we find all required episodes
while (episodes.length < desiredCount) {
pageCounter++;
let url = `https://api.mixcloud.com/${username}/feed/?limit=100`;
if (until) url += `&until=${until}`;
console.log(`Requesting feed page ${pageCounter}: ${url}`);
const feed = await (await fetch(url)).json();
// Extract episodes with numbers between 400 and 450
for (const item of feed.data) {
if (item.cloudcasts && item.cloudcasts.length) {
const slug = item.cloudcasts[0].slug || '';
const m = slug.match(/group-therapy-(\d+)/);
if (m) {
const epNum = parseInt(m[1], 10);
if (epNum >= minEp && epNum <= maxEp) {
const idMatch = item.key.match(/feed\/(\d+)\//);
if (idMatch) {
const numericId = idMatch[1];
episodes.push({ id: numericId, epNum });
console.log(`Found episode ${epNum} with ID ${numericId}`);
}
}
}
}
}
console.log(`After page ${pageCounter} we have ${episodes.length} episodes.`);
// Move to next page of feed if available
if (feed.paging && feed.paging.next) {
const params = new URL(feed.paging.next).searchParams;
until = params.get('until');
if (!until) {
console.log('No until parameter found; stopping.');
break;
}
} else {
console.log('No further paging; stopping feed traversal.');
break;
}
}
episodes.sort((a, b) => a.epNum - b.epNum);
console.log(`Collected ${episodes.length} episodes:`,
episodes.map(ep => ep.epNum));
// Build queue payload
const queue = episodes.map(ep => {
const cloudcastId = btoa(`Cloudcast:${ep.id}`);
return {
cloudcastId: cloudcastId,
situation: JSON.stringify({
tracking: [
{ type: 'source', referrer: '' },
{ type: 'view', view_name: 'user:uploads',
params: { username } },
{ type: 'platform', platform: 'www' },
{ type: 'url', url: `/${username}/uploads/?order=latest` }
]
})
};
});
console.log('Queue payload (first few items shown):',
queue.slice(0, 5));
// Read CSRF token from cookie
const csrfMatch = document.cookie.match(/csrftoken=([^;]+)/);
if (!csrfMatch) {
console.error('CSRF token not found; make sure you are logged in.');
return;
}
const csrf = csrfMatch[1];
// Get Mixcloud client version
const clientVersion = window.mixcloudBootData?.clientVersion
|| window.mixcloudBootData?.CLIENT_VERSION;
// Prepare GraphQL mutation body
const body = {
query: `mutation useChangePlayerQueueMutation($input: ChangePlayerQueueMutationInput!) {
changePlayerQueue(input: $input) { lastModified }
}`,
variables: {
input: {
queue: queue,
currentIndex: 0,
expectedLastModifiedDate: null
}
}
};
console.log('Sending GraphQL mutation to update queue…');
const response = await fetch('https://app.mixcloud.com/graphql', {
method: 'POST',
credentials: 'include',
headers: {
'Content-Type': 'application/json',
'x-csrftoken': csrf,
'x-mixcloud-platform': 'www',
'x-mixcloud-client-version': clientVersion
},
body: JSON.stringify(body)
});
const json = await response.json();
console.log('GraphQL response:', json);
})();