This repository has been archived by the owner on Dec 12, 2024. It is now read-only.
-
-
Notifications
You must be signed in to change notification settings - Fork 2
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
* refactor(Logo): change colours and font * refactor(Ui): rename ui to components * feat: add shadcn/ui * feat(Web): add landing page * fix: minor bug fixes with importing * feat(Utils): add notFoundError class to handle 404 error message * feat: add not-found page redesign * refactor(Ui): move components outside src directory * feat(Components): add theme toggle * feat(Ui): add select menu * feat(Utils): add useful nextjs page types * feat: add theme toggle to pages * feat(Ui): add form components * refactor: add redesigned login page * feat(Login): add light mode * fix(Login): redirect error * refactor: move auth layout to @paperplane/components * fix(Login): user not redirected to correct domain * refactor: add redesigned reset page * feat(Ui): add dialog component * refactor(SignUp): add redesigned page * feat(Components): remove un-used modal * feat(SignUp): remove useless return statement * feat(Ui): add avatar component * feat(Ui): add sheet component * feat(Components): add redesigned navbars * feat(Ui): add table component * fix(Navbar): minor bug fixes * fix(Navbar): more bug fixes * refactor(Dashboard): add redesigned home page * feat(Ui): add skeleton component * feat: add redesigned changelog modal * feat(Ui): add toast component * feat(Ui): add switch component * feat(DashboardHome): make more responsive for mobile * feat(Ui): add checkbox component * feat(Api): add new url create route * refactor(ShorturlDashboard): add redesigned page * feat(AuditlogTable): update border color for darkmode * refactor: re-position files and components * feat(Ui): add tabs component * feat(Api): add password field to paste-bin create api * feat(Ui): add textarea component * refactor(DashboardPastebin): add redesigned page * feat(Components): remove un-used files * feat(Server): add new upload api endpoint * refactor(FilesDashboard): add redesigned page * fix(Server): minor bug fixes * feat(Ui): add tooltip component * fix(Api): minor bug fixes * feat(FilesDashboard): add grid view * fix(FilesDashboard): minor bug fixes * feat(DashboardSettings): add Api key section * feat(DashboardSettings): add settings form * feat(DashboardSettings): add embed settings * feat(DashboardSettingsApi): add embed settings to response * feat(Ui): add alert-dialog * feat(DashboardSettings): add big red buttons section * chore: remove old settings page * chore(Components): remove un-used files * refactor(Components): move glitch component to new location * fix(Navbar): onClick listener attached incorrectly * feat(Components): add admin layout * feat(AdminPanel): add lib * feat(AdminPanel): add stats section * feat(AdminPanel): add auditlog * refactor(AdminPanel): add new page design * feat(Dashboard): add alert dialog for bulk delete * feat(AdminUserPanel): add user table * feat(Server): small change to api * feat(Ui): add scroll-area component * feat(AdminUserPanel): add edit dialog * fix(UpdateDialog): minor bug fixes * fix(UpdateDialog): minor bug fixes * fix(UpdateDialog): minor bug fixes * fix: critical bug fixes * feat(AdminUserPanel): add create dialog * refactor(AdminUserPanel): add redesigned page * feat(Api): add auth mode api * feat(AdminPanelSettings): add authMode component * feat(Server): update settings api * feat(AdminPanelSettings): add settings form * fix: bug fixes * feat(AdminPanelSettings): add big red buttons component * chore: remove un-used imports * feat(AdminPanelSettings): add sign up domain dialog * feat(AdminPanelSettings): add invite dialog * feat(AdminPanelSettings): add backups dialog * refactor(AdminPanelSettings): add redesigned page * fix: critical bug fix * refactor(FilesAuth): add redesigned page * refactor(BinAuth): add redesigned page * chore: remove un-used files * refactor(PasteBin): add redesigned page * feat(Files): add redesigned page * chore: remove un-used files * chore: regen lockfile * fix: add missing progress circle
- Loading branch information
Showing
249 changed files
with
11,617 additions
and
7,556 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,31 @@ | ||
import type { Response, Request } from "express"; | ||
import { Auth } from "../../../lib/Auth.js"; | ||
import type { Middleware, RequestMethods } from "../../../lib/types.js"; | ||
import type Server from "../../../Server.js"; | ||
|
||
export default async function handler(server: Server, req: Request, res: Response) { | ||
if (req.method === "GET") { | ||
res.send(server.envConfig.authMode); | ||
return; | ||
} | ||
|
||
if (req.method === "POST") { | ||
try { | ||
const data = req.body as { mode: "2fa" | "password" }; | ||
if (!["2fa", "password"].includes(data.mode)) { | ||
res.status(400).send({ message: "Invalid mode provided" }); | ||
return; | ||
} | ||
|
||
if (server.envConfig.authMode !== data.mode) await server.domains.resetAuth(); | ||
server.adminAuditLogs.register("Default Settings Update", "N/A"); | ||
res.sendStatus(204); | ||
} catch (err) { | ||
server.logger.fatal(`[AUTH-MODE:POST]: Fatal error while creating a new PaperPlane account `, err); | ||
res.status(500).send({ message: "Internal server error occured, please try again later." }); | ||
} | ||
} | ||
} | ||
|
||
export const methods: RequestMethods[] = ["get", "post"]; | ||
export const middleware: Middleware[] = [Auth.adminMiddleware.bind(Auth)]; |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,38 @@ | ||
import type { Response } from "express"; | ||
import { Auth } from "../../../lib/Auth.js"; | ||
import { type DashboardRequest, type Middleware, type RequestMethods } from "../../../lib/types.js"; | ||
import { Utils } from "../../../lib/utils.js"; | ||
import type Server from "../../../Server.js"; | ||
|
||
export default async function handler(server: Server, req: DashboardRequest, res: Response) { | ||
if (!req.locals.domain) { | ||
res.status(500).send({ message: "Internal server error, please try again later." }); | ||
return; | ||
} | ||
|
||
const { name, visible, url } = req.body; | ||
if (typeof url !== "string" || typeof visible !== "boolean") { | ||
res.status(400).send({ message: "No shorturl data provided" }); | ||
return; | ||
} | ||
|
||
const links = await server.prisma.url.findMany({ where: { domain: req.locals.domain.domain } }); | ||
const strategy = req.locals.domain.nameStrategy === "name" ? "id" : req.locals.domain.nameStrategy; | ||
let path = typeof name === "string" ? name : ""; | ||
|
||
if (!path.length || links.find((link) => link.id === path)) { | ||
path = Utils.generateId(strategy, req.locals.domain.nameLength) as string; | ||
while (links.find((link) => link.id === path)) path = Utils.generateId(strategy, req.locals.domain.nameLength) as string; | ||
} | ||
|
||
try { | ||
await server.prisma.url.create({ data: { date: new Date(), url, id: path, visible, domain: req.locals.domain.domain } }); | ||
res.send(`${Utils.getProtocol()}${req.locals.domain.domain}/r/${path}`); | ||
} catch (err) { | ||
server.logger.fatal(`[UPLOAD:POST]: Fatal error while uploading a shorturl`, err); | ||
res.status(500).send({ message: "Internal server error occured, please try again later." }); | ||
} | ||
} | ||
|
||
export const methods: RequestMethods[] = ["post"]; | ||
export const middleware: Middleware[] = [Auth.userMiddleware.bind(Auth)]; |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,85 @@ | ||
import type { Response } from "express"; | ||
import { Auth, Domain, type DashboardRequest, type Middleware, type RequestMethods, Utils } from "../../lib/index.js"; | ||
import formidable from "formidable"; | ||
import type Server from "../../Server.js"; | ||
|
||
export default async function handler(server: Server, req: DashboardRequest, res: Response) { | ||
if (!req.locals.domain) { | ||
res.status(500).send({ message: "Internal server error, please try again later." }); | ||
return; | ||
} | ||
|
||
const form = formidable({ | ||
filter: (part) => fileFilter(part, req.locals.domain), | ||
filename: (name, ext) => `${Auth.generateToken(32)}${ext}`, | ||
uploadDir: req.locals.domain.filesPath, | ||
keepExtensions: true, | ||
maxFileSize: getSize(req.locals.domain.uploadSize), | ||
maxFieldsSize: getSize(req.locals.domain.maxStorage === 0 ? 0 : req.locals.domain.maxStorage - req.locals.domain.storage) | ||
}); | ||
|
||
try { | ||
const [fields, files] = await form.parse(req); | ||
const uploadedFiles = files.file; | ||
if (!uploadedFiles) { | ||
res.status(400).send({ errors: [{ field: "upload", code: "MISSING_UPLOAD_FILES", message: "Missing uploaded files." }] }); | ||
return; | ||
} | ||
|
||
const name = fields.name?.[0]; | ||
const password = fields.password?.[0]; | ||
const visible = fields.visible?.[0]; | ||
if (uploadedFiles.length === 1) { | ||
const file = await req.locals.domain.registerUpload(uploadedFiles[0], { name, password, visible: visible === "true" ? true : false }); | ||
const fileUrl = `${Utils.getProtocol()}${req.locals.domain}/files/${file}`; | ||
res.send({ url: fileUrl, files: { [uploadedFiles[0].originalFilename!]: fileUrl } }); | ||
return; | ||
} | ||
|
||
const registedFiles = await Promise.all( | ||
uploadedFiles.map(async (file) => ({ url: await req.locals.domain.registerUpload(file), name: file.originalFilename! })) | ||
); | ||
res.send({ | ||
url: registedFiles[0], | ||
files: registedFiles | ||
.map((file) => ({ [file.name]: `${Utils.getProtocol()}${req.locals.domain}/files/${file.url}` })) | ||
.reduce((a, b) => ({ ...a, ...b }), {}) | ||
}); | ||
} catch (err) { | ||
server.logger.fatal(`[UPLOAD:POST]: Fatal error while uploading a file`, err); | ||
res.status(500).send({ | ||
errors: [{ field: undefined, code: "INTERNAL_ERROR", message: "Internal server error occured, please try again later." }] | ||
}); | ||
} | ||
} | ||
|
||
/** | ||
* Filters out disallowed files | ||
* @param part The formidable content part | ||
* @param domain The domain the upload is coming from | ||
* @returns | ||
*/ | ||
const fileFilter = (part: formidable.Part, domain: Domain) => { | ||
const { extensions, extensionsMode, disabled } = domain; | ||
if (disabled || !part.originalFilename || !part.mimetype) return false; | ||
|
||
const ext = part.originalFilename.split(".").filter(Boolean).slice(1).join("."); | ||
switch (extensionsMode) { | ||
case "block": | ||
if (extensions.includes(ext)) return false; | ||
break; | ||
case "pass": | ||
if (!extensions.includes(ext)) return false; | ||
break; | ||
} | ||
|
||
return true; | ||
}; | ||
|
||
const getSize = (size: number): number | undefined => { | ||
if (size < 0) return 0; | ||
return size === 0 ? undefined : size; | ||
}; | ||
|
||
export const methods: RequestMethods[] = ["post"]; | ||
export const middleware: Middleware[] = [Auth.userApiKeyMiddleware.bind(Auth)]; |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Oops, something went wrong.