From 5c3154c74527425dd719e63d55419370d8f1fc55 Mon Sep 17 00:00:00 2001 From: Yevheniy Oliynyk Date: Sat, 29 Jul 2023 19:36:11 +0300 Subject: [PATCH] notifications API --- src/index.ts | 4 ++ src/notifications/index.ts | 50 ++++++++++++++++++++++ tests/notifications/api.test.ts | 73 +++++++++++++++++++++++++++++++++ 3 files changed, 127 insertions(+) create mode 100644 src/notifications/index.ts create mode 100644 tests/notifications/api.test.ts diff --git a/src/index.ts b/src/index.ts index cfbf4af95..36e619510 100644 --- a/src/index.ts +++ b/src/index.ts @@ -7,6 +7,7 @@ import { Issues } from './issues'; import { Labels } from './labels'; import { Languages } from './languages'; import { MachineTranslation } from './machineTranslation'; +import { Notifications } from './notifications'; import { OrganizationWebhooks } from './organizationWebhooks'; import { ProjectsGroups } from './projectsGroups'; import { Reports } from './reports'; @@ -35,6 +36,7 @@ export * from './issues'; export * from './labels'; export * from './languages'; export * from './machineTranslation'; +export * from './notifications'; export * from './organizationWebhooks'; export * from './projectsGroups'; export * from './reports'; @@ -87,6 +89,7 @@ export default class Client extends CrowdinApi { readonly labelsApi: Labels; readonly stringCommentsApi: StringComments; readonly bundlesApi: Bundles; + readonly notificationsApi: Notifications; constructor(credentials: Credentials, config?: ClientConfig) { super(credentials, config); @@ -116,5 +119,6 @@ export default class Client extends CrowdinApi { this.labelsApi = new Labels(credentials, config); this.stringCommentsApi = new StringComments(credentials, config); this.bundlesApi = new Bundles(credentials, config); + this.notificationsApi = new Notifications(credentials, config); } } diff --git a/src/notifications/index.ts b/src/notifications/index.ts new file mode 100644 index 000000000..4b6db6b74 --- /dev/null +++ b/src/notifications/index.ts @@ -0,0 +1,50 @@ +import { CrowdinApi } from '../core'; + +export class Notifications extends CrowdinApi { + /** + * @param request request body + * @see https://developer.crowdin.com/api/v2/#operation/api.notify.post + */ + sendNotificationToAuthenticatedUser(request: NotificationsModel.Notification): Promise { + const url = `${this.url}/notify`; + return this.post(url, request, this.defaultConfig()); + } + + /** + * @param projectId project identifier + * @param request request body + * @see https://developer.crowdin.com/api/v2/#operation/api.projects.notify.post + */ + sendNotificationToProjectMembers( + projectId: number, + request: NotificationsModel.NotificationByUsers | NotificationsModel.NotificationByRole, + ): Promise { + const url = `${this.url}/projects/${projectId}/notify`; + return this.post(url, request, this.defaultConfig()); + } + + /** + * @param request request body + * @see https://developer.crowdin.com/enterprise/api/v2/#operation/api.notify.post + */ + sendNotificationToOrganizationMembers( + request: NotificationsModel.NotificationByUsers | NotificationsModel.NotificationByRole, + ): Promise { + const url = `${this.url}/notify`; + return this.post(url, request, this.defaultConfig()); + } +} + +export namespace NotificationsModel { + export interface Notification { + message: string; + } + + export interface NotificationByUsers extends Notification { + userIds: number[]; + } + + export interface NotificationByRole extends Notification { + role: 'owner' | 'admin'; + } +} diff --git a/tests/notifications/api.test.ts b/tests/notifications/api.test.ts new file mode 100644 index 000000000..f8a090de4 --- /dev/null +++ b/tests/notifications/api.test.ts @@ -0,0 +1,73 @@ +import * as nock from 'nock'; +import { Credentials, Notifications } from '../../src'; + +describe('Notifications API', () => { + let scope: nock.Scope; + const credentials: Credentials = { + token: 'testToken', + organization: 'testOrg', + }; + const api: Notifications = new Notifications(credentials); + const projectId = 2; + const message = 'Hello'; + const role = 'admin'; + const userId = 123; + + beforeAll(() => { + scope = nock(api.url) + .post( + '/notify', + { + message, + }, + { + reqheaders: { + Authorization: `Bearer ${api.token}`, + }, + }, + ) + .reply(200) + .post( + `/projects/${projectId}/notify`, + { + message, + role, + }, + { + reqheaders: { + Authorization: `Bearer ${api.token}`, + }, + }, + ) + .reply(200) + .post( + '/notify', + { + message, + userIds: [userId], + }, + { + reqheaders: { + Authorization: `Bearer ${api.token}`, + }, + }, + ) + .reply(200); + }); + + afterAll(() => { + scope.done(); + }); + + it('Send Notification to Authenticated User', async () => { + await api.sendNotificationToAuthenticatedUser({ message }); + }); + + it('Send Notification To Project Members', async () => { + await api.sendNotificationToProjectMembers(projectId, { message, role }); + }); + + it('Send Notification To Organization Members', async () => { + await api.sendNotificationToOrganizationMembers({ message, userIds: [userId] }); + }); +});