93 lines
3.8 KiB
Python
93 lines
3.8 KiB
Python
#!/usr/bin/env python3
|
|
"""V138 E2E - Copy URL button works + clipboard + toast feedback"""
|
|
import asyncio, json, os
|
|
from playwright.async_api import async_playwright
|
|
|
|
OUT = "/var/www/html/api/blade-tasks/v138-copy-url-proof"
|
|
os.makedirs(OUT, exist_ok=True)
|
|
|
|
async def main():
|
|
async with async_playwright() as p:
|
|
browser = await p.chromium.launch(headless=True, args=['--no-sandbox'])
|
|
# grant clipboard-write permission
|
|
ctx = await browser.new_context(
|
|
viewport={'width':1920,'height':1080},
|
|
permissions=['clipboard-read', 'clipboard-write']
|
|
)
|
|
page = await ctx.new_page()
|
|
errs = []
|
|
page.on('pageerror', lambda e: errs.append(str(e)))
|
|
|
|
await page.goto("https://weval-consulting.com/all-ia-hub.html?v=v138", wait_until='load', timeout=30000)
|
|
await page.wait_for_timeout(2000)
|
|
await page.click('[data-view="dashboards"]')
|
|
await page.wait_for_timeout(3500)
|
|
|
|
# Set state first via pin + sort + filter (exercise URL state V129)
|
|
await page.select_option('#dash-sort', 'mtime')
|
|
await page.wait_for_timeout(500)
|
|
await page.click('button[data-cat="pharma"]')
|
|
await page.wait_for_timeout(500)
|
|
await page.evaluate("__dashTogglePin('ethica-hub.html')")
|
|
await page.wait_for_timeout(600)
|
|
|
|
state_before = await page.evaluate("""() => ({
|
|
btn_exists: !!document.getElementById('v138-copy-btn'),
|
|
btn_text: document.getElementById('v138-copy-btn')?.textContent?.trim(),
|
|
hash: window.location.hash,
|
|
full_url: window.location.href
|
|
})""")
|
|
print("Before click:", json.dumps(state_before, indent=2))
|
|
|
|
# Click Share
|
|
await page.click('#v138-copy-btn')
|
|
await page.wait_for_timeout(300)
|
|
|
|
during = await page.evaluate("""() => ({
|
|
btn_text: document.getElementById('v138-copy-btn')?.textContent?.trim(),
|
|
btn_color: document.getElementById('v138-copy-btn')?.style.color
|
|
})""")
|
|
print("During feedback:", json.dumps(during, indent=2))
|
|
|
|
# Verify clipboard
|
|
clipboard = await page.evaluate("async () => await navigator.clipboard.readText()")
|
|
print("Clipboard content:", clipboard)
|
|
|
|
await page.wait_for_timeout(1800) # wait for feedback reset
|
|
|
|
after = await page.evaluate("""() => ({
|
|
btn_text: document.getElementById('v138-copy-btn')?.textContent?.trim(),
|
|
btn_color: document.getElementById('v138-copy-btn')?.style.color
|
|
})""")
|
|
print("After reset:", json.dumps(after, indent=2))
|
|
|
|
await ctx.close()
|
|
await browser.close()
|
|
|
|
verdict = 'OK' if (
|
|
state_before['btn_exists'] and
|
|
'Share' in state_before['btn_text'] and
|
|
'cat=pharma' in state_before['hash'] and
|
|
'Copied' in during['btn_text'] and
|
|
clipboard == state_before['full_url'] and
|
|
'Share' in after['btn_text'] and
|
|
not errs
|
|
) else 'PARTIAL'
|
|
|
|
report = {
|
|
'v138': 'copy-url-clipboard',
|
|
'btn_exists': state_before['btn_exists'],
|
|
'url_contains_state': 'cat=pharma' in state_before['hash'] and 'sort=mtime' in state_before['hash'],
|
|
'click_shows_copied_feedback': 'Copied' in during['btn_text'],
|
|
'clipboard_matches_url': clipboard == state_before['full_url'],
|
|
'feedback_resets': 'Share' in after['btn_text'],
|
|
'clipboard_preview': clipboard[:200] if clipboard else '',
|
|
'js_errors': errs,
|
|
'VERDICT': verdict
|
|
}
|
|
with open(f"{OUT}/proof.json",'w') as f: json.dump(report, f, indent=2)
|
|
print("=== VERDICT:", verdict)
|
|
print(json.dumps(report, indent=2))
|
|
|
|
asyncio.run(main())
|