@marinade.finance/notifications-ts-subscription-client 1.0.2-beta.4 → 1.0.3

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.
@@ -316,6 +316,93 @@ describe('SubscriptionClient', () => {
316
316
  })
317
317
  })
318
318
 
319
+ describe('listBroadcastNotifications', () => {
320
+ it('should send GET request to /broadcast with query params', async () => {
321
+ const mockFetch = global.fetch as jest.Mock
322
+ const responseBody = [
323
+ {
324
+ id: '1',
325
+ notification_type: 'sam_auction',
326
+ inner_type: 'announcement',
327
+ user_id: 'broadcast',
328
+ scope: 'broadcast',
329
+ priority: 'critical',
330
+ title: 'Test announcement',
331
+ message: 'Test announcement body',
332
+ data: {},
333
+ notification_id: null,
334
+ relevance_until: '2025-01-15T00:00:00Z',
335
+ created_at: '2025-01-01T00:00:00Z',
336
+ },
337
+ ]
338
+ mockFetch.mockResolvedValue({
339
+ ok: true,
340
+ json: () => Promise.resolve(responseBody),
341
+ } as Response)
342
+
343
+ const client = createSubscriptionClient({
344
+ base_url: 'http://localhost:3000',
345
+ })
346
+
347
+ const result = await client.listBroadcastNotifications({
348
+ notification_type: 'sam_auction',
349
+ priority: 'critical',
350
+ inner_type: 'announcement',
351
+ limit: 10,
352
+ offset: 5,
353
+ })
354
+
355
+ expect(result).toEqual(responseBody)
356
+ expect(mockFetch).toHaveBeenCalledTimes(1)
357
+ const [url, options] = mockFetch.mock.calls[0]
358
+ const parsed = new URL(url)
359
+ expect(parsed.pathname).toBe('/v1/notifications/broadcast')
360
+ expect(parsed.searchParams.get('notification_type')).toBe('sam_auction')
361
+ expect(parsed.searchParams.get('priority')).toBe('critical')
362
+ expect(parsed.searchParams.get('inner_type')).toBe('announcement')
363
+ expect(parsed.searchParams.get('limit')).toBe('10')
364
+ expect(parsed.searchParams.get('offset')).toBe('5')
365
+ expect(options?.method).toBe('GET')
366
+ })
367
+
368
+ it('should omit optional query params when not provided', async () => {
369
+ const mockFetch = global.fetch as jest.Mock
370
+ mockFetch.mockResolvedValue({
371
+ ok: true,
372
+ json: () => Promise.resolve([]),
373
+ } as Response)
374
+
375
+ const client = createSubscriptionClient({
376
+ base_url: 'http://localhost:3000',
377
+ })
378
+
379
+ await client.listBroadcastNotifications({})
380
+
381
+ const [url] = mockFetch.mock.calls[0]
382
+ expect(url).toBe('http://localhost:3000/v1/notifications/broadcast')
383
+ })
384
+
385
+ it('should throw NetworkError on HTTP error', async () => {
386
+ const mockFetch = global.fetch as jest.Mock
387
+ mockFetch.mockResolvedValue({
388
+ ok: false,
389
+ status: 500,
390
+ statusText: 'Internal Server Error',
391
+ text: () => Promise.resolve('server error'),
392
+ } as Response)
393
+
394
+ const client = createSubscriptionClient({
395
+ base_url: 'http://localhost:3000',
396
+ })
397
+
398
+ await expect(
399
+ client.listBroadcastNotifications({
400
+ notification_type: 'sam_auction',
401
+ }),
402
+ ).rejects.toThrow(NetworkError)
403
+ })
404
+ })
405
+
319
406
  describe('timeout', () => {
320
407
  it('should throw NetworkError on timeout', async () => {
321
408
  const mockFetch = global.fetch as jest.Mock
package/dist/index.d.ts CHANGED
@@ -2,8 +2,8 @@ import { SubscriptionClient } from './client';
2
2
  import type { SubscriptionClientConfig } from './types';
3
3
  export { SubscriptionClient };
4
4
  export { subscribeMessage, unsubscribeMessage, listSubscriptionsMessage, } from './message';
5
- export { NetworkError } from './types';
6
- export type { Logger, SubscriptionClientConfig, SubscribeRequest, SubscribeResponse, UnsubscribeRequest, UnsubscribeResponse, ListSubscriptionsQuery, ListSubscriptionsAuth, Subscription, ListNotificationsQuery, Notification, } from './types';
5
+ export { NetworkError, NOTIFICATION_PRIORITIES, BONDS_EVENT_INNER_TYPES, } from './types';
6
+ export type { Logger, SubscriptionClientConfig, SubscribeRequest, SubscribeResponse, UnsubscribeRequest, UnsubscribeResponse, ListSubscriptionsQuery, ListSubscriptionsAuth, Subscription, ListNotificationsQuery, ListBroadcastNotificationsQuery, Notification, NotificationScope, NotificationPriority, BondsEventInnerType, } from './types';
7
7
  export declare const NOTIFICATION_TYPE_SAM_AUCTION = "sam_auction";
8
8
  export declare const NOTIFICATION_TYPE_INSTITUTIONAL_SELECT = "institutional_select";
9
9
  export declare function createSubscriptionClient(config: SubscriptionClientConfig): SubscriptionClient;
package/dist/index.js CHANGED
@@ -1,6 +1,6 @@
1
1
  "use strict";
2
2
  Object.defineProperty(exports, "__esModule", { value: true });
3
- exports.NOTIFICATION_TYPE_INSTITUTIONAL_SELECT = exports.NOTIFICATION_TYPE_SAM_AUCTION = exports.NetworkError = exports.listSubscriptionsMessage = exports.unsubscribeMessage = exports.subscribeMessage = exports.SubscriptionClient = void 0;
3
+ exports.NOTIFICATION_TYPE_INSTITUTIONAL_SELECT = exports.NOTIFICATION_TYPE_SAM_AUCTION = exports.BONDS_EVENT_INNER_TYPES = exports.NOTIFICATION_PRIORITIES = exports.NetworkError = exports.listSubscriptionsMessage = exports.unsubscribeMessage = exports.subscribeMessage = exports.SubscriptionClient = void 0;
4
4
  exports.createSubscriptionClient = createSubscriptionClient;
5
5
  const client_1 = require("./client");
6
6
  Object.defineProperty(exports, "SubscriptionClient", { enumerable: true, get: function () { return client_1.SubscriptionClient; } });
@@ -10,6 +10,8 @@ Object.defineProperty(exports, "unsubscribeMessage", { enumerable: true, get: fu
10
10
  Object.defineProperty(exports, "listSubscriptionsMessage", { enumerable: true, get: function () { return message_1.listSubscriptionsMessage; } });
11
11
  var types_1 = require("./types");
12
12
  Object.defineProperty(exports, "NetworkError", { enumerable: true, get: function () { return types_1.NetworkError; } });
13
+ Object.defineProperty(exports, "NOTIFICATION_PRIORITIES", { enumerable: true, get: function () { return types_1.NOTIFICATION_PRIORITIES; } });
14
+ Object.defineProperty(exports, "BONDS_EVENT_INNER_TYPES", { enumerable: true, get: function () { return types_1.BONDS_EVENT_INNER_TYPES; } });
13
15
  exports.NOTIFICATION_TYPE_SAM_AUCTION = 'sam_auction';
14
16
  exports.NOTIFICATION_TYPE_INSTITUTIONAL_SELECT = 'institutional_select';
15
17
  function createSubscriptionClient(config) {
package/dist/types.d.ts CHANGED
@@ -66,28 +66,33 @@ export interface Subscription {
66
66
  export interface ListNotificationsQuery {
67
67
  user_id: string;
68
68
  notification_type?: string;
69
- priority?: string;
70
- inner_type?: string;
69
+ priority?: NotificationPriority;
70
+ inner_type?: BondsEventInnerType;
71
71
  limit?: number;
72
72
  offset?: number;
73
73
  }
74
74
  /** GET /v1/notifications/broadcast query (public, no auth required) */
75
75
  export interface ListBroadcastNotificationsQuery {
76
76
  notification_type?: string;
77
- priority?: string;
78
- inner_type?: string;
77
+ priority?: NotificationPriority;
78
+ inner_type?: BondsEventInnerType;
79
79
  limit?: number;
80
80
  offset?: number;
81
81
  }
82
82
  export type NotificationScope = 'broadcast' | 'individual';
83
+ export declare const NOTIFICATION_PRIORITIES: readonly ["critical", "warning", "info"];
84
+ export type NotificationPriority = (typeof NOTIFICATION_PRIORITIES)[number];
85
+ export declare const BONDS_EVENT_INNER_TYPES: readonly ["first_seen", "bond_removed", "auction_entered", "auction_exited", "cap_changed", "bond_underfunded_change", "bond_balance_change", "announcement", "version_bump", "sam_eligible_change"];
86
+ export type BondsEventInnerType = (typeof BONDS_EVENT_INNER_TYPES)[number];
83
87
  /** GET /v1/notifications response item */
84
88
  export interface Notification {
85
- id: number;
89
+ /** BIGSERIAL in PostgreSQL, serialized as string via JSON replacer */
90
+ id: string;
86
91
  notification_type: string;
87
- inner_type: string;
92
+ inner_type: BondsEventInnerType;
88
93
  user_id: string;
89
94
  scope: NotificationScope;
90
- priority: string;
95
+ priority: NotificationPriority;
91
96
  title: string | null;
92
97
  message: string;
93
98
  data: Record<string, unknown>;
package/dist/types.js CHANGED
@@ -1,6 +1,21 @@
1
1
  "use strict";
2
2
  Object.defineProperty(exports, "__esModule", { value: true });
3
- exports.NetworkError = void 0;
3
+ exports.NetworkError = exports.BONDS_EVENT_INNER_TYPES = exports.NOTIFICATION_PRIORITIES = void 0;
4
+ // Keep in sync with notifications-bonds/src/types.ts NotificationPriority
5
+ exports.NOTIFICATION_PRIORITIES = ['critical', 'warning', 'info'];
6
+ // Keep in sync with notifications-bonds-event-v1 BondsEventInnerType
7
+ exports.BONDS_EVENT_INNER_TYPES = [
8
+ 'first_seen',
9
+ 'bond_removed',
10
+ 'auction_entered',
11
+ 'auction_exited',
12
+ 'cap_changed',
13
+ 'bond_underfunded_change',
14
+ 'bond_balance_change',
15
+ 'announcement',
16
+ 'version_bump',
17
+ 'sam_eligible_change',
18
+ ];
4
19
  class NetworkError extends Error {
5
20
  constructor(message, status, response) {
6
21
  super(message);
package/index.ts CHANGED
@@ -8,7 +8,11 @@ export {
8
8
  unsubscribeMessage,
9
9
  listSubscriptionsMessage,
10
10
  } from './message'
11
- export { NetworkError } from './types'
11
+ export {
12
+ NetworkError,
13
+ NOTIFICATION_PRIORITIES,
14
+ BONDS_EVENT_INNER_TYPES,
15
+ } from './types'
12
16
  export type {
13
17
  Logger,
14
18
  SubscriptionClientConfig,
@@ -20,7 +24,11 @@ export type {
20
24
  ListSubscriptionsAuth,
21
25
  Subscription,
22
26
  ListNotificationsQuery,
27
+ ListBroadcastNotificationsQuery,
23
28
  Notification,
29
+ NotificationScope,
30
+ NotificationPriority,
31
+ BondsEventInnerType,
24
32
  } from './types'
25
33
 
26
34
  export const NOTIFICATION_TYPE_SAM_AUCTION = 'sam_auction'
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@marinade.finance/notifications-ts-subscription-client",
3
- "version": "1.0.2-beta.4",
3
+ "version": "1.0.3",
4
4
  "private": false,
5
5
  "main": "dist/index.js",
6
6
  "types": "dist/index.d.ts",
package/types.ts CHANGED
@@ -87,8 +87,8 @@ export interface Subscription {
87
87
  export interface ListNotificationsQuery {
88
88
  user_id: string
89
89
  notification_type?: string
90
- priority?: string
91
- inner_type?: string
90
+ priority?: NotificationPriority
91
+ inner_type?: BondsEventInnerType
92
92
  limit?: number
93
93
  offset?: number
94
94
  }
@@ -96,23 +96,43 @@ export interface ListNotificationsQuery {
96
96
  /** GET /v1/notifications/broadcast query (public, no auth required) */
97
97
  export interface ListBroadcastNotificationsQuery {
98
98
  notification_type?: string
99
- priority?: string
100
- inner_type?: string
99
+ priority?: NotificationPriority
100
+ inner_type?: BondsEventInnerType
101
101
  limit?: number
102
102
  offset?: number
103
103
  }
104
104
 
105
- // Keep in sync with notification-service/notifications/notifications.constants.ts NotificationScope
105
+ // Keep in sync with notification-service/notifications/notifications.constants.ts
106
106
  export type NotificationScope = 'broadcast' | 'individual'
107
107
 
108
+ // Keep in sync with notifications-bonds/src/types.ts NotificationPriority
109
+ export const NOTIFICATION_PRIORITIES = ['critical', 'warning', 'info'] as const
110
+ export type NotificationPriority = (typeof NOTIFICATION_PRIORITIES)[number]
111
+
112
+ // Keep in sync with notifications-bonds-event-v1 BondsEventInnerType
113
+ export const BONDS_EVENT_INNER_TYPES = [
114
+ 'first_seen',
115
+ 'bond_removed',
116
+ 'auction_entered',
117
+ 'auction_exited',
118
+ 'cap_changed',
119
+ 'bond_underfunded_change',
120
+ 'bond_balance_change',
121
+ 'announcement',
122
+ 'version_bump',
123
+ 'sam_eligible_change',
124
+ ] as const
125
+ export type BondsEventInnerType = (typeof BONDS_EVENT_INNER_TYPES)[number]
126
+
108
127
  /** GET /v1/notifications response item */
109
128
  export interface Notification {
110
- id: number
129
+ /** BIGSERIAL in PostgreSQL, serialized as string via JSON replacer */
130
+ id: string
111
131
  notification_type: string
112
- inner_type: string
132
+ inner_type: BondsEventInnerType
113
133
  user_id: string
114
134
  scope: NotificationScope
115
- priority: string
135
+ priority: NotificationPriority
116
136
  title: string | null
117
137
  message: string
118
138
  data: Record<string, unknown>