From e61c71df761ae627108810c4c02e767aedd6db9f Mon Sep 17 00:00:00 2001 From: Oleg Andreyev Date: Wed, 24 Jun 2020 01:07:15 +0300 Subject: [PATCH 1/4] based on specifications Window API, window size manipulation returns window rect, which could be useful for consumers --- lib/WebDriverDimension.php | 32 ++++++++++++++- lib/WebDriverWindow.php | 80 ++++++++++++++++++++++++++++++-------- 2 files changed, 94 insertions(+), 18 deletions(-) diff --git a/lib/WebDriverDimension.php b/lib/WebDriverDimension.php index dbc84abb1..3b6b7b851 100644 --- a/lib/WebDriverDimension.php +++ b/lib/WebDriverDimension.php @@ -16,14 +16,28 @@ class WebDriverDimension */ private $width; + /** + * @var int|float|null + */ + private $x; + + /** + * @var int|float|null + */ + private $y; + /** * @param int|float $width * @param int|float $height + * @param int|float|null $x + * @param int|float|null $y */ - public function __construct($width, $height) + public function __construct($width, $height, $x = null, $y = null) { $this->width = $width; $this->height = $height; + $this->x = $x; + $this->y = $y; } /** @@ -56,4 +70,20 @@ public function equals(self $dimension) { return $this->height === $dimension->getHeight() && $this->width === $dimension->getWidth(); } + + /** + * @return float|int|null + */ + public function getScreenX() + { + return $this->x; + } + + /** + * @return float|int|null + */ + public function getScreenY() + { + return $this->y; + } } diff --git a/lib/WebDriverWindow.php b/lib/WebDriverWindow.php index e212f92ed..4fa0427ff 100644 --- a/lib/WebDriverWindow.php +++ b/lib/WebDriverWindow.php @@ -59,16 +59,25 @@ public function getSize() [':windowHandle' => 'current'] ); + if (!$this->isW3cCompliant) { + $dimension = $this->getPosition(); + $dimensionArray = ['x' => $dimension->getX(), 'y' => $dimension->getY()]; + } else { + $dimensionArray = ['x' => $size['x'], 'y' => $size['y']]; + } + return new WebDriverDimension( $size['width'], - $size['height'] + $size['height'], + $dimensionArray['x'], + $dimensionArray['y'] ); } /** * Minimizes the current window if it is not already minimized. * - * @return WebDriverWindow The instance. + * @return WebDriverDimension */ public function minimize() { @@ -76,34 +85,44 @@ public function minimize() throw new UnsupportedOperationException('Minimize window is only supported in W3C mode'); } - $this->executor->execute(DriverCommand::MINIMIZE_WINDOW, []); + $size = $this->executor->execute(DriverCommand::MINIMIZE_WINDOW, []); - return $this; + return new WebDriverDimension( + $size['width'], + $size['height'], + $size['x'], + $size['y'] + ); } /** * Maximizes the current window if it is not already maximized * - * @return WebDriverWindow The instance. + * @return WebDriverDimension */ public function maximize() { if ($this->isW3cCompliant) { - $this->executor->execute(DriverCommand::MAXIMIZE_WINDOW, []); + $size = $this->executor->execute(DriverCommand::MAXIMIZE_WINDOW, []); } else { - $this->executor->execute( + $size = $this->executor->execute( DriverCommand::MAXIMIZE_WINDOW, [':windowHandle' => 'current'] ); } - return $this; + return new WebDriverDimension( + $size['width'], + $size['height'], + $size['x'], + $size['y'] + ); } /** * Makes the current window full screen. * - * @return WebDriverWindow The instance. + * @return WebDriverDimension */ public function fullscreen() { @@ -111,9 +130,14 @@ public function fullscreen() throw new UnsupportedOperationException('The Fullscreen window command is only supported in W3C mode'); } - $this->executor->execute(DriverCommand::FULLSCREEN_WINDOW, []); + $size = $this->executor->execute(DriverCommand::FULLSCREEN_WINDOW, []); - return $this; + return new WebDriverDimension( + $size['width'], + $size['height'], + $size['x'], + $size['y'] + ); } /** @@ -121,7 +145,8 @@ public function fullscreen() * dimension, not just the view port. * * @param WebDriverDimension $size - * @return WebDriverWindow The instance. + * + * @return WebDriverDimension */ public function setSize(WebDriverDimension $size) { @@ -130,9 +155,19 @@ public function setSize(WebDriverDimension $size) 'height' => $size->getHeight(), ':windowHandle' => 'current', ]; - $this->executor->execute(DriverCommand::SET_WINDOW_SIZE, $params); - return $this; + $size = $this->executor->execute(DriverCommand::SET_WINDOW_SIZE, $params); + + if (!$this->isW3cCompliant) { + return $this->getSize(); + } + + return new WebDriverDimension( + $size['width'], + $size['height'], + $size['x'], + $size['y'] + ); } /** @@ -140,7 +175,8 @@ public function setSize(WebDriverDimension $size) * corner of the screen. * * @param WebDriverPoint $position - * @return WebDriverWindow The instance. + * + * @return WebDriverDimension */ public function setPosition(WebDriverPoint $position) { @@ -149,9 +185,19 @@ public function setPosition(WebDriverPoint $position) 'y' => $position->getY(), ':windowHandle' => 'current', ]; - $this->executor->execute(DriverCommand::SET_WINDOW_POSITION, $params); - return $this; + $size = $this->executor->execute(DriverCommand::SET_WINDOW_POSITION, $params); + + if (!$this->isW3cCompliant) { + return $this->getSize(); + } + + return new WebDriverDimension( + $size['width'], + $size['height'], + $size['x'], + $size['y'] + ); } /** From 469613ff93433921b1979c3232ab61222f809ed7 Mon Sep 17 00:00:00 2001 From: Oleg Andreyev Date: Sat, 20 Mar 2021 23:44:35 +0200 Subject: [PATCH 2/4] added unit test for WebDriverWindow --- lib/WebDriverWindow.php | 12 ++ tests/unit/WebDriverWindowTest.php | 302 +++++++++++++++++++++++++++++ 2 files changed, 314 insertions(+) create mode 100644 tests/unit/WebDriverWindowTest.php diff --git a/lib/WebDriverWindow.php b/lib/WebDriverWindow.php index 4fa0427ff..d97debfb4 100644 --- a/lib/WebDriverWindow.php +++ b/lib/WebDriverWindow.php @@ -207,6 +207,12 @@ public function setPosition(WebDriverPoint $position) */ public function getScreenOrientation() { + if ($this->isW3cCompliant) { + throw new UnsupportedOperationException( + 'The Screen Orientation window command is only supported in OSS mode' + ); + } + return $this->executor->execute(DriverCommand::GET_SCREEN_ORIENTATION); } @@ -220,6 +226,12 @@ public function getScreenOrientation() */ public function setScreenOrientation($orientation) { + if ($this->isW3cCompliant) { + throw new UnsupportedOperationException( + 'The Screen Orientation window command is only supported in OSS mode' + ); + } + $orientation = mb_strtoupper($orientation); if (!in_array($orientation, ['PORTRAIT', 'LANDSCAPE'])) { throw new IndexOutOfBoundsException( diff --git a/tests/unit/WebDriverWindowTest.php b/tests/unit/WebDriverWindowTest.php new file mode 100644 index 000000000..ce3345767 --- /dev/null +++ b/tests/unit/WebDriverWindowTest.php @@ -0,0 +1,302 @@ +executor = $this->createMock(ExecuteMethod::class); + } + + public function testGetPosition() + { + $this->executor->method('execute') + ->with(DriverCommand::GET_WINDOW_POSITION, [':windowHandle' => 'current']) + ->willReturn(['x' => 0, 'y' => 0]); + + $target = new WebDriverWindow($this->executor); + $result = $target->getPosition(); + + $this->assertInstanceOf(WebDriverPoint::class, $result); + $this->assertEquals(0, $result->getX()); + $this->assertEquals(0, $result->getY()); + } + + public function w3cCompliantDataProvider() + { + yield [true]; + yield [false]; + } + + /** + * @dataProvider w3cCompliantDataProvider + * @param bool $w3cCompliant + */ + public function testGetSize($w3cCompliant) + { + if ($w3cCompliant) { + $result = ['width' => 100, 'height' => 100, 'x' => 0, 'y' => 0]; + + $this->executor->method('execute') + ->with(DriverCommand::GET_WINDOW_SIZE, [':windowHandle' => 'current']) + ->willReturn($result); + } else { + $result = ['width' => 100, 'height' => 100]; + + $this->executor->method('execute') + ->withConsecutive( + [DriverCommand::GET_WINDOW_SIZE, [':windowHandle' => 'current']], + [DriverCommand::GET_WINDOW_POSITION, [':windowHandle' => 'current']] + ) + ->willReturnOnConsecutiveCalls( + $result, + ['x' => 0, 'y' => 0] + ); + } + + $target = new WebDriverWindow($this->executor, $w3cCompliant); + + $result = $target->getSize(); + + $this->assertInstanceOf(WebDriverDimension::class, $result); + $this->assertEquals(100, $result->getWidth()); + $this->assertEquals(100, $result->getHeight()); + $this->assertEquals(0, $result->getScreenX()); + $this->assertEquals(0, $result->getScreenY()); + } + + /** + * @dataProvider w3cCompliantDataProvider + * @param bool $w3cCompliant + */ + public function testMinimize($w3cCompliant) + { + if ($w3cCompliant) { + $result = ['width' => 100, 'height' => 100, 'x' => 0, 'y' => 0]; + + $this->executor->method('execute') + ->with(DriverCommand::MINIMIZE_WINDOW, []) + ->willReturn($result); + } else { + $this->expectException(UnsupportedOperationException::class); + $this->expectExceptionMessage('Minimize window is only supported in W3C mode'); + } + + $target = new WebDriverWindow($this->executor, $w3cCompliant); + $result = $target->minimize(); + + $this->assertInstanceOf(WebDriverDimension::class, $result); + $this->assertEquals(100, $result->getWidth()); + $this->assertEquals(100, $result->getHeight()); + $this->assertEquals(0, $result->getScreenX()); + $this->assertEquals(0, $result->getScreenY()); + } + + /** + * @dataProvider w3cCompliantDataProvider + * @param bool $w3cCompliant + */ + public function testMaximize($w3cCompliant) + { + $result = ['width' => 100, 'height' => 100, 'x' => 0, 'y' => 0]; + + if ($w3cCompliant) { + $this->executor->method('execute') + ->with(DriverCommand::MAXIMIZE_WINDOW, []) + ->willReturn($result); + } else { + $this->executor->method('execute') + ->with(DriverCommand::MAXIMIZE_WINDOW, [':windowHandle' => 'current']) + ->willReturn($result); + } + + $target = new WebDriverWindow($this->executor, $w3cCompliant); + $result = $target->maximize(); + + $this->assertInstanceOf(WebDriverDimension::class, $result); + $this->assertEquals(100, $result->getWidth()); + $this->assertEquals(100, $result->getHeight()); + $this->assertEquals(0, $result->getScreenX()); + $this->assertEquals(0, $result->getScreenY()); + } + + /** + * @dataProvider w3cCompliantDataProvider + * @param bool $w3cCompliant + */ + public function testFullscreen($w3cCompliant) + { + if ($w3cCompliant) { + $result = ['width' => 100, 'height' => 100, 'x' => 0, 'y' => 0]; + + $this->executor->method('execute') + ->with(DriverCommand::FULLSCREEN_WINDOW, []) + ->willReturn($result); + } else { + $this->expectException(UnsupportedOperationException::class); + $this->expectExceptionMessage('The Fullscreen window command is only supported in W3C mode'); + } + + $target = new WebDriverWindow($this->executor, $w3cCompliant); + $result = $target->fullscreen(); + + $this->assertInstanceOf(WebDriverDimension::class, $result); + $this->assertEquals(100, $result->getWidth()); + $this->assertEquals(100, $result->getHeight()); + $this->assertEquals(0, $result->getScreenX()); + $this->assertEquals(0, $result->getScreenY()); + } + + /** + * @dataProvider w3cCompliantDataProvider + * @param bool $w3cCompliant + */ + public function testSetSize($w3cCompliant) + { + $dimension = new WebDriverDimension( + 100, + 100, + 0, + 0 + ); + + if ($w3cCompliant) { + $this->executor->method('execute') + ->with(DriverCommand::SET_WINDOW_SIZE, ['width' => 100, 'height' => 100, ':windowHandle' => 'current']) + ->willReturn(['width' => 100, 'height' => 100, 'x' => 0, 'y' => 0]); + } else { + $this->executor->method('execute') + ->withConsecutive( + [DriverCommand::SET_WINDOW_SIZE, ['width' => 100, 'height' => 100, ':windowHandle' => 'current']], + [DriverCommand::GET_WINDOW_SIZE, [':windowHandle' => 'current']], + [DriverCommand::GET_WINDOW_POSITION, [':windowHandle' => 'current']] + ) + ->willReturnOnConsecutiveCalls( + null, + ['width' => 100, 'height' => 100], + ['x' => 0, 'y' => 0] + ); + } + + $target = new WebDriverWindow($this->executor, $w3cCompliant); + $result = $target->setSize($dimension); + + $this->assertInstanceOf(WebDriverDimension::class, $result); + $this->assertEquals(100, $result->getWidth()); + $this->assertEquals(100, $result->getHeight()); + $this->assertEquals(0, $result->getScreenX()); + $this->assertEquals(0, $result->getScreenY()); + } + + /** + * @dataProvider w3cCompliantDataProvider + * @param bool $w3cCompliant + */ + public function testSetPosition($w3cCompliant) + { + $point = new WebDriverPoint( + 0, + 0 + ); + + if ($w3cCompliant) { + $this->executor->method('execute') + ->with( + DriverCommand::SET_WINDOW_POSITION, + ['x' => 0, 'y' => 0, ':windowHandle' => 'current'] + ) + ->willReturn(['width' => 100, 'height' => 100, 'x' => 0, 'y' => 0]); + } else { + $this->executor->method('execute') + ->withConsecutive( + [DriverCommand::SET_WINDOW_POSITION, ['x' => 0, 'y' => 0, ':windowHandle' => 'current']], + [DriverCommand::GET_WINDOW_SIZE, [':windowHandle' => 'current']], + [DriverCommand::GET_WINDOW_POSITION, [':windowHandle' => 'current']] + ) + ->willReturnOnConsecutiveCalls( + null, + ['width' => 100, 'height' => 100], + ['x' => 0, 'y' => 0] + ); + } + + $target = new WebDriverWindow($this->executor, $w3cCompliant); + $result = $target->setPosition($point); + + $this->assertInstanceOf(WebDriverDimension::class, $result); + $this->assertEquals(100, $result->getWidth()); + $this->assertEquals(100, $result->getHeight()); + $this->assertEquals(0, $result->getScreenX()); + $this->assertEquals(0, $result->getScreenY()); + } + + /** + * @dataProvider w3cCompliantDataProvider + * @param bool $w3cCompliant + */ + public function testGetScreenOrientation($w3cCompliant) + { + if ($w3cCompliant) { + $this->expectException(UnsupportedOperationException::class); + $this->expectExceptionMessage('The Screen Orientation window command is only supported in OSS mode'); + } else { + $this->executor + ->method('execute') + ->with(DriverCommand::GET_SCREEN_ORIENTATION) + ->willReturn('LANDSCAPE'); + } + + $target = new WebDriverWindow($this->executor, $w3cCompliant); + $result = $target->getScreenOrientation(); + + if (method_exists($this, 'assertIsString')) { + $this->assertIsString($result); + } else { + /** @phpstan-ignore-next-line */ + $this->assertInternalType('string', $result); + } + + $this->assertEquals('LANDSCAPE', $result); + } + + public function w3cCompliantDataProviderOrientation() + { + yield [true, 'LANDSCAPE']; + yield [false, 'LANDSCAPE']; + yield [false, 'FOO']; + } + + /** + * @dataProvider w3cCompliantDataProviderOrientation + * @param bool $w3cCompliant + * @param string $orientation + */ + public function testSetScreenOrientation($w3cCompliant, $orientation) + { + if ($w3cCompliant) { + $this->expectException(UnsupportedOperationException::class); + $this->expectExceptionMessage('The Screen Orientation window command is only supported in OSS mode'); + } elseif ($orientation === 'FOO') { + $this->expectException(IndexOutOfBoundsException::class); + $this->expectExceptionMessage('Orientation must be either PORTRAIT, or LANDSCAPE'); + } else { + $this->executor + ->method('execute') + ->with(DriverCommand::SET_SCREEN_ORIENTATION, ['orientation' => $orientation]); + } + + $target = new WebDriverWindow($this->executor, $w3cCompliant); + $target->setScreenOrientation($orientation); + + $this->assertTrue(true); + } +} From c0cb4521c613471cb964300f90d98fd54547b30b Mon Sep 17 00:00:00 2001 From: Oleg Andreyev Date: Sun, 21 Mar 2021 00:13:32 +0200 Subject: [PATCH 3/4] minimal phpunit 5.7.15 (generators are fixed) --- composer.json | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/composer.json b/composer.json index 8453c8169..028f547be 100644 --- a/composer.json +++ b/composer.json @@ -28,7 +28,7 @@ "php-coveralls/php-coveralls": "^2.4", "php-mock/php-mock-phpunit": "^1.1 || ^2.0", "php-parallel-lint/php-parallel-lint": "^1.2", - "phpunit/phpunit": "^5.7 || ^7 || ^8 || ^9", + "phpunit/phpunit": "^5.7,>=5.7.15 || ^7 || ^8 || ^9", "squizlabs/php_codesniffer": "^3.5", "symfony/var-dumper": "^3.3 || ^4.0 || ^5.0" }, From f37e591fe257fca66be929c3fe4758f84bb3153c Mon Sep 17 00:00:00 2001 From: Oleg Andreyev Date: Sat, 20 Mar 2021 23:51:33 +0200 Subject: [PATCH 4/4] apply-phpunit-patches.sh added debug --- scripts/apply-phpunit-patches.sh | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/scripts/apply-phpunit-patches.sh b/scripts/apply-phpunit-patches.sh index 478e01c74..609cf7b95 100755 --- a/scripts/apply-phpunit-patches.sh +++ b/scripts/apply-phpunit-patches.sh @@ -1,7 +1,7 @@ #!/bin/sh # All commands below must no fail -set -e +set -ex # Be in the root dir cd "$(dirname $0)/../"