| 
									
										
										
										
											2020-08-03 15:23:53 -07:00
										 |  |  | /** | 
					
						
							|  |  |  |  * Copyright 2018 Google Inc. All rights reserved. | 
					
						
							|  |  |  |  * Modifications copyright (c) Microsoft Corporation. | 
					
						
							|  |  |  |  * | 
					
						
							|  |  |  |  * Licensed under the Apache License, Version 2.0 (the "License"); | 
					
						
							|  |  |  |  * you may not use this file except in compliance with the License. | 
					
						
							|  |  |  |  * You may obtain a copy of the License at | 
					
						
							|  |  |  |  * | 
					
						
							|  |  |  |  *     http://www.apache.org/licenses/LICENSE-2.0
 | 
					
						
							|  |  |  |  * | 
					
						
							|  |  |  |  * Unless required by applicable law or agreed to in writing, software | 
					
						
							|  |  |  |  * distributed under the License is distributed on an "AS IS" BASIS, | 
					
						
							|  |  |  |  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. | 
					
						
							|  |  |  |  * See the License for the specific language governing permissions and | 
					
						
							|  |  |  |  * limitations under the License. | 
					
						
							|  |  |  |  */ | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2021-05-06 07:08:22 -07:00
										 |  |  | import { test as it, expect } from './pageTest'; | 
					
						
							| 
									
										
										
										
											2020-08-03 15:23:53 -07:00
										 |  |  | 
 | 
					
						
							|  |  |  | it('should have a nice preview', async ({ page, server }) => { | 
					
						
							|  |  |  |   await page.goto(`${server.PREFIX}/dom.html`); | 
					
						
							|  |  |  |   const outer = await page.$('#outer'); | 
					
						
							|  |  |  |   const inner = await page.$('#inner'); | 
					
						
							|  |  |  |   const check = await page.$('#check'); | 
					
						
							|  |  |  |   const text = await inner.evaluateHandle(e => e.firstChild); | 
					
						
							|  |  |  |   await page.evaluate(() => 1);  // Give them a chance to calculate the preview.
 | 
					
						
							|  |  |  |   expect(String(outer)).toBe('JSHandle@<div id="outer" name="value">…</div>'); | 
					
						
							|  |  |  |   expect(String(inner)).toBe('JSHandle@<div id="inner">Text,↵more text</div>'); | 
					
						
							|  |  |  |   expect(String(text)).toBe('JSHandle@#text=Text,↵more text'); | 
					
						
							|  |  |  |   expect(String(check)).toBe('JSHandle@<input checked id="check" foo="bar"" type="checkbox"/>'); | 
					
						
							|  |  |  | }); | 
					
						
							| 
									
										
										
										
											2020-08-05 11:43:40 -07:00
										 |  |  | 
 | 
					
						
							| 
									
										
										
										
											2020-08-03 15:23:53 -07:00
										 |  |  | it('getAttribute should work', async ({ page, server }) => { | 
					
						
							|  |  |  |   await page.goto(`${server.PREFIX}/dom.html`); | 
					
						
							|  |  |  |   const handle = await page.$('#outer'); | 
					
						
							|  |  |  |   expect(await handle.getAttribute('name')).toBe('value'); | 
					
						
							|  |  |  |   expect(await handle.getAttribute('foo')).toBe(null); | 
					
						
							|  |  |  |   expect(await page.getAttribute('#outer', 'name')).toBe('value'); | 
					
						
							|  |  |  |   expect(await page.getAttribute('#outer', 'foo')).toBe(null); | 
					
						
							|  |  |  | }); | 
					
						
							| 
									
										
										
										
											2020-08-05 11:43:40 -07:00
										 |  |  | 
 | 
					
						
							| 
									
										
										
										
											2021-06-23 22:19:20 -07:00
										 |  |  | it('inputValue should work', async ({ page, server }) => { | 
					
						
							|  |  |  |   await page.goto(`${server.PREFIX}/dom.html`); | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2021-08-03 10:22:40 -05:00
										 |  |  |   await page.selectOption('#select', 'foo'); | 
					
						
							|  |  |  |   expect(await page.inputValue('#select')).toBe('foo'); | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2021-06-23 22:19:20 -07:00
										 |  |  |   await page.fill('#textarea', 'text value'); | 
					
						
							|  |  |  |   expect(await page.inputValue('#textarea')).toBe('text value'); | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  |   await page.fill('#input', 'input value'); | 
					
						
							|  |  |  |   expect(await page.inputValue('#input')).toBe('input value'); | 
					
						
							|  |  |  |   const handle = await page.$('#input'); | 
					
						
							|  |  |  |   expect(await handle.inputValue()).toBe('input value'); | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2021-09-24 20:51:09 -07:00
										 |  |  |   expect(await page.inputValue('#inner').catch(e => e.message)).toContain('Node is not an <input>, <textarea> or <select> element'); | 
					
						
							| 
									
										
										
										
											2021-06-23 22:19:20 -07:00
										 |  |  |   const handle2 = await page.$('#inner'); | 
					
						
							| 
									
										
										
										
											2021-09-24 20:51:09 -07:00
										 |  |  |   expect(await handle2.inputValue().catch(e => e.message)).toContain('Node is not an <input>, <textarea> or <select> element'); | 
					
						
							| 
									
										
										
										
											2021-06-23 22:19:20 -07:00
										 |  |  | }); | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2020-08-03 15:23:53 -07:00
										 |  |  | it('innerHTML should work', async ({ page, server }) => { | 
					
						
							|  |  |  |   await page.goto(`${server.PREFIX}/dom.html`); | 
					
						
							|  |  |  |   const handle = await page.$('#outer'); | 
					
						
							|  |  |  |   expect(await handle.innerHTML()).toBe('<div id="inner">Text,\nmore text</div>'); | 
					
						
							|  |  |  |   expect(await page.innerHTML('#outer')).toBe('<div id="inner">Text,\nmore text</div>'); | 
					
						
							|  |  |  | }); | 
					
						
							| 
									
										
										
										
											2020-08-05 11:43:40 -07:00
										 |  |  | 
 | 
					
						
							| 
									
										
										
										
											2020-08-03 15:23:53 -07:00
										 |  |  | it('innerText should work', async ({ page, server }) => { | 
					
						
							|  |  |  |   await page.goto(`${server.PREFIX}/dom.html`); | 
					
						
							|  |  |  |   const handle = await page.$('#inner'); | 
					
						
							|  |  |  |   expect(await handle.innerText()).toBe('Text, more text'); | 
					
						
							|  |  |  |   expect(await page.innerText('#inner')).toBe('Text, more text'); | 
					
						
							|  |  |  | }); | 
					
						
							| 
									
										
										
										
											2020-08-05 11:43:40 -07:00
										 |  |  | 
 | 
					
						
							| 
									
										
										
										
											2020-08-03 15:23:53 -07:00
										 |  |  | it('innerText should throw', async ({ page, server }) => { | 
					
						
							|  |  |  |   await page.setContent(`<svg>text</svg>`); | 
					
						
							|  |  |  |   const error1 = await page.innerText('svg').catch(e => e); | 
					
						
							| 
									
										
										
										
											2021-09-24 20:51:09 -07:00
										 |  |  |   expect(error1.message).toContain('Node is not an HTMLElement'); | 
					
						
							| 
									
										
										
										
											2020-08-03 15:23:53 -07:00
										 |  |  |   const handle = await page.$('svg'); | 
					
						
							|  |  |  |   const error2 = await handle.innerText().catch(e => e); | 
					
						
							| 
									
										
										
										
											2021-09-24 20:51:09 -07:00
										 |  |  |   expect(error2.message).toContain('Node is not an HTMLElement'); | 
					
						
							| 
									
										
										
										
											2020-08-03 15:23:53 -07:00
										 |  |  | }); | 
					
						
							| 
									
										
										
										
											2020-08-05 11:43:40 -07:00
										 |  |  | 
 | 
					
						
							| 
									
										
										
										
											2020-08-03 15:23:53 -07:00
										 |  |  | it('textContent should work', async ({ page, server }) => { | 
					
						
							|  |  |  |   await page.goto(`${server.PREFIX}/dom.html`); | 
					
						
							|  |  |  |   const handle = await page.$('#inner'); | 
					
						
							|  |  |  |   expect(await handle.textContent()).toBe('Text,\nmore text'); | 
					
						
							|  |  |  |   expect(await page.textContent('#inner')).toBe('Text,\nmore text'); | 
					
						
							|  |  |  | }); | 
					
						
							| 
									
										
										
										
											2020-08-05 11:43:40 -07:00
										 |  |  | 
 | 
					
						
							| 
									
										
										
										
											2021-01-08 12:27:54 -08:00
										 |  |  | it('isVisible and isHidden should work', async ({ page }) => { | 
					
						
							|  |  |  |   await page.setContent(`<div>Hi</div><span></span>`); | 
					
						
							| 
									
										
										
										
											2021-02-10 07:12:43 -08:00
										 |  |  | 
 | 
					
						
							| 
									
										
										
										
											2021-01-08 12:27:54 -08:00
										 |  |  |   const div = await page.$('div'); | 
					
						
							|  |  |  |   expect(await div.isVisible()).toBe(true); | 
					
						
							|  |  |  |   expect(await div.isHidden()).toBe(false); | 
					
						
							|  |  |  |   expect(await page.isVisible('div')).toBe(true); | 
					
						
							|  |  |  |   expect(await page.isHidden('div')).toBe(false); | 
					
						
							| 
									
										
										
										
											2021-02-10 07:12:43 -08:00
										 |  |  | 
 | 
					
						
							| 
									
										
										
										
											2021-01-08 12:27:54 -08:00
										 |  |  |   const span = await page.$('span'); | 
					
						
							|  |  |  |   expect(await span.isVisible()).toBe(false); | 
					
						
							|  |  |  |   expect(await span.isHidden()).toBe(true); | 
					
						
							|  |  |  |   expect(await page.isVisible('span')).toBe(false); | 
					
						
							|  |  |  |   expect(await page.isHidden('span')).toBe(true); | 
					
						
							| 
									
										
										
										
											2021-02-10 07:12:43 -08:00
										 |  |  | 
 | 
					
						
							|  |  |  |   expect(await page.isVisible('no-such-element')).toBe(false); | 
					
						
							|  |  |  |   expect(await page.isHidden('no-such-element')).toBe(true); | 
					
						
							| 
									
										
										
										
											2021-01-08 12:27:54 -08:00
										 |  |  | }); | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2021-09-27 18:58:08 +02:00
										 |  |  | it('isVisible should not throw when the DOM element is not connected', async ({ page }) => { | 
					
						
							| 
									
										
										
										
											2021-08-05 21:10:33 +02:00
										 |  |  |   await page.setContent(`<div id="root"></div>`); | 
					
						
							|  |  |  |   await page.evaluate(() => { | 
					
						
							|  |  |  |     function insert() { | 
					
						
							|  |  |  |       document.getElementById('root').innerHTML = '<div id="problem">Problem</div>'; | 
					
						
							|  |  |  |       window.requestAnimationFrame(remove); | 
					
						
							|  |  |  |     } | 
					
						
							|  |  |  |     function remove() { | 
					
						
							|  |  |  |       const node = document.getElementById('problem'); | 
					
						
							|  |  |  |       node?.parentNode?.removeChild(node); | 
					
						
							|  |  |  |       window.requestAnimationFrame(insert); | 
					
						
							|  |  |  |     } | 
					
						
							|  |  |  |     window.requestAnimationFrame(insert); | 
					
						
							|  |  |  |   }); | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  |   for (let i = 0; i < 10; i++) | 
					
						
							|  |  |  |     await page.isVisible('#problem'); | 
					
						
							|  |  |  | }); | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2021-01-08 12:27:54 -08:00
										 |  |  | it('isEnabled and isDisabled should work', async ({ page }) => { | 
					
						
							|  |  |  |   await page.setContent(`
 | 
					
						
							|  |  |  |     <button disabled>button1</button> | 
					
						
							|  |  |  |     <button>button2</button> | 
					
						
							|  |  |  |     <div>div</div> | 
					
						
							|  |  |  |   `);
 | 
					
						
							|  |  |  |   const div = await page.$('div'); | 
					
						
							|  |  |  |   expect(await div.isEnabled()).toBe(true); | 
					
						
							|  |  |  |   expect(await div.isDisabled()).toBe(false); | 
					
						
							|  |  |  |   expect(await page.isEnabled('div')).toBe(true); | 
					
						
							|  |  |  |   expect(await page.isDisabled('div')).toBe(false); | 
					
						
							|  |  |  |   const button1 = await page.$(':text("button1")'); | 
					
						
							|  |  |  |   expect(await button1.isEnabled()).toBe(false); | 
					
						
							|  |  |  |   expect(await button1.isDisabled()).toBe(true); | 
					
						
							|  |  |  |   expect(await page.isEnabled(':text("button1")')).toBe(false); | 
					
						
							|  |  |  |   expect(await page.isDisabled(':text("button1")')).toBe(true); | 
					
						
							|  |  |  |   const button2 = await page.$(':text("button2")'); | 
					
						
							|  |  |  |   expect(await button2.isEnabled()).toBe(true); | 
					
						
							|  |  |  |   expect(await button2.isDisabled()).toBe(false); | 
					
						
							|  |  |  |   expect(await page.isEnabled(':text("button2")')).toBe(true); | 
					
						
							|  |  |  |   expect(await page.isDisabled(':text("button2")')).toBe(false); | 
					
						
							|  |  |  | }); | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2022-03-01 18:10:16 +01:00
										 |  |  | it('isEnabled and isDisabled should work with <select/> option/optgroup correctly', async ({ page }) => { | 
					
						
							|  |  |  |   await page.setContent(`
 | 
					
						
							|  |  |  |     <select name="select"> | 
					
						
							|  |  |  |       <option id="enabled1" value="1">Enabled</option> | 
					
						
							|  |  |  |       <option id="disabled1" value="2" disabled>Disabled</option> | 
					
						
							|  |  |  |       <optgroup label="Foo1"> | 
					
						
							|  |  |  |         <option value="mercedes">Mercedes</option> | 
					
						
							|  |  |  |       </optgroup> | 
					
						
							|  |  |  |       <optgroup label="Foo2" disabled> | 
					
						
							|  |  |  |         <option value="mercedes">Mercedes</option> | 
					
						
							|  |  |  |       </optgroup> | 
					
						
							|  |  |  |     </select> | 
					
						
							|  |  |  |   `);
 | 
					
						
							|  |  |  |   expect((await (await page.$('#enabled1')).isEnabled())).toBe(true); | 
					
						
							|  |  |  |   expect((await (await page.$('#enabled1')).isDisabled())).toBe(false); | 
					
						
							|  |  |  |   expect((await (await page.$('#disabled1')).isEnabled())).toBe(false); | 
					
						
							|  |  |  |   expect((await (await page.$('#disabled1')).isDisabled())).toBe(true); | 
					
						
							|  |  |  |   expect((await (await page.$('optgroup >> nth=0')).isEnabled())).toBe(true); | 
					
						
							|  |  |  |   expect((await (await page.$('optgroup >> nth=0')).isDisabled())).toBe(false); | 
					
						
							|  |  |  |   expect((await (await page.$('optgroup >> nth=1')).isEnabled())).toBe(false); | 
					
						
							|  |  |  |   expect((await (await page.$('optgroup >> nth=1')).isDisabled())).toBe(true); | 
					
						
							|  |  |  | }); | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2021-01-08 12:27:54 -08:00
										 |  |  | it('isEditable should work', async ({ page }) => { | 
					
						
							|  |  |  |   await page.setContent(`<input id=input1 disabled><textarea></textarea><input id=input2>`); | 
					
						
							|  |  |  |   await page.$eval('textarea', t => t.readOnly = true); | 
					
						
							|  |  |  |   const input1 = await page.$('#input1'); | 
					
						
							|  |  |  |   expect(await input1.isEditable()).toBe(false); | 
					
						
							|  |  |  |   expect(await page.isEditable('#input1')).toBe(false); | 
					
						
							|  |  |  |   const input2 = await page.$('#input2'); | 
					
						
							|  |  |  |   expect(await input2.isEditable()).toBe(true); | 
					
						
							|  |  |  |   expect(await page.isEditable('#input2')).toBe(true); | 
					
						
							|  |  |  |   const textarea = await page.$('textarea'); | 
					
						
							|  |  |  |   expect(await textarea.isEditable()).toBe(false); | 
					
						
							|  |  |  |   expect(await page.isEditable('textarea')).toBe(false); | 
					
						
							|  |  |  | }); | 
					
						
							| 
									
										
										
										
											2021-01-08 17:36:17 -08:00
										 |  |  | 
 | 
					
						
							| 
									
										
										
										
											2021-09-27 18:58:08 +02:00
										 |  |  | it('isChecked should work', async ({ page }) => { | 
					
						
							| 
									
										
										
										
											2021-01-08 17:36:17 -08:00
										 |  |  |   await page.setContent(`<input type='checkbox' checked><div>Not a checkbox</div>`); | 
					
						
							|  |  |  |   const handle = await page.$('input'); | 
					
						
							|  |  |  |   expect(await handle.isChecked()).toBe(true); | 
					
						
							|  |  |  |   expect(await page.isChecked('input')).toBe(true); | 
					
						
							|  |  |  |   await handle.evaluate(input => input.checked = false); | 
					
						
							|  |  |  |   expect(await handle.isChecked()).toBe(false); | 
					
						
							|  |  |  |   expect(await page.isChecked('input')).toBe(false); | 
					
						
							|  |  |  |   const error = await page.isChecked('div').catch(e => e); | 
					
						
							|  |  |  |   expect(error.message).toContain('Not a checkbox or radio button'); | 
					
						
							|  |  |  | }); |