Files
wehub-resource-sync 7a0da7932b
Backwards Compatibility / Verify Encryption Constants (push) Waiting to run
Backwards Compatibility / PyPI Version Compatibility (push) Waiting to run
Backwards Compatibility / Database Migration Tests (push) Waiting to run
CodeQL Advanced / Analyze (javascript-typescript) (push) Waiting to run
CodeQL Advanced / Analyze (python) (push) Waiting to run
Docker Tests (Consolidated) / UI Tests (Puppeteer) [research-form] (push) Blocked by required conditions
Docker Tests (Consolidated) / UI Tests (Puppeteer) [research-metrics] (push) Blocked by required conditions
Docker Tests (Consolidated) / UI Tests (Puppeteer) [research-workflow] (push) Blocked by required conditions
Docker Tests (Consolidated) / UI Tests (Puppeteer) [settings-core] (push) Blocked by required conditions
Docker Tests (Consolidated) / UI Tests (Puppeteer) [settings-pages] (push) Blocked by required conditions
Docker Tests (Consolidated) / UI Tests (Puppeteer) [history-news] (push) Blocked by required conditions
Docker Tests (Consolidated) / UI Tests (Puppeteer) [library] (push) Blocked by required conditions
Docker Tests (Consolidated) / UI Tests (Puppeteer) [link-analytics] (push) Blocked by required conditions
Docker Tests (Consolidated) / UI Tests (Puppeteer) [mobile] (push) Blocked by required conditions
Docker Tests (Consolidated) / detect-changes (push) Waiting to run
Docker Tests (Consolidated) / Build Test Image (push) Waiting to run
Docker Tests (Consolidated) / All Pytest Tests + Coverage (push) Blocked by required conditions
Docker Tests (Consolidated) / UI Tests (Puppeteer) [accessibility] (push) Blocked by required conditions
Docker Tests (Consolidated) / UI Tests (Puppeteer) [api-crud] (push) Blocked by required conditions
Docker Tests (Consolidated) / UI Tests (Puppeteer) [auth-login] (push) Blocked by required conditions
Docker Tests (Consolidated) / UI Tests (Puppeteer) [auth-pages] (push) Blocked by required conditions
Docker Tests (Consolidated) / UI Tests (Puppeteer) [auth-register] (push) Blocked by required conditions
Docker Tests (Consolidated) / UI Tests (Puppeteer) [chat-core] (push) Blocked by required conditions
Docker Tests (Consolidated) / UI Tests (Puppeteer) [chat-lifecycle] (push) Blocked by required conditions
Docker Tests (Consolidated) / UI Tests (Puppeteer) [error-benchmark] (push) Blocked by required conditions
Docker Tests (Consolidated) / UI Tests (Puppeteer) (push) Blocked by required conditions
Docker Tests (Consolidated) / Accessibility Tests (push) Blocked by required conditions
Docker Tests (Consolidated) / LLM Unit Tests (push) Blocked by required conditions
Docker Tests (Consolidated) / LLM Example Tests (push) Blocked by required conditions
Docker Tests (Consolidated) / Production Image Smoke Test (push) Blocked by required conditions
Docker Tests (Consolidated) / Infrastructure Tests (push) Blocked by required conditions
OSSF Scorecard / OSSF Security Scorecard Analysis (push) Waiting to run
OSV-Scanner (Scheduled) / scan-scheduled (push) Failing after 0s
Create Release / test-gate (push) Has been cancelled
Create Release / release-gate (push) Has been cancelled
Create Release / ci-gate (push) Has been cancelled
Create Release / version-check (push) Has been cancelled
Create Release / e2e-test-gate (push) Has been cancelled
Create Release / responsive-test-gate (push) Has been cancelled
Create Release / compat-test-gate (push) Has been cancelled
Create Release / compose-integration-gate (push) Has been cancelled
Create Release / vulture-gate (push) Has been cancelled
Create Release / build (push) Has been cancelled
Create Release / provenance (push) Has been cancelled
Create Release / prerelease-docker (push) Has been cancelled
Create Release / publish-docker (push) Has been cancelled
Create Release / create-release (push) Has been cancelled
Create Release / cleanup-changelog (push) Has been cancelled
Create Release / trigger-pypi (push) Has been cancelled
Create Release / monitor-pypi (push) Has been cancelled
Create Release / Clean up orphan prerelease tags and signatures (push) Has been cancelled
chore: import upstream snapshot with attribution
2026-07-13 13:08:55 +08:00

283 lines
10 KiB
JavaScript

/**
* Test Context Overflow Dashboard
* Tests the context overflow analytics page functionality
*/
const puppeteer = require('puppeteer');
const AuthHelper = require('./auth_helper');
const BASE_URL = process.env.BASE_URL || 'http://127.0.0.1:5000';
const HEADLESS = process.env.HEADLESS !== 'false';
const SLOW_MO = parseInt(process.env.SLOW_MO || '0', 10);
describe('Context Overflow Dashboard Tests', () => {
let browser;
let page;
let authHelper;
beforeAll(async () => {
browser = await puppeteer.launch({
headless: HEADLESS,
slowMo: SLOW_MO,
args: ['--no-sandbox', '--disable-setuid-sandbox']
});
});
afterAll(async () => {
if (browser) {
await browser.close();
}
});
beforeEach(async () => {
page = await browser.newPage();
await page.setViewport({ width: 1280, height: 800 });
authHelper = new AuthHelper(page, BASE_URL);
// Set longer timeout for slower operations
page.setDefaultTimeout(30000);
});
afterEach(async () => {
if (page) {
await page.close();
}
});
test('Context overflow dashboard loads and displays data', async () => {
console.log('📊 Testing context overflow dashboard...');
// Login first
await authHelper.ensureAuthenticated();
// Navigate to context overflow page
console.log(' Navigating to context overflow page...');
await page.goto(`${BASE_URL}/metrics/context-overflow`, {
waitUntil: 'domcontentloaded',
timeout: 30000
});
// Wait for page to load
await page.waitForSelector('#context-overflow', { timeout: 10000 });
console.log(' ✅ Context overflow page loaded');
// Sanity-check that the controller JS was extracted out of the
// template into its own deferred file. If someone re-inlines the
// IIFE later, the deferred-script ordering bug returns silently.
const externalScripts = await page.$$eval('script[defer][src]', els =>
els.map(s => s.getAttribute('src'))
);
expect(externalScripts).toContain('/static/js/components/context-overflow.js');
expect(externalScripts).toContain('/static/js/components/context-overflow-shared.js');
// Wait for loading to complete
console.log(' Waiting for data to load...');
await page.waitForFunction(
() => {
const loading = document.getElementById('loading');
const content = document.getElementById('content');
return loading && loading.style.display === 'none' &&
content && content.style.display !== 'none';
},
{ timeout: 15000 }
);
console.log(' ✅ Data loading complete');
// Check for main sections
const sections = await page.evaluate(() => {
const results = {
hasOverviewCards: false,
hasContextChart: false,
hasModelStats: false,
hasTruncatedList: false,
truncationRate: null,
avgTokensLost: null,
modelsTracked: null,
dataCoverage: null
};
// Check overview cards
const overviewCards = document.querySelector('.overflow-grid');
results.hasOverviewCards = !!overviewCards;
// Get metrics values
const truncationRate = document.getElementById('truncation-rate');
if (truncationRate) {
results.truncationRate = truncationRate.textContent.trim();
}
const avgTokensLost = document.getElementById('avg-tokens-lost');
if (avgTokensLost) {
results.avgTokensLost = avgTokensLost.textContent.trim();
}
const modelsTracked = document.getElementById('models-tracked');
if (modelsTracked) {
results.modelsTracked = modelsTracked.textContent.trim();
}
const dataCoverage = document.getElementById('data-coverage');
if (dataCoverage) {
results.dataCoverage = dataCoverage.textContent.trim();
}
// Check charts
const contextChart = document.getElementById('context-chart');
results.hasContextChart = !!contextChart;
// Check model stats section
const modelStats = document.getElementById('model-stats');
results.hasModelStats = !!modelStats;
// Check truncated list section
const truncatedList = document.getElementById('truncated-list');
results.hasTruncatedList = !!truncatedList;
return results;
});
console.log(' 📊 Dashboard sections found:');
console.log(` - Overview cards: ${sections.hasOverviewCards ? '✅' : '❌'}`);
console.log(` - Context chart: ${sections.hasContextChart ? '✅' : '❌'}`);
console.log(` - Model stats: ${sections.hasModelStats ? '✅' : '❌'}`);
console.log(` - Truncated list: ${sections.hasTruncatedList ? '✅' : '❌'}`);
console.log(' 📈 Metrics values:');
console.log(` - Truncation rate: ${sections.truncationRate}`);
console.log(` - Avg tokens lost: ${sections.avgTokensLost}`);
console.log(` - Models tracked: ${sections.modelsTracked}`);
console.log(` - Data coverage: ${sections.dataCoverage}`);
// Verify all main sections are present
expect(sections.hasOverviewCards).toBe(true);
expect(sections.hasContextChart).toBe(true);
expect(sections.hasModelStats).toBe(true);
expect(sections.hasTruncatedList).toBe(true);
// Verify metrics are displayed (even if 0)
expect(sections.truncationRate).not.toBeNull();
expect(sections.avgTokensLost).not.toBeNull();
expect(sections.modelsTracked).not.toBeNull();
expect(sections.dataCoverage).not.toBeNull();
});
test('Time range selector works', async () => {
console.log('🕐 Testing time range selector...');
// Login first
await authHelper.ensureAuthenticated();
// Navigate to context overflow page
await page.goto(`${BASE_URL}/metrics/context-overflow`, {
waitUntil: 'domcontentloaded',
timeout: 30000
});
// Wait for page to load
await page.waitForSelector('.time-range-selector', { timeout: 10000 });
// Get initial active period
const initialPeriod = await page.evaluate(() => {
const activeBtn = document.querySelector('.time-range-btn.active');
return activeBtn ? activeBtn.getAttribute('data-period') : null;
});
console.log(` Initial period: ${initialPeriod}`);
// Try clicking different time periods
const periods = ['7d', '30d', '3m', '1y', 'all'];
for (const period of periods) {
console.log(` Testing period: ${period}`);
// Click the time range button
await page.click(`[data-period="${period}"]`);
// Wait a moment for the request to start
await new Promise(resolve => setTimeout(resolve, 500));
// Verify the button is now active
const isActive = await page.evaluate((p) => {
const btn = document.querySelector(`[data-period="${p}"]`);
return btn && btn.classList.contains('active');
}, period);
expect(isActive).toBe(true);
console.log(` ✅ ${period} button activated`);
}
});
test('API endpoint returns data', async () => {
console.log('🔌 Testing API endpoint...');
// Login first
await authHelper.ensureAuthenticated();
// Get cookies for authenticated request
const cookies = await page.cookies();
const sessionCookie = cookies.find(c => c.name === 'session');
if (!sessionCookie) {
console.log(' ⚠️ No session cookie found');
return;
}
// Make API request
const response = await page.evaluate(async (baseUrl) => {
try {
const res = await fetch(`${baseUrl}/metrics/api/context-overflow?period=30d`, {
method: 'GET',
credentials: 'include',
headers: {
'Accept': 'application/json'
}
});
const data = await res.json();
return {
status: res.status,
ok: res.ok,
data
};
} catch (error) {
return {
error: error.message
};
}
}, BASE_URL);
console.log(` API Response status: ${response.status}`);
console.log(` API Response OK: ${response.ok}`);
if (response.data) {
console.log(` API Response status field: ${response.data.status}`);
if (response.data.overview) {
console.log(' 📊 Overview data:');
console.log(` - Total requests: ${response.data.overview.total_requests}`);
console.log(` - Requests with context: ${response.data.overview.requests_with_context_data}`);
console.log(` - Truncated requests: ${response.data.overview.truncated_requests}`);
console.log(` - Truncation rate: ${response.data.overview.truncation_rate}%`);
}
if (response.data.model_stats) {
console.log(` 📊 Model stats count: ${response.data.model_stats.length}`);
}
if (response.data.context_limits) {
console.log(` 📊 Context limits count: ${response.data.context_limits.length}`);
}
if (response.data.chart_data) {
console.log(` 📊 Chart data points: ${response.data.chart_data.length}`);
}
}
// Verify response structure
expect(response.status).toBe(200);
expect(response.ok).toBe(true);
expect(response.data).toBeDefined();
expect(response.data.status).toBe('success');
expect(response.data.overview).toBeDefined();
});
});