mirror of
https://github.com/documenso/documenso.git
synced 2025-11-14 08:42:12 +10:00
92 lines
2.6 KiB
TypeScript
92 lines
2.6 KiB
TypeScript
// server/index.ts
|
|
import { Hono } from 'hono';
|
|
import { PDFDocument } from 'pdf-lib';
|
|
|
|
import { auth } from '@documenso/auth/server';
|
|
import { AppError } from '@documenso/lib/errors/app-error';
|
|
import { jobsClient } from '@documenso/lib/jobs/client';
|
|
import { createDocumentData } from '@documenso/lib/server-only/document-data/create-document-data';
|
|
import { putFile } from '@documenso/lib/universal/upload/put-file';
|
|
import { getPresignGetUrl } from '@documenso/lib/universal/upload/server-actions';
|
|
|
|
import { openApiTrpcServerHandler } from './trpc/hono-trpc-open-api';
|
|
import { reactRouterTrpcServer } from './trpc/hono-trpc-remix';
|
|
|
|
const app = new Hono();
|
|
|
|
// Auth server.
|
|
app.route('/api/auth', auth);
|
|
|
|
// API servers. Todo: Configure max durations, etc?
|
|
app.use('/api/jobs/*', jobsClient.getHonoApiHandler());
|
|
app.use('/api/v1/*', reactRouterTrpcServer); // Todo: ts-rest
|
|
app.use('/api/v2/*', async (c) => openApiTrpcServerHandler(c));
|
|
app.use('/api/trpc/*', reactRouterTrpcServer);
|
|
|
|
// Temp uploader.
|
|
app
|
|
.post('/api/file', async (c) => {
|
|
try {
|
|
const formData = await c.req.formData();
|
|
const file = formData.get('file') as File;
|
|
|
|
if (!file) {
|
|
return c.json({ error: 'No file provided' }, 400);
|
|
}
|
|
|
|
// Add file size validation
|
|
const MAX_FILE_SIZE = 10 * 1024 * 1024; // 10MB
|
|
if (file.size > MAX_FILE_SIZE) {
|
|
return c.json({ error: 'File too large' }, 400);
|
|
}
|
|
|
|
const arrayBuffer = await file.arrayBuffer();
|
|
|
|
const pdf = await PDFDocument.load(arrayBuffer).catch((e) => {
|
|
console.error(`PDF upload parse error: ${e.message}`);
|
|
|
|
throw new AppError('INVALID_DOCUMENT_FILE');
|
|
});
|
|
|
|
if (pdf.isEncrypted) {
|
|
throw new AppError('INVALID_DOCUMENT_FILE');
|
|
}
|
|
|
|
if (!file.name.endsWith('.pdf')) {
|
|
file.name = `${file.name}.pdf`;
|
|
}
|
|
|
|
const { type, data } = await putFile(file);
|
|
|
|
const result = await createDocumentData({ type, data });
|
|
|
|
return c.json(result);
|
|
} catch (error) {
|
|
console.error('Upload failed:', error);
|
|
return c.json({ error: 'Upload failed' }, 500);
|
|
}
|
|
})
|
|
.get('/api/file', async (c) => {
|
|
const key = c.req.query('key');
|
|
|
|
const { url } = await getPresignGetUrl(key || '');
|
|
|
|
const response = await fetch(url, {
|
|
method: 'GET',
|
|
});
|
|
|
|
if (!response.ok) {
|
|
throw new Error(`Failed to get file "${key}", failed with status code ${response.status}`);
|
|
}
|
|
|
|
const buffer = await response.arrayBuffer();
|
|
|
|
const binaryData = new Uint8Array(buffer);
|
|
|
|
return c.json({
|
|
binaryData,
|
|
});
|
|
});
|
|
|
|
export default app;
|