Skip to content

Commit

Permalink
refactor: Conform custom background to RESTFUL standard
Browse files Browse the repository at this point in the history
  • Loading branch information
matthe815 committed Aug 1, 2024
1 parent 4f5dddb commit f3bf22d
Show file tree
Hide file tree
Showing 6 changed files with 144 additions and 122 deletions.
4 changes: 2 additions & 2 deletions src/components/edit/ImagesCard.jsx
Original file line number Diff line number Diff line change
Expand Up @@ -78,7 +78,7 @@ function ImagesCard ({ values, errors, handleChange, user }) {

values.background = `${user}.png`

return fetch('/api/account/background-upload', {
return fetch('/api/account/background', {
method: 'POST',
body: formData
})
Expand All @@ -94,7 +94,7 @@ function ImagesCard ({ values, errors, handleChange, user }) {
<img
alt='Background Preview'
className='img-thumbnail mx-auto d-block'
src={!Number.isNaN(Number(values.background.replace(/.*\//, '').replace(/\.png$/, ''))) ? 'api/account/uploaded-background' : `/img/background/${values.background}`}
src={!Number.isNaN(Number(values.background.replace(/.*\//, '').replace(/\.png$/, ''))) ? 'api/account/background' : `/img/background/${values.background}`}
/>
</Col>
</Row>
Expand Down
106 changes: 0 additions & 106 deletions src/pages/api/account/background-upload.js

This file was deleted.

112 changes: 112 additions & 0 deletions src/pages/api/account/background.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,112 @@
import { IncomingForm, Fields, Files } from 'formidable'
import { readFile } from 'node:fs/promises'
import path from 'node:path'
import { ncWithSession } from '@/lib/routing'
import HTTP_CODE from '@/lib/constants/httpStatusCodes'
import { saveFileBuffer } from '@/lib/utils/fileUtils'
import { CACHE } from '@/lib/constants/filePaths'
import prisma from '@/lib/db'
import { makeBanner } from '@/lib/riitag/banner'
import logger from '@/lib/logger'
import { Request, Response } from 'express'
import { setFileHeaders } from '../../../lib/utils/utils'
import fs from 'node:fs'

async function backgroundPost (request: Request, response: Response) {
if (request.socket.bytesRead > 2_107_638) {
return response
.status(HTTP_CODE.REQUEST_ENTITY_TOO_LARGE)
.send({ error: 'Request entity too large.' })
}

// @ts-ignore
const username: string = request.session?.username

if (!username) {
return response
.status(HTTP_CODE.UNAUTHORIZED)
.json({ error: 'Unauthorized' })
}

const data: unknown = await new Promise((resolve, reject): void => {
const form = new IncomingForm()

form.parse(request, (error, fields: Fields<string>, files: Files<string>): void => {
if (error) return reject(error)
return resolve({ fields, files })
})
})
.catch((error) => {
logger.error(error)
return response
.status(HTTP_CODE.BAD_REQUEST)
.send({ error: 'Invalid data' })
})

// @ts-ignore
const { file } = data.files

if (file.mimetype !== 'image/png') {
return response
.status(HTTP_CODE.BAD_REQUEST)
.send({ error: 'Invalid data' })
}

// Hard cap of 2MBs for custom backgrounds
if (file.size > 2_000_000) {
return response
.status(HTTP_CODE.REQUEST_ENTITY_TOO_LARGE)
.send({ error: 'Request entity too large.' })
}

let user: {username: string} = await prisma.user.findFirst({
where: {
username
},
select: {
username: true
}
})

const filepath: string = path.resolve(CACHE.BACKGROUNDS, `${user.username}.png`)
await saveFileBuffer(filepath, await readFile(file.filepath))

user = await prisma.user.update({
where: {
username
},
data: {
background: `${user.username}.png`
}
})

await makeBanner(user)
return response.status(HTTP_CODE.OK).send()
}

async function backgroundGet (request: Request, response: Response) {
// @ts-ignore
const username = request.session?.username

if (!username) {
return response
.status(HTTP_CODE.UNAUTHORIZED)
.json({ error: 'Unauthorized' })
}

response.setHeader('Content-Type', 'image/png')
setFileHeaders(response, `${username}.png`)
return response
.status(HTTP_CODE.OK)
.send(await fs.promises.readFile(path.resolve(CACHE.BACKGROUNDS, username + '.png')))
}

const handler = ncWithSession().post(backgroundPost).get(backgroundGet)

export const config = {
api: {
bodyParser: false
}
}

export default handler
12 changes: 0 additions & 12 deletions src/pages/api/account/uploaded-background.js
Original file line number Diff line number Diff line change
Expand Up @@ -6,19 +6,7 @@ import { setFileHeaders } from '@/lib/utils/utils';
import { CACHE } from '@/lib/constants/filePaths';

async function getMyUploadedBackground(request, response) {
const username = request.session?.username;

if (!username) {
return response
.status(HTTP_CODE.UNAUTHORIZED)
.json({ error: 'Unauthorized' });
}

response.setHeader('Content-Type', 'image/png');
setFileHeaders(response, `${username}.png`);
return response
.status(HTTP_CODE.OK)
.send(await fs.promises.readFile(path.resolve(CACHE.BACKGROUNDS, username + ".png")));
}

const handler = ncWithSession().get(getMyUploadedBackground);
Expand Down
4 changes: 2 additions & 2 deletions src/pages/edit.jsx
Original file line number Diff line number Diff line change
Expand Up @@ -155,12 +155,12 @@ function EditPage ({ tagInfo, user, language }) {
render ({ data, toastProps }) {
if (data.status !== 200) {
toastProps.type = 'error'
return 'An error occured, please try again later'
return 'An error occurred, please try again later'
}
return 'Saved!'
}
},
error: 'An error occured, please try again later.'
error: 'An error occurred, please try again later.'
}
)

Expand Down
28 changes: 28 additions & 0 deletions tsconfig.json
Original file line number Diff line number Diff line change
@@ -0,0 +1,28 @@
{
"compilerOptions": {
"lib": [
"dom",
"dom.iterable",
"esnext"
],
"allowJs": true,
"skipLibCheck": true,
"strict": false,
"noEmit": true,
"incremental": true,
"module": "esnext",
"esModuleInterop": true,
"moduleResolution": "node",
"resolveJsonModule": true,
"isolatedModules": true,
"jsx": "preserve"
},
"include": [
"next-env.d.ts",
"**/*.ts",
"**/*.tsx"
],
"exclude": [
"node_modules"
]
}

0 comments on commit f3bf22d

Please sign in to comment.