← back to Norma
app/api/social/connect/route.ts
78 lines
import { NextRequest, NextResponse } from 'next/server';
import { requireRole } from '@/lib/require-role';
import { storeSocialCredentials, disconnectSocial, PLATFORM_FIELDS } from '@/lib/credentials';
import { auditLog } from '@/lib/audit';
const VALID_PLATFORMS = ['twitter', 'bluesky', 'facebook', 'instagram'];
/**
* POST /api/social/connect
* Store credentials for a social platform.
* Body: { platform: string, credentials: Record<string, string> }
*/
export async function POST(request: NextRequest) {
const auth = requireRole(request, 'admin');
if (auth instanceof NextResponse) return auth;
const body = await request.json().catch(() => ({}));
const { platform, credentials } = body;
if (!platform || !VALID_PLATFORMS.includes(platform)) {
return NextResponse.json(
{ error: `Invalid platform. Must be one of: ${VALID_PLATFORMS.join(', ')}` },
{ status: 400 },
);
}
if (!credentials || typeof credentials !== 'object') {
return NextResponse.json({ error: 'credentials object is required' }, { status: 400 });
}
// Validate that at least one credential field is provided
const fields = PLATFORM_FIELDS[platform] || [];
const providedKeys = fields.map((f) => f.key).filter((k) => credentials[k]);
if (providedKeys.length === 0) {
return NextResponse.json(
{ error: `At least one credential field required for ${platform}` },
{ status: 400 },
);
}
await storeSocialCredentials(platform, credentials);
await auditLog('social.connected', 'social_account', platform, {
connectedBy: auth.username,
fieldsProvided: providedKeys,
});
return NextResponse.json({ success: true, platform, status: 'connected' });
}
/**
* DELETE /api/social/connect
* Disconnect a social platform — clears tokens.
* Body: { platform: string }
*/
export async function DELETE(request: NextRequest) {
const auth = requireRole(request, 'admin');
if (auth instanceof NextResponse) return auth;
const body = await request.json().catch(() => ({}));
const { platform } = body;
if (!platform || !VALID_PLATFORMS.includes(platform)) {
return NextResponse.json(
{ error: `Invalid platform. Must be one of: ${VALID_PLATFORMS.join(', ')}` },
{ status: 400 },
);
}
await disconnectSocial(platform);
await auditLog('social.disconnected', 'social_account', platform, {
disconnectedBy: auth.username,
});
return NextResponse.json({ success: true, platform, status: 'disconnected' });
}