|
|
|
|
@ -16,6 +16,7 @@ use OC\AppFramework\Utility\ControllerMethodReflector; |
|
|
|
|
use OCP\AppFramework\Controller; |
|
|
|
|
use OCP\AppFramework\Http; |
|
|
|
|
use OCP\AppFramework\Http\DataResponse; |
|
|
|
|
use OCP\AppFramework\Http\InvalidEnumParameterException; |
|
|
|
|
use OCP\AppFramework\Http\InvalidStringParameterException; |
|
|
|
|
use OCP\AppFramework\Http\JSONResponse; |
|
|
|
|
use OCP\AppFramework\Http\ParameterOutOfRangeException; |
|
|
|
|
@ -30,6 +31,16 @@ use PHPUnit\Framework\MockObject\MockObject; |
|
|
|
|
use Psr\Container\ContainerInterface; |
|
|
|
|
use Psr\Log\LoggerInterface; |
|
|
|
|
|
|
|
|
|
enum TestStringBackedEnum: string { |
|
|
|
|
case Foo = 'foo'; |
|
|
|
|
case Bar = 'bar'; |
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
enum TestIntBackedEnum: int { |
|
|
|
|
case One = 1; |
|
|
|
|
case Two = 2; |
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
class TestController extends Controller { |
|
|
|
|
/** |
|
|
|
|
* @param string $appName |
|
|
|
|
@ -70,6 +81,18 @@ class TestController extends Controller { |
|
|
|
|
public function test(): Response { |
|
|
|
|
return new DataResponse(); |
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
public function execStringBackedEnum(TestStringBackedEnum $enum) { |
|
|
|
|
return [$enum]; |
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
public function execIntBackedEnum(TestIntBackedEnum $enum) { |
|
|
|
|
return [$enum]; |
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
public function execNullableBackedEnum(?TestStringBackedEnum $enum = null) { |
|
|
|
|
return [$enum]; |
|
|
|
|
} |
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
/** |
|
|
|
|
@ -316,6 +339,88 @@ class DispatcherTest extends \Test\TestCase { |
|
|
|
|
$this->assertEquals('[3,false,4,1]', $response[3]); |
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
public function testControllerParametersInjectedStringBackedEnum(): void { |
|
|
|
|
$this->request = new Request( |
|
|
|
|
[ |
|
|
|
|
'post' => [ |
|
|
|
|
'enum' => 'foo', |
|
|
|
|
], |
|
|
|
|
'method' => 'POST', |
|
|
|
|
], |
|
|
|
|
$this->createMock(IRequestId::class), |
|
|
|
|
$this->createMock(IConfig::class) |
|
|
|
|
); |
|
|
|
|
$this->dispatcher = new Dispatcher( |
|
|
|
|
$this->http, $this->middlewareDispatcher, $this->reflector, |
|
|
|
|
$this->request, |
|
|
|
|
$this->config, |
|
|
|
|
Server::get(IDBConnection::class), |
|
|
|
|
$this->logger, |
|
|
|
|
$this->eventLogger, |
|
|
|
|
$this->container |
|
|
|
|
); |
|
|
|
|
$controller = new TestController('app', $this->request); |
|
|
|
|
|
|
|
|
|
$this->dispatcherPassthrough(); |
|
|
|
|
$response = $this->dispatcher->dispatch($controller, 'execStringBackedEnum'); |
|
|
|
|
|
|
|
|
|
$this->assertEquals('["foo"]', $response[3]); |
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
public function testControllerParametersInjectedIntBackedEnum(): void { |
|
|
|
|
$this->request = new Request( |
|
|
|
|
[ |
|
|
|
|
'post' => [ |
|
|
|
|
'enum' => '2', |
|
|
|
|
], |
|
|
|
|
'method' => 'POST', |
|
|
|
|
], |
|
|
|
|
$this->createMock(IRequestId::class), |
|
|
|
|
$this->createMock(IConfig::class) |
|
|
|
|
); |
|
|
|
|
$this->dispatcher = new Dispatcher( |
|
|
|
|
$this->http, $this->middlewareDispatcher, $this->reflector, |
|
|
|
|
$this->request, |
|
|
|
|
$this->config, |
|
|
|
|
Server::get(IDBConnection::class), |
|
|
|
|
$this->logger, |
|
|
|
|
$this->eventLogger, |
|
|
|
|
$this->container |
|
|
|
|
); |
|
|
|
|
$controller = new TestController('app', $this->request); |
|
|
|
|
|
|
|
|
|
$this->dispatcherPassthrough(); |
|
|
|
|
$response = $this->dispatcher->dispatch($controller, 'execIntBackedEnum'); |
|
|
|
|
|
|
|
|
|
$this->assertEquals('[2]', $response[3]); |
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
public function testControllerParametersInjectedNullableBackedEnumDefault(): void { |
|
|
|
|
$this->request = new Request( |
|
|
|
|
[ |
|
|
|
|
'post' => [], |
|
|
|
|
'method' => 'POST', |
|
|
|
|
], |
|
|
|
|
$this->createMock(IRequestId::class), |
|
|
|
|
$this->createMock(IConfig::class) |
|
|
|
|
); |
|
|
|
|
$this->dispatcher = new Dispatcher( |
|
|
|
|
$this->http, $this->middlewareDispatcher, $this->reflector, |
|
|
|
|
$this->request, |
|
|
|
|
$this->config, |
|
|
|
|
Server::get(IDBConnection::class), |
|
|
|
|
$this->logger, |
|
|
|
|
$this->eventLogger, |
|
|
|
|
$this->container |
|
|
|
|
); |
|
|
|
|
$controller = new TestController('app', $this->request); |
|
|
|
|
|
|
|
|
|
$this->dispatcherPassthrough(); |
|
|
|
|
$response = $this->dispatcher->dispatch($controller, 'execNullableBackedEnum'); |
|
|
|
|
|
|
|
|
|
$this->assertEquals('[null]', $response[3]); |
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
public function testControllerParametersInjectedDefaultOverwritten(): void { |
|
|
|
|
$this->request = new Request( |
|
|
|
|
[ |
|
|
|
|
@ -628,4 +733,62 @@ class DispatcherTest extends \Test\TestCase { |
|
|
|
|
$this->assertTrue(true); |
|
|
|
|
} |
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
public static function backedEnumDataProvider(): array { |
|
|
|
|
return [ |
|
|
|
|
[TestStringBackedEnum::class, 'foo', TestStringBackedEnum::Foo], |
|
|
|
|
[TestStringBackedEnum::class, 'bar', TestStringBackedEnum::Bar], |
|
|
|
|
[TestIntBackedEnum::class, '1', TestIntBackedEnum::One], |
|
|
|
|
[TestIntBackedEnum::class, 1, TestIntBackedEnum::One], |
|
|
|
|
[TestIntBackedEnum::class, 2, TestIntBackedEnum::Two], |
|
|
|
|
]; |
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
#[\PHPUnit\Framework\Attributes\DataProvider('backedEnumDataProvider')] |
|
|
|
|
public function testResolveBackedEnumValue(string $enumClass, string|int $input, \BackedEnum $expected): void { |
|
|
|
|
$this->reflector = $this->createMock(ControllerMethodReflector::class); |
|
|
|
|
$this->dispatcher = new Dispatcher( |
|
|
|
|
$this->http, |
|
|
|
|
$this->middlewareDispatcher, |
|
|
|
|
$this->reflector, |
|
|
|
|
$this->request, |
|
|
|
|
$this->config, |
|
|
|
|
Server::get(IDBConnection::class), |
|
|
|
|
$this->logger, |
|
|
|
|
$this->eventLogger, |
|
|
|
|
$this->container, |
|
|
|
|
); |
|
|
|
|
|
|
|
|
|
$result = self::invokePrivate($this->dispatcher, 'resolveBackedEnumValue', ['myArgument', $enumClass, $input]); |
|
|
|
|
$this->assertSame($expected, $result); |
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
public static function invalidBackedEnumDataProvider(): array { |
|
|
|
|
return [ |
|
|
|
|
[TestStringBackedEnum::class, 'invalid'], |
|
|
|
|
[TestIntBackedEnum::class, 'not-a-number'], |
|
|
|
|
[TestIntBackedEnum::class, 99], |
|
|
|
|
[TestStringBackedEnum::class, ['array']], |
|
|
|
|
]; |
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
#[\PHPUnit\Framework\Attributes\DataProvider('invalidBackedEnumDataProvider')] |
|
|
|
|
public function testResolveBackedEnumValueThrowsOnInvalidValue(string $enumClass, mixed $input): void { |
|
|
|
|
$this->reflector = $this->createMock(ControllerMethodReflector::class); |
|
|
|
|
$this->dispatcher = new Dispatcher( |
|
|
|
|
$this->http, |
|
|
|
|
$this->middlewareDispatcher, |
|
|
|
|
$this->reflector, |
|
|
|
|
$this->request, |
|
|
|
|
$this->config, |
|
|
|
|
Server::get(IDBConnection::class), |
|
|
|
|
$this->logger, |
|
|
|
|
$this->eventLogger, |
|
|
|
|
$this->container, |
|
|
|
|
); |
|
|
|
|
|
|
|
|
|
$this->expectException(InvalidEnumParameterException::class); |
|
|
|
|
|
|
|
|
|
self::invokePrivate($this->dispatcher, 'resolveBackedEnumValue', ['myArgument', $enumClass, $input]); |
|
|
|
|
} |
|
|
|
|
} |
|
|
|
|
|