From ff6237d5d5884c375bdd38c1172ebc94f0aa2e0d Mon Sep 17 00:00:00 2001 From: James Seconde Date: Mon, 14 Aug 2023 09:29:38 +0100 Subject: [PATCH 1/5] remove legacy array check, refactor to use new method from 8.1 or fall back to correct logic --- src/OpenTok/Util/Validators.php | 12 ++++++------ 1 file changed, 6 insertions(+), 6 deletions(-) diff --git a/src/OpenTok/Util/Validators.php b/src/OpenTok/Util/Validators.php index 1499a71..5ff0bc3 100755 --- a/src/OpenTok/Util/Validators.php +++ b/src/OpenTok/Util/Validators.php @@ -429,16 +429,16 @@ public static function validateDTMFDigits(string $digits): void throw new InvalidArgumentException('DTMF digits can only support 0-9, p, #, and * characters'); } - // Helpers - - // credit: http://stackoverflow.com/a/173479 public static function isAssoc($arr): bool { - if (array() === $arr) { - return false; + if (!function_exists('array_is_list')) { + if ($arr === []) { + return true; + } + return array_keys($arr) === range(0, count($arr) - 1); } - return array_keys($arr) !== range(0, count($arr) - 1); + return array_is_list($arr); } protected static function decodeSessionId($sessionId) From 4129c31c9afd40f8e07af8e8ba278916135dc7a9 Mon Sep 17 00:00:00 2001 From: James Seconde Date: Mon, 14 Aug 2023 10:04:32 +0100 Subject: [PATCH 2/5] invert method to correct the return value --- src/OpenTok/Util/Validators.php | 11 +++++++---- 1 file changed, 7 insertions(+), 4 deletions(-) diff --git a/src/OpenTok/Util/Validators.php b/src/OpenTok/Util/Validators.php index 5ff0bc3..022b86f 100755 --- a/src/OpenTok/Util/Validators.php +++ b/src/OpenTok/Util/Validators.php @@ -432,13 +432,16 @@ public static function validateDTMFDigits(string $digits): void public static function isAssoc($arr): bool { if (!function_exists('array_is_list')) { - if ($arr === []) { - return true; + function array_is_list(array $arr): bool + { + if ($arr === []) { + return true; + } + return array_keys($arr) === range(0, count($arr) - 1); } - return array_keys($arr) === range(0, count($arr) - 1); } - return array_is_list($arr); + return !array_is_list($arr); } protected static function decodeSessionId($sessionId) From eb57509514209bcffc4dc9f76920b37c000dc2d8 Mon Sep 17 00:00:00 2001 From: James Seconde Date: Mon, 14 Aug 2023 10:27:43 +0100 Subject: [PATCH 3/5] increase test coverage --- src/OpenTok/Util/Validators.php | 5 ++ tests/OpenTokTest/LayoutTest.php | 9 +++ .../OpenTokTest/Validators/ValidatorsTest.php | 74 +++++++++++++++---- 3 files changed, 72 insertions(+), 16 deletions(-) diff --git a/src/OpenTok/Util/Validators.php b/src/OpenTok/Util/Validators.php index 9e1ebdf..4e30013 100755 --- a/src/OpenTok/Util/Validators.php +++ b/src/OpenTok/Util/Validators.php @@ -428,6 +428,11 @@ public static function validateLayoutClassListItem($layoutClassList) if (!is_array($layoutClassList)) { throw new InvalidArgumentException('Each element in the streamClassArray must have a layoutClassList array.'); } + + if (!isset($layoutClassList['layoutClassList'])) { + throw new InvalidArgumentException('layoutClassList not set in array'); + } + if (!is_array($layoutClassList['layoutClassList'])) { throw new InvalidArgumentException('Each element in the layoutClassList array must be a string (defining class names).'); } diff --git a/tests/OpenTokTest/LayoutTest.php b/tests/OpenTokTest/LayoutTest.php index ad17613..60a5925 100644 --- a/tests/OpenTokTest/LayoutTest.php +++ b/tests/OpenTokTest/LayoutTest.php @@ -3,6 +3,7 @@ namespace OpenTokTest; use OpenTok\Layout; +use OpenTok\Util\Validators; use PHPStan\Testing\TestCase; class LayoutTest extends TestCase @@ -21,6 +22,14 @@ public function testStylesheetIsNotInSerializedArrayIfNotCustom() } } + public function testWillValidateLayout(): void + { + $this->expectException(\InvalidArgumentException::class); + $object = ['bestFit' => true]; + + Validators::validateLayout($object); + } + public function testStylesheetIsInSerializedArrayIfCustom() { $layout = Layout::createCustom(['stylesheet' => 'foo']); diff --git a/tests/OpenTokTest/Validators/ValidatorsTest.php b/tests/OpenTokTest/Validators/ValidatorsTest.php index 57c28db..5809fb7 100644 --- a/tests/OpenTokTest/Validators/ValidatorsTest.php +++ b/tests/OpenTokTest/Validators/ValidatorsTest.php @@ -72,28 +72,28 @@ public function testWillPassCorrectForceMutePayload(): void Validators::validateForceMuteAllOptions($options); } - public function testIsAssocWithValidArray(): void + public function testIsAssocWithIndexedArray(): void { - $haystack = [ - 'one' => '1', - 'two' => '2', - 'three' => '3', - 'four' => '4' - ]; + $array = [1, 2, 3, 4]; + $this->assertFalse(Validators::isAssoc($array)); + } - $this->assertTrue(Validators::isAssoc($haystack)); + public function testIsAssocWithAssociativeArray(): void + { + $array = ['a' => 1, 'b' => 2, 'c' => 3]; + $this->assertTrue(Validators::isAssoc($array)); } - public function testIsAssocWithInvalidArray(): void + public function testIsAssocWithMixedKeysArray(): void { - $haystack = [ - 'one', - 'two', - 'three', - 'four' - ]; + $array = [1, 'a' => 2, 3]; + $this->assertTrue(Validators::isAssoc($array)); + } - $this->assertFalse(Validators::isAssoc($haystack)); + public function testIsAssocWithEmptyArray(): void + { + $array = []; + $this->assertFalse(Validators::isAssoc($array)); } public function testWillFailWhenStreamIdsAreNotCorrect(): void @@ -178,6 +178,48 @@ public function testValidResolutions($resolution, $isValid): void Validators::validateResolution($resolution); } + public function testValidLayoutClassListItem(): void + { + $layoutClassList = [ + 'id' => 'example_id', + 'layoutClassList' => ['class1', 'class2'] + ]; + + $this->assertNull(Validators::validateLayoutClassListItem($layoutClassList)); + } + + public function testInvalidIdType(): void + { + $this->expectException(InvalidArgumentException::class); + $layoutClassList = [ + 'id' => 123, + 'layoutClassList' => ['class1', 'class2'] + ]; + + Validators::validateLayoutClassListItem($layoutClassList); + } + + public function testMissingLayoutClassList(): void + { + $this->expectException(InvalidArgumentException::class); + $layoutClassList = [ + 'id' => 'example_id' + ]; + + Validators::validateLayoutClassListItem($layoutClassList); + } + + public function testInvalidLayoutClassListType(): void + { + $this->expectException(InvalidArgumentException::class); + $layoutClassList = [ + 'id' => 'example_id', + 'layoutClassList' => 'invalid_class' + ]; + + Validators::validateLayoutClassListItem($layoutClassList); + } + public function resolutionProvider(): array { return [ From 8aadbfded5b571694d836e45c2c5c2de53e265d6 Mon Sep 17 00:00:00 2001 From: James Seconde Date: Mon, 14 Aug 2023 11:11:54 +0100 Subject: [PATCH 4/5] increase test coverage --- .../OpenTokTest/Validators/ValidatorsTest.php | 67 +++++++++++++++++++ 1 file changed, 67 insertions(+) diff --git a/tests/OpenTokTest/Validators/ValidatorsTest.php b/tests/OpenTokTest/Validators/ValidatorsTest.php index 5809fb7..84e5397 100644 --- a/tests/OpenTokTest/Validators/ValidatorsTest.php +++ b/tests/OpenTokTest/Validators/ValidatorsTest.php @@ -3,6 +3,7 @@ namespace OpenTokTest\Validators; use OpenTok\Exception\InvalidArgumentException; +use OpenTok\Util\Client; use OpenTok\Util\Validators; use PHPUnit\Framework\TestCase; @@ -219,6 +220,72 @@ public function testInvalidLayoutClassListType(): void Validators::validateLayoutClassListItem($layoutClassList); } + public function testValidateClient(): void + { + $client = new Client(); + Validators::validateClient($client); + + // No exception, which was the test so fake a pass + $this->assertTrue(true); + } + + public function testExceptionOnInvalidClient(): void + { + $this->expectException(\InvalidArgumentException::class); + $client = new \stdClass(); + Validators::validateClient($client); + } + + public function testThrowsErrorOnInvalidStreamMode(): void + { + $this->expectException(\InvalidArgumentException::class); + $streamMode = ['auto']; + Validators::validateHasStreamMode($streamMode); + } + + public function testValidateSignalPayload(): void + { + $validPayload = ['type' => 'signal_type', 'data' => 'signal_data']; + $this->assertNull(Validators::validateSignalPayload($validPayload)); + + $invalidDataPayload = ['type' => 'signal_type', 'data' => 123]; + $this->expectException(InvalidArgumentException::class); + $this->expectExceptionMessage("Signal Payload cannot be null:"); + Validators::validateSignalPayload($invalidDataPayload); + + $invalidTypePayload = ['type' => null, 'data' => 'signal_data']; + $this->expectException(InvalidArgumentException::class); + $this->expectExceptionMessage("Signal Payload cannot be null:"); + Validators::validateSignalPayload($invalidTypePayload); + + // Invalid payload: both type and data are null + $invalidBothPayload = ['type' => null, 'data' => null]; + $this->expectException(InvalidArgumentException::class); + $this->expectExceptionMessage("Signal Payload cannot be null:"); + Validators::validateSignalPayload($invalidBothPayload); + } + + /** + * @dataProvider connectionIdProvider + */ + public function testConnectionId($input, $expectException): void + { + if ($expectException) { + $this->expectException(\InvalidArgumentException::class); + } + + Validators::validateConnectionId($input); + $this->assertTrue(true); + } + + public function connectionIdProvider(): array + { + return [ + [['this' => 'is not a string'], true], + ['', true], + ['valid_connection_string', false] + ]; + } public function resolutionProvider(): array { From ee9f3ad4cb3ab6463315954a8e0b8d1ea8778bee Mon Sep 17 00:00:00 2001 From: James Seconde Date: Mon, 14 Aug 2023 12:00:15 +0100 Subject: [PATCH 5/5] increase test coverage, fix validator order --- src/OpenTok/Util/Validators.php | 8 +++---- .../OpenTokTest/Validators/ValidatorsTest.php | 21 ++++++++++++------- 2 files changed, 18 insertions(+), 11 deletions(-) diff --git a/src/OpenTok/Util/Validators.php b/src/OpenTok/Util/Validators.php index 4e30013..ad67ed5 100755 --- a/src/OpenTok/Util/Validators.php +++ b/src/OpenTok/Util/Validators.php @@ -421,14 +421,14 @@ public static function validateAutoArchiveResolution($archiveResolution) public static function validateLayoutClassListItem($layoutClassList) { - if (!is_string($layoutClassList['id'])) { - throw new InvalidArgumentException('Each element in the streamClassArray must have an id string.'); - } - if (!is_array($layoutClassList)) { throw new InvalidArgumentException('Each element in the streamClassArray must have a layoutClassList array.'); } + if (!is_string($layoutClassList['id'])) { + throw new InvalidArgumentException('Each element in the streamClassArray must have an id string.'); + } + if (!isset($layoutClassList['layoutClassList'])) { throw new InvalidArgumentException('layoutClassList not set in array'); } diff --git a/tests/OpenTokTest/Validators/ValidatorsTest.php b/tests/OpenTokTest/Validators/ValidatorsTest.php index 84e5397..c5e7390 100644 --- a/tests/OpenTokTest/Validators/ValidatorsTest.php +++ b/tests/OpenTokTest/Validators/ValidatorsTest.php @@ -67,7 +67,7 @@ public function testWillPassCorrectForceMutePayload(): void 'streamId1', 'streamId2' ], - 'active' => true + 'active' => true ]; Validators::validateForceMuteAllOptions($options); @@ -106,7 +106,7 @@ public function testWillFailWhenStreamIdsAreNotCorrect(): void 3536, 'streamId2' ], - 'active' => true + 'active' => true ]; Validators::validateForceMuteAllOptions($options); @@ -121,7 +121,7 @@ public function testWillFailWhenActiveIsNotBool(): void 'streamId1', 'streamId2' ], - 'active' => 'true' + 'active' => 'true' ]; Validators::validateForceMuteAllOptions($options); @@ -133,7 +133,7 @@ public function testWillFailWhenStreamIdsIsNotArray(): void $options = [ 'excludedStreams' => 'streamIdOne', - 'active' => false + 'active' => false ]; Validators::validateForceMuteAllOptions($options); @@ -143,7 +143,7 @@ public function testWillValidateWebsocketConfiguration(): void { $this->expectNotToPerformAssertions(); $websocketConfig = [ - 'uri' => 'ws://valid-websocket', + 'uri' => 'ws://valid-websocket', 'streams' => [ '525503c7-913e-43a1-84b4-31b2e9fe668b', '14026813-4f50-4a5a-9b72-fea25430916d' @@ -163,14 +163,14 @@ public function testWillThrowExceptionOnInvalidWebsocketConfiguration(): void ] ]; Validators::validateWebsocketOptions($websocketConfig); - } + } /** * @dataProvider resolutionProvider */ public function testValidResolutions($resolution, $isValid): void { - if (!$isValid) { + if ( ! $isValid) { $this->expectException(InvalidArgumentException::class); } else { $this->expectNotToPerformAssertions(); @@ -179,6 +179,13 @@ public function testValidResolutions($resolution, $isValid): void Validators::validateResolution($resolution); } + public function testValidLayoutClassListItemErrorOnString(): void + { + $input = 'example_id'; + $this->expectException(\InvalidArgumentException::class); + Validators::validateLayoutClassListItem($input); + } + public function testValidLayoutClassListItem(): void { $layoutClassList = [