@communecter/cocolight-api-client 1.0.76 → 1.0.78

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@communecter/cocolight-api-client",
3
- "version": "1.0.76",
3
+ "version": "1.0.78",
4
4
  "description": "Client Axios simplifié pour l'API cocolight",
5
5
  "repository": {
6
6
  "type": "git",
@@ -2231,9 +2231,8 @@ export class BaseEntity<TServerData = any> {
2231
2231
  * - `connectTypeConnect` : valeur envoyée pour `connect()`
2232
2232
  * - `connectTypeDisconnect` : valeur envoyée pour `disconnect()`
2233
2233
  * @throws {ApiError} - Si le type d'entité est inconnu.
2234
- * @protected
2235
2234
  */
2236
- protected _getLinkMeta(): LinkMeta {
2235
+ _getLinkMeta(): LinkMeta {
2237
2236
  const map = {
2238
2237
  organizations: {
2239
2238
  linkType: "memberOf",
@@ -2,7 +2,7 @@
2
2
  import { ApiAuthenticationError } from "../error.js";
3
3
 
4
4
  import type ApiClient from "../ApiClient.js";
5
- import type { PersonRegisterData, AuthenticateUrlData, RefreshTokenUrlData, PasswordRecoveryData, ServerExchangeTokenData, ChangePasswordData, DeleteAccountData, UpdateSettingsData, UpdateBlockDescriptionData, UpdateBlockInfoData, UpdateBlockSocialData, UpdateBlockLocalityData, UpdateBlockSlugData, CheckData, ProfilImageData, ProfilBannerData, GetElementsAboutData, MulticonnectData, GetNewsData, GetNewsByIdData, AddNewsData, AddImageNewsData, AddFileNewsData, DeleteNewsData, UpdateNewsData, ShareNewsData, GetCommentsData, AddCommentsData, DeleteCommentsData, UpdateCommentsData, SearchTagsData, ShowVoteData, GlobalAutocompleteData, CityAutocompleteData, CityAutocompleteByCountryData, SuggestionInputData, GetProjectsNoAdminData, GetProjectsAdminData, GetPoisNoAdminData, GetPoisAdminData, GetOrganizationsNoAdminData, GetOrganizationsAdminData, GetMembersNoAdminData, GetMembersAdminData, GetFriendsAdminData, GetSubscriptionsData, GetSubscriptionsAdminData, GetSubscribersData, GetSubscribersAdminData, GetContributorsNoAdminData, GetContributorsAdminData, GetBadgesData, GetBadgesFiltersData, ConnectData, DisconnectData, GetElementsKeyData, GetFavorisData, DeleteFavorisData, AddFavorisData, AddOrganizationData, AddProjectData, AddPoiData, AddEventData, DeletePoiData, DeleteEventData, DeleteElementData, AddImageElementData, LinkValidateData, SearchMemberAutocompleteData, GetNotificationsData, GetNotificationsCountData, NotificationUpdateData, MarkNotificationAsReadData, ActivitypubSearchData, ActivitypubLinkData, ActivitypubGetCommunityData, GetBadgeData, AddBadgesData, AssignBadgesData, GetEventsData, ShareEventsData, InviteEventData, FollowData, GetCostumJsonData, GlobalAutocompleteCostumData, CostumEventRequestActorsData, CostumEventRequestSubeventsData, CostumEventRequestElementEventData, CostumEventRequestCategoriesData, CostumEventRequestDatesData, CostumEventRequestEventData, CostumEventRequestLinkTlToEventData, CostumEventRequestLoadContextTagData, GetGalleryData, GetAttendeesNoAdminData, GetAttendeesAdminData, CoformAnswersSearchData, CoformAnswersByIdData, AddVoteData, AddReportAbuseData, UpdatePathValueData } from "./EndpointApi.types.js";
5
+ import type { PersonRegisterData, AuthenticateUrlData, RefreshTokenUrlData, PasswordRecoveryData, ServerExchangeTokenData, ChangePasswordData, DeleteAccountData, UpdateSettingsData, UpdateBlockDescriptionData, UpdateBlockInfoData, UpdateBlockSocialData, UpdateBlockLocalityData, UpdateBlockSlugData, CheckData, ProfilImageData, ProfilBannerData, GetElementsAboutData, MulticonnectData, GetNewsData, GetNewsByIdData, AddNewsData, AddImageNewsData, AddFileNewsData, DeleteNewsData, UpdateNewsData, ShareNewsData, GetCommentsData, AddCommentsData, DeleteCommentsData, UpdateCommentsData, SearchTagsData, ShowVoteData, GlobalAutocompleteData, CityAutocompleteData, CityAutocompleteByCountryData, SuggestionInputData, GetProjectsNoAdminData, GetProjectsAdminData, GetPoisNoAdminData, GetPoisAdminData, GetOrganizationsNoAdminData, GetOrganizationsAdminData, GetMembersNoAdminData, GetMembersAdminData, GetFriendsAdminData, GetSubscriptionsData, GetSubscriptionsAdminData, GetSubscribersData, GetSubscribersAdminData, GetContributorsNoAdminData, GetContributorsAdminData, GetBadgesData, GetBadgesFiltersData, ConnectData, DisconnectData, GetElementsKeyData, GetFavorisData, DeleteFavorisData, AddFavorisData, AddOrganizationData, AddProjectData, AddPoiData, AddEventData, DeletePoiData, DeleteEventData, DeleteElementData, AddImageElementData, LinkValidateData, SearchMemberAutocompleteData, GetNotificationsData, GetNotificationsCountData, NotificationUpdateData, MarkNotificationAsReadData, ActivitypubSearchData, ActivitypubLinkData, ActivitypubGetCommunityData, GetBadgeData, AddBadgesData, AssignBadgesData, GetEventsData, ShareEventsData, InviteEventData, FollowData, GetCostumJsonData, GlobalAutocompleteCostumData, CostumEventRequestActorsData, CostumEventRequestSubeventsData, CostumEventRequestElementEventData, CostumEventRequestCategoriesData, CostumEventRequestDatesData, CostumEventRequestEventData, CostumEventRequestLinkTlToEventData, CostumEventRequestLoadContextTagData, GetGalleryData, GetAttendeesNoAdminData, GetAttendeesAdminData, CoformAnswersSearchData, CoformAnswersByIdData, AddVoteData, AddReportAbuseData, UpdatePathValueData, DeleteDocumentByContextData } from "./EndpointApi.types.js";
6
6
 
7
7
  /**
8
8
  * Classe EndpointApi générée automatiquement depuis endpoints-copie.json
@@ -1688,6 +1688,22 @@ export class EndpointApi {
1688
1688
  return this.callIsConnected("UPDATE_PATH_VALUE", data);
1689
1689
  }
1690
1690
 
1691
+ /**
1692
+ * Supprimer une image/document par contexte d’entité : Supprimer des documents associés à une entité dans un contexte spécifique
1693
+ * Constant : DELETE_DOCUMENT_BY_CONTEXT
1694
+ * @param data - Données envoyées à l'API
1695
+ * @returns Les données de réponse.
1696
+ * @throws {ApiResponseError} - En cas d'erreur détectée dans la réponse.
1697
+ * @throws {ApiAuthenticationError} - En cas d'erreur d'authentification.
1698
+ * @throws {Error} - En cas d'erreur inattendue.
1699
+ */
1700
+ async deleteDocumentByContext(data: DeleteDocumentByContextData): Promise<any> {
1701
+ if (!data || typeof data !== "object") {
1702
+ throw new TypeError("Le paramètre data doit être un objet.");
1703
+ }
1704
+ return this.callIsConnected("DELETE_DOCUMENT_BY_CONTEXT", data);
1705
+ }
1706
+
1691
1707
  }
1692
1708
 
1693
1709
  export default EndpointApi;
@@ -4870,3 +4870,32 @@ export interface UpdatePathValueData {
4870
4870
  };
4871
4871
  [k: string]: unknown;
4872
4872
  }
4873
+
4874
+
4875
+ export interface DeleteDocumentByContextData {
4876
+ /**
4877
+ * ID de l’utilisateur
4878
+ */
4879
+ parentId?: string;
4880
+ /**
4881
+ * Type de contexte de l’entité
4882
+ */
4883
+ parentType?: "citoyens" | "organizations" | "projects" | "events" | "poi";
4884
+ path: "communecter";
4885
+ /**
4886
+ * ID image/document à supprimer
4887
+ */
4888
+ ids?: string;
4889
+ pathParams?: {
4890
+ /**
4891
+ * ID du contexte de l’entité
4892
+ */
4893
+ contextId: string;
4894
+ /**
4895
+ * Type de contexte de l’entité
4896
+ */
4897
+ contextType: "citoyens" | "organizations" | "projects" | "events" | "poi";
4898
+ [k: string]: unknown;
4899
+ };
4900
+ [k: string]: unknown;
4901
+ }
package/src/api/News.ts CHANGED
@@ -163,12 +163,26 @@ export class News extends BaseEntity<NewsItemNormalized> {
163
163
  payload.idNews = this.id;
164
164
 
165
165
  let hasChanged = false;
166
- await this.callIsConnected(() => this.endpointApi.updateNews(payload as UpdateNewsData)) as any;
167
- // TODO : voir si j'ai ce qui faut dans data de UPDATE_NEWS pour mettre à jour #serverData
168
- // c'est dans data.object
169
- // if(data?.object){
170
- // this._serverData = { ...data.object };
166
+
167
+
168
+ // il faut que j'ai les ids des images et fichiers avant la mise à jour venant de serverData
169
+ // if (this._serverData?.mediaImg?.images && this._serverData?.mediaImg?.images.length > 0) {
170
+ // imagesIds = this._serverData.mediaImg.images.map((img: any) => img.id);
171
171
  // }
172
+
173
+ // if (this._serverData?.mediaFile?.files && this._serverData?.mediaFile?.files.length > 0) {
174
+ // filesIds = this._serverData.mediaFile.files.map((f: any) => f.id);
175
+ // }
176
+
177
+ // comparer avec this._draftData.mediaImg.images pour voir si des images ont été supprimées
178
+ // comparer avec this._draftData.mediaFile.files pour voir si des fichiers ont été supprimés
179
+
180
+
181
+ await this.callIsConnected(() => this.endpointApi.updateNews(payload as UpdateNewsData)) as any;
182
+
183
+ // TODO : je voudrais pouvoir comparer les images et fichiers pour supprimer ceux qui ont été enlevés
184
+ // avec deleteDocumentByContext() mais il faut que j'ai les ids des images et fichiers avant la mise à jour
185
+
172
186
  hasChanged = true;
173
187
  return hasChanged;
174
188
  };
@@ -262,6 +276,8 @@ export class News extends BaseEntity<NewsItemNormalized> {
262
276
  return dataFile;
263
277
  }
264
278
 
279
+
280
+
265
281
  /**
266
282
  * Supprimer une actualité : Supprime une actualité existante.
267
283
  * Constant : DELETE_NEWS
@@ -335,7 +335,7 @@ export class Organization extends BaseEntity<OrganizationItemNormalized> {
335
335
  const { toBeValidated, isAdmin, isAdminPending, isInviting, roles = [] } = options;
336
336
 
337
337
  if(this.isMe){
338
- finalData.pathParams = { type: this.getEntityType(), id: this.id };
338
+ finalData.pathParams = { id: this.id };
339
339
  // finalData.filters = {
340
340
  // [`links.memberOf.${this.id}`]: { "$exists": true },
341
341
  // [`links.memberOf.${this.id}.toBeValidated`]: { "$exists": false },
package/src/api/User.ts CHANGED
@@ -888,6 +888,191 @@ export class User extends BaseEntity<UserItemNormalized> {
888
888
  }
889
889
  return super.entityBySlug(slug);
890
890
  }
891
+
892
+ /**
893
+ * Valide les préconditions communes pour les méthodes de vérification de rôle.
894
+ * @private
895
+ * @param methodName - Nom de la méthode appelante (pour les messages d'erreur).
896
+ * @param expectedTypes - Types d'entité parent autorisés.
897
+ * @throws {ApiError} 401 - Si l'utilisateur n'est pas connecté.
898
+ * @throws {ApiError} 401 - Si l'utilisateur connecté n'est pas administrateur de l'entité parente.
899
+ * @throws {ApiError} 404 - Si l'utilisateur n'est pas enregistré.
900
+ * @throws {ApiError} 404 - Si l'entité parente n'est pas enregistrée.
901
+ * @throws {ApiError} 400 - Si le type d'entité parent n'est pas valide.
902
+ */
903
+ private _validateRoleCheckPreconditions(methodName: string, expectedTypes: string[]): void {
904
+ if (!this.userId) {
905
+ throw new ApiError(`Vous devez être connecté pour ${methodName}.`, 401);
906
+ }
907
+
908
+ if(!this.parent?.isAdmin()){
909
+ throw new ApiError("Vous devez être administrateur pour effectuer cette action.", 401);
910
+ }
911
+
912
+ if (!this.id) {
913
+ throw new ApiError(`${this.constructor.name} non enregistrée.`, 404);
914
+ }
915
+
916
+ if(!this.parent?.id){
917
+ throw new ApiError("L'entité parente n'est pas enregistrée.", 404);
918
+ }
919
+
920
+ if (!expectedTypes.includes(this.parent.getEntityType())) {
921
+ throw new ApiError(`L'entité doit être de type : ${expectedTypes.join(", ")}, reçu : ${this.parent.getEntityType()}`, 400);
922
+ }
923
+ }
924
+
925
+ /**
926
+ * Récupère le lien utilisateur pour l'entité parente.
927
+ * @private
928
+ * @returns Le lien utilisateur ou null.
929
+ */
930
+ private _getUserLinkForParent(): any {
931
+ const { linkType } = this.parent!._getLinkMeta();
932
+ const parentId = this.parent!.id;
933
+ if (!parentId) return null;
934
+ return this?.serverData?.links?.[linkType]?.[parentId] || null;
935
+ }
936
+
937
+ /**
938
+ * Vérifie si l'utilisateur est administrateur de l'entité parente.
939
+ *
940
+ * Cette méthode permet de vérifier si un utilisateur possède les droits d'administration
941
+ * sur l'organisation ou le projet parent. Elle est particulièrement utile après avoir
942
+ * récupéré des membres via `getMembers()` pour déterminer leur niveau de permissions.
943
+ *
944
+ * @returns `true` si l'utilisateur est administrateur de l'entité parente, `false` sinon.
945
+ *
946
+ * @throws {ApiError} 401 - Si l'utilisateur n'est pas connecté.
947
+ * @throws {ApiError} 401 - Si l'utilisateur connecté n'est pas administrateur de l'entité parente.
948
+ * @throws {ApiError} 404 - Si l'utilisateur n'est pas enregistré (pas d'ID).
949
+ * @throws {ApiError} 404 - Si l'entité parente n'est pas enregistrée (pas d'ID).
950
+ * @throws {ApiError} 400 - Si l'entité parente n'est pas de type "organizations" ou "projects".
951
+ *
952
+ * @example
953
+ * // Vérifier les admins d'une organisation
954
+ * const org = await me.organization({ slug: "openAtlas" });
955
+ * const members = await org.getMembers();
956
+ *
957
+ * for (const member of members.results) {
958
+ * if (member.getEntityType() === "citoyens") {
959
+ * if (member.isAdmin()) {
960
+ * console.log(`${member.data.name} est administrateur`);
961
+ * }
962
+ * }
963
+ * }
964
+ *
965
+ * @example
966
+ * // Récupérer uniquement les membres admins
967
+ * const org = await me.organization({ slug: "myOrg" });
968
+ * const adminMembers = await org.getMembers({}, { isAdmin: true });
969
+ *
970
+ * // Vérifier chaque admin
971
+ * for (const admin of adminMembers.results) {
972
+ * if (admin.getEntityType() === "citoyens" && admin.isAdmin()) {
973
+ * console.log(`${admin.data.name} a les droits admin`);
974
+ * }
975
+ * }
976
+ */
977
+ override isAdmin(): boolean {
978
+ this._validateRoleCheckPreconditions("isAdmin", ["organizations", "projects"]);
979
+ const userLink = this._getUserLinkForParent();
980
+ return this._validateUserLink(userLink) && userLink?.isAdmin === true && !userLink?.isAdminPending;
981
+ }
982
+
983
+ /**
984
+ * Vérifie si l'utilisateur est membre de l'organisation parente.
985
+ *
986
+ * Cette méthode permet de vérifier si un utilisateur est membre actif d'une organisation.
987
+ * Elle est utile pour déterminer si un utilisateur a accès aux ressources de l'organisation.
988
+ *
989
+ * @returns `true` si l'utilisateur est membre validé de l'organisation parente, `false` sinon.
990
+ *
991
+ * @throws {ApiError} 401 - Si l'utilisateur n'est pas connecté.
992
+ * @throws {ApiError} 401 - Si l'utilisateur connecté n'est pas administrateur de l'entité parente.
993
+ * @throws {ApiError} 404 - Si l'utilisateur n'est pas enregistré (pas d'ID).
994
+ * @throws {ApiError} 404 - Si l'entité parente n'est pas enregistrée (pas d'ID).
995
+ * @throws {ApiError} 400 - Si l'entité parente n'est pas de type "organizations".
996
+ *
997
+ * @example
998
+ * // Vérifier les membres d'une organisation
999
+ * const org = await me.organization({ slug: "myOrg" });
1000
+ * const members = await org.getMembers();
1001
+ *
1002
+ * for (const member of members.results) {
1003
+ * if (member.getEntityType() === "citoyens" && member.isMember()) {
1004
+ * console.log(`${member.data.name} est membre de l'organisation`);
1005
+ * }
1006
+ * }
1007
+ */
1008
+ override isMember(): boolean {
1009
+ this._validateRoleCheckPreconditions("isMember", ["organizations"]);
1010
+ const userLink = this._getUserLinkForParent();
1011
+ return this._validateUserLink(userLink);
1012
+ }
1013
+
1014
+ /**
1015
+ * Vérifie si l'utilisateur est contributeur du projet parent.
1016
+ *
1017
+ * Cette méthode permet de vérifier si un utilisateur est contributeur actif d'un projet.
1018
+ * Elle est utile pour déterminer si un utilisateur peut participer aux activités du projet.
1019
+ *
1020
+ * @returns `true` si l'utilisateur est contributeur validé du projet parent, `false` sinon.
1021
+ *
1022
+ * @throws {ApiError} 401 - Si l'utilisateur n'est pas connecté.
1023
+ * @throws {ApiError} 401 - Si l'utilisateur connecté n'est pas administrateur de l'entité parente.
1024
+ * @throws {ApiError} 404 - Si l'utilisateur n'est pas enregistré (pas d'ID).
1025
+ * @throws {ApiError} 404 - Si l'entité parente n'est pas enregistrée (pas d'ID).
1026
+ * @throws {ApiError} 400 - Si l'entité parente n'est pas de type "projects".
1027
+ *
1028
+ * @example
1029
+ * // Vérifier les contributeurs d'un projet
1030
+ * const project = await me.project({ slug: "myProject" });
1031
+ * const contributors = await project.getContributors();
1032
+ *
1033
+ * for (const contributor of contributors.results) {
1034
+ * if (contributor.getEntityType() === "citoyens" && contributor.isContributor()) {
1035
+ * console.log(`${contributor.data.name} est contributeur du projet`);
1036
+ * }
1037
+ * }
1038
+ */
1039
+ override isContributor(): boolean {
1040
+ this._validateRoleCheckPreconditions("isContributor", ["projects"]);
1041
+ const userLink = this._getUserLinkForParent();
1042
+ return this._validateUserLink(userLink);
1043
+ }
1044
+
1045
+ /**
1046
+ * Vérifie si l'utilisateur est participant de l'événement parent.
1047
+ *
1048
+ * Cette méthode permet de vérifier si un utilisateur est inscrit comme participant à un événement.
1049
+ * Elle est utile pour déterminer si un utilisateur a confirmé sa participation à l'événement.
1050
+ *
1051
+ * @returns `true` si l'utilisateur est participant validé de l'événement parent, `false` sinon.
1052
+ *
1053
+ * @throws {ApiError} 401 - Si l'utilisateur n'est pas connecté.
1054
+ * @throws {ApiError} 401 - Si l'utilisateur connecté n'est pas administrateur de l'entité parente.
1055
+ * @throws {ApiError} 404 - Si l'utilisateur n'est pas enregistré (pas d'ID).
1056
+ * @throws {ApiError} 404 - Si l'entité parente n'est pas enregistrée (pas d'ID).
1057
+ * @throws {ApiError} 400 - Si l'entité parente n'est pas de type "events".
1058
+ *
1059
+ * @example
1060
+ * // Vérifier les participants d'un événement
1061
+ * const event = await me.event({ slug: "myEvent" });
1062
+ * const attendees = await event.getAttendees();
1063
+ *
1064
+ * for (const attendee of attendees.results) {
1065
+ * if (attendee.getEntityType() === "citoyens" && attendee.isAttendee()) {
1066
+ * console.log(`${attendee.data.name} participe à l'événement`);
1067
+ * }
1068
+ * }
1069
+ */
1070
+ override isAttendee(): boolean {
1071
+ this._validateRoleCheckPreconditions("isAttendee", ["events"]);
1072
+ const userLink = this._getUserLinkForParent();
1073
+ return this._validateUserLink(userLink);
1074
+ }
1075
+
891
1076
  }
892
1077
 
893
1078
  // Incorporation des mixins dans User