working error

This commit is contained in:
Nate Kelley 2025-10-02 16:31:53 -06:00
parent f47891003e
commit d2c6328259
No known key found for this signature in database
GPG Key ID: FD90372AB8D98B4F
5 changed files with 50 additions and 53 deletions

View File

@ -1,19 +1,21 @@
import { chromium } from 'playwright';
import { type Browser, chromium, type Page } from 'playwright';
import { env } from '@/env';
import { getSupabaseServerClient } from '@/integrations/supabase/server';
export const browserLogin = async ({
export const browserLogin = async <T = Buffer<ArrayBufferLike>>({
accessToken,
width,
height,
fullPath,
request,
callback,
}: {
accessToken: string;
width: number;
height: number;
fullPath: string;
request: Request;
callback: ({ page, browser }: { page: Page; browser: Browser }) => Promise<T>;
}) => {
const supabase = getSupabaseServerClient();
const jwtPayload = JSON.parse(Buffer.from(accessToken.split('.')[1], 'base64').toString());
@ -63,17 +65,25 @@ export const browserLogin = async ({
const page = await context.newPage();
const fullPathWithOrigin = `${origin}${fullPath}`;
let pageError: Error | null = null;
page.on('console', (msg) => {
const hasError = msg.type() === 'error';
if (hasError) {
browser.close();
throw new Error(`Error in browser: ${msg.text()}`);
const text = msg.text();
// React logs errors to console even when caught by error boundaries
if (msg.type() === 'error' && (text.includes('Error:') || text.includes('occurred in'))) {
pageError = new Error(`Page error: ${text}`);
}
});
await page.goto(fullPathWithOrigin, { waitUntil: 'networkidle' });
return { context, browser, page };
const result = await callback({ page, browser });
if (pageError) {
throw pageError;
}
return { result };
} catch (error) {
console.error('Error logging in to browser', error);
await browser.close();

View File

@ -0,0 +1,13 @@
export const createScreenshotResponse = ({
screenshotBuffer,
}: {
screenshotBuffer: Buffer<ArrayBufferLike>;
}) => {
if (!screenshotBuffer) {
throw new Error('Screenshot buffer is required');
}
return new Response(new Uint8Array(screenshotBuffer), {
headers: { 'Content-Type': 'image/png', 'Content-Length': screenshotBuffer.length.toString() },
});
};

View File

@ -1,5 +0,0 @@
import { z } from 'zod';
export const GetScreenshotRequestSharedSchema = z.object({});
export type GetScreenshotRequestShared = z.infer<typeof GetScreenshotRequestSharedSchema>;

View File

@ -1,7 +1,6 @@
import { createFileRoute } from '@tanstack/react-router';
import { prefetchGetMetric } from '@/api/buster_rest/metrics';
import { useGetUserBasicInfo } from '@/api/buster_rest/users/useGetUserInfo';
import { Route as ScreenshotsRoute } from '../_content';
import { GetMetricScreenshotQuerySchema } from '../metrics.$metricId.index';
export const Route = createFileRoute('/screenshots/_content/metrics/$metricId/content')({
@ -14,7 +13,7 @@ export const Route = createFileRoute('/screenshots/_content/metrics/$metricId/co
id: params.metricId,
version_number: search.version_number,
});
if (!res || true) {
if (!res) {
throw new Error('Metric not found');
}
return {

View File

@ -1,11 +1,10 @@
import { createServerFileRoute } from '@tanstack/react-start/server';
import { z } from 'zod';
import { browserLogin } from '@/api/server-functions/screenshots/browser-login';
import { browserLogin } from '@/api/server-functions/browser-login';
import { createScreenshotResponse } from '@/api/server-functions/screenshot-helpers';
import { getSupabaseServerClient } from '@/integrations/supabase/server';
import { createHrefFromLink } from '@/lib/routes';
const isDev = import.meta.env.DEV;
export const GetMetricScreenshotParamsSchema = z.object({
metricId: z.string(),
});
@ -36,7 +35,8 @@ export const ServerRoute = createServerFileRoute('/screenshots/metrics/$metricId
Object.fromEntries(new URL(request.url).searchParams)
);
const { browser, page } = await browserLogin({
try {
const { result: screenshotBuffer } = await browserLogin({
accessToken,
width,
height,
@ -46,33 +46,15 @@ export const ServerRoute = createServerFileRoute('/screenshots/metrics/$metricId
search: { version_number, type, width, height },
}),
request,
});
try {
callback: async ({ page }) => {
const screenshotBuffer = await page.screenshot({
type,
});
if (!isDev) {
return new Response(
JSON.stringify({
success: true,
}),
{
status: 200,
headers: {
'Content-Type': 'application/json',
},
}
);
}
return new Response(new Uint8Array(screenshotBuffer), {
headers: {
'Content-Type': 'image/png',
'Content-Length': screenshotBuffer.length.toString(),
return screenshotBuffer;
},
});
return createScreenshotResponse({ screenshotBuffer });
} catch (error) {
console.error('Error capturing metric screenshot', error);
return new Response(
@ -81,8 +63,6 @@ export const ServerRoute = createServerFileRoute('/screenshots/metrics/$metricId
}),
{ status: 500, headers: { 'Content-Type': 'application/json' } }
);
} finally {
await browser.close();
}
},
});