- Converted web application from Next.js to SolidJS with Vite - Replaced React components with SolidJS components - Implemented GraphQL client using URQL - Added authentication, room, and chat components - Updated project structure and configuration files - Removed unnecessary Next.js and docs-related files - Added Docker support for web and API applications
112 lines
2.8 KiB
TypeScript
112 lines
2.8 KiB
TypeScript
import { PrismaClient } from '@prisma/client';
|
|
import { AuthenticationError, ForbiddenError } from 'apollo-server-express';
|
|
import { PubSub, withFilter } from 'graphql-subscriptions';
|
|
|
|
const prisma = new PrismaClient();
|
|
const pubsub = new PubSub();
|
|
|
|
export const MESSAGE_ADDED = 'MESSAGE_ADDED';
|
|
|
|
export const messageResolvers = {
|
|
Query: {
|
|
messages: async (_: any, { roomId }: { roomId: string }, context: any) => {
|
|
if (!context.userId) {
|
|
throw new AuthenticationError('You must be logged in to view messages');
|
|
}
|
|
|
|
// Check if user is a member of the room
|
|
const room = await prisma.room.findUnique({
|
|
where: { id: roomId },
|
|
include: { members: true },
|
|
});
|
|
|
|
if (!room) {
|
|
throw new ForbiddenError('Room not found');
|
|
}
|
|
|
|
const isMember = room.members.some(
|
|
(member: { id: string }) => member.id === context.userId
|
|
);
|
|
if (!isMember) {
|
|
throw new ForbiddenError('You are not a member of this room');
|
|
}
|
|
|
|
return prisma.message.findMany({
|
|
where: { roomId },
|
|
orderBy: { createdAt: 'asc' },
|
|
});
|
|
},
|
|
},
|
|
Mutation: {
|
|
sendMessage: async (
|
|
_: any,
|
|
{ content, roomId }: { content: string; roomId: string },
|
|
context: any
|
|
) => {
|
|
if (!context.userId) {
|
|
throw new AuthenticationError(
|
|
'You must be logged in to send a message'
|
|
);
|
|
}
|
|
|
|
// Check if user is a member of the room
|
|
const room = await prisma.room.findUnique({
|
|
where: { id: roomId },
|
|
include: { members: true },
|
|
});
|
|
|
|
if (!room) {
|
|
throw new ForbiddenError('Room not found');
|
|
}
|
|
|
|
const isMember = room.members.some(
|
|
(member: { id: string }) => member.id === context.userId
|
|
);
|
|
if (!isMember) {
|
|
throw new ForbiddenError('You are not a member of this room');
|
|
}
|
|
|
|
const message = await prisma.message.create({
|
|
data: {
|
|
content,
|
|
user: {
|
|
connect: { id: context.userId },
|
|
},
|
|
room: {
|
|
connect: { id: roomId },
|
|
},
|
|
},
|
|
include: {
|
|
user: true,
|
|
room: true,
|
|
},
|
|
});
|
|
|
|
pubsub.publish(MESSAGE_ADDED, { messageAdded: message, roomId });
|
|
|
|
return message;
|
|
},
|
|
},
|
|
Subscription: {
|
|
messageAdded: {
|
|
subscribe: withFilter(
|
|
() => pubsub.asyncIterator([MESSAGE_ADDED]),
|
|
(payload, variables) => {
|
|
return payload.roomId === variables.roomId;
|
|
}
|
|
),
|
|
},
|
|
},
|
|
Message: {
|
|
user: async (parent: any) => {
|
|
return prisma.user.findUnique({
|
|
where: { id: parent.userId },
|
|
});
|
|
},
|
|
room: async (parent: any) => {
|
|
return prisma.room.findUnique({
|
|
where: { id: parent.roomId },
|
|
});
|
|
},
|
|
},
|
|
};
|