feat: implement album links endpoints
This commit is contained in:
parent
858f0ae4b0
commit
b0ab951a98
|
@ -66,7 +66,7 @@ model links {
|
|||
id Int @id @default(autoincrement())
|
||||
userId Int
|
||||
albumId Int
|
||||
identifier String
|
||||
identifier String @unique
|
||||
views Int @default(0)
|
||||
enabled Boolean @default(true)
|
||||
enableDownload Boolean @default(false)
|
||||
|
@ -74,7 +74,7 @@ model links {
|
|||
createdAt DateTime @default(now())
|
||||
editedAt DateTime?
|
||||
|
||||
@@unique([userId, albumId, identifier], name: "links_userid_albumid_identifier_unique")
|
||||
@@unique([userId, identifier], name: "links_userid_identifier_unique")
|
||||
}
|
||||
|
||||
model settings {
|
||||
|
@ -107,15 +107,13 @@ model tags {
|
|||
|
||||
model users {
|
||||
id Int @id @default(autoincrement())
|
||||
username String
|
||||
username String @unique
|
||||
password String
|
||||
enabled Boolean @default(true)
|
||||
isAdmin Boolean @default(false)
|
||||
apiKey String?
|
||||
apiKey String? @unique
|
||||
passwordEditedAt DateTime?
|
||||
apiKeyEditedAt DateTime?
|
||||
createdAt DateTime @default(now())
|
||||
editedAt DateTime?
|
||||
|
||||
@@unique([username, apiKey], name: "users_username_apikey_unique")
|
||||
}
|
||||
|
|
|
@ -4,7 +4,9 @@ import prisma from '../../../../structures/database';
|
|||
interface body {
|
||||
ip: string;
|
||||
}
|
||||
|
||||
export const middlewares = ['auth', 'admin'];
|
||||
|
||||
export const run = async (req: FastifyRequest, res: FastifyReply) => {
|
||||
if (!req.body) return res.status(400).send({ message: 'No body provided' });
|
||||
// const { username, password }: { username: string; password: string } = req.body;
|
||||
|
|
|
@ -0,0 +1,26 @@
|
|||
import type { FastifyReply } from 'fastify';
|
||||
import type { RequestWithUser } from '../../../../structures/interfaces';
|
||||
import prisma from '../../../../structures/database';
|
||||
|
||||
interface params {
|
||||
id: number;
|
||||
}
|
||||
|
||||
export const middlewares = ['auth'];
|
||||
|
||||
export const run = async (req: RequestWithUser, res: FastifyReply) => {
|
||||
const { id } = req.params as params;
|
||||
if (!id) return res.status(400).send({ message: 'Invalid id supplied' });
|
||||
|
||||
const links = await prisma.links.findMany({
|
||||
where: {
|
||||
albumId: id,
|
||||
userId: req.user.id
|
||||
}
|
||||
});
|
||||
|
||||
return res.send({
|
||||
message: 'Successfully retrieved links',
|
||||
links
|
||||
});
|
||||
};
|
|
@ -5,41 +5,39 @@ import { RequestWithUser } from '../../../../../structures/interfaces';
|
|||
interface body {
|
||||
identifier: string;
|
||||
}
|
||||
|
||||
export const middlewares = ['auth'];
|
||||
|
||||
export const run = async (req: RequestWithUser, res: FastifyReply) => {
|
||||
if (!req.params) return res.status(400).send({ message: 'No body provided' });
|
||||
const { identifier } = req.body as body;
|
||||
if (!identifier) return res.status(400).send({ message: 'No ip provided' });
|
||||
if (!identifier) return res.status(400).send({ message: 'No identifier provided' });
|
||||
|
||||
const link = await prisma.links.findFirst({
|
||||
where: {
|
||||
identifier,
|
||||
userId: req.user.id
|
||||
userId: req.user.id,
|
||||
identifier
|
||||
}
|
||||
});
|
||||
|
||||
if (!link) return res.status(400).send({ message: 'No link found' });
|
||||
|
||||
await prisma.links.delete({
|
||||
where: {
|
||||
links_userid_albumid_identifier_unique: {
|
||||
|
||||
links_userid_identifier_unique: {
|
||||
userId: req.user.id,
|
||||
identifier
|
||||
}
|
||||
}
|
||||
});
|
||||
|
||||
const albumLink = await prisma.albumsLinks.findFirst({
|
||||
where: {
|
||||
linkId: link.id
|
||||
}
|
||||
});
|
||||
|
||||
await prisma.albumsLinks.delete({
|
||||
where: {
|
||||
id: albumLink.id
|
||||
linkId: link.id
|
||||
}
|
||||
});
|
||||
|
||||
return res.send({
|
||||
message: 'Successfully banned the ip'
|
||||
message: 'Successfully deleted the link'
|
||||
});
|
||||
};
|
||||
|
|
|
@ -0,0 +1,44 @@
|
|||
import type { FastifyReply } from 'fastify';
|
||||
import type { RequestWithUser } from '../../../../structures/interfaces';
|
||||
import prisma from '../../../../structures/database';
|
||||
|
||||
interface body {
|
||||
identifier: string;
|
||||
enableDownload: boolean;
|
||||
expiresAt: Date;
|
||||
}
|
||||
|
||||
export const middlewares = ['auth'];
|
||||
|
||||
export const run = async (req: RequestWithUser, res: FastifyReply) => {
|
||||
if (!req.params) return res.status(400).send({ message: 'No body provided' });
|
||||
const { identifier, enableDownload, expiresAt } = req.body as body;
|
||||
if (!identifier) return res.status(400).send({ message: 'No identifier provided' });
|
||||
|
||||
const link = await prisma.links.findFirst({
|
||||
where: {
|
||||
userId: req.user.id,
|
||||
identifier
|
||||
}
|
||||
});
|
||||
|
||||
if (!link) return res.status(400).send({ message: 'No link found' });
|
||||
|
||||
const updateObj = {
|
||||
enableDownload: enableDownload || false,
|
||||
expiresAt // This one should be null if not supplied
|
||||
};
|
||||
|
||||
await prisma.links.update({
|
||||
where: {
|
||||
identifier
|
||||
},
|
||||
data: {
|
||||
...updateObj
|
||||
}
|
||||
});
|
||||
|
||||
return res.send({
|
||||
message: 'Successfully edited link'
|
||||
});
|
||||
};
|
|
@ -0,0 +1,61 @@
|
|||
import type { FastifyReply } from 'fastify';
|
||||
import prisma from '../../../../structures/database';
|
||||
import { RequestWithUser } from '../../../../structures/interfaces';
|
||||
import { getUniqueAlbumIdentifier } from '../../../../utils/Util';
|
||||
|
||||
interface body {
|
||||
albumId: number;
|
||||
identifier?: string;
|
||||
}
|
||||
|
||||
export const middlewares = ['auth'];
|
||||
|
||||
export const run = async (req: RequestWithUser, res: FastifyReply) => {
|
||||
if (!req.params) return res.status(400).send({ message: 'No body provided' });
|
||||
const { albumId } = req.body as body;
|
||||
if (!albumId) return res.status(400).send({ message: 'No albumId provided' });
|
||||
|
||||
const exists = await prisma.albums.findFirst({
|
||||
where: {
|
||||
id: albumId,
|
||||
userId: req.user.id
|
||||
}
|
||||
});
|
||||
|
||||
if (!exists) return res.status(400).send({ message: 'Album doesn\t exist' });
|
||||
|
||||
let { identifier } = req.body as body;
|
||||
if (identifier) {
|
||||
if (!req.user.isAdmin) return res.status(401).send({ message: 'Only administrators can create custom links' });
|
||||
if (!(/^[a-zA-Z0-9-_]+$/.test(identifier))) return res.status(400).send({ message: 'Only alphanumeric, dashes, and underscore characters are allowed' });
|
||||
|
||||
const identifierExists = await prisma.links.findFirst({
|
||||
where: {
|
||||
identifier
|
||||
}
|
||||
});
|
||||
if (identifierExists) return res.status(400).send({ message: 'Album with this identifier already exists' });
|
||||
} else {
|
||||
identifier = await getUniqueAlbumIdentifier();
|
||||
if (!identifier) return res.status(500).send({ message: 'There was a problem allocating a link for your album' });
|
||||
}
|
||||
|
||||
const insertObj = {
|
||||
identifier,
|
||||
userId: req.user.id,
|
||||
albumId,
|
||||
enabled: true,
|
||||
enableDownload: true,
|
||||
expiresAt: null,
|
||||
views: 0
|
||||
};
|
||||
|
||||
await prisma.links.create({
|
||||
data: insertObj
|
||||
});
|
||||
|
||||
return res.send({
|
||||
message: 'Successfully created link',
|
||||
data: insertObj
|
||||
});
|
||||
};
|
|
@ -1,35 +0,0 @@
|
|||
const Route = require('../../../structures/Route');
|
||||
|
||||
class linkDELETE extends Route {
|
||||
constructor() {
|
||||
super('/album/link/delete/:identifier', 'delete');
|
||||
}
|
||||
|
||||
async run(req, res, db, user) {
|
||||
const { identifier } = req.params;
|
||||
if (!identifier) return res.status(400).json({ message: 'Invalid identifier supplied' });
|
||||
|
||||
try {
|
||||
const link = await db.table('links')
|
||||
.where({ identifier, userId: user.id })
|
||||
.first();
|
||||
|
||||
if (!link) return res.status(400).json({ message: 'Identifier doesn\'t exist or doesnt\'t belong to the user' });
|
||||
|
||||
await db.table('links')
|
||||
.where({ id: link.id })
|
||||
.delete();
|
||||
await db.table('albumsLinks')
|
||||
.where({ linkId: link.id })
|
||||
.delete();
|
||||
} catch (error) {
|
||||
return super.error(res, error);
|
||||
}
|
||||
|
||||
return res.json({
|
||||
message: 'Successfully deleted link'
|
||||
});
|
||||
}
|
||||
}
|
||||
|
||||
module.exports = linkDELETE;
|
|
@ -1,38 +0,0 @@
|
|||
const Route = require('../../../structures/Route');
|
||||
|
||||
class linkEditPOST extends Route {
|
||||
constructor() {
|
||||
super('/album/link/edit', 'post');
|
||||
}
|
||||
|
||||
async run(req, res, db, user) {
|
||||
if (!req.body) return res.status(400).json({ message: 'No body provided' });
|
||||
const { identifier, enableDownload, expiresAt } = req.body;
|
||||
if (!identifier) return res.status(400).json({ message: 'Invalid album identifier supplied' });
|
||||
|
||||
/*
|
||||
Make sure the link exists
|
||||
*/
|
||||
const link = await db
|
||||
.table('links')
|
||||
.where({ identifier, userId: user.id })
|
||||
.first();
|
||||
if (!link) return res.status(400).json({ message: "The link doesn't exist or doesn't belong to the user" });
|
||||
|
||||
try {
|
||||
const updateObj = {
|
||||
enableDownload: enableDownload || false,
|
||||
expiresAt // This one should be null if not supplied
|
||||
};
|
||||
await db
|
||||
.table('links')
|
||||
.where({ identifier })
|
||||
.update(updateObj);
|
||||
return res.json({ message: 'Editing the link was successful', data: updateObj });
|
||||
} catch (error) {
|
||||
return super.error(res, error);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
module.exports = linkEditPOST;
|
|
@ -1,68 +0,0 @@
|
|||
const Route = require('../../../structures/Route');
|
||||
const Util = require('../../../utils/Util');
|
||||
|
||||
class linkPOST extends Route {
|
||||
constructor() {
|
||||
super('/album/link/new', 'post');
|
||||
}
|
||||
|
||||
async run(req, res, db, user) {
|
||||
if (!req.body) return res.status(400).json({ message: 'No body provided' });
|
||||
const { albumId } = req.body;
|
||||
if (!albumId) return res.status(400).json({ message: 'No album provided' });
|
||||
|
||||
/*
|
||||
Make sure the album exists
|
||||
*/
|
||||
const exists = await db
|
||||
.table('albums')
|
||||
.where({ id: albumId, userId: user.id })
|
||||
.first();
|
||||
if (!exists) return res.status(400).json({ message: 'Album doesn\t exist' });
|
||||
|
||||
let { identifier } = req.body;
|
||||
if (identifier) {
|
||||
if (!user.isAdmin) return res.status(401).json({ message: 'Only administrators can create custom links' });
|
||||
|
||||
if (!(/^[a-zA-Z0-9-_]+$/.test(identifier))) return res.status(400).json({ message: 'Only alphanumeric, dashes, and underscore characters are allowed' });
|
||||
|
||||
/*
|
||||
Make sure that the id doesn't already exists in the database
|
||||
*/
|
||||
const idExists = await db
|
||||
.table('links')
|
||||
.where({ identifier })
|
||||
.first();
|
||||
|
||||
if (idExists) return res.status(400).json({ message: 'Album with this identifier already exists' });
|
||||
} else {
|
||||
/*
|
||||
Try to allocate a new identifier in the database
|
||||
*/
|
||||
identifier = await Util.getUniqueAlbumIdentifier();
|
||||
if (!identifier) return res.status(500).json({ message: 'There was a problem allocating a link for your album' });
|
||||
}
|
||||
|
||||
try {
|
||||
const insertObj = {
|
||||
identifier,
|
||||
userId: user.id,
|
||||
albumId,
|
||||
enabled: true,
|
||||
enableDownload: true,
|
||||
expiresAt: null,
|
||||
views: 0
|
||||
};
|
||||
await db.table('links').insert(insertObj).wasMutated();
|
||||
|
||||
return res.json({
|
||||
message: 'The link was created successfully',
|
||||
data: insertObj
|
||||
});
|
||||
} catch (error) {
|
||||
return super.error(res, error);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
module.exports = linkPOST;
|
|
@ -1,22 +0,0 @@
|
|||
const Route = require('../../../structures/Route');
|
||||
|
||||
class linkPOST extends Route {
|
||||
constructor() {
|
||||
super('/album/:id/links', 'get');
|
||||
}
|
||||
|
||||
async run(req, res, db, user) {
|
||||
const { id } = req.params;
|
||||
if (!id) return res.status(400).json({ message: 'Invalid id supplied' });
|
||||
|
||||
const links = await db.table('links')
|
||||
.where({ albumId: id, userId: user.id });
|
||||
|
||||
return res.json({
|
||||
message: 'Successfully retrieved links',
|
||||
links
|
||||
});
|
||||
}
|
||||
}
|
||||
|
||||
module.exports = linkPOST;
|
Loading…
Reference in New Issue