e2e/specs/usage.spec.ts
Rama main · réplica de lectura del repositorio original.
import type { Page } from '@playwright/test';
import { test } from '../fixtures';
import type { AppHelper } from '../helpers/app';
import { generateRandomSlug, getUserData } from '../helpers/data';
import type { UsageHelper } from '../helpers/usage';
// Generous per-test budget: each test drives the full org/project/target/token setup through
// the UI before polling Insights.
test.describe.configure({ mode: 'serial', timeout: 120_000 });
type UsageReport = {
size: number;
map: Record<
string,
{
operation: string;
operationName: string;
fields: string[];
}
>;
operations: Array<{
operationMapKey: string;
timestamp: number;
execution: {
ok: boolean;
duration: number;
errorsTotal: number;
};
metadata: {
client: {
name?: string;
version: string;
};
};
}>;
};
function usageReport(client: { name?: string; version: string }): UsageReport {
return {
size: 1,
map: {
op1: {
operation: 'query ping { ping }',
operationName: 'ping',
fields: ['Query', 'Query.ping'],
},
},
operations: [
{
operationMapKey: 'op1',
timestamp: Date.now(),
execution: {
ok: true,
duration: 200_000_000,
errorsTotal: 0,
},
metadata: {
client,
},
},
],
};
}
async function createTargetAndToken(page: Page, app: AppHelper, usage: UsageHelper) {
const organizationSlug = generateRandomSlug();
const projectSlug = generateRandomSlug();
const targetSlug = 'development';
await app.createUserAndOrganization(getUserData(), organizationSlug);
await app.createProject(projectSlug);
await page.locator(`a[href="/${organizationSlug}/${projectSlug}/${targetSlug}"]`).click();
await app.waitForTargetPage(targetSlug);
const token = await usage.createRegistryAccessToken({
organizationSlug,
projectSlug,
targetSlug,
});
return {
organizationSlug,
projectSlug,
targetSlug,
token,
};
}
test.describe('usage reporting', () => {
test('usage report should be visible in Insights', async ({ page, app, usage }) => {
const target = await createTargetAndToken(page, app, usage);
await usage.sendUsageReport({
token: target.token,
report: usageReport({ name: 'ios', version: 'v1.2.3' }),
});
await page.goto(
`/${target.organizationSlug}/${target.projectSlug}/${target.targetSlug}/insights`,
);
await usage.expectInsightOperation('_ping');
await page.goto(
`/${target.organizationSlug}/${target.projectSlug}/${target.targetSlug}/insights/client/ios`,
);
await usage.expectInsightOperation('_ping');
await usage.expectInsightVersion('v1.2.3');
});
test('usage report with "unknown" client should be visible in Insights', async ({
page,
app,
usage,
}) => {
const target = await createTargetAndToken(page, app, usage);
await usage.sendUsageReport({
token: target.token,
report: usageReport({ name: 'unknown', version: 'v1.2.3' }),
});
await page.goto(
`/${target.organizationSlug}/${target.projectSlug}/${target.targetSlug}/insights`,
);
await usage.expectInsightOperation('_ping');
await page.goto(
`/${target.organizationSlug}/${target.projectSlug}/${target.targetSlug}/insights/client/unknown`,
);
await usage.expectInsightOperation('_ping');
await usage.expectInsightVersion('v1.2.3');
});
test('usage report with missing client name should be visible in Insights', async ({
page,
app,
usage,
}) => {
const target = await createTargetAndToken(page, app, usage);
await usage.sendUsageReport({
token: target.token,
report: usageReport({ name: undefined, version: 'v1.2.3' }),
});
await page.goto(
`/${target.organizationSlug}/${target.projectSlug}/${target.targetSlug}/insights`,
);
await usage.expectInsightOperation('_ping');
await page.goto(
`/${target.organizationSlug}/${target.projectSlug}/${target.targetSlug}/insights/client/unknown`,
);
await usage.expectInsightOperation('_ping');
await usage.expectInsightVersion('v1.2.3');
});
test('usage report with missing and "unknown" client names should be visible in Insights', async ({
page,
app,
usage,
}) => {
const target = await createTargetAndToken(page, app, usage);
await usage.sendUsageReport({
token: target.token,
report: {
size: 1,
map: {
op1: {
operation: 'query ping { ping }',
operationName: 'ping',
fields: ['Query', 'Query.ping'],
},
op2: {
operation: 'query pong { pong }',
operationName: 'pong',
fields: ['Query', 'Query.pong'],
},
},
operations: [
{
operationMapKey: 'op1',
timestamp: Date.now(),
execution: {
ok: true,
duration: 200_000_000,
errorsTotal: 0,
},
metadata: {
client: {
name: undefined,
version: 'vUndefined',
},
},
},
{
operationMapKey: 'op2',
timestamp: Date.now(),
execution: {
ok: true,
duration: 200_000_000,
errorsTotal: 0,
},
metadata: {
client: {
name: 'unknown',
version: 'vUnknown',
},
},
},
],
},
});
await page.goto(
`/${target.organizationSlug}/${target.projectSlug}/${target.targetSlug}/insights`,
);
await usage.expectInsightOperation('_ping');
await usage.expectInsightOperation('_pong');
await page.goto(
`/${target.organizationSlug}/${target.projectSlug}/${target.targetSlug}/insights/client/unknown`,
);
await usage.expectInsightOperation('_ping');
await usage.expectInsightOperation('_pong');
await usage.expectInsightVersion('vUndefined');
await usage.expectInsightVersion('vUnknown');
});
});