Files
WP-LIT-MCP/tests/Unit/Integrations/Divi/Release/FeatureSetsTest.php
T
Jan-Niclas LoosenandClaude Opus 5.5 c85131603b feat(compat): Profile, Gates und Pods über den Kompatibilitätskern
Neu: Tier, Profile, Compatibility, CapabilityLocked, CapabilityGate, CompatibilityComponent, ProvidesCompatibility, DiviProfile sowie PodsFeature, PodsCompatibility und PodsIntegration. Das CapabilityGate sperrt gesperrte und unbekannte Fähigkeits-IDs (übernimmt die Sperre unbekannter IDs vom DiviFeatureGate) und delegiert nur Divi ausdrücklich. Pods-Schema, -Lesen, -Schreiben und -Feldrechte laufen über usable(PodsFeature::…); Schreiben verlangt FieldRead und FieldWrite, damit ein Rollback keine Werte verliert. lit-site-status meldet Pods über die CompatibilityComponent.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
2026-11-06 12:26:54 +01:00

135 lines
4.7 KiB
PHP

<?php
declare(strict_types=1);
namespace LIT\MCP\Tests\Unit\Integrations\Divi\Release;
use Brain\Monkey\Functions;
use LIT\MCP\Abilities\Ability;
use LIT\MCP\Abilities\DeclaresRequirements;
use LIT\MCP\Integrations\Divi\Release\DiviFeature;
use LIT\MCP\Integrations\Divi\Release\FeatureSets;
use LIT\MCP\Integrations\Divi\Release\RequiresDiviFeatures;
use LIT\MCP\Tests\Unit\TestCase;
use Mockery;
final class FeatureSetsTest extends TestCase
{
/** @var array<int, string> */
private array $types = [];
private bool $mayEdit = true;
protected function setUp(): void
{
parent::setUp();
Functions\when('get_post_type')->alias(fn (int $id): string|false => $this->types[$id] ?? false);
Functions\when('current_user_can')->alias(fn (string $capability): bool => $this->mayEdit);
}
public function testMergeKeepsEveryFeatureOnceInTheOrderOfItsFirstAppearance(): void
{
$merged = FeatureSets::merge(
[DiviFeature::Catalog, DiviFeature::Roles],
[],
[DiviFeature::Roles, DiviFeature::PageRead, DiviFeature::Catalog]
);
self::assertSame([DiviFeature::Catalog, DiviFeature::Roles, DiviFeature::PageRead], $merged);
self::assertSame([], FeatureSets::merge());
}
public function testAPageOrPostAddsNothing(): void
{
$this->types = [5 => 'page', 6 => 'post', 7 => 'project'];
foreach ([5, 6, 7, '5'] as $id) {
self::assertSame([], FeatureSets::ofEntry($id, true), (string) $id);
self::assertSame([], FeatureSets::ofEntry($id, false), (string) $id);
}
}
public function testAnIdThatNamesNoEntryAddsNothing(): void
{
foreach ([null, 0, -3, 'abc', '1.5', [], 404] as $id) {
self::assertSame([], FeatureSets::ofEntry($id, true), var_export($id, true));
}
}
public function testALibraryEntryNeedsTheRolesAndWritingAlsoTheLibrary(): void
{
$this->types = [7 => 'et_pb_layout'];
self::assertSame([DiviFeature::Roles], FeatureSets::ofEntry(7, false));
self::assertSame(
[DiviFeature::Roles, DiviFeature::LibraryRead, DiviFeature::LibraryWrite],
FeatureSets::ofEntry('7', true)
);
}
public function testEveryThemeBuilderLayoutNeedsTheRolesAndWritingAlsoTheThemeBuilder(): void
{
$this->types = [1 => 'et_header_layout', 2 => 'et_body_layout', 3 => 'et_footer_layout'];
foreach ([1, 2, 3] as $id) {
self::assertSame([DiviFeature::Roles], FeatureSets::ofEntry($id, false), (string) $id);
self::assertSame(
[DiviFeature::Roles, DiviFeature::ThemeBuilderRead, DiviFeature::ThemeBuilderWrite],
FeatureSets::ofEntry($id, true),
(string) $id
);
}
}
public function testAnEntryTheCallerMayNotEditAddsNothingSoALockNeverNamesItsKind(): void
{
$this->types = [7 => 'et_pb_layout', 9 => 'et_body_layout'];
$this->mayEdit = false;
foreach ([7, 9] as $id) {
self::assertSame([], FeatureSets::ofEntry($id, true), (string) $id);
self::assertSame([], FeatureSets::ofEntry($id, false), (string) $id);
}
}
public function testTemplatesAndThemeBuilderPostsAreNoLayouts(): void
{
$this->types = [1 => 'et_template', 2 => 'et_theme_builder'];
self::assertSame([], FeatureSets::ofEntry(1, true));
self::assertSame([], FeatureSets::ofEntry(2, true));
}
public function testDeclaredByReadsTheDiviToolsOwnList(): void
{
$tool = Mockery::mock(Ability::class, RequiresDiviFeatures::class);
$tool->expects('diviFeatures')->with(['a' => 1])->andReturn([DiviFeature::Roles, DiviFeature::Roles]);
self::assertSame([DiviFeature::Roles], FeatureSets::declaredBy($tool, ['a' => 1]));
}
public function testDeclaredByTranslatesTheIdsOfACoreTool(): void
{
$tool = Mockery::mock(Ability::class, DeclaresRequirements::class);
$tool->expects('requirements')->with(['divi' => []])->andReturn(['page-write', 'catalog']);
self::assertSame(
[DiviFeature::PageWrite, DiviFeature::Catalog],
FeatureSets::declaredBy($tool, ['divi' => []])
);
}
public function testDeclaredByIgnoresIdsThatAreNoDiviFeature(): void
{
$tool = Mockery::mock(Ability::class, DeclaresRequirements::class);
$tool->allows('requirements')->andReturn(['pods-field-read', 'page-write']);
self::assertSame([DiviFeature::PageWrite], FeatureSets::declaredBy($tool, ['divi' => []]));
}
public function testDeclaredByIsEmptyForAnyOtherTool(): void
{
self::assertSame([], FeatureSets::declaredBy(Mockery::mock(Ability::class), ['x' => 1]));
}
}