File size: 1,966 Bytes
8a49743 |
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 |
import sharp from 'sharp';
import { client, collections } from '$lib/server/db';
import { generateId } from '$lib/utils/generateId';
import type { ClientSession } from 'mongodb';
import { error } from '@sveltejs/kit';
export async function generatePicture(
buffer: Buffer,
name: string,
opts?: { productId?: string; cb?: (session: ClientSession) => Promise<void> }
): Promise<void> {
const image = sharp(buffer);
const { width, height } = await image.metadata();
if (!width || !height) {
throw error(400, 'Invalid image: no height or width');
}
const formats: Array<{ width: number; height: number; data: Buffer }> = [];
if (width <= 2048 && height <= 2048) {
formats.push({
width,
height,
data: await image.toFormat('webp').toBuffer()
});
}
for (const size of [2048, 1024, 512]) {
if (width > size || height > size) {
const buffer = await image
.resize(width > height ? { width: size } : { height: size })
.toFormat('webp')
.toBuffer();
const metadata = await sharp(buffer).metadata();
formats.push({
width: metadata.width!,
height: metadata.height!,
data: buffer
});
}
}
const _id = generateId(name);
await client.withSession(async (session) => {
await collections.pictures.insertOne(
{
_id,
name,
storage: formats.map((format) => ({
_id: `${_id}-${format.width}x${format.height}`,
width: format.width,
height: format.height,
size: format.data.length
})),
...(opts?.productId && { productId: opts.productId }),
createdAt: new Date(),
updatedAt: new Date()
},
{ session }
);
await collections.picturesFs.insertMany(
formats.map(
(format) => ({
_id: `${_id}-${format.width}x${format.height}`,
createdAt: new Date(),
updatedAt: new Date(),
size: format.data.length,
data: format.data,
picture: _id
}),
{ session }
)
);
if (opts?.cb) {
await opts.cb(session);
}
});
}
|