/** * @file Résolveurs des requêtes GraphQL. * @author akka vodol, ofacklam * @memberof GraphQL * @desc On ne définit dans ce fichier que les resolvers pour les types Query et Mutations. * En effet on exploite les default resolvers fournis par Apollo Server (le deuxième point) : * * > Explicit resolvers are not needed for every type, since Apollo Server provides a default that can perform two actions depending on the contents of parent: * > - Return the property from parent with the relevant field name * > - Calls a function on parent with the relevant field name and provide the remaining resolver parameters as arguments * https://www.apollographql.com/docs/apollo-server/v2/essentials/data.html#default * * Dans notre cas, le type de retour de chaque resolver est un objet JS (Group, Message, Request ou User) * défini dans un des fichiers de `./object_resolvers/` ; donc les méthodes des classes Group, Message, Request et User * dont le prototype est (parent, args, context: Context, info) sont utilisées comme resolvers de l'objet GraphQL respectif. */ import { AuthenticationError } from "apollo-server-core"; import { Context } from "./typeDefs/queries"; import { User } from "./object_resolvers/users"; import { Group, SimpleGroup, MetaGroup } from "./object_resolvers/groups"; import { Announcement, Event, PrivatePost, Question, Answer, Message } from "./object_resolvers/messages"; import { UserJoinGroup, GroupJoinMetagroup, GroupCoauthorEvent, Request } from "./object_resolvers/requests"; import { GroupCollection, GroupSet } from "./models/tools"; export const resolvers = { Query: { // User queries de base // @rights connectedOrOnplatal user: async function (root, args, context: Context): Promise<User> { if(context.models.auth.isConnectedOrOnplatal()) { return context.models.user.getUser(args.uid); } throw new AuthenticationError("Not connected or on-platal"); }, // Group queries de base // @rights connectedOrOnplatal group: async function (root, args, context: Context): Promise<Group> { if (context.models.auth.isConnectedOrOnplatal()) { return context.models.group.getGroup(args.gid); } throw new AuthenticationError("Not connected or on-platal"); }, // @rights connectedOrOnplatal simpleGroup: async function (obj, args, context: Context): Promise<SimpleGroup> { if (context.models.auth.isConnectedOrOnplatal()) { return context.models.group.getSimpleGroup(args.gid); } throw new AuthenticationError("Not connected or on-platal"); }, // @rights connectedOrOnplatal metaGroup: async function (obj, args, context: Context): Promise<MetaGroup> { if (context.models.auth.isConnectedOrOnplatal()) { return context.models.group.getMetaGroup(args.gid); } throw new AuthenticationError("Not connected or on-platal"); }, // Message queries de base //message -> not implemented -> message(mid: ID!): Message // @rights membre d'un groupe author ou d'un groupe recipient announcement: async function (root, args, context: Context): Promise<Announcement> { //TODO : verifier les autorisations throw "Not implemented"; return context.models.message.getAnnouncement(args.mid); throw new AuthenticationError("Not connected or on-platal"); }, // @rights membre d'un groupe author ou d'un groupe recipient event: async function (root, args, context: Context): Promise<Event> { //TODO : verifier les autorisations throw "Not implemented"; return context.models.message.getEvent(args.mid); throw new AuthenticationError("Not connected or on-platal"); }, // @rights membre du groupe recipient privatePost: async function (root, args, context: Context): Promise<PrivatePost> { //TODO : verifier les autorisations throw "Not implemented"; return context.models.message.getPrivatePost(args.mid); throw new AuthenticationError("Not connected or on-platal"); }, // @rights viewer du groupe recipient question: async function (root, args, context: Context): Promise<Question> { //TODO : verifier les autorisations throw "Not implemented"; return context.models.message.getQuestion(args.mid); throw new AuthenticationError("Not connected or on-platal"); }, // @rights viewer du groupe author answer: async function (root, args, context: Context): Promise<Answer> { //TODO : verifier les autorisations throw "Not implemented"; return context.models.message.getAnswer(args.mid); throw new AuthenticationError("Not connected or on-platal"); }, // Request queries de base //request -> not implemented -> request(rid: ID!): Request // @rights admin du groupe destinaire ou le user émetteur userJoinGroupRequest: async function (root, args, context: Context): Promise<UserJoinGroup> { //TODO : verifier les autorisations throw "Not implemented"; return context.models.request.getUserJoinGroupRequest(args.rid); throw new AuthenticationError("Not connected or on-platal"); }, // @rights admin du groupe émetteur ou destinataire groupJoinMetagroupRequest: async function (root, args, context: Context): Promise<GroupJoinMetagroup> { //TODO : verifier les autorisations throw "Not implemented"; return context.models.request.getGroupJoinMetagroupRequest(args.rid); throw new AuthenticationError("Not connected or on-platal"); }, // @rights admin du groupe émetteur ou destinataire groupCoauthorEventRequest: async function (root, args, context: Context): Promise<GroupCoauthorEvent> { //TODO : verifier les autorisations throw "Not implemented"; return context.models.request.getGroupCoauthorEventRequest(args.rid); throw new AuthenticationError("Not connected or on-platal"); }, // Tous les Messages visibles par un utilisateur(dont le uid, et donc les autorisations, est passé par context) // @rights member of groups allMessages: async function (root, args, context: Context): Promise<Message[]> { let groups = context.models.auth.groupsMember(); return context.models.message.getAllMessages(groups); }, // @rights member of groups allAnnouncements: async function (root, args, context: Context): Promise<Announcement[]> { let groups = context.models.auth.groupsMember(); return context.models.message.getAllAnnouncements(groups); }, // @rights member of groups allEvents: async function (root, args, context: Context): Promise<Event[]> { let groups = context.models.auth.groupsMember(); return context.models.message.getAllEvents(groups); }, // @rights member of groups allPrivatePosts: async function (root, args, context: Context): Promise<PrivatePost[]> { let groups = context.models.auth.groupsMember(); return context.models.message.getAllPrivatePosts(groups); }, // Tous les Groupes visibles par un utilisateur. // Correspondrait au sous - champ "viewerOf" de User, volontairement non - défini comme tel.Tous les autres cas de figure sont couverts par les sous - champs "<permission>Of" de User // @rights viewer of groups allGroups: async function (root, args, context: Context): Promise<Group[]> { let visibleGroupCollection = context.models.auth.groupsViewer(); return context.models.group.getAllGroupsByCollection(visibleGroupCollection); }, // @rights viewer of groups allSimpleGroups: async function (root, args, context: Context): Promise<SimpleGroup[]> { let visibleGroupCollection = context.models.auth.groupsViewer(); return context.models.group.getAllSimpleGroups(visibleGroupCollection.simpleGroups); }, // TOL // @rights connectedOrOnplatal searchTOL: async function (root, args, context: Context): Promise<User[]> { if (context.models.auth.isConnectedOrOnplatal()) { return context.models.user.searchTOL(args); } throw new AuthenticationError("Not connected or on-platal"); } }, Mutation: { // Groups - independent mutations // @rights authenticated editProfile: async function (root, args, context: Context): Promise<User> { if(context.models.auth.isAuthenticated()) { return context.models.user.editProfile(args); } throw new AuthenticationError("Not authenticated"); }, // Viewer mutations // @rights viewer likeGroup: async function (root, args, context: Context): Promise<boolean> { if (context.models.auth.isViewer(args.gid)) { return context.models.group.likeGroup(args.gid) } throw new AuthenticationError("Not a viewer"); }, // @rights viewer unlikeGroup: async function (root, args, context: Context): Promise<boolean> { if (context.models.auth.isViewer(args.gid)) { return context.models.group.unlikeGroup(args.gid) } throw new AuthenticationError("Not a viewer"); }, // @rights member d'un groupe author ou recipient userParticipate: async function (root, args, context: Context): Promise<boolean> { throw "Not implemented"; //TODO : Vérifier les autorisations return context.models.message.userParticipate(context.user.uid, args.forEvent); throw new AuthenticationError("Not a viewer"); }, // @rights member d'un groupe author ou recipient userUnparticipate: async function (root, args, context: Context): Promise<boolean> { throw "Not implemented"; //TODO : Vérifier les autorisations return context.models.message.userUnparticipate(context.user.uid, args.forEvent); throw new AuthenticationError("Not a viewer"); }, // @rights viewer userRequestJoinGroup: async function (root, args, context: Context): Promise<UserJoinGroup> { if(context.models.auth.isViewer(args.toGroup)) { return context.models.request.userRequestJoinGroup(args.toGroup, args.comment); } throw new AuthenticationError("Not a viewer"); }, // @rights viewer createQuestion: async function (root, args, context: Context): Promise<Question> { if (context.models.auth.isViewer(args.toGroup)) { return context.models.message.createQuestion(args.toGroup, args.title, args.content); } throw new AuthenticationError("Not a viewer"); }, // @rights viewer du groupe et author de la question editQuestion: async function (root, args, context: Context): Promise<Question> { throw "Not implemented"; // TODO : Vérifier qu'il est l'auteur de la question et viewer return context.models.message.editQuestion(args.questionToEdit, args.title, args.content); throw new AuthenticationError("Not a viewer"); }, // @rights viewer du groupe et author de la question removeQuestion: async function (root, args, context: Context): Promise<boolean> { throw "Not implemented"; // TODO : Vérifier qu'il est l'auteur de la question et viewer return context.models.message.removeQuestion(args.questionToRemove); throw new AuthenticationError("Not a viewer"); }, // Member mutations // @rights member userLeaveGroup: async function (root, args, context: Context): Promise<boolean> { if (context.models.auth.isMember(args.gid)) { return context.models.group.userLeaveGroup(args.gid); } throw new AuthenticationError("Not a member"); }, // @rights member createPrivatePost: async function (root, args, context: Context): Promise<PrivatePost> { if (context.models.auth.isMember(args.toGroup)) { return context.models.message.createPrivatePost(args.toGroup, args.title, args.content); } throw new AuthenticationError("Not a member"); }, // @rights member du groupe et author du post editPrivatePost: async function (root, args, context: Context): Promise<PrivatePost> { throw "Not implemented"; // TODO : Vérifier qu'il est l'auteur du post et member return context.models.message.editPrivatePost(args.privatePostToEdit, args.title, args.content); throw new AuthenticationError("Not a member"); }, // @rights member du groupe et author du post removePrivatePost: async function (root, args, context: Context): Promise<boolean> { throw "Not implemented"; // TODO : Vérifier qu'il est l'auteur du post et member return context.models.message.removePrivatePost(args.privatePostToRemove); throw new AuthenticationError("Not a member"); }, // Speaker mutations // @rights speaker writePostsSummary: async function (root, args, context: Context): Promise<boolean> { if (context.models.auth.isSpeaker(args.forGroup)) { return context.models.group.writePostsSummary(args.forGroup, args.content); } throw new AuthenticationError("Not a speaker"); }, // @rights speaker groupParticipate: async function (root, args, context: Context): Promise<boolean> { if (context.models.auth.isSpeaker(args.gid)) { return context.models.message.groupParticipate(args.gid, args.forEvent); } throw new AuthenticationError("Not a speaker"); }, // @rights speaker groupUnparticipate: async function (root, args, context: Context): Promise<boolean> { if (context.models.auth.isSpeaker(args.gid)) { return context.models.message.groupUnparticipate(args.gid, args.forEvent); } throw new AuthenticationError("Not a speaker"); }, // @rights speaker du groupe émetteur groupRequestCoauthorEvent: async function (root, args, context: Context): Promise<GroupCoauthorEvent> { if (context.models.auth.isSpeaker(args.fromGroup)) { return context.models.request.groupRequestCoauthorEvent(args.fromGroup, args.toGroup, args.forEvent, args.comment); } throw new AuthenticationError("Not a speaker"); }, // @rights speaker du groupe émetteur createAnnouncement: async function (root, args, context: Context): Promise<Announcement> { if (context.models.auth.isSpeaker(args.fromGroup)) { return context.models.message.createAnnouncement(args.fromGroup, new GroupSet(args.toGroups), args.title, args.content, args.forEvent); } throw new AuthenticationError("Not a speaker"); }, // @rights speaker du groupe émetteur editAnnouncement: async function (root, args, context: Context): Promise<Announcement> { throw "Not implemented"; // TODO : Vérifier les autorisations. return context.models.message.editAnnouncement(args.announcementToEdit, args.title, args.content, args.forEvent); throw new AuthenticationError("Not a speaker"); }, // @rights speaker du groupe émetteur removeAnnouncement: async function (root, args, context: Context): Promise<boolean> { throw "Not implemented"; // TODO : Vérifier les autorisations return context.models.message.removeAnnouncement(args.announcementToRemove); throw new AuthenticationError("Not a speaker"); }, // @rights speaker du groupe émetteur createEvent: async function (root, args, context: Context): Promise<Event> { if (context.models.auth.isSpeaker(args.fromGroup)) { return context.models.message.createEvent(args.fromGroup, new GroupSet(args.toGroups), args.title, args.content, args.location, args.startTime, args.endTime, args.forAnnouncement); } throw new AuthenticationError("Not a speaker"); }, // @rights speaker du groupe émetteur editEvent: async function (root, args, context: Context): Promise<Event> { throw "Not implemented"; // TODO : Vérifier les autorisations. return context.models.message.editEvent(args.eventToEdit, args.title, args.content, args.location, args.startTime, args.endTime, args.forAnnouncement); throw new AuthenticationError("Not a speaker"); }, // @rights speaker du groupe émetteur removeEvent: async function (root, args, context: Context): Promise<boolean> { throw "Not implemented"; // TODO : Vérifier les autorisations return context.models.message.removeEvent(args.eventToRemove); throw new AuthenticationError("Not a speaker"); }, // @rights speaker du groupe createAnswer: async function (root, args, context: Context): Promise<Answer> { throw "Not implemented"; // TODO : Vérifier les autorisations. return context.models.message.createAnswer(args.forQuestion, args.title, args.content); throw new AuthenticationError("Not a speaker"); }, // @rights speaker du groupe editAnswer: async function (root, args, context: Context): Promise<Answer> { throw "Not implemented"; // TODO : Vérifier les autorisations. return context.models.message.editAnswer(args.answerToEdit, args.title, args.content); throw new AuthenticationError("Not a speaker"); }, // @rights speaker du groupe removeAnswer: async function (root, args, context: Context): Promise<boolean> { throw "Not implemented"; // TODO : Vérifier les autorisations return context.models.message.removeAnswer(args.answerToRemove); throw new AuthenticationError("Not a speaker"); }, // Admin mutations // @rights admin of parent group createSubgroup: async function (root, args, context: Context): Promise<Group> { if(context.models.auth.isAdmin(args.fromGroup)) { return context.models.group.createSubgroup(args); } throw new AuthenticationError("Not an admin"); }, // @rights admin makeAdmin: async function (root, args, context: Context): Promise<User> { if (context.models.auth.isAdmin(args.forGroup)) { return context.models.group.makeAdmin(args.forGroup, args.uid); } throw new AuthenticationError("Not an admin"); }, // @rights admin unmakeAdmin: async function (root, args, context: Context): Promise<User> { if (context.models.auth.isAdmin(args.forGroup)) { return context.models.group.unmakeAdmin(args.forGroup, args.uid); } throw new AuthenticationError("Not an admin"); }, // @rights admin makeSpeaker: async function (root, args, context: Context): Promise<User> { if (context.models.auth.isAdmin(args.forGroup)) { return context.models.group.makeSpeaker(args.forGroup, args.uid); } throw new AuthenticationError("Not an admin"); }, // @rights admin unmakeSpeaker: async function (root, args, context: Context): Promise<User> { if (context.models.auth.isAdmin(args.forGroup)) { return context.models.group.unmakeSpeaker(args.forGroup, args.uid); } throw new AuthenticationError("Not an admin"); }, // @rights admin editGroup: async function (root, args, context: Context): Promise<Group> { if (context.models.auth.isAdmin(args.forGroup)) { return context.models.group.editGroup(args); } throw new AuthenticationError("Not an admin"); }, // @rights admin addVisibilityEdge: async function (root, args, context: Context): Promise<boolean> { if (context.models.auth.isAdmin(args.forGroup)) { return context.models.group.addVisibilityEdge(args.forGroup, args.visibleBy); } throw new AuthenticationError("Not an admin"); }, // @rights admin removeVisibilityEdge: async function (root, args, context: Context): Promise<boolean> { if (context.models.auth.isAdmin(args.forGroup)) { return context.models.group.removeVisibilityEdge(args.forGroup, args.visibleBy); } throw new AuthenticationError("Not an admin"); }, // @rights admin du groupe émetteur groupRequestJoinMetagroup: async function (root, args, context: Context): Promise<GroupJoinMetagroup> { if (context.models.auth.isAdmin(args.fromGroup)) { return context.models.request.groupRequestJoinMetagroup(args.fromGroup, args.toMetagroup, args.comment); } throw new AuthenticationError("Not an admin"); }, // @rights admin du groupe destinataire acceptUserJoinRequest: async function (root, args, context: Context): Promise<boolean> { let req = await UserJoinGroup.tryCreate(args.request); throw "Not implemented"; //TODO : Vérifier les autorisations //if (context.models.auth.isAdmin(req.to)) { return context.models.request.acceptUserJoinRequest(req, args.comment); throw new AuthenticationError("Not an admin"); }, // @rights admin du groupe destinataire acceptGroupJoinRequest: async function (root, args, context: Context): Promise<boolean> { let req = await GroupJoinMetagroup.tryCreate(args.request); throw "Not implemented"; //TODO : Vérifier les autorisations //if (context.models.auth.isAdmin(req.to)) { return context.models.request.acceptGroupJoinRequest(req, args.comment); throw new AuthenticationError("Not an admin"); }, // @rights admin du groupe destinataire refuseUserJoinRequest: async function (root, args, context: Context): Promise<boolean> { let req = await UserJoinGroup.tryCreate(args.request); throw "Not implemented"; //TODO : Vérifier les autorisations //if (context.models.auth.isAdmin(req.to)) { return context.models.request.refuseUserJoinRequest(req, args.comment); throw new AuthenticationError("Not an admin"); }, // @rights admin du groupe destinataire refuseGroupJoinRequest: async function (root, args, context: Context): Promise<boolean> { let req = await GroupJoinMetagroup.tryCreate(args.request); throw "Not implemented"; //TODO : Vérifier les autorisations //if (context.models.auth.isAdmin(req.to)) { return context.models.request.refuseGroupJoinRequest(req, args.comment); throw new AuthenticationError("Not an admin"); }, // @rights admin removeUser: async function (root, args, context: Context): Promise<User> { if(context.models.auth.isAdmin(args.fromGroup)) { return context.models.group.removeUser(args.fromGroup, args.uid); } throw new AuthenticationError("Not an admin"); }, // @rights admin du groupe destinataire acceptGroupCoauthorEventRequest: async function (root, args, context: Context): Promise<boolean> { // Pour l'instant, ce n'est pas a implémenter... let req = await GroupCoauthorEvent.tryCreate(args.request); throw "Not implemented"; //TODO : Vérifier les autorisations //if (context.models.auth.isAdmin(req.to)) { return context.models.request.acceptGroupCoauthorEventRequest(req, args.comment); throw new AuthenticationError("Not an admin"); }, // @rights admin du groupe destinataire refuseGroupCoauthorEventRequest: async function (root, args, context: Context): Promise<boolean> { // Pour l'instant, ce n'est pas a implémenter... let req = await GroupCoauthorEvent.tryCreate(args.request); throw "Not implemented"; //TODO : Vérifier les autorisations //if (context.models.auth.isAdmin(req.to)) { return context.models.request.refuseGroupCoauthorEventRequest(req, args.comment); throw new AuthenticationError("Not an admin"); }, // @rights admin du groupe censorQuestion: async function (root, args, context: Context): Promise<boolean> { throw "Not implemented"; //TODO : Vérifier les autorisations return context.models.message.censorQuestion(args.questionToCensor); throw new AuthenticationError("Not an admin"); }, // @rights admin du groupe censorAnswer: async function (root, args, context: Context): Promise<boolean> { throw "Not implemented"; //TODO : Vérifier les autorisations return context.models.message.censorAnswer(args.answerToCensor); throw new AuthenticationError("Not an admin"); }, // @rights admin du groupe censorPrivatePost: async function (root, args, context: Context): Promise<boolean> { throw "Not implemented"; //TODO : Vérifier les autorisations return context.models.message.censorPrivatePost(args.privatePostToCensor); throw new AuthenticationError("Not an admin"); }, // @rights admin d'un groupe author censorAnnouncement: async function (root, args, context: Context): Promise<boolean> { throw "Not implemented"; //TODO : Vérifier les autorisations return context.models.message.censorAnnouncement(args.announcementToCensor); throw new AuthenticationError("Not an admin"); }, // @rights admin d'un groupe author censorEvent: async function (root, args, context: Context): Promise<boolean> { throw "Not implemented"; //TODO : Vérifier les autorisations return context.models.message.censorEvent(args.eventToCensor); throw new AuthenticationError("Not an admin"); } } };