Skip to content

Commit dd8a946

Browse files
gkorlandCopilot
andcommitted
Fix Playwright helpers for redesigned UI
Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
1 parent 692df49 commit dd8a946

1 file changed

Lines changed: 43 additions & 17 deletions

File tree

e2e/logic/POM/codeGraph.ts

Lines changed: 43 additions & 17 deletions
Original file line numberDiff line numberDiff line change
@@ -30,7 +30,15 @@ export default class CodeGraph extends BasePage {
3030
}
3131

3232
private get navBaritem(): (navItem: string) => Locator {
33-
return (navItem: string) => this.scopedLocator(`//a[p[text() = '${navItem}']]`);
33+
return (navItem: string) => {
34+
const navItemSelectors: Record<string, string> = {
35+
"Main Website": "//a[@title='Home' or .//p[normalize-space()='Main Website'] or contains(@href, 'falkordb.com')]",
36+
"Github": "//a[@title='Github' or .//p[normalize-space()='Github'] or contains(@href, 'github.com/FalkorDB/code-graph')]",
37+
"Discord": "//a[@title='Discord' or .//p[normalize-space()='Discord'] or contains(@href, 'discord.gg/falkordb')]",
38+
};
39+
const selector = navItemSelectors[navItem] ?? `//a[@title='${navItem}' or .//p[normalize-space()='${navItem}']]`;
40+
return this.scopedLocator(selector).first();
41+
};
3442
}
3543

3644
private get createNewProjectBtn(): Locator {
@@ -186,6 +194,10 @@ export default class CodeGraph extends BasePage {
186194
return this.scopedLocator("//falkordb-canvas").locator("canvas").first();
187195
}
188196

197+
private get canvasHost(): Locator {
198+
return this.scopedLocator("falkordb-canvas").first();
199+
}
200+
189201
private get zoomInBtn(): Locator {
190202
return this.scopedLocator("//button[@title='Zoom In']");
191203
}
@@ -203,11 +215,11 @@ export default class CodeGraph extends BasePage {
203215
}
204216

205217
private get clearGraphBtn(): Locator {
206-
return this.scopedLocator("//button[p[text()='Reset Graph']]");
218+
return this.container.getByRole('button', { name: 'Reset Graph' });
207219
}
208220

209221
private get unhideNodesBtn(): Locator {
210-
return this.scopedLocator("//button[p[text()='Unhide Nodes']]");
222+
return this.container.getByRole('button', { name: 'Unhide Nodes' });
211223
}
212224

213225
private get elementMenuButton(): (buttonID: string) => Locator {
@@ -411,7 +423,14 @@ export default class CodeGraph extends BasePage {
411423
} else {
412424
await interactWhenVisible(this.selectGraphInComboBoxByName(graph), (el) => el.click(), `Graph option ${graph}`);
413425
}
414-
await this.page.waitForTimeout(2000); // graph animation delay
426+
const graphGetter = this.isMobile ? "graphMobile" : "graphDesktop";
427+
await this.page.waitForFunction((getterName) => {
428+
const getter = (window as any)[getterName];
429+
const graphData = typeof getter === "function" ? getter() : null;
430+
const nodes = graphData?.elements?.nodes || graphData?.nodes;
431+
return Array.isArray(nodes) && nodes.length > 0;
432+
}, graphGetter, { timeout: 10000 });
433+
await this.page.waitForTimeout(3000);
415434
}
416435

417436
async createProject(url: string): Promise<void> {
@@ -486,10 +505,14 @@ export default class CodeGraph extends BasePage {
486505

487506
async nodeClick(x: number, y: number): Promise<void> {
488507
await this.waitForCanvasAnimationToEnd();
508+
const boundingBox = await this.canvasElement.boundingBox();
509+
if (!boundingBox) throw new Error("Canvas bounding box not found");
510+
const targetX = Math.min(Math.max(x, boundingBox.x + 1), boundingBox.x + boundingBox.width - 1);
511+
const targetY = Math.min(Math.max(y, boundingBox.y + 1), boundingBox.y + boundingBox.height - 1);
489512
for (let attempt = 1; attempt <= 3; attempt++) {
490-
await this.canvasElement.hover({ position: { x, y } });
513+
await this.page.mouse.move(targetX, targetY);
491514
await this.page.waitForTimeout(500);
492-
await this.canvasElement.click({ position: { x, y }, button: 'right' });
515+
await this.page.mouse.click(targetX, targetY, { button: 'right' });
493516
if (await this.elementMenu.isVisible()) {
494517
return;
495518
}
@@ -628,6 +651,10 @@ export default class CodeGraph extends BasePage {
628651
return {
629652
left: rect.left,
630653
top: rect.top,
654+
width: rect.width,
655+
height: rect.height,
656+
canvasWidth: canvas.width,
657+
canvasHeight: canvas.height,
631658
transform: ctx?.getTransform() || null,
632659
};
633660
});
@@ -642,16 +669,20 @@ export default class CodeGraph extends BasePage {
642669
const nodes = graphData.elements?.nodes || graphData.nodes;
643670
if (!nodes) throw new Error("No nodes found in graph data!");
644671

645-
const { a, e, d, f } = transformData.transform;
672+
const { a, b, c, d, e, f } = transformData.transform;
673+
const cssScaleX = transformData.canvasWidth ? transformData.width / transformData.canvasWidth : 1;
674+
const cssScaleY = transformData.canvasHeight ? transformData.height / transformData.canvasHeight : 1;
646675
return nodes.map((node: any) => {
676+
const relativeX = (node.x * a + node.y * c + e) * cssScaleX;
677+
const relativeY = (node.x * b + node.y * d + f) * cssScaleY;
647678
// Canvas format has properties nested in 'data' object and 'labels' instead of 'category'
648679
// Flatten the structure for backward compatibility
649680
const flatNode = {
650681
...node,
651682
...(node.data || {}), // Spread data properties to top level
652683
category: node.labels?.[0] || node.category, // Use labels[0] or fallback to category
653-
screenX: transformData.left + node.x * a + e - 35,
654-
screenY: transformData.top + node.y * d + f - 190,
684+
screenX: transformData.left + relativeX,
685+
screenY: transformData.top + relativeY,
655686
};
656687
return flatNode;
657688
});
@@ -660,15 +691,10 @@ export default class CodeGraph extends BasePage {
660691

661692
async getCanvasScaling(): Promise<{ scaleX: number; scaleY: number }> {
662693
await this.waitForCanvasAnimationToEnd();
663-
const { scaleX, scaleY } = await this.canvasElement.evaluate((canvas: HTMLCanvasElement) => {
664-
const ctx = canvas.getContext('2d');
665-
const transform = ctx?.getTransform();
666-
return {
667-
scaleX: transform?.a || 1,
668-
scaleY: transform?.d || 1,
669-
};
694+
const zoom = await this.canvasHost.evaluate((canvas: { getZoom?: () => number }) => {
695+
return typeof canvas.getZoom === "function" ? canvas.getZoom() : 1;
670696
});
671-
return { scaleX, scaleY };
697+
return { scaleX: zoom, scaleY: zoom };
672698
}
673699

674700
async downloadImage(): Promise<Download> {

0 commit comments

Comments
 (0)