mirror of
https://github.com/Tyrrrz/DiscordChatExporter.git
synced 2026-01-31 23:29:12 +00:00
Use alternative endpoint to retrieve threads when requested by a bot (#1037)
Co-authored-by: Oleksii Holub <1935960+Tyrrrz@users.noreply.github.com>
This commit is contained in:
@@ -36,6 +36,12 @@ public class GetChannelsCommand : DiscordCommandBase
|
||||
.ThenBy(c => c.Name)
|
||||
.ToArray();
|
||||
|
||||
var threads = IncludeThreads
|
||||
? (await Discord.GetGuildThreadsAsync(GuildId, cancellationToken))
|
||||
.OrderBy(c => c.Name)
|
||||
.ToArray()
|
||||
: Array.Empty<ChannelThread>();
|
||||
|
||||
foreach (var channel in channels)
|
||||
{
|
||||
// Channel ID
|
||||
@@ -51,31 +57,24 @@ public class GetChannelsCommand : DiscordCommandBase
|
||||
using (console.WithForegroundColor(ConsoleColor.White))
|
||||
await console.Output.WriteLineAsync($"{channel.Category.Name} / {channel.Name}");
|
||||
|
||||
if (IncludeThreads)
|
||||
foreach (var thread in threads.Where(t => t.ParentId == channel.Id))
|
||||
{
|
||||
var threads = (await Discord.GetChannelThreadsAsync(channel.Id, cancellationToken))
|
||||
.OrderBy(c => c.Name)
|
||||
.ToArray();
|
||||
// Indent
|
||||
await console.Output.WriteAsync('\t');
|
||||
|
||||
foreach (var thread in threads)
|
||||
{
|
||||
// Indent
|
||||
await console.Output.WriteAsync('\t');
|
||||
// Thread ID
|
||||
await console.Output.WriteAsync(
|
||||
thread.Id.ToString().PadRight(18, ' ')
|
||||
);
|
||||
|
||||
// Thread ID
|
||||
await console.Output.WriteAsync(
|
||||
thread.Id.ToString().PadRight(18, ' ')
|
||||
);
|
||||
// Separator
|
||||
using (console.WithForegroundColor(ConsoleColor.DarkGray))
|
||||
await console.Output.WriteAsync(" | ");
|
||||
|
||||
// Separator
|
||||
using (console.WithForegroundColor(ConsoleColor.DarkGray))
|
||||
await console.Output.WriteAsync(" | ");
|
||||
|
||||
// Thread name
|
||||
using (console.WithForegroundColor(ConsoleColor.White))
|
||||
await console.Output.WriteLineAsync($"Thread / {thread.Name}");
|
||||
}
|
||||
}
|
||||
// Thread name
|
||||
using (console.WithForegroundColor(ConsoleColor.White))
|
||||
await console.Output.WriteLineAsync($"Thread / {thread.Name}");
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -10,6 +10,7 @@ public record ChannelThread(
|
||||
Snowflake Id,
|
||||
ChannelKind Kind,
|
||||
Snowflake GuildId,
|
||||
Snowflake ParentId,
|
||||
string Name,
|
||||
Snowflake? LastMessageId) : IHasId
|
||||
{
|
||||
@@ -18,6 +19,7 @@ public record ChannelThread(
|
||||
var id = json.GetProperty("id").GetNonWhiteSpaceString().Pipe(Snowflake.Parse);
|
||||
var kind = (ChannelKind)json.GetProperty("type").GetInt32();
|
||||
var guildId = json.GetProperty("guild_id").GetNonWhiteSpaceString().Pipe(Snowflake.Parse);
|
||||
var parentId = json.GetProperty("parent_id").GetNonWhiteSpaceString().Pipe(Snowflake.Parse);
|
||||
var name = json.GetProperty("name").GetNonWhiteSpaceString();
|
||||
|
||||
var lastMessageId = json
|
||||
@@ -29,6 +31,7 @@ public record ChannelThread(
|
||||
id,
|
||||
kind,
|
||||
guildId,
|
||||
parentId,
|
||||
name,
|
||||
lastMessageId
|
||||
);
|
||||
|
||||
@@ -311,30 +311,68 @@ public class DiscordClient
|
||||
return Channel.Parse(response, category);
|
||||
}
|
||||
|
||||
public async IAsyncEnumerable<ChannelThread> GetChannelThreadsAsync(
|
||||
Snowflake channelId,
|
||||
public async IAsyncEnumerable<ChannelThread> GetGuildThreadsAsync(
|
||||
Snowflake guildId,
|
||||
[EnumeratorCancellation] CancellationToken cancellationToken = default)
|
||||
{
|
||||
var currentOffset = 0;
|
||||
while (true)
|
||||
var channels = (await GetGuildChannelsAsync(guildId, cancellationToken))
|
||||
.ToArray();
|
||||
var tokenKind = _resolvedTokenKind ??= await GetTokenKindAsync(cancellationToken);
|
||||
|
||||
if (tokenKind == TokenKind.Bot)
|
||||
{
|
||||
var url = new UrlBuilder()
|
||||
.SetPath($"channels/{channelId}/threads/search")
|
||||
.SetQueryParameter("offset", currentOffset.ToString())
|
||||
.Build();
|
||||
|
||||
var response = await TryGetJsonResponseAsync(url, cancellationToken);
|
||||
if (response is null)
|
||||
break;
|
||||
|
||||
foreach (var threadJson in response.Value.GetProperty("threads").EnumerateArray())
|
||||
var response = await GetJsonResponseAsync($"guilds/{guildId}/threads/active", cancellationToken);
|
||||
foreach (var threadJson in response.GetProperty("threads").EnumerateArray())
|
||||
{
|
||||
yield return ChannelThread.Parse(threadJson);
|
||||
currentOffset++;
|
||||
}
|
||||
}
|
||||
foreach (var channel in channels)
|
||||
{
|
||||
if (tokenKind == TokenKind.User)
|
||||
{
|
||||
var currentOffset = 0;
|
||||
while (true)
|
||||
{
|
||||
var url = new UrlBuilder()
|
||||
.SetPath($"channels/{channel.Id}/threads/search")
|
||||
.SetQueryParameter("offset", currentOffset.ToString())
|
||||
.Build();
|
||||
|
||||
if (!response.Value.GetProperty("has_more").GetBoolean())
|
||||
break;
|
||||
var response = await TryGetJsonResponseAsync(url, cancellationToken);
|
||||
if (response is null)
|
||||
break;
|
||||
|
||||
foreach (var threadJson in response.Value.GetProperty("threads").EnumerateArray())
|
||||
{
|
||||
yield return ChannelThread.Parse(threadJson);
|
||||
currentOffset++;
|
||||
}
|
||||
|
||||
if (!response.Value.GetProperty("has_more").GetBoolean())
|
||||
break;
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
var responsePublic = await TryGetJsonResponseAsync($"channels/{channel.Id}/threads/archived/public", cancellationToken);
|
||||
var responsePrivate = await TryGetJsonResponseAsync($"channels/{channel.Id}/threads/archived/private", cancellationToken);
|
||||
|
||||
if (responsePublic is not null)
|
||||
{
|
||||
foreach (var threadJson in responsePublic.Value.GetProperty("threads").EnumerateArray())
|
||||
{
|
||||
yield return ChannelThread.Parse(threadJson);
|
||||
}
|
||||
}
|
||||
if (responsePrivate is not null)
|
||||
{
|
||||
foreach (var threadJson in responsePrivate.Value.GetProperty("threads").EnumerateArray())
|
||||
{
|
||||
yield return ChannelThread.Parse(threadJson);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
Reference in New Issue
Block a user