Migrate backend from PocketBase to Directus
Full cutover: auth, users, collection and friendships now run on Directus via @directus/sdk, with owner/visibility rules enforced by Directus permissions. - middleware: Directus session (directus_auth cookie) with token refresh - /login is Directus (email normalized to lowercase), new /register page (first/last name, username) backed by public registration - collection, friends and profile pages + all API endpoints ported; ownership and addressee-only accept/decline enforced by permissions - display names use first_name/last_name everywhere (nav, friends, profile) - PocketBase SDK, POCKETBASE_URL and pb_schema.json removed - README and compose updated for DIRECTUS_URL
This commit is contained in:
@@ -1,7 +1,9 @@
|
||||
import type { APIRoute } from "astro";
|
||||
import { updateItem } from "@directus/sdk";
|
||||
import { isLoggedIn } from "../../../lib/auth";
|
||||
|
||||
export const POST: APIRoute = async ({ request, locals }) => {
|
||||
if (!locals.pb.authStore.isValid) {
|
||||
if (!isLoggedIn(locals)) {
|
||||
return new Response(JSON.stringify({ error: "Unauthorized" }), {
|
||||
status: 401,
|
||||
headers: { "Content-Type": "application/json" },
|
||||
@@ -10,37 +12,41 @@ export const POST: APIRoute = async ({ request, locals }) => {
|
||||
|
||||
try {
|
||||
const { friendshipId } = await request.json();
|
||||
const id = Number(friendshipId);
|
||||
|
||||
if (!friendshipId) {
|
||||
return new Response(JSON.stringify({ error: "Missing friendship id" }), {
|
||||
status: 400,
|
||||
headers: { "Content-Type": "application/json" },
|
||||
});
|
||||
if (!id || Number.isNaN(id)) {
|
||||
return new Response(
|
||||
JSON.stringify({ error: "Missing friendship id" }),
|
||||
{
|
||||
status: 400,
|
||||
headers: { "Content-Type": "application/json" },
|
||||
},
|
||||
);
|
||||
}
|
||||
|
||||
const friendship = await locals.pb.collection("friendships").getOne(friendshipId);
|
||||
|
||||
// Only the addressee can decline
|
||||
if (friendship.addressee !== locals.pb.authStore.record!.id) {
|
||||
return new Response(JSON.stringify({ error: "Forbidden" }), {
|
||||
status: 403,
|
||||
headers: { "Content-Type": "application/json" },
|
||||
});
|
||||
}
|
||||
|
||||
await locals.pb.collection("friendships").update(friendshipId, {
|
||||
status: "declined",
|
||||
});
|
||||
// Only the addressee can decline — enforced by the Directus update
|
||||
// permission (addressee = $CURRENT_USER, status field only).
|
||||
await locals.directus!.request(
|
||||
updateItem("friendships", id, { status: "declined" }),
|
||||
);
|
||||
|
||||
return new Response(JSON.stringify({ success: true }), {
|
||||
status: 200,
|
||||
headers: { "Content-Type": "application/json" },
|
||||
});
|
||||
} catch (err) {
|
||||
} catch (err: any) {
|
||||
console.error("Decline friend failed:", err);
|
||||
return new Response(JSON.stringify({ error: "Failed to decline" }), {
|
||||
status: 500,
|
||||
headers: { "Content-Type": "application/json" },
|
||||
});
|
||||
const forbidden =
|
||||
err?.errors?.[0]?.extensions?.code === "FORBIDDEN" ||
|
||||
err?.response?.status === 403;
|
||||
return new Response(
|
||||
JSON.stringify({
|
||||
error: forbidden ? "Forbidden" : "Failed to decline",
|
||||
}),
|
||||
{
|
||||
status: forbidden ? 403 : 500,
|
||||
headers: { "Content-Type": "application/json" },
|
||||
},
|
||||
);
|
||||
}
|
||||
};
|
||||
|
||||
Reference in New Issue
Block a user