chore: deprecate locator.frameLocator() (#32306)
This commit is contained in:
parent
3d9342aa77
commit
4340d153df
|
|
@ -2195,6 +2195,7 @@ A glob pattern, regex pattern or predicate receiving frame's `url` as a [URL] ob
|
||||||
|
|
||||||
## method: Page.frameLocator
|
## method: Page.frameLocator
|
||||||
* since: v1.17
|
* since: v1.17
|
||||||
|
regular [`Locator`] instead.
|
||||||
- returns: <[FrameLocator]>
|
- returns: <[FrameLocator]>
|
||||||
|
|
||||||
When working with iframes, you can create a frame locator that will enter the iframe and allow selecting elements
|
When working with iframes, you can create a frame locator that will enter the iframe and allow selecting elements
|
||||||
|
|
|
||||||
|
|
@ -191,15 +191,9 @@ export class Recorder implements InstrumentationListener {
|
||||||
});
|
});
|
||||||
|
|
||||||
await this._context.exposeBinding('__pw_recorderSetSelector', false, async ({ frame }, selector: string) => {
|
await this._context.exposeBinding('__pw_recorderSetSelector', false, async ({ frame }, selector: string) => {
|
||||||
const selectorPromises: Promise<string | undefined>[] = [];
|
const selectorChain = await generateFrameSelector(frame);
|
||||||
let currentFrame: Frame | null = frame;
|
selectorChain.push(selector);
|
||||||
while (currentFrame) {
|
await this._recorderApp?.setSelector(selectorChain.join(' >> internal:control=enter-frame >> '), true);
|
||||||
selectorPromises.push(findFrameSelector(currentFrame));
|
|
||||||
currentFrame = currentFrame.parentFrame();
|
|
||||||
}
|
|
||||||
const fullSelector = (await Promise.all(selectorPromises)).filter(Boolean);
|
|
||||||
fullSelector.push(selector);
|
|
||||||
await this._recorderApp?.setSelector(fullSelector.join(' >> internal:control=enter-frame >> '), true);
|
|
||||||
});
|
});
|
||||||
|
|
||||||
await this._context.exposeBinding('__pw_recorderSetMode', false, async ({ frame }, mode: Mode) => {
|
await this._context.exposeBinding('__pw_recorderSetMode', false, async ({ frame }, mode: Mode) => {
|
||||||
|
|
@ -539,45 +533,14 @@ class ContextRecorder extends EventEmitter {
|
||||||
private _describeMainFrame(page: Page): actions.FrameDescription {
|
private _describeMainFrame(page: Page): actions.FrameDescription {
|
||||||
return {
|
return {
|
||||||
pageAlias: this._pageAliases.get(page)!,
|
pageAlias: this._pageAliases.get(page)!,
|
||||||
isMainFrame: true,
|
framePath: [],
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
||||||
private async _describeFrame(frame: Frame): Promise<actions.FrameDescription> {
|
private async _describeFrame(frame: Frame): Promise<actions.FrameDescription> {
|
||||||
const page = frame._page;
|
|
||||||
const pageAlias = this._pageAliases.get(page)!;
|
|
||||||
const chain: Frame[] = [];
|
|
||||||
for (let ancestor: Frame | null = frame; ancestor; ancestor = ancestor.parentFrame())
|
|
||||||
chain.push(ancestor);
|
|
||||||
chain.reverse();
|
|
||||||
|
|
||||||
if (chain.length === 1)
|
|
||||||
return this._describeMainFrame(page);
|
|
||||||
|
|
||||||
const selectorPromises: Promise<string | undefined>[] = [];
|
|
||||||
for (let i = 0; i < chain.length - 1; i++)
|
|
||||||
selectorPromises.push(findFrameSelector(chain[i + 1]));
|
|
||||||
|
|
||||||
const result = await raceAgainstDeadline(() => Promise.all(selectorPromises), monotonicTime() + 2000);
|
|
||||||
if (!result.timedOut && result.result.every(selector => !!selector)) {
|
|
||||||
return {
|
|
||||||
pageAlias,
|
|
||||||
isMainFrame: false,
|
|
||||||
selectorsChain: result.result as string[],
|
|
||||||
};
|
|
||||||
}
|
|
||||||
// Best effort to find a selector for the frame.
|
|
||||||
const selectorsChain = [];
|
|
||||||
for (let i = 0; i < chain.length - 1; i++) {
|
|
||||||
if (chain[i].name())
|
|
||||||
selectorsChain.push(`iframe[name=${quoteCSSAttributeValue(chain[i].name())}]`);
|
|
||||||
else
|
|
||||||
selectorsChain.push(`iframe[src=${quoteCSSAttributeValue(chain[i].url())}]`);
|
|
||||||
}
|
|
||||||
return {
|
return {
|
||||||
pageAlias,
|
pageAlias: this._pageAliases.get(frame._page)!,
|
||||||
isMainFrame: false,
|
framePath: await generateFrameSelector(frame),
|
||||||
selectorsChain,
|
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -691,20 +654,41 @@ function isScreenshotCommand(metadata: CallMetadata) {
|
||||||
return metadata.method.toLowerCase().includes('screenshot');
|
return metadata.method.toLowerCase().includes('screenshot');
|
||||||
}
|
}
|
||||||
|
|
||||||
async function findFrameSelector(frame: Frame): Promise<string | undefined> {
|
async function generateFrameSelector(frame: Frame): Promise<string[]> {
|
||||||
try {
|
const selectorPromises: Promise<string>[] = [];
|
||||||
|
while (frame) {
|
||||||
const parent = frame.parentFrame();
|
const parent = frame.parentFrame();
|
||||||
const frameElement = await frame.frameElement();
|
if (!parent)
|
||||||
if (!frameElement || !parent)
|
break;
|
||||||
return;
|
selectorPromises.push(generateFrameSelectorInParent(parent, frame));
|
||||||
const utility = await parent._utilityContext();
|
frame = parent;
|
||||||
const injected = await utility.injectedScript();
|
|
||||||
const selector = await injected.evaluate((injected, element) => {
|
|
||||||
return injected.generateSelectorSimple(element as Element, { testIdAttributeName: '', omitInternalEngines: true });
|
|
||||||
}, frameElement);
|
|
||||||
return selector;
|
|
||||||
} catch (e) {
|
|
||||||
}
|
}
|
||||||
|
const result = await Promise.all(selectorPromises);
|
||||||
|
return result.reverse();
|
||||||
|
}
|
||||||
|
|
||||||
|
async function generateFrameSelectorInParent(parent: Frame, frame: Frame): Promise<string> {
|
||||||
|
const result = await raceAgainstDeadline(async () => {
|
||||||
|
try {
|
||||||
|
const frameElement = await frame.frameElement();
|
||||||
|
if (!frameElement || !parent)
|
||||||
|
return;
|
||||||
|
const utility = await parent._utilityContext();
|
||||||
|
const injected = await utility.injectedScript();
|
||||||
|
const selector = await injected.evaluate((injected, element) => {
|
||||||
|
return injected.generateSelectorSimple(element as Element);
|
||||||
|
}, frameElement);
|
||||||
|
return selector;
|
||||||
|
} catch (e) {
|
||||||
|
return e.toString();
|
||||||
|
}
|
||||||
|
}, monotonicTime() + 2000);
|
||||||
|
if (!result.timedOut && result.result)
|
||||||
|
return result.result;
|
||||||
|
|
||||||
|
if (frame.name())
|
||||||
|
return `iframe[name=${quoteCSSAttributeValue(frame.name())}]`;
|
||||||
|
return `iframe[src=${quoteCSSAttributeValue(frame.url())}]`;
|
||||||
}
|
}
|
||||||
|
|
||||||
async function innerPerformAction(frame: Frame, action: string, params: any, cb: (callMetadata: CallMetadata) => Promise<any>): Promise<boolean> {
|
async function innerPerformAction(frame: Frame, action: string, params: any, cb: (callMetadata: CallMetadata) => Promise<any>): Promise<boolean> {
|
||||||
|
|
|
||||||
|
|
@ -146,7 +146,7 @@ export class CodeGenerator extends EventEmitter {
|
||||||
this.addAction({
|
this.addAction({
|
||||||
frame: {
|
frame: {
|
||||||
pageAlias,
|
pageAlias,
|
||||||
isMainFrame: true,
|
framePath: [],
|
||||||
},
|
},
|
||||||
committed: true,
|
committed: true,
|
||||||
action: {
|
action: {
|
||||||
|
|
|
||||||
|
|
@ -72,14 +72,8 @@ export class CSharpLanguageGenerator implements LanguageGenerator {
|
||||||
return formatter.format();
|
return formatter.format();
|
||||||
}
|
}
|
||||||
|
|
||||||
let subject: string;
|
const locators = actionInContext.frame.framePath.map(selector => `.${this._asLocator(selector)}.ContentFrame()`);
|
||||||
if (actionInContext.frame.isMainFrame) {
|
const subject = `${pageAlias}${locators.join('')}`;
|
||||||
subject = pageAlias;
|
|
||||||
} else {
|
|
||||||
const locators = actionInContext.frame.selectorsChain.map(selector => `.FrameLocator(${quote(selector)})`);
|
|
||||||
subject = `${pageAlias}${locators.join('')}`;
|
|
||||||
}
|
|
||||||
|
|
||||||
const signals = toSignalMap(action);
|
const signals = toSignalMap(action);
|
||||||
|
|
||||||
if (signals.dialog) {
|
if (signals.dialog) {
|
||||||
|
|
|
||||||
|
|
@ -63,16 +63,8 @@ export class JavaLanguageGenerator implements LanguageGenerator {
|
||||||
return formatter.format();
|
return formatter.format();
|
||||||
}
|
}
|
||||||
|
|
||||||
let subject: string;
|
const locators = actionInContext.frame.framePath.map(selector => `.${this._asLocator(selector, false)}.contentFrame()`);
|
||||||
let inFrameLocator = false;
|
const subject = `${pageAlias}${locators.join('')}`;
|
||||||
if (actionInContext.frame.isMainFrame) {
|
|
||||||
subject = pageAlias;
|
|
||||||
} else {
|
|
||||||
const locators = actionInContext.frame.selectorsChain.map(selector => `.frameLocator(${quote(selector)})`);
|
|
||||||
subject = `${pageAlias}${locators.join('')}`;
|
|
||||||
inFrameLocator = true;
|
|
||||||
}
|
|
||||||
|
|
||||||
const signals = toSignalMap(action);
|
const signals = toSignalMap(action);
|
||||||
|
|
||||||
if (signals.dialog) {
|
if (signals.dialog) {
|
||||||
|
|
@ -82,7 +74,7 @@ export class JavaLanguageGenerator implements LanguageGenerator {
|
||||||
});`);
|
});`);
|
||||||
}
|
}
|
||||||
|
|
||||||
let code = this._generateActionCall(subject, action, inFrameLocator);
|
let code = this._generateActionCall(subject, action, !!actionInContext.frame.framePath.length);
|
||||||
|
|
||||||
if (signals.popup) {
|
if (signals.popup) {
|
||||||
code = `Page ${signals.popup.popupAlias} = ${pageAlias}.waitForPopup(() -> {
|
code = `Page ${signals.popup.popupAlias} = ${pageAlias}.waitForPopup(() -> {
|
||||||
|
|
|
||||||
|
|
@ -52,14 +52,8 @@ export class JavaScriptLanguageGenerator implements LanguageGenerator {
|
||||||
return formatter.format();
|
return formatter.format();
|
||||||
}
|
}
|
||||||
|
|
||||||
let subject: string;
|
const locators = actionInContext.frame.framePath.map(selector => `.${this._asLocator(selector)}.contentFrame()`);
|
||||||
if (actionInContext.frame.isMainFrame) {
|
const subject = `${pageAlias}${locators.join('')}`;
|
||||||
subject = pageAlias;
|
|
||||||
} else {
|
|
||||||
const locators = actionInContext.frame.selectorsChain.map(selector => `.frameLocator(${quote(selector)})`);
|
|
||||||
subject = `${pageAlias}${locators.join('')}`;
|
|
||||||
}
|
|
||||||
|
|
||||||
const signals = toSignalMap(action);
|
const signals = toSignalMap(action);
|
||||||
|
|
||||||
if (signals.dialog) {
|
if (signals.dialog) {
|
||||||
|
|
|
||||||
|
|
@ -59,14 +59,8 @@ export class PythonLanguageGenerator implements LanguageGenerator {
|
||||||
return formatter.format();
|
return formatter.format();
|
||||||
}
|
}
|
||||||
|
|
||||||
let subject: string;
|
const locators = actionInContext.frame.framePath.map(selector => `.${this._asLocator(selector)}.content_frame()`);
|
||||||
if (actionInContext.frame.isMainFrame) {
|
const subject = `${pageAlias}${locators.join('')}`;
|
||||||
subject = pageAlias;
|
|
||||||
} else {
|
|
||||||
const locators = actionInContext.frame.selectorsChain.map(selector => `.frame_locator(${quote(selector)})`);
|
|
||||||
subject = `${pageAlias}${locators.join('')}`;
|
|
||||||
}
|
|
||||||
|
|
||||||
const signals = toSignalMap(action);
|
const signals = toSignalMap(action);
|
||||||
|
|
||||||
if (signals.dialog)
|
if (signals.dialog)
|
||||||
|
|
|
||||||
|
|
@ -150,13 +150,7 @@ export type DialogSignal = BaseSignal & {
|
||||||
|
|
||||||
export type Signal = NavigationSignal | PopupSignal | DownloadSignal | DialogSignal;
|
export type Signal = NavigationSignal | PopupSignal | DownloadSignal | DialogSignal;
|
||||||
|
|
||||||
type FrameDescriptionMainFrame = {
|
export type FrameDescription = {
|
||||||
isMainFrame: true;
|
pageAlias: string;
|
||||||
|
framePath: string[];
|
||||||
};
|
};
|
||||||
|
|
||||||
type FrameDescriptionChildFrame = {
|
|
||||||
isMainFrame: false;
|
|
||||||
selectorsChain: string[];
|
|
||||||
};
|
|
||||||
|
|
||||||
export type FrameDescription = { pageAlias: string } & (FrameDescriptionMainFrame | FrameDescriptionChildFrame);
|
|
||||||
|
|
|
||||||
|
|
@ -120,20 +120,20 @@ await page.GetByRole(AriaRole.Button, new() { Name = "Submit" }).Nth(1).ClickAsy
|
||||||
frameHello1.click('text=Hello1'),
|
frameHello1.click('text=Hello1'),
|
||||||
]);
|
]);
|
||||||
|
|
||||||
expect(sources.get('JavaScript')!.text).toContain(`
|
expect.soft(sources.get('JavaScript')!.text).toContain(`
|
||||||
await page.frameLocator('#frame1').getByText('Hello1').click();`);
|
await page.locator('#frame1').contentFrame().getByText('Hello1').click();`);
|
||||||
|
|
||||||
expect(sources.get('Java')!.text).toContain(`
|
expect.soft(sources.get('Java')!.text).toContain(`
|
||||||
page.frameLocator("#frame1").getByText("Hello1").click();`);
|
page.locator("#frame1").contentFrame().getByText("Hello1").click();`);
|
||||||
|
|
||||||
expect(sources.get('Python')!.text).toContain(`
|
expect.soft(sources.get('Python')!.text).toContain(`
|
||||||
page.frame_locator("#frame1").get_by_text("Hello1").click()`);
|
page.locator("#frame1").content_frame().get_by_text("Hello1").click()`);
|
||||||
|
|
||||||
expect(sources.get('Python Async')!.text).toContain(`
|
expect.soft(sources.get('Python Async')!.text).toContain(`
|
||||||
await page.frame_locator("#frame1").get_by_text("Hello1").click()`);
|
await page.locator("#frame1").content_frame().get_by_text("Hello1").click()`);
|
||||||
|
|
||||||
expect(sources.get('C#')!.text).toContain(`
|
expect.soft(sources.get('C#')!.text).toContain(`
|
||||||
await page.FrameLocator("#frame1").GetByText("Hello1").ClickAsync();`);
|
await page.Locator("#frame1").ContentFrame().GetByText("Hello1").ClickAsync();`);
|
||||||
|
|
||||||
|
|
||||||
[sources] = await Promise.all([
|
[sources] = await Promise.all([
|
||||||
|
|
@ -142,19 +142,19 @@ await page.FrameLocator("#frame1").GetByText("Hello1").ClickAsync();`);
|
||||||
]);
|
]);
|
||||||
|
|
||||||
expect.soft(sources.get('JavaScript')!.text).toContain(`
|
expect.soft(sources.get('JavaScript')!.text).toContain(`
|
||||||
await page.frameLocator('#frame1').frameLocator('iframe').getByText('Hello2').click();`);
|
await page.locator('#frame1').contentFrame().locator('iframe').contentFrame().getByText('Hello2').click();`);
|
||||||
|
|
||||||
expect.soft(sources.get('Java')!.text).toContain(`
|
expect.soft(sources.get('Java')!.text).toContain(`
|
||||||
page.frameLocator("#frame1").frameLocator("iframe").getByText("Hello2").click();`);
|
page.locator("#frame1").contentFrame().locator("iframe").contentFrame().getByText("Hello2").click();`);
|
||||||
|
|
||||||
expect.soft(sources.get('Python')!.text).toContain(`
|
expect.soft(sources.get('Python')!.text).toContain(`
|
||||||
page.frame_locator("#frame1").frame_locator("iframe").get_by_text("Hello2").click()`);
|
page.locator("#frame1").content_frame().locator("iframe").content_frame().get_by_text("Hello2").click()`);
|
||||||
|
|
||||||
expect.soft(sources.get('Python Async')!.text).toContain(`
|
expect.soft(sources.get('Python Async')!.text).toContain(`
|
||||||
await page.frame_locator("#frame1").frame_locator("iframe").get_by_text("Hello2").click()`);
|
await page.locator("#frame1").content_frame().locator("iframe").content_frame().get_by_text("Hello2").click()`);
|
||||||
|
|
||||||
expect.soft(sources.get('C#')!.text).toContain(`
|
expect.soft(sources.get('C#')!.text).toContain(`
|
||||||
await page.FrameLocator("#frame1").FrameLocator("iframe").GetByText("Hello2").ClickAsync();`);
|
await page.Locator("#frame1").ContentFrame().Locator("iframe").ContentFrame().GetByText("Hello2").ClickAsync();`);
|
||||||
|
|
||||||
|
|
||||||
[sources] = await Promise.all([
|
[sources] = await Promise.all([
|
||||||
|
|
@ -163,19 +163,19 @@ await page.FrameLocator("#frame1").FrameLocator("iframe").GetByText("Hello2").Cl
|
||||||
]);
|
]);
|
||||||
|
|
||||||
expect.soft(sources.get('JavaScript')!.text).toContain(`
|
expect.soft(sources.get('JavaScript')!.text).toContain(`
|
||||||
await page.frameLocator('#frame1').frameLocator('iframe').frameLocator('iframe[name="one"]').getByText('HelloNameOne').click();`);
|
await page.locator('#frame1').contentFrame().locator('iframe').contentFrame().locator('iframe[name="one"]').contentFrame().getByText('HelloNameOne').click();`);
|
||||||
|
|
||||||
expect.soft(sources.get('Java')!.text).toContain(`
|
expect.soft(sources.get('Java')!.text).toContain(`
|
||||||
page.frameLocator("#frame1").frameLocator("iframe").frameLocator("iframe[name=\\"one\\"]").getByText("HelloNameOne").click();`);
|
page.locator("#frame1").contentFrame().locator("iframe").contentFrame().locator("iframe[name=\\"one\\"]").contentFrame().getByText("HelloNameOne").click();`);
|
||||||
|
|
||||||
expect.soft(sources.get('Python')!.text).toContain(`
|
expect.soft(sources.get('Python')!.text).toContain(`
|
||||||
page.frame_locator("#frame1").frame_locator("iframe").frame_locator("iframe[name=\\"one\\"]").get_by_text("HelloNameOne").click()`);
|
page.locator("#frame1").content_frame().locator("iframe").content_frame().locator("iframe[name=\\"one\\"]").content_frame().get_by_text("HelloNameOne").click()`);
|
||||||
|
|
||||||
expect.soft(sources.get('Python Async')!.text).toContain(`
|
expect.soft(sources.get('Python Async')!.text).toContain(`
|
||||||
await page.frame_locator("#frame1").frame_locator("iframe").frame_locator("iframe[name=\\"one\\"]").get_by_text("HelloNameOne").click()`);
|
await page.locator("#frame1").content_frame().locator("iframe").content_frame().locator("iframe[name=\\"one\\"]").content_frame().get_by_text("HelloNameOne").click()`);
|
||||||
|
|
||||||
expect.soft(sources.get('C#')!.text).toContain(`
|
expect.soft(sources.get('C#')!.text).toContain(`
|
||||||
await page.FrameLocator("#frame1").FrameLocator("iframe").FrameLocator("iframe[name=\\"one\\"]").GetByText("HelloNameOne").ClickAsync();`);
|
await page.Locator("#frame1").ContentFrame().Locator("iframe").ContentFrame().Locator("iframe[name=\\"one\\"]").ContentFrame().GetByText("HelloNameOne").ClickAsync();`);
|
||||||
|
|
||||||
[sources] = await Promise.all([
|
[sources] = await Promise.all([
|
||||||
recorder.waitForOutput('JavaScript', 'HelloNameAnonymous'),
|
recorder.waitForOutput('JavaScript', 'HelloNameAnonymous'),
|
||||||
|
|
@ -183,19 +183,19 @@ await page.FrameLocator("#frame1").FrameLocator("iframe").FrameLocator("iframe[n
|
||||||
]);
|
]);
|
||||||
|
|
||||||
expect.soft(sources.get('JavaScript')!.text).toContain(`
|
expect.soft(sources.get('JavaScript')!.text).toContain(`
|
||||||
await page.frameLocator('#frame1').frameLocator('iframe').frameLocator('iframe >> nth=2').getByText('HelloNameAnonymous').click();`);
|
await page.locator('#frame1').contentFrame().locator('iframe').contentFrame().locator('iframe').nth(2).contentFrame().getByText('HelloNameAnonymous').click();`);
|
||||||
|
|
||||||
expect.soft(sources.get('Java')!.text).toContain(`
|
expect.soft(sources.get('Java')!.text).toContain(`
|
||||||
page.frameLocator("#frame1").frameLocator("iframe").frameLocator("iframe >> nth=2").getByText("HelloNameAnonymous").click();`);
|
page.locator("#frame1").contentFrame().locator("iframe").contentFrame().locator("iframe").nth(2).contentFrame().getByText("HelloNameAnonymous").click();`);
|
||||||
|
|
||||||
expect.soft(sources.get('Python')!.text).toContain(`
|
expect.soft(sources.get('Python')!.text).toContain(`
|
||||||
page.frame_locator("#frame1").frame_locator("iframe").frame_locator("iframe >> nth=2").get_by_text("HelloNameAnonymous").click()`);
|
page.locator("#frame1").content_frame().locator("iframe").content_frame().locator("iframe").nth(2).content_frame().get_by_text("HelloNameAnonymous").click()`);
|
||||||
|
|
||||||
expect.soft(sources.get('Python Async')!.text).toContain(`
|
expect.soft(sources.get('Python Async')!.text).toContain(`
|
||||||
await page.frame_locator("#frame1").frame_locator("iframe").frame_locator("iframe >> nth=2").get_by_text("HelloNameAnonymous").click()`);
|
await page.locator("#frame1").content_frame().locator("iframe").content_frame().locator("iframe").nth(2).content_frame().get_by_text("HelloNameAnonymous").click()`);
|
||||||
|
|
||||||
expect.soft(sources.get('C#')!.text).toContain(`
|
expect.soft(sources.get('C#')!.text).toContain(`
|
||||||
await page.FrameLocator("#frame1").FrameLocator("iframe").FrameLocator("iframe >> nth=2").GetByText("HelloNameAnonymous").ClickAsync();`);
|
await page.Locator("#frame1").ContentFrame().Locator("iframe").ContentFrame().Locator("iframe").Nth(2).ContentFrame().GetByText("HelloNameAnonymous").ClickAsync();`);
|
||||||
});
|
});
|
||||||
|
|
||||||
test('should generate frame locators with special characters in name attribute', async ({ page, openRecorder, server }) => {
|
test('should generate frame locators with special characters in name attribute', async ({ page, openRecorder, server }) => {
|
||||||
|
|
@ -208,22 +208,22 @@ await page.FrameLocator("#frame1").FrameLocator("iframe").FrameLocator("iframe >
|
||||||
});
|
});
|
||||||
const [sources] = await Promise.all([
|
const [sources] = await Promise.all([
|
||||||
recorder.waitForOutput('JavaScript', 'Click me'),
|
recorder.waitForOutput('JavaScript', 'Click me'),
|
||||||
page.frameLocator('iframe[name="foo<bar\'\\"`>"]').getByRole('button', { name: 'Click me' }).click(),
|
page.locator('iframe[name="foo<bar\'\\"`>"]').contentFrame().getByRole('button', { name: 'Click me' }).click(),
|
||||||
]);
|
]);
|
||||||
expect.soft(sources.get('JavaScript')!.text).toContain(`
|
expect.soft(sources.get('JavaScript')!.text).toContain(`
|
||||||
await page.frameLocator('iframe[name="foo\\\\<bar\\\\\\'\\\\"\\\\\`\\\\>"]').getByRole('button', { name: 'Click me' }).click();`);
|
await page.locator('iframe[name="foo\\\\<bar\\\\\\'\\\\"\\\\\`\\\\>"]').contentFrame().getByRole('button', { name: 'Click me' }).click();`);
|
||||||
|
|
||||||
expect.soft(sources.get('Java')!.text).toContain(`
|
expect.soft(sources.get('Java')!.text).toContain(`
|
||||||
page.frameLocator("iframe[name=\\"foo\\\\<bar\\\\'\\\\\\"\\\\\`\\\\>\\"]").getByRole(AriaRole.BUTTON, new FrameLocator.GetByRoleOptions().setName("Click me")).click()`);
|
page.locator("iframe[name=\\"foo\\\\<bar\\\\'\\\\\\"\\\\\`\\\\>\\"]").contentFrame().getByRole(AriaRole.BUTTON, new FrameLocator.GetByRoleOptions().setName("Click me")).click()`);
|
||||||
|
|
||||||
expect.soft(sources.get('Python')!.text).toContain(`
|
expect.soft(sources.get('Python')!.text).toContain(`
|
||||||
page.frame_locator("iframe[name=\\"foo\\\\<bar\\\\'\\\\\\"\\\\\`\\\\>\\"]").get_by_role("button", name="Click me").click()`);
|
page.locator("iframe[name=\\"foo\\\\<bar\\\\'\\\\\\"\\\\\`\\\\>\\"]").content_frame().get_by_role("button", name="Click me").click()`);
|
||||||
|
|
||||||
expect.soft(sources.get('Python Async')!.text).toContain(`
|
expect.soft(sources.get('Python Async')!.text).toContain(`
|
||||||
await page.frame_locator("iframe[name=\\"foo\\\\<bar\\\\'\\\\\\"\\\\\`\\\\>\\"]").get_by_role("button", name="Click me").click()`);
|
await page.locator("iframe[name=\\"foo\\\\<bar\\\\'\\\\\\"\\\\\`\\\\>\\"]").content_frame().get_by_role("button", name="Click me").click()`);
|
||||||
|
|
||||||
expect.soft(sources.get('C#')!.text).toContain(`
|
expect.soft(sources.get('C#')!.text).toContain(`
|
||||||
await page.FrameLocator("iframe[name=\\"foo\\\\<bar\\\\'\\\\\\"\\\\\`\\\\>\\"]").GetByRole(AriaRole.Button, new() { Name = "Click me" }).ClickAsync();`);
|
await page.Locator("iframe[name=\\"foo\\\\<bar\\\\'\\\\\\"\\\\\`\\\\>\\"]").ContentFrame().GetByRole(AriaRole.Button, new() { Name = "Click me" }).ClickAsync();`);
|
||||||
});
|
});
|
||||||
|
|
||||||
test('should generate frame locators with title attribute', async ({ page, openRecorder, server }) => {
|
test('should generate frame locators with title attribute', async ({ page, openRecorder, server }) => {
|
||||||
|
|
@ -234,27 +234,27 @@ await page.FrameLocator("iframe[name=\\"foo\\\\<bar\\\\'\\\\\\"\\\\\`\\\\>\\"]")
|
||||||
|
|
||||||
const [sources] = await Promise.all([
|
const [sources] = await Promise.all([
|
||||||
recorder.waitForOutput('JavaScript', 'Click me'),
|
recorder.waitForOutput('JavaScript', 'Click me'),
|
||||||
page.frameLocator('[title="hello world"]').getByRole('button', { name: 'Click me' }).click(),
|
page.locator('[title="hello world"]').contentFrame().getByRole('button', { name: 'Click me' }).click(),
|
||||||
]);
|
]);
|
||||||
|
|
||||||
expect(sources.get('JavaScript')!.text).toContain(
|
expect.soft(sources.get('JavaScript')!.text).toContain(
|
||||||
`await page.frameLocator('iframe[title="hello world"]').getByRole('button', { name: 'Click me' }).click();`
|
`await page.locator('iframe[title="hello world"]').contentFrame().getByRole('button', { name: 'Click me' }).click();`
|
||||||
);
|
);
|
||||||
|
|
||||||
expect(sources.get('Java')!.text).toContain(
|
expect.soft(sources.get('Java')!.text).toContain(
|
||||||
`page.frameLocator(\"iframe[title=\\\"hello world\\\"]\").getByRole(AriaRole.BUTTON, new FrameLocator.GetByRoleOptions().setName(\"Click me\")).click();`
|
`page.locator(\"iframe[title=\\\"hello world\\\"]\").contentFrame().getByRole(AriaRole.BUTTON, new FrameLocator.GetByRoleOptions().setName(\"Click me\")).click();`
|
||||||
);
|
);
|
||||||
|
|
||||||
expect(sources.get('Python')!.text).toContain(
|
expect.soft(sources.get('Python')!.text).toContain(
|
||||||
`page.frame_locator(\"iframe[title=\\\"hello world\\\"]\").get_by_role(\"button\", name=\"Click me\").click()`
|
`page.locator(\"iframe[title=\\\"hello world\\\"]\").content_frame().get_by_role(\"button\", name=\"Click me\").click()`
|
||||||
);
|
);
|
||||||
|
|
||||||
expect(sources.get('Python Async')!.text).toContain(
|
expect.soft(sources.get('Python Async')!.text).toContain(
|
||||||
`await page.frame_locator("iframe[title=\\\"hello world\\\"]").get_by_role("button", name="Click me").click()`
|
`await page.locator("iframe[title=\\\"hello world\\\"]").content_frame().get_by_role("button", name="Click me").click()`
|
||||||
);
|
);
|
||||||
|
|
||||||
expect(sources.get('C#')!.text).toContain(
|
expect.soft(sources.get('C#')!.text).toContain(
|
||||||
`await page.FrameLocator("iframe[title=\\\"hello world\\\"]").GetByRole(AriaRole.Button, new() { Name = "Click me" }).ClickAsync();`
|
`await page.Locator("iframe[title=\\\"hello world\\\"]").ContentFrame().GetByRole(AriaRole.Button, new() { Name = "Click me" }).ClickAsync();`
|
||||||
);
|
);
|
||||||
});
|
});
|
||||||
|
|
||||||
|
|
@ -266,27 +266,27 @@ await page.FrameLocator("iframe[name=\\"foo\\\\<bar\\\\'\\\\\\"\\\\\`\\\\>\\"]")
|
||||||
|
|
||||||
const [sources] = await Promise.all([
|
const [sources] = await Promise.all([
|
||||||
recorder.waitForOutput('JavaScript', 'Click me'),
|
recorder.waitForOutput('JavaScript', 'Click me'),
|
||||||
page.frameLocator('[name="hello world"]').getByRole('button', { name: 'Click me' }).click(),
|
page.locator('[name="hello world"]').contentFrame().getByRole('button', { name: 'Click me' }).click(),
|
||||||
]);
|
]);
|
||||||
|
|
||||||
expect(sources.get('JavaScript')!.text).toContain(
|
expect.soft(sources.get('JavaScript')!.text).toContain(
|
||||||
`await page.frameLocator('iframe[name="hello world"]').getByRole('button', { name: 'Click me' }).click();`
|
`await page.locator('iframe[name="hello world"]').contentFrame().getByRole('button', { name: 'Click me' }).click();`
|
||||||
);
|
);
|
||||||
|
|
||||||
expect(sources.get('Java')!.text).toContain(
|
expect.soft(sources.get('Java')!.text).toContain(
|
||||||
`page.frameLocator(\"iframe[name=\\\"hello world\\\"]\").getByRole(AriaRole.BUTTON, new FrameLocator.GetByRoleOptions().setName(\"Click me\")).click();`
|
`page.locator(\"iframe[name=\\\"hello world\\\"]\").contentFrame().getByRole(AriaRole.BUTTON, new FrameLocator.GetByRoleOptions().setName(\"Click me\")).click();`
|
||||||
);
|
);
|
||||||
|
|
||||||
expect(sources.get('Python')!.text).toContain(
|
expect.soft(sources.get('Python')!.text).toContain(
|
||||||
`page.frame_locator(\"iframe[name=\\\"hello world\\\"]\").get_by_role(\"button\", name=\"Click me\").click()`
|
`page.locator(\"iframe[name=\\\"hello world\\\"]\").content_frame().get_by_role(\"button\", name=\"Click me\").click()`
|
||||||
);
|
);
|
||||||
|
|
||||||
expect(sources.get('Python Async')!.text).toContain(
|
expect.soft(sources.get('Python Async')!.text).toContain(
|
||||||
`await page.frame_locator("iframe[name=\\\"hello world\\\"]").get_by_role("button", name="Click me").click()`
|
`await page.locator("iframe[name=\\\"hello world\\\"]").content_frame().get_by_role("button", name="Click me").click()`
|
||||||
);
|
);
|
||||||
|
|
||||||
expect(sources.get('C#')!.text).toContain(
|
expect.soft(sources.get('C#')!.text).toContain(
|
||||||
`await page.FrameLocator("iframe[name=\\\"hello world\\\"]").GetByRole(AriaRole.Button, new() { Name = "Click me" }).ClickAsync();`
|
`await page.Locator("iframe[name=\\\"hello world\\\"]").ContentFrame().GetByRole(AriaRole.Button, new() { Name = "Click me" }).ClickAsync();`
|
||||||
);
|
);
|
||||||
});
|
});
|
||||||
|
|
||||||
|
|
@ -298,27 +298,27 @@ await page.FrameLocator("iframe[name=\\"foo\\\\<bar\\\\'\\\\\\"\\\\\`\\\\>\\"]")
|
||||||
|
|
||||||
const [sources] = await Promise.all([
|
const [sources] = await Promise.all([
|
||||||
recorder.waitForOutput('JavaScript', 'Click me'),
|
recorder.waitForOutput('JavaScript', 'Click me'),
|
||||||
page.frameLocator('[id="hello-world"]').getByRole('button', { name: 'Click me' }).click(),
|
page.locator('[id="hello-world"]').contentFrame().getByRole('button', { name: 'Click me' }).click(),
|
||||||
]);
|
]);
|
||||||
|
|
||||||
expect(sources.get('JavaScript')!.text).toContain(
|
expect.soft(sources.get('JavaScript')!.text).toContain(
|
||||||
`await page.frameLocator('#hello-world').getByRole('button', { name: 'Click me' }).click();`
|
`await page.locator('#hello-world').contentFrame().getByRole('button', { name: 'Click me' }).click();`
|
||||||
);
|
);
|
||||||
|
|
||||||
expect(sources.get('Java')!.text).toContain(
|
expect.soft(sources.get('Java')!.text).toContain(
|
||||||
`page.frameLocator(\"#hello-world\").getByRole(AriaRole.BUTTON, new FrameLocator.GetByRoleOptions().setName(\"Click me\")).click();`
|
`page.locator(\"#hello-world\").contentFrame().getByRole(AriaRole.BUTTON, new FrameLocator.GetByRoleOptions().setName(\"Click me\")).click();`
|
||||||
);
|
);
|
||||||
|
|
||||||
expect(sources.get('Python')!.text).toContain(
|
expect.soft(sources.get('Python')!.text).toContain(
|
||||||
`page.frame_locator(\"#hello-world\").get_by_role(\"button\", name=\"Click me\").click()`
|
`page.locator(\"#hello-world\").content_frame().get_by_role(\"button\", name=\"Click me\").click()`
|
||||||
);
|
);
|
||||||
|
|
||||||
expect(sources.get('Python Async')!.text).toContain(
|
expect.soft(sources.get('Python Async')!.text).toContain(
|
||||||
`await page.frame_locator("#hello-world").get_by_role("button", name="Click me").click()`
|
`await page.locator("#hello-world").content_frame().get_by_role("button", name="Click me").click()`
|
||||||
);
|
);
|
||||||
|
|
||||||
expect(sources.get('C#')!.text).toContain(
|
expect.soft(sources.get('C#')!.text).toContain(
|
||||||
`await page.FrameLocator("#hello-world").GetByRole(AriaRole.Button, new() { Name = "Click me" }).ClickAsync();`
|
`await page.Locator("#hello-world").ContentFrame().GetByRole(AriaRole.Button, new() { Name = "Click me" }).ClickAsync();`
|
||||||
);
|
);
|
||||||
});
|
});
|
||||||
|
|
||||||
|
|
@ -330,27 +330,27 @@ await page.FrameLocator("iframe[name=\\"foo\\\\<bar\\\\'\\\\\\"\\\\\`\\\\>\\"]")
|
||||||
|
|
||||||
const [sources] = await Promise.all([
|
const [sources] = await Promise.all([
|
||||||
recorder.waitForOutput('JavaScript', 'my-testid'),
|
recorder.waitForOutput('JavaScript', 'my-testid'),
|
||||||
page.frameLocator('iframe[data-testid="my-testid"]').getByRole('button', { name: 'Click me' }).click(),
|
page.locator('iframe[data-testid="my-testid"]').contentFrame().getByRole('button', { name: 'Click me' }).click(),
|
||||||
]);
|
]);
|
||||||
|
|
||||||
expect(sources.get('JavaScript')!.text).toContain(
|
expect.soft(sources.get('JavaScript')!.text).toContain(
|
||||||
`await page.frameLocator('[data-testid="my-testid"]').getByRole('button', { name: 'Click me' }).click();`
|
`await page.locator('[data-testid="my-testid"]').contentFrame().getByRole('button', { name: 'Click me' }).click();`
|
||||||
);
|
);
|
||||||
|
|
||||||
expect(sources.get('Java')!.text).toContain(
|
expect.soft(sources.get('Java')!.text).toContain(
|
||||||
`page.frameLocator(\"[data-testid=\\\"my-testid\\\"]\").getByRole(AriaRole.BUTTON, new FrameLocator.GetByRoleOptions().setName(\"Click me\")).click();`
|
`page.locator(\"[data-testid=\\\"my-testid\\\"]\").contentFrame().getByRole(AriaRole.BUTTON, new FrameLocator.GetByRoleOptions().setName(\"Click me\")).click();`
|
||||||
);
|
);
|
||||||
|
|
||||||
expect(sources.get('Python')!.text).toContain(
|
expect.soft(sources.get('Python')!.text).toContain(
|
||||||
`page.frame_locator(\"[data-testid=\\\"my-testid\\\"]\").get_by_role(\"button\", name=\"Click me\").click()`
|
`page.locator(\"[data-testid=\\\"my-testid\\\"]\").content_frame().get_by_role(\"button\", name=\"Click me\").click()`
|
||||||
);
|
);
|
||||||
|
|
||||||
expect(sources.get('Python Async')!.text).toContain(
|
expect.soft(sources.get('Python Async')!.text).toContain(
|
||||||
`await page.frame_locator("[data-testid=\\\"my-testid\\\"]").get_by_role("button", name="Click me").click()`
|
`await page.locator("[data-testid=\\\"my-testid\\\"]").content_frame().get_by_role("button", name="Click me").click()`
|
||||||
);
|
);
|
||||||
|
|
||||||
expect(sources.get('C#')!.text).toContain(
|
expect.soft(sources.get('C#')!.text).toContain(
|
||||||
`await page.FrameLocator("[data-testid=\\\"my-testid\\\"]").GetByRole(AriaRole.Button, new() { Name = "Click me" }).ClickAsync();`
|
`await page.Locator("[data-testid=\\\"my-testid\\\"]").ContentFrame().GetByRole(AriaRole.Button, new() { Name = "Click me" }).ClickAsync();`
|
||||||
);
|
);
|
||||||
});
|
});
|
||||||
|
|
||||||
|
|
@ -365,19 +365,19 @@ await page.FrameLocator("iframe[name=\\"foo\\\\<bar\\\\'\\\\\\"\\\\\`\\\\>\\"]")
|
||||||
]);
|
]);
|
||||||
|
|
||||||
expect.soft(sources.get('JavaScript')!.text).toContain(`
|
expect.soft(sources.get('JavaScript')!.text).toContain(`
|
||||||
await page.frameLocator('#frame1').getByRole('button', { name: 'Submit' }).click();`);
|
await page.locator('#frame1').contentFrame().getByRole('button', { name: 'Submit' }).click();`);
|
||||||
|
|
||||||
expect.soft(sources.get('Java')!.text).toContain(`
|
expect.soft(sources.get('Java')!.text).toContain(`
|
||||||
page.frameLocator("#frame1").getByRole(AriaRole.BUTTON, new FrameLocator.GetByRoleOptions().setName("Submit")).click();`);
|
page.locator("#frame1").contentFrame().getByRole(AriaRole.BUTTON, new FrameLocator.GetByRoleOptions().setName("Submit")).click();`);
|
||||||
|
|
||||||
expect.soft(sources.get('Python')!.text).toContain(`
|
expect.soft(sources.get('Python')!.text).toContain(`
|
||||||
page.frame_locator("#frame1").get_by_role("button", name="Submit").click()`);
|
page.locator("#frame1").content_frame().get_by_role("button", name="Submit").click()`);
|
||||||
|
|
||||||
expect.soft(sources.get('Python Async')!.text).toContain(`
|
expect.soft(sources.get('Python Async')!.text).toContain(`
|
||||||
await page.frame_locator("#frame1").get_by_role("button", name="Submit").click()`);
|
await page.locator("#frame1").content_frame().get_by_role("button", name="Submit").click()`);
|
||||||
|
|
||||||
expect.soft(sources.get('C#')!.text).toContain(`
|
expect.soft(sources.get('C#')!.text).toContain(`
|
||||||
await page.FrameLocator("#frame1").GetByRole(AriaRole.Button, new() { Name = "Submit" }).ClickAsync();`);
|
await page.Locator("#frame1").ContentFrame().GetByRole(AriaRole.Button, new() { Name = "Submit" }).ClickAsync();`);
|
||||||
});
|
});
|
||||||
|
|
||||||
test('should generate getByTestId', async ({ page, openRecorder }) => {
|
test('should generate getByTestId', async ({ page, openRecorder }) => {
|
||||||
|
|
|
||||||
Loading…
Reference in a new issue