110 lines
4.6 KiB
Python
110 lines
4.6 KiB
Python
#!/usr/bin/env python3
|
|
"""V137 E2E - Refresh button + age indicator work"""
|
|
import asyncio, json, os
|
|
from playwright.async_api import async_playwright
|
|
|
|
OUT = "/var/www/html/api/blade-tasks/v137-refresh-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'])
|
|
ctx = await browser.new_context(viewport={'width':1920,'height':1080})
|
|
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=v137", wait_until='load', timeout=30000)
|
|
await page.wait_for_timeout(3500) # wait for initial fetch
|
|
|
|
initial = await page.evaluate("""() => {
|
|
const btn = document.getElementById('v137-refresh-btn');
|
|
const kpi = document.getElementById('v135-kpi-live');
|
|
return {
|
|
btn_exists: !!btn,
|
|
btn_title: btn?.title,
|
|
btn_disabled: btn?.disabled,
|
|
kpi_innerHTML: kpi?.innerHTML,
|
|
kpi_title_has_scan: kpi?.title?.includes('Scan:'),
|
|
kpi_has_ago: kpi?.innerHTML?.includes('ago') || kpi?.innerHTML?.includes('just now')
|
|
};
|
|
}""")
|
|
print("Initial:", json.dumps(initial, indent=2))
|
|
|
|
# Click refresh btn
|
|
await page.click('#v137-refresh-btn')
|
|
await page.wait_for_timeout(300)
|
|
|
|
during = await page.evaluate("""() => {
|
|
const btn = document.getElementById('v137-refresh-btn');
|
|
return {
|
|
animation: btn?.style.animation,
|
|
disabled: btn?.disabled
|
|
};
|
|
}""")
|
|
print("During refresh:", json.dumps(during))
|
|
|
|
await page.wait_for_timeout(1500) # wait for completion
|
|
|
|
after = await page.evaluate("""() => {
|
|
const btn = document.getElementById('v137-refresh-btn');
|
|
const kpi = document.getElementById('v135-kpi-live');
|
|
return {
|
|
btn_disabled: btn?.disabled,
|
|
animation: btn?.style.animation,
|
|
kpi_still_valid: !!kpi?.innerHTML?.includes('%')
|
|
};
|
|
}""")
|
|
print("After refresh:", json.dumps(after))
|
|
|
|
# Verify click banner still opens modal (backward compat V136)
|
|
await page.click('#v135-kpi-live')
|
|
await page.wait_for_timeout(1200)
|
|
modal_state = await page.evaluate("() => document.getElementById('v136-health-modal')?.style.display")
|
|
print("Modal after banner click:", modal_state)
|
|
|
|
await page.keyboard.press('Escape')
|
|
await page.wait_for_timeout(500)
|
|
|
|
# Click refresh btn while modal closed should NOT open modal (stopPropagation test)
|
|
await page.click('#v137-refresh-btn')
|
|
await page.wait_for_timeout(300)
|
|
modal_state2 = await page.evaluate("() => document.getElementById('v136-health-modal')?.style.display")
|
|
print("Modal after refresh click (should be none):", modal_state2)
|
|
|
|
await ctx.close()
|
|
await browser.close()
|
|
|
|
verdict = 'OK' if (
|
|
initial['btn_exists'] and
|
|
initial['kpi_title_has_scan'] and
|
|
initial['kpi_has_ago'] and
|
|
not initial['btn_disabled'] and
|
|
'v137spin' in (during['animation'] or '') and
|
|
during['disabled'] and
|
|
not after['btn_disabled'] and
|
|
after['kpi_still_valid'] and
|
|
modal_state == 'flex' and # banner click opens modal
|
|
modal_state2 in (None, 'none') and # refresh click does NOT open modal
|
|
not errs
|
|
) else 'PARTIAL'
|
|
|
|
report = {
|
|
'v137': 'refresh-button-age-indicator',
|
|
'btn_exists': initial['btn_exists'],
|
|
'age_indicator_in_banner': initial['kpi_has_ago'],
|
|
'scan_info_in_tooltip': initial['kpi_title_has_scan'],
|
|
'spin_animation_active': 'v137spin' in (during['animation'] or ''),
|
|
'btn_disabled_during': during['disabled'],
|
|
'btn_reenabled_after': not after['btn_disabled'],
|
|
'banner_click_still_opens_modal': modal_state == 'flex',
|
|
'refresh_click_stopPropagation_works': modal_state2 in (None, 'none'),
|
|
'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())
|