Mercurial > hg > isophonics-drupal-site
comparison core/tests/Drupal/FunctionalJavascriptTests/WebDriverTestBase.php @ 17:129ea1e6d783
Update, including to Drupal core 8.6.10
author | Chris Cannam |
---|---|
date | Thu, 28 Feb 2019 13:21:36 +0000 |
parents | |
children | af1871eacc83 |
comparison
equal
deleted
inserted
replaced
16:c2387f117808 | 17:129ea1e6d783 |
---|---|
1 <?php | |
2 | |
3 namespace Drupal\FunctionalJavascriptTests; | |
4 | |
5 use Behat\Mink\Exception\DriverException; | |
6 use Drupal\Tests\BrowserTestBase; | |
7 use Zumba\GastonJS\Exception\DeadClient; | |
8 use Zumba\Mink\Driver\PhantomJSDriver; | |
9 | |
10 /** | |
11 * Runs a browser test using a driver that supports Javascript. | |
12 * | |
13 * Base class for testing browser interaction implemented in JavaScript. | |
14 */ | |
15 abstract class WebDriverTestBase extends BrowserTestBase { | |
16 | |
17 /** | |
18 * {@inheritdoc} | |
19 * | |
20 * To use a legacy phantomjs based approach, please use PhantomJSDriver::class. | |
21 */ | |
22 protected $minkDefaultDriverClass = DrupalSelenium2Driver::class; | |
23 | |
24 /** | |
25 * {@inheritdoc} | |
26 */ | |
27 protected function initMink() { | |
28 if ($this->minkDefaultDriverClass === DrupalSelenium2Driver::class) { | |
29 $this->minkDefaultDriverArgs = ['chrome', NULL, 'http://localhost:4444']; | |
30 } | |
31 elseif ($this->minkDefaultDriverClass === PhantomJSDriver::class) { | |
32 // Set up the template cache used by the PhantomJS mink driver. | |
33 $path = $this->tempFilesDirectory . DIRECTORY_SEPARATOR . 'browsertestbase-templatecache'; | |
34 $this->minkDefaultDriverArgs = [ | |
35 'http://127.0.0.1:8510', | |
36 $path, | |
37 ]; | |
38 if (!file_exists($path)) { | |
39 mkdir($path); | |
40 } | |
41 } | |
42 | |
43 try { | |
44 return parent::initMink(); | |
45 } | |
46 catch (DeadClient $e) { | |
47 $this->markTestSkipped('PhantomJS is either not installed or not running. Start it via phantomjs --ssl-protocol=any --ignore-ssl-errors=true vendor/jcalderonzumba/gastonjs/src/Client/main.js 8510 1024 768&'); | |
48 } | |
49 catch (DriverException $e) { | |
50 if ($this->minkDefaultDriverClass === DrupalSelenium2Driver::class) { | |
51 $this->markTestSkipped("The test wasn't able to connect to your webdriver instance. For more information read core/tests/README.md.\n\nThe original message while starting Mink: {$e->getMessage()}"); | |
52 } | |
53 else { | |
54 throw $e; | |
55 } | |
56 } | |
57 catch (\Exception $e) { | |
58 $this->markTestSkipped('An unexpected error occurred while starting Mink: ' . $e->getMessage()); | |
59 } | |
60 } | |
61 | |
62 /** | |
63 * {@inheritdoc} | |
64 */ | |
65 protected function tearDown() { | |
66 if ($this->mink) { | |
67 // Wait for all requests to finish. It is possible that an AJAX request is | |
68 // still on-going. | |
69 $result = $this->getSession()->wait(5000, '(typeof(jQuery)=="undefined" || (0 === jQuery.active && 0 === jQuery(\':animated\').length))'); | |
70 if (!$result) { | |
71 // If the wait is unsuccessful, there may still be an AJAX request in | |
72 // progress. If we tear down now, then this AJAX request may fail with | |
73 // missing database tables, because tear down will have removed them. | |
74 // Rather than allow it to fail, throw an explicit exception now | |
75 // explaining what the problem is. | |
76 throw new \RuntimeException('Unfinished AJAX requests while tearing down a test'); | |
77 } | |
78 } | |
79 parent::tearDown(); | |
80 } | |
81 | |
82 /** | |
83 * {@inheritdoc} | |
84 */ | |
85 protected function getMinkDriverArgs() { | |
86 if ($this->minkDefaultDriverClass === DrupalSelenium2Driver::class) { | |
87 return getenv('MINK_DRIVER_ARGS_WEBDRIVER') ?: getenv('MINK_DRIVER_ARGS_PHANTOMJS') ?: parent::getMinkDriverArgs(); | |
88 } | |
89 elseif ($this->minkDefaultDriverClass === PhantomJSDriver::class) { | |
90 return getenv('MINK_DRIVER_ARGS_PHANTOMJS') ?: parent::getMinkDriverArgs(); | |
91 } | |
92 return parent::getMinkDriverArgs(); | |
93 } | |
94 | |
95 /** | |
96 * Asserts that the element with the given CSS selector is visible. | |
97 * | |
98 * @param string $css_selector | |
99 * The CSS selector identifying the element to check. | |
100 * @param string $message | |
101 * Optional message to show alongside the assertion. | |
102 * | |
103 * @deprecated in Drupal 8.1.0, will be removed before Drupal 9.0.0. Use | |
104 * \Behat\Mink\Element\NodeElement::isVisible() instead. | |
105 */ | |
106 protected function assertElementVisible($css_selector, $message = '') { | |
107 $this->assertTrue($this->getSession()->getDriver()->isVisible($this->cssSelectToXpath($css_selector)), $message); | |
108 @trigger_error('The ' . __METHOD__ . ' method is deprecated since version 8.1.0 and will be removed in 9.0.0. Use \Behat\Mink\Element\NodeElement::isVisible() instead.', E_USER_DEPRECATED); | |
109 } | |
110 | |
111 /** | |
112 * Asserts that the element with the given CSS selector is not visible. | |
113 * | |
114 * @param string $css_selector | |
115 * The CSS selector identifying the element to check. | |
116 * @param string $message | |
117 * Optional message to show alongside the assertion. | |
118 * | |
119 * @deprecated in Drupal 8.1.0, will be removed before Drupal 9.0.0. Use | |
120 * \Behat\Mink\Element\NodeElement::isVisible() instead. | |
121 */ | |
122 protected function assertElementNotVisible($css_selector, $message = '') { | |
123 $this->assertFalse($this->getSession()->getDriver()->isVisible($this->cssSelectToXpath($css_selector)), $message); | |
124 @trigger_error('The ' . __METHOD__ . ' method is deprecated since version 8.1.0 and will be removed in 9.0.0. Use \Behat\Mink\Element\NodeElement::isVisible() instead.', E_USER_DEPRECATED); | |
125 } | |
126 | |
127 /** | |
128 * Waits for the given time or until the given JS condition becomes TRUE. | |
129 * | |
130 * @param string $condition | |
131 * JS condition to wait until it becomes TRUE. | |
132 * @param int $timeout | |
133 * (Optional) Timeout in milliseconds, defaults to 10000. | |
134 * @param string $message | |
135 * (optional) A message to display with the assertion. If left blank, a | |
136 * default message will be displayed. | |
137 * | |
138 * @throws \PHPUnit_Framework_AssertionFailedError | |
139 * | |
140 * @see \Behat\Mink\Driver\DriverInterface::evaluateScript() | |
141 */ | |
142 protected function assertJsCondition($condition, $timeout = 10000, $message = '') { | |
143 $message = $message ?: "Javascript condition met:\n" . $condition; | |
144 $result = $this->getSession()->getDriver()->wait($timeout, $condition); | |
145 $this->assertTrue($result, $message); | |
146 } | |
147 | |
148 /** | |
149 * Creates a screenshot. | |
150 * | |
151 * @param string $filename | |
152 * The file name of the resulting screenshot. If using the default phantomjs | |
153 * driver then this should be a JPG filename. | |
154 * @param bool $set_background_color | |
155 * (optional) By default this method will set the background color to white. | |
156 * Set to FALSE to override this behaviour. | |
157 * | |
158 * @throws \Behat\Mink\Exception\UnsupportedDriverActionException | |
159 * When operation not supported by the driver. | |
160 * @throws \Behat\Mink\Exception\DriverException | |
161 * When the operation cannot be done. | |
162 */ | |
163 protected function createScreenshot($filename, $set_background_color = TRUE) { | |
164 $session = $this->getSession(); | |
165 if ($set_background_color) { | |
166 $session->executeScript("document.body.style.backgroundColor = 'white';"); | |
167 } | |
168 $image = $session->getScreenshot(); | |
169 file_put_contents($filename, $image); | |
170 } | |
171 | |
172 /** | |
173 * {@inheritdoc} | |
174 */ | |
175 public function assertSession($name = NULL) { | |
176 return new WebDriverWebAssert($this->getSession($name), $this->baseUrl); | |
177 } | |
178 | |
179 /** | |
180 * Gets the current Drupal javascript settings and parses into an array. | |
181 * | |
182 * Unlike BrowserTestBase::getDrupalSettings(), this implementation reads the | |
183 * current values of drupalSettings, capturing all changes made via javascript | |
184 * after the page was loaded. | |
185 * | |
186 * @return array | |
187 * The Drupal javascript settings array. | |
188 * | |
189 * @see \Drupal\Tests\BrowserTestBase::getDrupalSettings() | |
190 */ | |
191 protected function getDrupalSettings() { | |
192 $script = <<<EndOfScript | |
193 (function () { | |
194 if (typeof drupalSettings !== 'undefined') { | |
195 return drupalSettings; | |
196 } | |
197 })(); | |
198 EndOfScript; | |
199 | |
200 return $this->getSession()->evaluateScript($script) ?: []; | |
201 } | |
202 | |
203 /** | |
204 * {@inheritdoc} | |
205 */ | |
206 protected function getHtmlOutputHeaders() { | |
207 // The webdriver API does not support fetching headers. | |
208 return ''; | |
209 } | |
210 | |
211 } |