feat(2FA): create API routes for admins
This commit is contained in:
1 parent
7c51e1ce4a
commit
ab73667d7b
7 files changed
+129
-2
No files matched your search
@@ -0,0 +1,29 @@
|
||||
import { z } from 'zod';
|
||||
import prisma from '@/lib/prisma';
|
||||
import { parseRequest } from '@/lib/request';
|
||||
import { json, unauthorized } from '@/lib/response';
|
||||
import { canEnforceTwoFactorAuthForEveryone } from '@/permissions';
|
||||
|
||||
export async function POST(request: Request) {
|
||||
const schema = z.object({ required: z.boolean() });
|
||||
|
||||
const { auth, body, error } = await parseRequest(request, schema);
|
||||
|
||||
if (error) {
|
||||
return error();
|
||||
}
|
||||
|
||||
if (!(await canEnforceTwoFactorAuthForEveryone(auth))) {
|
||||
return unauthorized();
|
||||
}
|
||||
|
||||
const { required } = body;
|
||||
|
||||
await prisma.client.appSetting.upsert({
|
||||
where: { key: 'twoFactorRequiredGlobal' },
|
||||
update: { value: String(required) },
|
||||
create: { key: 'twoFactorRequiredGlobal', value: String(required) },
|
||||
});
|
||||
|
||||
return json({ ok: true, required });
|
||||
}
|
||||
@@ -0,0 +1,29 @@
|
||||
import { z } from 'zod';
|
||||
import prisma from '@/lib/prisma';
|
||||
import { parseRequest } from '@/lib/request';
|
||||
import { json, unauthorized } from '@/lib/response';
|
||||
import { canEnforceTwoFactorAuthForTeam } from '@/permissions';
|
||||
|
||||
export async function POST(request: Request, { params }: { params: Promise<{ teamId: string }> }) {
|
||||
const schema = z.object({ required: z.boolean() });
|
||||
|
||||
const { auth, body, error } = await parseRequest(request, schema);
|
||||
|
||||
if (error) {
|
||||
return error();
|
||||
}
|
||||
|
||||
const { teamId } = await params;
|
||||
|
||||
if (!(await canEnforceTwoFactorAuthForTeam(auth, teamId))) {
|
||||
return unauthorized();
|
||||
}
|
||||
const { required } = body;
|
||||
|
||||
await prisma.client.team.update({
|
||||
where: { id: teamId },
|
||||
data: { twoFactorRequired: required },
|
||||
});
|
||||
|
||||
return json({ ok: true, teamId, twoFactorRequired: required });
|
||||
}
|
||||
@@ -0,0 +1,45 @@
|
||||
import { z } from 'zod';
|
||||
import prisma from '@/lib/prisma';
|
||||
import { parseRequest } from '@/lib/request';
|
||||
import { json, unauthorized } from '@/lib/response';
|
||||
import { updateUser } from '@/queries/prisma/user';
|
||||
import { canEnforceTwoFactorAuthForUser } from '@/permissions';
|
||||
|
||||
export async function GET(request: Request, { params }: { params: Promise<{ userId: string }> }) {
|
||||
const { auth, error } = await parseRequest(request);
|
||||
|
||||
if (error) {
|
||||
return error();
|
||||
}
|
||||
|
||||
if (!(await canEnforceTwoFactorAuthForUser(auth))) {
|
||||
return unauthorized();
|
||||
}
|
||||
|
||||
const { userId } = await params;
|
||||
|
||||
const twoFactor = await prisma.client.twoFactorAuth.findUnique({ where: { userId } });
|
||||
|
||||
return json({ isEnabled: twoFactor?.isEnabled ?? false });
|
||||
}
|
||||
|
||||
export async function POST(request: Request, { params }: { params: Promise<{ userId: string }> }) {
|
||||
const schema = z.object({ required: z.boolean() });
|
||||
|
||||
const { auth, body, error } = await parseRequest(request, schema);
|
||||
|
||||
if (error) {
|
||||
return error();
|
||||
}
|
||||
|
||||
if (!(await canEnforceTwoFactorAuthForUser(auth))) {
|
||||
return unauthorized();
|
||||
}
|
||||
|
||||
const { userId } = await params;
|
||||
const { required } = body;
|
||||
|
||||
const user = await updateUser(userId, { twoFactorRequired: required });
|
||||
|
||||
return json({ ok: true, userId: user.id, twoFactorRequired: required });
|
||||
}
|
||||
@@ -8,7 +8,11 @@ export async function canViewLink({ user, shareToken }: Auth, linkId: string) {
|
||||
return true;
|
||||
}
|
||||
|
||||
if (shareToken?.linkId === linkId || shareToken?.websiteId === linkId || shareToken?.linkIds?.includes(linkId)) {
|
||||
if (
|
||||
shareToken?.linkId === linkId ||
|
||||
shareToken?.websiteId === linkId ||
|
||||
shareToken?.linkIds?.includes(linkId)
|
||||
) {
|
||||
return true;
|
||||
}
|
||||
|
||||
|
||||
@@ -8,7 +8,11 @@ export async function canViewPixel({ user, shareToken }: Auth, pixelId: string)
|
||||
return true;
|
||||
}
|
||||
|
||||
if (shareToken?.pixelId === pixelId || shareToken?.websiteId === pixelId || shareToken?.pixelIds?.includes(pixelId)) {
|
||||
if (
|
||||
shareToken?.pixelId === pixelId ||
|
||||
shareToken?.websiteId === pixelId ||
|
||||
shareToken?.pixelIds?.includes(pixelId)
|
||||
) {
|
||||
return true;
|
||||
}
|
||||
|
||||
|
||||
@@ -90,3 +90,11 @@ export async function canCreateTeamWebsite({ user }: Auth, teamId: string) {
|
||||
export async function canViewAllTeams({ user }: Auth) {
|
||||
return user?.isAdmin ?? false;
|
||||
}
|
||||
|
||||
export async function canEnforceTwoFactorAuthForTeam({ user }: Auth, teamId: string) {
|
||||
if (!user) {
|
||||
return false;
|
||||
}
|
||||
|
||||
return user.isAdmin;
|
||||
}
|
||||
@@ -35,3 +35,11 @@ export async function canUpdateUser({ user }: Auth, viewedUserId: string) {
|
||||
export async function canDeleteUser({ user }: Auth) {
|
||||
return user?.isAdmin ?? false;
|
||||
}
|
||||
|
||||
export async function canEnforceTwoFactorAuthForEveryone({ user }: Auth) {
|
||||
return user?.isAdmin ?? false;
|
||||
}
|
||||
|
||||
export async function canEnforceTwoFactorAuthForUser({ user }: Auth) {
|
||||
return user?.isAdmin ?? false;
|
||||
}
|
||||
Reference in new issue
Block a user