diff --git a/eslint-suppressions.json b/eslint-suppressions.json index 780f3e9a216..1342b16018d 100644 --- a/eslint-suppressions.json +++ b/eslint-suppressions.json @@ -1813,33 +1813,6 @@ "count": 1 } }, - "packages/notification-services-controller/src/NotificationServicesController/processors/process-notifications.ts": { - "@typescript-eslint/explicit-function-return-type": { - "count": 2 - }, - "id-length": { - "count": 6 - } - }, - "packages/notification-services-controller/src/NotificationServicesController/services/api-notifications.ts": { - "@typescript-eslint/explicit-function-return-type": { - "count": 8 - }, - "id-denylist": { - "count": 1 - }, - "id-length": { - "count": 4 - }, - "no-param-reassign": { - "count": 2 - } - }, - "packages/notification-services-controller/src/NotificationServicesController/services/feature-announcements.test.ts": { - "@typescript-eslint/explicit-function-return-type": { - "count": 2 - } - }, "packages/notification-services-controller/src/NotificationServicesController/services/feature-announcements.ts": { "@typescript-eslint/explicit-function-return-type": { "count": 2 diff --git a/packages/notification-services-controller/src/NotificationServicesController/processors/process-notifications.ts b/packages/notification-services-controller/src/NotificationServicesController/processors/process-notifications.ts index dd26ff2806a..30d268688a0 100644 --- a/packages/notification-services-controller/src/NotificationServicesController/processors/process-notifications.ts +++ b/packages/notification-services-controller/src/NotificationServicesController/processors/process-notifications.ts @@ -17,18 +17,19 @@ import type { NormalisedAPINotification } from '../types/notification-api/notifi import type { RawSnapNotification } from '../types/snaps'; const isOnChainNotification = ( - n: RawNotificationUnion, -): n is NormalisedAPINotification => - NOTIFICATION_API_TRIGGER_TYPES_SET.has(n.type); + notification: RawNotificationUnion, +): notification is NormalisedAPINotification => + NOTIFICATION_API_TRIGGER_TYPES_SET.has(notification.type); const isFeatureAnnouncement = ( - n: RawNotificationUnion, -): n is FeatureAnnouncementRawNotification => - n.type === TRIGGER_TYPES.FEATURES_ANNOUNCEMENT; + notification: RawNotificationUnion, +): notification is FeatureAnnouncementRawNotification => + notification.type === TRIGGER_TYPES.FEATURES_ANNOUNCEMENT; const isSnapNotification = ( - n: RawNotificationUnion, -): n is RawSnapNotification => n.type === TRIGGER_TYPES.SNAP; + notification: RawNotificationUnion, +): notification is RawSnapNotification => + notification.type === TRIGGER_TYPES.SNAP; /** * Process feature announcement and wallet notifications into a shared/normalised notification shape. @@ -42,15 +43,18 @@ export function processNotification( notification: RawNotificationUnion, readNotifications: string[] = [], ): INotification { - const exhaustedAllCases = (_: never) => { + const exhaustedAllCases = (_uncheckedCase: never): never => { const type: string = notification?.type; throw new Error(`No processor found for notification kind ${type}`); }; if (isFeatureAnnouncement(notification)) { - const n = processFeatureAnnouncement(notification); - n.isRead = isFeatureAnnouncementRead(n, readNotifications); - return n; + const processedNotification = processFeatureAnnouncement(notification); + processedNotification.isRead = isFeatureAnnouncementRead( + processedNotification, + readNotifications, + ); + return processedNotification; } if (isSnapNotification(notification)) { @@ -86,8 +90,11 @@ export function safeProcessNotification( } } -const isNotUndefined = (t?: Item): t is Item => Boolean(t); +const isNotUndefined = (item?: Item): item is Item => Boolean(item); export const processAndFilterNotifications = ( - ns: RawNotificationUnion[], + notifications: RawNotificationUnion[], readIds: string[], -) => ns.map((n) => safeProcessNotification(n, readIds)).filter(isNotUndefined); +): INotification[] => + notifications + .map((notification) => safeProcessNotification(notification, readIds)) + .filter(isNotUndefined); diff --git a/packages/notification-services-controller/src/NotificationServicesController/services/api-notifications.ts b/packages/notification-services-controller/src/NotificationServicesController/services/api-notifications.ts index bfbfb2a8e33..9cd4537fb85 100644 --- a/packages/notification-services-controller/src/NotificationServicesController/services/api-notifications.ts +++ b/packages/notification-services-controller/src/NotificationServicesController/services/api-notifications.ts @@ -24,7 +24,7 @@ const TRIGGER_API_ENV = { prd: 'https://trigger.api.cx.metamask.io', } satisfies Record; -export const TRIGGER_API = (env: ENV = 'prd') => +export const TRIGGER_API = (env: ENV = 'prd'): string => TRIGGER_API_ENV[env] ?? TRIGGER_API_ENV.prd; const NOTIFICATION_API_ENV = { @@ -33,24 +33,26 @@ const NOTIFICATION_API_ENV = { prd: 'https://notification.api.cx.metamask.io', }; -export const NOTIFICATION_API = (env: ENV = 'prd') => +export const NOTIFICATION_API = (env: ENV = 'prd'): string => NOTIFICATION_API_ENV[env] ?? NOTIFICATION_API_ENV.prd; // Gets notification settings for each account provided -export const TRIGGER_API_NOTIFICATIONS_QUERY_ENDPOINT = (env: ENV = 'prd') => - `${TRIGGER_API(env)}/api/v2/notifications/query`; +export const TRIGGER_API_NOTIFICATIONS_QUERY_ENDPOINT = ( + env: ENV = 'prd', +): string => `${TRIGGER_API(env)}/api/v2/notifications/query`; // Used to create/update account notifications for each account provided -export const TRIGGER_API_NOTIFICATIONS_ENDPOINT = (env: ENV = 'prd') => +export const TRIGGER_API_NOTIFICATIONS_ENDPOINT = (env: ENV = 'prd'): string => `${TRIGGER_API(env)}/api/v2/notifications`; // Lists notifications for each account provided -export const NOTIFICATION_API_LIST_ENDPOINT = (env: ENV = 'prd') => +export const NOTIFICATION_API_LIST_ENDPOINT = (env: ENV = 'prd'): string => `${NOTIFICATION_API(env)}/api/v3/notifications`; -// Makrs notifications as read -export const NOTIFICATION_API_MARK_ALL_AS_READ_ENDPOINT = (env: ENV = 'prd') => - `${NOTIFICATION_API(env)}/api/v3/notifications/mark-as-read`; +// Marks notifications as read +export const NOTIFICATION_API_MARK_ALL_AS_READ_ENDPOINT = ( + env: ENV = 'prd', +): string => `${NOTIFICATION_API(env)}/api/v3/notifications/mark-as-read`; /** * fetches notification config (accounts enabled vs disabled) @@ -66,31 +68,31 @@ export async function getNotificationsApiConfigCached( bearerToken: string, addresses: string[], env: ENV = 'prd', -) { +): Promise<{ address: string; enabled: boolean }[]> { if (addresses.length === 0) { return []; } - addresses = addresses.map((a) => a.toLowerCase()); + const normalizedAddresses = addresses.map((addr) => addr.toLowerCase()); - const cached = notificationsConfigCache.get(addresses); + const cached = notificationsConfigCache.get(normalizedAddresses); if (cached) { return cached; } type RequestBody = { address: string }[]; type Response = { address: string; enabled: boolean }[]; - const body: RequestBody = addresses.map((address) => ({ address })); - const data = await makeApiCall( + const body: RequestBody = normalizedAddresses.map((address) => ({ address })); + const apiResponse = await makeApiCall( bearerToken, TRIGGER_API_NOTIFICATIONS_QUERY_ENDPOINT(env), 'POST', body, ) - .then((r) => (r.ok ? r.json() : null)) + .then((response) => (response.ok ? response.json() : null)) .catch(() => null); - const result = data ?? []; + const result = apiResponse ?? []; if (result.length > 0) { notificationsConfigCache.set(result); @@ -111,25 +113,25 @@ export async function updateOnChainNotifications( bearerToken: string, addresses: { address: string; enabled: boolean }[], env: ENV = 'prd', -) { +): Promise { if (addresses.length === 0) { return; } - addresses = addresses.map((a) => { - a.address = a.address.toLowerCase(); - return a; - }); + const normalizedAddresses = addresses.map((item) => ({ + ...item, + address: item.address.toLowerCase(), + })); type RequestBody = { address: string; enabled: boolean }[]; - const body: RequestBody = addresses; + const body: RequestBody = normalizedAddresses; await makeApiCall( bearerToken, TRIGGER_API_NOTIFICATIONS_ENDPOINT(env), 'POST', body, ) - .then(() => notificationsConfigCache.set(addresses)) + .then(() => notificationsConfigCache.set(normalizedAddresses)) .catch(() => null); } @@ -160,7 +162,7 @@ export async function getAPINotifications( Schema.paths['/api/v3/notifications']['post']['responses']['200']['content']['application/json']; const body: RequestBody = { - addresses: addresses.map((a) => a.toLowerCase()), + addresses: addresses.map((addr) => addr.toLowerCase()), locale, platform, }; @@ -170,23 +172,25 @@ export async function getAPINotifications( 'POST', body, ) - .then((r) => (r.ok ? r.json() : null)) + .then((response) => + response.ok ? response.json() : null, + ) .catch(() => null); // Transform and sort notifications const transformedNotifications = notifications - ?.map((n): UnprocessedRawNotification | undefined => { - if (!n.notification_type) { + ?.map((notification): UnprocessedRawNotification | undefined => { + if (!notification.notification_type) { return undefined; } try { - return toRawAPINotification(n); + return toRawAPINotification(notification); } catch { return undefined; } }) - .filter((n): n is NormalisedAPINotification => Boolean(n)); + .filter((item): item is NormalisedAPINotification => Boolean(item)); return transformedNotifications ?? []; } @@ -223,7 +227,7 @@ export async function markNotificationsAsRead( 'POST', body, ); - } catch (err) { - log.error('Error marking notifications as read:', err); + } catch (error) { + log.error('Error marking notifications as read:', error); } } diff --git a/packages/notification-services-controller/src/NotificationServicesController/services/feature-announcements.test.ts b/packages/notification-services-controller/src/NotificationServicesController/services/feature-announcements.test.ts index 2168ae507ed..a8f68a007ed 100644 --- a/packages/notification-services-controller/src/NotificationServicesController/services/feature-announcements.test.ts +++ b/packages/notification-services-controller/src/NotificationServicesController/services/feature-announcements.test.ts @@ -33,7 +33,7 @@ describe('Feature Announcement Notifications', () => { const assertEnvEmpty = async ( override: Partial, - ) => { + ): Promise => { const result = await getFeatureAnnouncementNotifications({ ...featureAnnouncementsEnv, ...override, @@ -125,7 +125,7 @@ describe('Feature Announcement Notifications', () => { minimumVersion: string | undefined, maximumVersion: string | undefined, platformVersion: string | undefined, - ) => { + ): Promise => { const apiResponse = createMockFeatureAnnouncementAPIResult(); if (apiResponse.items?.[0]) { apiResponse.items[0].fields.extensionMinimumVersionNumber = undefined;