diff --git a/src/Rest/Helpers/Channel/Channel/ThreadChannelBuilder.php b/src/Rest/Helpers/Channel/Channel/ThreadChannelBuilder.php new file mode 100644 index 0000000..83c304e --- /dev/null +++ b/src/Rest/Helpers/Channel/Channel/ThreadChannelBuilder.php @@ -0,0 +1,86 @@ + $tagIds + */ + public function setAppliedTags(array $tagIds): self + { + $this->data['applied_tags'] = array_values($tagIds); + + return $this; + } + + /** + * @return list|null + */ + public function getAppliedTags(): ?array + { + return $this->data['applied_tags'] ?? null; + } + + public function setArchived(bool $archived): self + { + $this->data['archived'] = $archived; + + return $this; + } + + /** + * A locked thread can still be read, but only a moderator may unarchive it. + */ + public function setLocked(bool $locked): self + { + $this->data['locked'] = $locked; + + return $this; + } + + /** + * Whether anyone in the thread may add others to it. Private threads only. + */ + public function setInvitable(bool $invitable): self + { + $this->data['invitable'] = $invitable; + + return $this; + } + + /** + * How long the thread sits idle before archiving itself, in minutes. + * Discord takes 60, 1440, 4320 or 10080. + */ + public function setAutoArchiveDuration(int $minutes): self + { + $this->data['auto_archive_duration'] = $minutes; + + return $this; + } +} diff --git a/tests/Rest/ChannelTest.php b/tests/Rest/ChannelTest.php index bf512be..f0bce73 100644 --- a/tests/Rest/ChannelTest.php +++ b/tests/Rest/ChannelTest.php @@ -22,6 +22,7 @@ use Tempcord\Discord\Rest\Helpers\Channel\Channel\GuildStageVoiceChannelBuilder; use Tempcord\Discord\Rest\Helpers\Channel\Channel\GuildTextChannelBuilder; use Tempcord\Discord\Rest\Helpers\Channel\Channel\GuildVoiceChannelBuilder; +use Tempcord\Discord\Rest\Helpers\Channel\Channel\ThreadChannelBuilder; use Tempcord\Discord\Rest\Helpers\Channel\EditMessageBuilder; use Tempcord\Discord\Rest\Helpers\Channel\EditPermissionsBuilder; use Tempcord\Discord\Rest\Helpers\Channel\MessageBuilder; @@ -192,6 +193,17 @@ public static function httpBindingsProvider(): array 'returnType' => PartsChannel::class, ] ], + 'Modify channel with Thread' => [ + 'method' => 'modify', + 'args' => ['::channel id::', new ThreadChannelBuilder()], + 'mockOptions' => [ + 'method' => 'patch', + 'return' => (object) [], + ], + 'validationOptions' => [ + 'returnType' => PartsChannel::class, + ] + ], 'Delete channel' => [ 'method' => 'delete', 'args' => ['::channel id::'], diff --git a/tests/Rest/Helpers/Channel/Channel/ThreadChannelBuilderTest.php b/tests/Rest/Helpers/Channel/Channel/ThreadChannelBuilderTest.php new file mode 100644 index 0000000..5c545b1 --- /dev/null +++ b/tests/Rest/Helpers/Channel/Channel/ThreadChannelBuilderTest.php @@ -0,0 +1,81 @@ +setAppliedTags(['::voting::', '::urgent::']); + + $this->assertSame(['applied_tags' => ['::voting::', '::urgent::']], $builder->get()); + $this->assertSame(['::voting::', '::urgent::'], $builder->getAppliedTags()); + } + + /** + * Discord replaces the whole set, so the keys have to be a plain list — an + * array with gaps in it serialises to an object and the call is refused. + */ + public function testTagsAreSentAsAList(): void + { + $tags = [3 => '::voting::', 7 => '::urgent::']; + + $this->assertSame( + '{"applied_tags":["::voting::","::urgent::"]}', + json_encode(ThreadChannelBuilder::new()->setAppliedTags($tags)->get()), + ); + } + + public function testTakingEveryTagOffIsSaidWithAnEmptyList(): void + { + $this->assertSame(['applied_tags' => []], ThreadChannelBuilder::new()->setAppliedTags([])->get()); + } + + public function testItArchivesAndLocks(): void + { + $builder = ThreadChannelBuilder::new()->setArchived(true)->setLocked(true); + + $this->assertSame(['archived' => true, 'locked' => true], $builder->get()); + } + + public function testItSetsTheIdleTimeBeforeArchiving(): void + { + $this->assertSame( + ['auto_archive_duration' => 1440], + ThreadChannelBuilder::new()->setAutoArchiveDuration(1440)->get(), + ); + } + + public function testItSetsWhoMayAddOthers(): void + { + $this->assertSame(['invitable' => false], ThreadChannelBuilder::new()->setInvitable(false)->get()); + } + + public function testItSetsSlowmode(): void + { + $this->assertSame( + ['rate_limit_per_user' => 30], + ThreadChannelBuilder::new()->setRateLimitPerUser(30)->get(), + ); + } + + public function testItRenames(): void + { + $this->assertSame(['name' => '::title::'], ThreadChannelBuilder::new()->setName('::title::')->get()); + } + + /** + * A thread has no channel type of its own to send, unlike every other + * builder here — Discord infers it from the channel being modified, and + * sending one is refused. + */ + public function testItSendsNoChannelType(): void + { + $this->assertArrayNotHasKey('type', ThreadChannelBuilder::new()->setName('::title::')->get()); + } +}