delete all your messages from a discord server, while also saving each message (plus a bit of context) as json think it worked like this: - run copyparty -i 127.0.0.1 -v .::w - fill in your $AUTHKEY, $ID_USER_SELF and $ID_GUILD in the script below - get $AUTHKEY from the network log, browser sends it for every request as header "Authorization" - get $ID_USER_SELF by rightclicking yourself and "Copy ID" after enabling that feature in settings - get $ID_GUILD (server ID) the same way - hit F12, select Console, paste the script in the commandline, then type rm_all() and hit enter # placeholder values to update $AUTHKEY = your own auth key (ascii.ascii.ascii) $ID_USER_SELF = your own ID (numeric value) $ID_GUILD = server ID (numeric value) # the script var auth = '$AUTHKEY' var ref = 'https://discord.com/channels/$ID_GUILD/$ID_GUILD'; var query = '/api/v6/guilds/$ID_GUILD/messages/search?author_id=$ID_USER_SELF'; function sleep(ms) { return new Promise(resolve => setTimeout(resolve, ms)); } async function search() { var rsp = await fetch(query, {"mode": "cors", "credentials": "include", "referrer": ref, "headers": {"Authorization": auth}}); return rsp.json(); } function getlist(m) { var rm = []; for (var a=0; a 0) { await sleep(1000 + Math.floor(Math.random() * 2000)); await rm_all(); }} function rm_all() { search().then(data => {fetch('http://127.0.0.1:3923/', {method:"PUT", body: JSON.stringify(data)}).then(r1 => {r1.text().then(r2 => {console.log(r2)})}); nuke(getlist(data.messages));}); } # time estimate for f in put-*; do n=$(awk -F, -v f="$f" 'BEGIN {sub(/[^-]+-/,"",f);sub(/-.*/,"",f);printf "%s ",f} {v=$1;sub(/^[^0-9]+/,"",v);print v;exit}' <"$f"); echo $n; done | awk '{printf "%.3f %d\n", $1-o1, o2-$2; o1=$1; o2=$2}' | sort -n # 34.5 sec for 25 msgs = 1.38 msgs/sec ## ## notes ## # search query GET /api/v6/guilds/$ID_GUILD/messages/search?author_id=$ID_USER_SELF HTTP/1.1 Host: discord.com Authorization: $AUTHKEY Connection: keep-alive Referer: https://discord.com/channels/$ID_GUILD/$ID_GUILD/736220593745297508 # search response HTTP/2 200 OK content-type: application/json via: 1.1 google expect-ct: max-age=604800, report-uri="https://report-uri.cloudflare.com/cdn-cgi/beacon/expect-ct" content-encoding: br X-Firefox-Spdy: h2 # search response { "total_results": 14569, "messages": [ [ { "id": "$ID_MESSAGE_1", "type": 0, "content": "", "channel_id": "$ID_GUILD", "author": { "id": "$ID_USER_1", "username": "$NAME_USER_1", "avatar": "$MD5SUM_AVATAR", "discriminator": "$D4_USER_1", "public_flags": 0 }, "attachments": [ { "id": "$ID_ATTACHMENT_1", "filename": "standard_gammelost_pultost.png", "size": 2195687, "url": "https://cdn.discordapp.com/attachments/$ID_GUILD/$ID_ATTACHMENT_1/standard_gammelost_pultost.png", "proxy_url": "https://media.discordapp.net/attachments/$ID_GUILD/$ID_ATTACHMENT_1/standard_gammelost_pultost.png", "width": 1200, "height": 1200 } ], "embeds": [], "mentions": [], "mention_roles": [], "pinned": false, "mention_everyone": false, "tts": false, "timestamp": "2020-07-14T09:47:33.526000+00:00", "edited_timestamp": null, "flags": 0 }, { "id": "$ID_MESSAGE_2", "type": 0, "content": "<@$ID_USER_SELF>", "channel_id": "$ID_GUILD", "author": { "id": "$ID_USER_2", "username": "$NAME_USER_2", "avatar": "$MD5SUM_AVATAR", "discriminator": "$D4_USER_2", "public_flags": 0 }, "attachments": [ { "id": "$ID_ATTACHMENT_2", "filename": "oQqlX0_12.jpg", "size": 3605, "url": "https://cdn.discordapp.com/attachments/$ID_GUILD/$ID_ATTACHMENT_2/oQqlX0_12.jpg", "proxy_url": "https://media.discordapp.net/attachments/$ID_GUILD/$ID_ATTACHMENT_2/oQqlX0_12.jpg", "width": 93, "height": 125 } ], "embeds": [], "mentions": [ { "id": "$ID_USER_SELF", "username": "$NAME_USER_SELF", "avatar": "$MD5SUM_AVATAR", "discriminator": "$D4_USER_SELF", "public_flags": 0 } ], "mention_roles": [], "pinned": false, "mention_everyone": false, "tts": false, "timestamp": "2020-07-14T09:48:33.526000+00:00", "edited_timestamp": null, "flags": 0 }, { "id": "$ID_MESSAGE_3", "type": 0, "content": "thx", "channel_id": "$ID_GUILD", "author": { "id": "$ID_USER_SELF", "username": "$NAME_USER_SELF", "avatar": "$MD5SUM_AVATAR", "discriminator": "$D4_USER_SELF", "public_flags": 0 }, "attachments": [], "embeds": [], "mentions": [], "mention_roles": [], "pinned": false, "mention_everyone": false, "tts": false, "timestamp": "2020-07-14T09:49:33.526000+00:00", "edited_timestamp": null, "flags": 0, "hit": true }, { "id": "$ID_MESSAGE_4", "type": 0, "content": "Ost", "channel_id": "$ID_GUILD", "author": { "id": "$ID_USER_3", "username": "$NAME_USER_3", "avatar": "$MD5SUM_AVATAR", "discriminator": "$D4_USER_3", "public_flags": 0 }, "attachments": [], "embeds": [], "mentions": [], "mention_roles": [], "pinned": false, "mention_everyone": false, "tts": false, "timestamp": "2020-07-14T09:50:33.526000+00:00", "edited_timestamp": null, "flags": 0 } ], [ { "id": "$ID_MESSAGE_5", "type": 0, "content": "we **need** it all", "channel_id": "$ID_GUILD", "author": { "id": "$ID_USER_4", "username": "$NAME_USER_4", "avatar": "$MD5SUM_AVATAR", "discriminator": "$D4_USER_4", "public_flags": 0 }, "attachments": [], "embeds": [], "mentions": [], "mention_roles": [], "pinned": false, "mention_everyone": false, "tts": false, "timestamp": "2020-07-14T09:46:33.526000+00:00", "edited_timestamp": null, "flags": 0 }, ... ] ], "analytics_id": "$MD5SUM_SOMETHING" } # cleanup cmd var m = j.messages; var rm = []; for (var a=0; a isn't this what multiple accounts is for" ] Array(4) [ "$ID_GUILD", "$ID_MESSAGE_13", "2020-03-xxT88:88:88.888000+00:00", "cc <@!$ID_USER_3>" ] # delete DELETE /api/v6/channels/$ID_GUILD/messages/$ID_MESSAGE_3 HTTP/1.1 Host: discord.com Authorization: $AUTHKEY X-Super-Properties: $HUGE_BASE64_STRING Origin: https://discord.com Connection: keep-alive Referer: https://discord.com/channels/$ID_GUILD/$ID_GUILD/$ID_MESSAGE_3 HTTP/2 204 No Content access-control-allow-origin: https://discord.com access-control-allow-credentials: true access-control-allow-methods: POST, GET, PUT, PATCH, DELETE access-control-allow-headers: Content-Type, Authorization, X-Track, X-Super-Properties, X-Context-Properties, X-Failed-Requests, X-Fingerprint, X-RPC-Proxy, X-Debug-Options, x-client-trace-id, If-None-Match, X-RateLimit-Precision strict-transport-security: max-age=31536000; includeSubDomains; preload via: 1.1 google expect-ct: max-age=604800, report-uri="https://report-uri.cloudflare.com/cdn-cgi/beacon/expect-ct" x-content-type-options: nosniff X-Firefox-Spdy: h2 # copyparty push test await fetch('http://127.0.0.1:42825/', {method:"PUT"}, body: JSON.stringify({'foo':'bar'})) await fetch('http://127.0.0.1:42827/', {method:"POST", body: JSON.stringify([1,2,3])}); await fetch('http://127.0.0.1:3923/?raw', {method:"POST", body: JSON.stringify([1,2,3])}); await fetch('http://127.0.0.1:3923/', {method:"PUT", body: JSON.stringify([1,2,3,4])}); (await fetch('http://127.0.0.1:3923/', {method:"PUT", body: JSON.stringify(data)})).text();