feat(api): formats for uploaded images

This commit is contained in:
diced 2022-02-20 22:01:31 -08:00
parent 762d2927f7
commit 2b9af0e0de
No known key found for this signature in database
GPG key ID: 85AB64C74535D76E
9 changed files with 53 additions and 13 deletions

View file

@ -16,6 +16,9 @@
- Fast
- Built with Next.js & React
- Token protected uploading
- Image uploading
- URL shortening
- Text uploading
- Easy setup instructions on [docs](https://zipline.diced.tech/) (One command install `docker-compose up`)
## Installing

View file

@ -8,6 +8,7 @@
"build": "npm-run-all build:schema build:next",
"build:next": "next build",
"build:schema": "prisma generate --schema=prisma/schema.prisma",
"migrate:dev": "prisma migrate dev --create-only",
"start": "node server",
"lint": "next lint",
"seed": "ts-node --compiler-options \"{\\\"module\\\":\\\"commonjs\\\"}\" --transpile-only prisma/seed.ts"
@ -39,6 +40,7 @@
"react-redux": "^7.2.4",
"redux": "^4.1.0",
"redux-thunk": "^2.3.0",
"uuid": "^8.3.2",
"yup": "^0.32.9"
},
"devDependencies": {

View file

@ -0,0 +1,5 @@
-- CreateEnum
CREATE TYPE "ImageFormat" AS ENUM ('UUID', 'DATE', 'RANDOM');
-- AlterTable
ALTER TABLE "Image" ADD COLUMN "format" "ImageFormat" NOT NULL DEFAULT E'RANDOM';

View file

@ -0,0 +1,2 @@
-- AlterEnum
ALTER TYPE "ImageFormat" ADD VALUE 'NAME';

View file

@ -38,6 +38,13 @@ model Theme {
userId Int
}
enum ImageFormat {
UUID
DATE
RANDOM
NAME
}
model Image {
id Int @id @default(autoincrement())
file String
@ -47,6 +54,7 @@ model Image {
favorite Boolean @default(false)
embed Boolean @default(false)
invisible InvisibleImage?
format ImageFormat @default(RANDOM)
user User @relation(fields: [userId], references: [id])
userId Int
}

View file

@ -1,4 +1,4 @@
const NextServer = require('next/dist/server/next-server').default;
const next = require('next').default;
const defaultConfig = require('next/dist/server/config-shared').defaultConfig;
const { createServer } = require('http');
const { stat, mkdir } = require('fs/promises');
@ -41,18 +41,17 @@ async function run() {
await migrations();
await mkdir(config.uploader.directory, { recursive: true });
const app = new NextServer({
const app = next({
dir: '.',
dev,
quiet: dev,
customServer: false,
host: config.core.host,
quiet: !dev,
hostname: config.core.host,
port: config.core.port,
conf: Object.assign(defaultConfig, nextConfig),
});
await app.prepare();
await stat('./.next');
const handle = app.getRequestHandler();
const prisma = new PrismaClient();

View file

@ -126,4 +126,5 @@ module.exports = {
getStats,
log,
sizeOfDir,
shouldUseYarn,
};

View file

@ -6,6 +6,9 @@ import { createInvisImage, randomChars } from 'lib/util';
import { writeFile } from 'fs/promises';
import { join } from 'path';
import Logger from 'lib/logger';
import { ImageFormat, InvisibleImage } from '@prisma/client';
import { format as formatDate } from 'fecha';
import { v4 } from 'uuid';
const uploader = multer({
storage: multer.memoryStorage(),
@ -22,29 +25,46 @@ async function handler(req: NextApiReq, res: NextApiRes) {
});
if (!user) return res.forbid('authorization incorect');
if (user.ratelimited) return res.ratelimited();
if (!req.files) return res.error('no files');
if (req.files && req.files.length === 0) return res.error('no files');
const rawFormat = ((req.headers.format || '') as string).toUpperCase() || 'RANDOM';
const format: ImageFormat = Object.keys(ImageFormat).includes(rawFormat) && ImageFormat[rawFormat];
const files = [];
for (let i = 0; i !== req.files.length; ++i) {
const file = req.files[i];
if (file.size > zconfig.uploader[user.administrator ? 'admin_limit' : 'user_limit']) return res.error('file size too big');
if (file.size > zconfig.uploader[user.administrator ? 'admin_limit' : 'user_limit']) return res.error(`file[${i}] size too big`);
const ext = file.originalname.split('.').pop();
if (zconfig.uploader.disabled_extentions.includes(ext)) return res.error('disabled extension recieved: ' + ext);
const rand = randomChars(zconfig.uploader.length);
let fileName: string;
let invis;
switch (format) {
case ImageFormat.RANDOM:
fileName = randomChars(zconfig.uploader.length);
break;
case ImageFormat.DATE:
fileName = formatDate(new Date(), 'YYYY-MM-DD_HH:mm:ss');
break;
case ImageFormat.UUID:
fileName = v4();
break;
case ImageFormat.NAME:
fileName = file.originalname.split('.')[0];
break;
}
let invis: InvisibleImage;
const image = await prisma.image.create({
data: {
file: `${rand}.${ext}`,
file: `${fileName}.${ext}`,
mimetype: file.mimetype,
userId: user.id,
embed: !!req.headers.embed,
format,
},
});

View file

@ -6346,7 +6346,7 @@ util-deprecate@^1.0.1, util-deprecate@~1.0.1:
resolved "https://registry.npmjs.org/util-deprecate/-/util-deprecate-1.0.2.tgz"
integrity sha1-RQ1Nyfpw3nMnYvvS1KKJgUGaDM8=
uuid@8.3.2, uuid@^8.3.0:
uuid@8.3.2, uuid@^8.3.0, uuid@^8.3.2:
version "8.3.2"
resolved "https://registry.yarnpkg.com/uuid/-/uuid-8.3.2.tgz#80d5b5ced271bb9af6c445f21a1a04c606cefbe2"
integrity sha512-+NYs2QeMWy+GWFOEm9xnn6HCDp0l7QBD7ml8zLUmJ+93Q5NF0NocErnwkTkXVFNiX3/fpC6afS8Dhb/gz7R7eg==