@dismissible/nestjs-dismissible 0.0.2-canary.8976e84.0 → 0.0.2-canary.a611bd3.0
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/README.md +58 -74
- package/package.json +19 -17
- package/src/api/dismissible-item-response.dto.d.ts +9 -0
- package/src/api/dismissible-item-response.dto.js +40 -0
- package/src/api/dismissible-item-response.dto.js.map +1 -0
- package/src/api/dismissible-item.mapper.d.ts +12 -0
- package/src/api/dismissible-item.mapper.js +30 -0
- package/src/api/dismissible-item.mapper.js.map +1 -0
- package/src/api/dismissible-item.mapper.spec.d.ts +1 -0
- package/src/api/dismissible-item.mapper.spec.js +43 -0
- package/src/api/dismissible-item.mapper.spec.js.map +1 -0
- package/src/api/{index.ts → index.d.ts} +1 -4
- package/src/api/index.js +8 -0
- package/src/api/index.js.map +1 -0
- package/src/api/use-cases/{api-tags.constants.ts → api-tags.constants.d.ts} +1 -1
- package/src/api/use-cases/api-tags.constants.js +8 -0
- package/src/api/use-cases/api-tags.constants.js.map +1 -0
- package/src/api/use-cases/dismiss/dismiss.controller.d.ts +15 -0
- package/src/api/use-cases/dismiss/dismiss.controller.js +74 -0
- package/src/api/use-cases/dismiss/dismiss.controller.js.map +1 -0
- package/src/api/use-cases/dismiss/dismiss.controller.spec.d.ts +1 -0
- package/src/api/use-cases/dismiss/dismiss.controller.spec.js +37 -0
- package/src/api/use-cases/dismiss/dismiss.controller.spec.js.map +1 -0
- package/src/api/use-cases/dismiss/dismiss.response.dto.d.ts +12 -0
- package/src/api/use-cases/dismiss/dismiss.response.dto.js +12 -0
- package/src/api/use-cases/dismiss/dismiss.response.dto.js.map +1 -0
- package/src/api/use-cases/dismiss/index.js +6 -0
- package/src/api/use-cases/dismiss/index.js.map +1 -0
- package/src/api/use-cases/get-or-create/get-or-create.controller.d.ts +15 -0
- package/src/api/use-cases/get-or-create/get-or-create.controller.js +70 -0
- package/src/api/use-cases/get-or-create/get-or-create.controller.js.map +1 -0
- package/src/api/use-cases/get-or-create/get-or-create.controller.spec.d.ts +1 -0
- package/src/api/use-cases/get-or-create/get-or-create.controller.spec.js +32 -0
- package/src/api/use-cases/get-or-create/get-or-create.controller.spec.js.map +1 -0
- package/src/api/use-cases/get-or-create/get-or-create.response.dto.d.ts +12 -0
- package/src/api/use-cases/get-or-create/get-or-create.response.dto.js +12 -0
- package/src/api/use-cases/get-or-create/get-or-create.response.dto.js.map +1 -0
- package/src/api/use-cases/get-or-create/{index.ts → index.d.ts} +0 -1
- package/src/api/use-cases/get-or-create/index.js +6 -0
- package/src/api/use-cases/get-or-create/index.js.map +1 -0
- package/src/api/use-cases/index.js +7 -0
- package/src/api/use-cases/index.js.map +1 -0
- package/src/api/use-cases/restore/index.js +6 -0
- package/src/api/use-cases/restore/index.js.map +1 -0
- package/src/api/use-cases/restore/restore.controller.d.ts +15 -0
- package/src/api/use-cases/restore/restore.controller.js +74 -0
- package/src/api/use-cases/restore/restore.controller.js.map +1 -0
- package/src/api/use-cases/restore/restore.controller.spec.d.ts +1 -0
- package/src/api/use-cases/restore/restore.controller.spec.js +37 -0
- package/src/api/use-cases/restore/restore.controller.spec.js.map +1 -0
- package/src/api/use-cases/restore/restore.response.dto.d.ts +12 -0
- package/src/api/use-cases/restore/restore.response.dto.js +12 -0
- package/src/api/use-cases/restore/restore.response.dto.js.map +1 -0
- package/src/api/validation/index.d.ts +2 -0
- package/src/api/validation/index.js +6 -0
- package/src/api/validation/index.js.map +1 -0
- package/src/api/validation/param-validation.pipe.d.ts +11 -0
- package/src/api/validation/param-validation.pipe.js +36 -0
- package/src/api/validation/param-validation.pipe.js.map +1 -0
- package/src/api/validation/param-validation.pipe.spec.d.ts +1 -0
- package/src/api/validation/param-validation.pipe.spec.js +269 -0
- package/src/api/validation/param-validation.pipe.spec.js.map +1 -0
- package/src/api/validation/param.decorators.d.ts +28 -0
- package/src/api/validation/param.decorators.js +36 -0
- package/src/api/validation/param.decorators.js.map +1 -0
- package/src/core/dismissible-core.service.d.ts +56 -0
- package/src/core/dismissible-core.service.js +147 -0
- package/src/core/dismissible-core.service.js.map +1 -0
- package/src/core/dismissible-core.service.spec.d.ts +1 -0
- package/src/core/dismissible-core.service.spec.js +309 -0
- package/src/core/dismissible-core.service.spec.js.map +1 -0
- package/src/core/dismissible.service.d.ts +45 -0
- package/src/core/dismissible.service.js +127 -0
- package/src/core/dismissible.service.js.map +1 -0
- package/src/core/dismissible.service.spec.d.ts +1 -0
- package/src/core/dismissible.service.spec.js +159 -0
- package/src/core/dismissible.service.spec.js.map +1 -0
- package/src/core/hook-runner.service.d.ts +88 -0
- package/src/core/hook-runner.service.js +226 -0
- package/src/core/hook-runner.service.js.map +1 -0
- package/src/core/hook-runner.service.spec.d.ts +1 -0
- package/src/core/hook-runner.service.spec.js +538 -0
- package/src/core/hook-runner.service.spec.js.map +1 -0
- package/src/core/{index.ts → index.d.ts} +0 -1
- package/src/core/index.js +9 -0
- package/src/core/index.js.map +1 -0
- package/src/core/lifecycle-hook.interface.d.ts +1 -0
- package/src/core/lifecycle-hook.interface.js +7 -0
- package/src/core/lifecycle-hook.interface.js.map +1 -0
- package/src/core/service-responses.interface.d.ts +28 -0
- package/src/core/service-responses.interface.js +3 -0
- package/src/core/service-responses.interface.js.map +1 -0
- package/src/dismissible.module.d.ts +13 -0
- package/src/dismissible.module.integration.spec.d.ts +1 -0
- package/src/dismissible.module.integration.spec.js +529 -0
- package/src/dismissible.module.integration.spec.js.map +1 -0
- package/src/dismissible.module.js +77 -0
- package/src/dismissible.module.js.map +1 -0
- package/src/events/dismissible.events.d.ts +45 -0
- package/src/events/dismissible.events.js +53 -0
- package/src/events/dismissible.events.js.map +1 -0
- package/src/events/events.constants.d.ts +17 -0
- package/src/events/events.constants.js +17 -0
- package/src/events/events.constants.js.map +1 -0
- package/src/events/index.js +6 -0
- package/src/events/index.js.map +1 -0
- package/src/exceptions/dismissible.exceptions.d.ts +26 -0
- package/src/exceptions/dismissible.exceptions.js +49 -0
- package/src/exceptions/dismissible.exceptions.js.map +1 -0
- package/src/exceptions/dismissible.exceptions.spec.d.ts +1 -0
- package/src/exceptions/dismissible.exceptions.spec.js +40 -0
- package/src/exceptions/dismissible.exceptions.spec.js.map +1 -0
- package/src/exceptions/index.js +5 -0
- package/src/exceptions/index.js.map +1 -0
- package/src/{index.ts → index.d.ts} +1 -1
- package/src/index.js +12 -0
- package/src/index.js.map +1 -0
- package/src/response/dtos/base-response.dto.d.ts +6 -0
- package/src/response/dtos/base-response.dto.js +18 -0
- package/src/response/dtos/base-response.dto.js.map +1 -0
- package/src/response/dtos/error-response.dto.d.ts +19 -0
- package/src/response/dtos/error-response.dto.js +39 -0
- package/src/response/dtos/error-response.dto.js.map +1 -0
- package/src/response/dtos/index.js +7 -0
- package/src/response/dtos/index.js.map +1 -0
- package/src/response/dtos/{success-response.dto.ts → success-response.dto.d.ts} +6 -12
- package/src/response/dtos/success-response.dto.js +34 -0
- package/src/response/dtos/success-response.dto.js.map +1 -0
- package/src/response/http-exception-filter.d.ts +4 -0
- package/src/response/http-exception-filter.js +24 -0
- package/src/response/http-exception-filter.js.map +1 -0
- package/src/response/http-exception-filter.spec.d.ts +1 -0
- package/src/response/http-exception-filter.spec.js +137 -0
- package/src/response/http-exception-filter.spec.js.map +1 -0
- package/src/response/index.js +8 -0
- package/src/response/index.js.map +1 -0
- package/src/response/response.module.d.ts +2 -0
- package/src/response/response.module.js +17 -0
- package/src/response/response.module.js.map +1 -0
- package/src/response/response.service.d.ts +6 -0
- package/src/response/response.service.js +25 -0
- package/src/response/response.service.js.map +1 -0
- package/src/response/response.service.spec.d.ts +1 -0
- package/src/response/response.service.spec.js +58 -0
- package/src/response/response.service.spec.js.map +1 -0
- package/src/testing/factories.d.ts +14 -0
- package/src/testing/factories.js +58 -0
- package/src/testing/factories.js.map +1 -0
- package/src/testing/index.js +5 -0
- package/src/testing/index.js.map +1 -0
- package/src/utils/date/date.service.d.ts +8 -0
- package/src/utils/date/date.service.js +24 -0
- package/src/utils/date/date.service.js.map +1 -0
- package/src/utils/date/date.service.spec.d.ts +1 -0
- package/src/utils/date/date.service.spec.js +83 -0
- package/src/utils/date/date.service.spec.js.map +1 -0
- package/src/utils/date/index.js +5 -0
- package/src/utils/date/index.js.map +1 -0
- package/src/utils/dismissible.helper.d.ts +4 -0
- package/src/utils/dismissible.helper.js +15 -0
- package/src/utils/dismissible.helper.js.map +1 -0
- package/src/utils/index.js +7 -0
- package/src/utils/index.js.map +1 -0
- package/src/validation/dismissible-input.dto.d.ts +21 -0
- package/src/validation/dismissible-input.dto.js +54 -0
- package/src/validation/dismissible-input.dto.js.map +1 -0
- package/src/validation/index.d.ts +1 -0
- package/src/validation/index.js +5 -0
- package/src/validation/index.js.map +1 -0
- package/jest.config.ts +0 -29
- package/project.json +0 -42
- package/src/api/dismissible-item-response.dto.ts +0 -38
- package/src/api/dismissible-item.mapper.spec.ts +0 -63
- package/src/api/dismissible-item.mapper.ts +0 -33
- package/src/api/use-cases/dismiss/dismiss.controller.spec.ts +0 -42
- package/src/api/use-cases/dismiss/dismiss.controller.ts +0 -63
- package/src/api/use-cases/dismiss/dismiss.response.dto.ts +0 -7
- package/src/api/use-cases/get-or-create/get-or-create.controller.spec.ts +0 -76
- package/src/api/use-cases/get-or-create/get-or-create.controller.ts +0 -106
- package/src/api/use-cases/get-or-create/get-or-create.request.dto.ts +0 -17
- package/src/api/use-cases/get-or-create/get-or-create.response.dto.ts +0 -7
- package/src/api/use-cases/restore/restore.controller.spec.ts +0 -42
- package/src/api/use-cases/restore/restore.controller.ts +0 -63
- package/src/api/use-cases/restore/restore.response.dto.ts +0 -7
- package/src/core/create-options.ts +0 -9
- package/src/core/dismissible-core.service.spec.ts +0 -357
- package/src/core/dismissible-core.service.ts +0 -161
- package/src/core/dismissible.service.spec.ts +0 -144
- package/src/core/dismissible.service.ts +0 -188
- package/src/core/hook-runner.service.spec.ts +0 -304
- package/src/core/hook-runner.service.ts +0 -267
- package/src/core/lifecycle-hook.interface.ts +0 -122
- package/src/core/service-responses.interface.ts +0 -34
- package/src/dismissible.module.ts +0 -83
- package/src/events/dismissible.events.ts +0 -105
- package/src/events/events.constants.ts +0 -21
- package/src/exceptions/dismissible.exceptions.spec.ts +0 -50
- package/src/exceptions/dismissible.exceptions.ts +0 -69
- package/src/request/index.ts +0 -2
- package/src/request/request-context.decorator.ts +0 -14
- package/src/request/request-context.interface.ts +0 -6
- package/src/response/dtos/base-response.dto.ts +0 -11
- package/src/response/dtos/error-response.dto.ts +0 -36
- package/src/response/http-exception-filter.ts +0 -21
- package/src/response/response.module.ts +0 -9
- package/src/response/response.service.spec.ts +0 -86
- package/src/response/response.service.ts +0 -20
- package/src/testing/factories.ts +0 -45
- package/src/utils/date/date.service.spec.ts +0 -104
- package/src/utils/date/date.service.ts +0 -19
- package/src/utils/dismissible.helper.ts +0 -9
- package/tsconfig.json +0 -13
- package/tsconfig.lib.json +0 -14
- /package/src/api/use-cases/dismiss/{index.ts → index.d.ts} +0 -0
- /package/src/api/use-cases/{index.ts → index.d.ts} +0 -0
- /package/src/api/use-cases/restore/{index.ts → index.d.ts} +0 -0
- /package/src/events/{index.ts → index.d.ts} +0 -0
- /package/src/exceptions/{index.ts → index.d.ts} +0 -0
- /package/src/response/dtos/{index.ts → index.d.ts} +0 -0
- /package/src/response/{index.ts → index.d.ts} +0 -0
- /package/src/testing/{index.ts → index.d.ts} +0 -0
- /package/src/utils/date/{index.ts → index.d.ts} +0 -0
- /package/src/utils/{index.ts → index.d.ts} +0 -0
package/README.md
CHANGED
|
@@ -6,14 +6,16 @@ A powerful NestJS library for managing dismissible state in your applications. P
|
|
|
6
6
|
|
|
7
7
|
## Features
|
|
8
8
|
|
|
9
|
-
-
|
|
10
|
-
-
|
|
11
|
-
-
|
|
12
|
-
-
|
|
13
|
-
-
|
|
14
|
-
-
|
|
15
|
-
-
|
|
16
|
-
-
|
|
9
|
+
- **Simple API** - Easy-to-use service methods for get-or-create, dismiss, and restore operations
|
|
10
|
+
- **High Performance** - Built on Fastify for maximum throughput
|
|
11
|
+
- **Flexible Storage** - Default in-memory storage with support for custom storage adapters (PostgreSQL, Redis, etc.)
|
|
12
|
+
- **Lifecycle Hooks** - Intercept and customize operations with pre/post hooks
|
|
13
|
+
- **JWT Authentication** - Optional JWT auth hook for securing endpoints with OIDC providers
|
|
14
|
+
- **Event-Driven** - Built-in event emission for all operations
|
|
15
|
+
- **Type-Safe** - Full TypeScript support
|
|
16
|
+
- **Validation** - Automatic validation of dismissible items
|
|
17
|
+
- **Swagger Integration** - Auto-generated API documentation
|
|
18
|
+
- **React Client** - Works out of the box with [@dismissible/react-client](https://www.npmjs.com/package/@dismissible/react-client)
|
|
17
19
|
|
|
18
20
|
## Installation
|
|
19
21
|
|
|
@@ -41,21 +43,21 @@ export class AppModule {}
|
|
|
41
43
|
|
|
42
44
|
The module automatically registers REST endpoints for all operations:
|
|
43
45
|
|
|
44
|
-
- `GET /v1/
|
|
45
|
-
- `DELETE /v1/
|
|
46
|
-
- `POST /v1/
|
|
46
|
+
- `GET /v1/users/:userId/items/:itemId` - Get or create an item
|
|
47
|
+
- `DELETE /v1/users/:userId/items/:itemId` - Dismiss an item
|
|
48
|
+
- `POST /v1/users/:userId/items/:itemId` - Restore a dismissed item
|
|
47
49
|
|
|
48
50
|
Example request:
|
|
49
51
|
|
|
50
52
|
```bash
|
|
51
53
|
# Get or create an item
|
|
52
|
-
curl http://localhost:3000/v1/
|
|
54
|
+
curl http://localhost:3000/v1/users/user-123/items/welcome-banner
|
|
53
55
|
|
|
54
56
|
# Dismiss an item
|
|
55
|
-
curl -X DELETE http://localhost:3000/v1/
|
|
57
|
+
curl -X DELETE http://localhost:3000/v1/users/user-123/items/welcome-banner
|
|
56
58
|
|
|
57
59
|
# Restore a dismissed item
|
|
58
|
-
curl -X POST http://localhost:3000/v1/
|
|
60
|
+
curl -X POST http://localhost:3000/v1/users/user-123/items/welcome-banner
|
|
59
61
|
```
|
|
60
62
|
|
|
61
63
|
### React Client Integration
|
|
@@ -156,9 +158,6 @@ export class FeaturesController {
|
|
|
156
158
|
const result = await this.dismissibleService.getOrCreate(
|
|
157
159
|
itemId,
|
|
158
160
|
userId,
|
|
159
|
-
{
|
|
160
|
-
metadata: { version: '1.0', category: 'onboarding' },
|
|
161
|
-
},
|
|
162
161
|
undefined, // optional request context
|
|
163
162
|
);
|
|
164
163
|
|
|
@@ -182,6 +181,33 @@ export class FeaturesController {
|
|
|
182
181
|
}
|
|
183
182
|
```
|
|
184
183
|
|
|
184
|
+
### JWT Authentication
|
|
185
|
+
|
|
186
|
+
Secure your API endpoints using the JWT Auth Hook with any OIDC-compliant identity provider:
|
|
187
|
+
|
|
188
|
+
```typescript
|
|
189
|
+
import { Module } from '@nestjs/common';
|
|
190
|
+
import { DismissibleModule } from '@dismissible/nestjs-dismissible';
|
|
191
|
+
import { JwtAuthHookModule, JwtAuthHook } from '@dismissible/nestjs-jwt-auth-hook';
|
|
192
|
+
|
|
193
|
+
@Module({
|
|
194
|
+
imports: [
|
|
195
|
+
JwtAuthHookModule.forRoot({
|
|
196
|
+
enabled: true,
|
|
197
|
+
wellKnownUrl: 'https://auth.example.com/.well-known/openid-configuration',
|
|
198
|
+
issuer: 'https://auth.example.com',
|
|
199
|
+
audience: 'my-api',
|
|
200
|
+
}),
|
|
201
|
+
DismissibleModule.forRoot({
|
|
202
|
+
hooks: [JwtAuthHook],
|
|
203
|
+
}),
|
|
204
|
+
],
|
|
205
|
+
})
|
|
206
|
+
export class AppModule {}
|
|
207
|
+
```
|
|
208
|
+
|
|
209
|
+
See the [@dismissible/nestjs-jwt-auth-hook](https://www.npmjs.com/package/@dismissible/nestjs-jwt-auth-hook) package for detailed configuration options.
|
|
210
|
+
|
|
185
211
|
### Custom Lifecycle Hooks
|
|
186
212
|
|
|
187
213
|
Lifecycle hooks allow you to intercept operations and add custom logic, validation, or mutations:
|
|
@@ -189,10 +215,8 @@ Lifecycle hooks allow you to intercept operations and add custom logic, validati
|
|
|
189
215
|
```typescript
|
|
190
216
|
import { Injectable } from '@nestjs/common';
|
|
191
217
|
import { IDismissibleLifecycleHook, IHookResult } from '@dismissible/nestjs-dismissible';
|
|
192
|
-
import { BaseMetadata } from '@dismissible/nestjs-dismissible-item';
|
|
193
|
-
|
|
194
218
|
@Injectable()
|
|
195
|
-
export class AuditHook implements IDismissibleLifecycleHook
|
|
219
|
+
export class AuditHook implements IDismissibleLifecycleHook {
|
|
196
220
|
// Lower priority runs first (default is 0)
|
|
197
221
|
readonly priority = 10;
|
|
198
222
|
|
|
@@ -215,7 +239,7 @@ export class AuditHook implements IDismissibleLifecycleHook<BaseMetadata> {
|
|
|
215
239
|
|
|
216
240
|
async onAfterCreate(
|
|
217
241
|
itemId: string,
|
|
218
|
-
item: DismissibleItemDto
|
|
242
|
+
item: DismissibleItemDto,
|
|
219
243
|
userId: string,
|
|
220
244
|
context?: IRequestContext,
|
|
221
245
|
): Promise<void> {
|
|
@@ -293,42 +317,6 @@ export class AnalyticsService {
|
|
|
293
317
|
}
|
|
294
318
|
```
|
|
295
319
|
|
|
296
|
-
### Custom Metadata Types
|
|
297
|
-
|
|
298
|
-
Define custom metadata types for type-safe item properties:
|
|
299
|
-
|
|
300
|
-
```typescript
|
|
301
|
-
import { BaseMetadata } from '@dismissible/nestjs-dismissible-item';
|
|
302
|
-
|
|
303
|
-
interface OnboardingMetadata extends BaseMetadata {
|
|
304
|
-
step: number;
|
|
305
|
-
completedAt?: string;
|
|
306
|
-
skipped: boolean;
|
|
307
|
-
}
|
|
308
|
-
|
|
309
|
-
// Use in your service
|
|
310
|
-
@Injectable()
|
|
311
|
-
export class OnboardingService {
|
|
312
|
-
constructor(private readonly dismissibleService: DismissibleService<OnboardingMetadata>) {}
|
|
313
|
-
|
|
314
|
-
async trackStep(userId: string, step: number) {
|
|
315
|
-
const result = await this.dismissibleService.getOrCreate(
|
|
316
|
-
`onboarding-step-${step}`,
|
|
317
|
-
userId,
|
|
318
|
-
{
|
|
319
|
-
metadata: {
|
|
320
|
-
step,
|
|
321
|
-
skipped: false,
|
|
322
|
-
},
|
|
323
|
-
},
|
|
324
|
-
undefined,
|
|
325
|
-
);
|
|
326
|
-
|
|
327
|
-
return result.item;
|
|
328
|
-
}
|
|
329
|
-
}
|
|
330
|
-
```
|
|
331
|
-
|
|
332
320
|
### Custom Logger
|
|
333
321
|
|
|
334
322
|
Provide a custom logger implementation:
|
|
@@ -376,17 +364,15 @@ The main service for interacting with dismissible items.
|
|
|
376
364
|
|
|
377
365
|
#### Methods
|
|
378
366
|
|
|
379
|
-
**`getOrCreate(itemId, userId,
|
|
367
|
+
**`getOrCreate(itemId, userId, context?)`**
|
|
380
368
|
|
|
381
369
|
Retrieves an existing item or creates a new one if it doesn't exist.
|
|
382
370
|
|
|
383
371
|
- `itemId: string` - Unique identifier for the item
|
|
384
372
|
- `userId: string` - User identifier (required)
|
|
385
|
-
- `options?: ICreateItemOptions<TMetadata>` - Optional creation options
|
|
386
|
-
- `metadata?: TMetadata` - Custom metadata to attach to the item
|
|
387
373
|
- `context?: IRequestContext` - Optional request context for tracing
|
|
388
374
|
|
|
389
|
-
Returns: `Promise<IGetOrCreateServiceResponse
|
|
375
|
+
Returns: `Promise<IGetOrCreateServiceResponse>`
|
|
390
376
|
|
|
391
377
|
**`dismiss(itemId, userId, context?)`**
|
|
392
378
|
|
|
@@ -396,7 +382,7 @@ Marks an item as dismissed.
|
|
|
396
382
|
- `userId: string` - User identifier
|
|
397
383
|
- `context?: IRequestContext` - Optional request context
|
|
398
384
|
|
|
399
|
-
Returns: `Promise<IDismissServiceResponse
|
|
385
|
+
Returns: `Promise<IDismissServiceResponse>`
|
|
400
386
|
|
|
401
387
|
**`restore(itemId, userId, context?)`**
|
|
402
388
|
|
|
@@ -406,12 +392,12 @@ Restores a previously dismissed item.
|
|
|
406
392
|
- `userId: string` - User identifier
|
|
407
393
|
- `context?: IRequestContext` - Optional request context
|
|
408
394
|
|
|
409
|
-
Returns: `Promise<IRestoreServiceResponse
|
|
395
|
+
Returns: `Promise<IRestoreServiceResponse>`
|
|
410
396
|
|
|
411
397
|
### Module Configuration
|
|
412
398
|
|
|
413
399
|
```typescript
|
|
414
|
-
interface IDismissibleModuleOptions
|
|
400
|
+
interface IDismissibleModuleOptions {
|
|
415
401
|
// Custom storage module (defaults to in-memory storage)
|
|
416
402
|
storage?: DynamicModule | Type<any>;
|
|
417
403
|
|
|
@@ -419,7 +405,7 @@ interface IDismissibleModuleOptions<TMetadata extends BaseMetadata> {
|
|
|
419
405
|
logger?: Type<IDismissibleLogger>;
|
|
420
406
|
|
|
421
407
|
// Lifecycle hooks to register
|
|
422
|
-
hooks?: Type<IDismissibleLifecycleHook
|
|
408
|
+
hooks?: Type<IDismissibleLifecycleHook>[];
|
|
423
409
|
}
|
|
424
410
|
```
|
|
425
411
|
|
|
@@ -435,13 +421,13 @@ The library emits the following events:
|
|
|
435
421
|
All events include:
|
|
436
422
|
|
|
437
423
|
- `id: string` - The item identifier
|
|
438
|
-
- `item: DismissibleItemDto
|
|
424
|
+
- `item: DismissibleItemDto` - The current item state
|
|
439
425
|
- `userId: string` - The user identifier
|
|
440
426
|
- `context?: IRequestContext` - Optional request context
|
|
441
427
|
|
|
442
428
|
Dismiss and restore events also include:
|
|
443
429
|
|
|
444
|
-
- `previousItem: DismissibleItemDto
|
|
430
|
+
- `previousItem: DismissibleItemDto` - The item state before the operation
|
|
445
431
|
|
|
446
432
|
## Lifecycle Hooks
|
|
447
433
|
|
|
@@ -481,21 +467,19 @@ Implement the `IDismissibleStorage` interface to create a custom storage adapter
|
|
|
481
467
|
```typescript
|
|
482
468
|
import { Injectable } from '@nestjs/common';
|
|
483
469
|
import { IDismissibleStorage } from '@dismissible/nestjs-storage';
|
|
484
|
-
import { DismissibleItemDto
|
|
470
|
+
import { DismissibleItemDto } from '@dismissible/nestjs-dismissible-item';
|
|
485
471
|
|
|
486
472
|
@Injectable()
|
|
487
|
-
export class RedisStorageAdapter
|
|
488
|
-
|
|
489
|
-
> implements IDismissibleStorage<TMetadata> {
|
|
490
|
-
async get(userId: string, itemId: string): Promise<DismissibleItemDto<TMetadata> | null> {
|
|
473
|
+
export class RedisStorageAdapter implements IDismissibleStorage {
|
|
474
|
+
async get(userId: string, itemId: string): Promise<DismissibleItemDto | null> {
|
|
491
475
|
// Your implementation
|
|
492
476
|
}
|
|
493
477
|
|
|
494
|
-
async create(userId: string, item: DismissibleItemDto
|
|
478
|
+
async create(userId: string, item: DismissibleItemDto): Promise<void> {
|
|
495
479
|
// Your implementation
|
|
496
480
|
}
|
|
497
481
|
|
|
498
|
-
async update(userId: string, item: DismissibleItemDto
|
|
482
|
+
async update(userId: string, item: DismissibleItemDto): Promise<void> {
|
|
499
483
|
// Your implementation
|
|
500
484
|
}
|
|
501
485
|
}
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@dismissible/nestjs-dismissible",
|
|
3
|
-
"version": "0.0.2-canary.
|
|
3
|
+
"version": "0.0.2-canary.a611bd3.0",
|
|
4
4
|
"description": "Dismissible state management library for NestJS applications",
|
|
5
5
|
"main": "./src/index.js",
|
|
6
6
|
"types": "./src/index.d.ts",
|
|
@@ -11,18 +11,25 @@
|
|
|
11
11
|
"types": "./src/index.d.ts"
|
|
12
12
|
}
|
|
13
13
|
},
|
|
14
|
+
"files": [
|
|
15
|
+
"src",
|
|
16
|
+
"README.md"
|
|
17
|
+
],
|
|
14
18
|
"dependencies": {
|
|
15
|
-
"@nestjs/event-emitter": "
|
|
16
|
-
"
|
|
19
|
+
"@nestjs/event-emitter": "3.0.1",
|
|
20
|
+
"@dismissible/nestjs-dismissible-hooks": "0.0.2-canary.a611bd3.0",
|
|
21
|
+
"@dismissible/nestjs-dismissible-item": "0.0.2-canary.a611bd3.0",
|
|
22
|
+
"@dismissible/nestjs-dismissible-request": "0.0.2-canary.a611bd3.0",
|
|
23
|
+
"@dismissible/nestjs-storage": "0.0.2-canary.a611bd3.0",
|
|
24
|
+
"@dismissible/nestjs-logger": "0.0.2-canary.a611bd3.0",
|
|
25
|
+
"@dismissible/nestjs-validation": "0.0.2-canary.a611bd3.0"
|
|
17
26
|
},
|
|
18
27
|
"peerDependencies": {
|
|
19
|
-
"@nestjs/common": "^11.0.0",
|
|
20
|
-
"@nestjs/core": "^11.0.0",
|
|
21
|
-
"@nestjs/swagger": "^11.0.0",
|
|
22
|
-
"
|
|
23
|
-
"
|
|
24
|
-
"class-validator": "^0.14.0",
|
|
25
|
-
"class-transformer": "^0.5.0"
|
|
28
|
+
"@nestjs/common": "10.0.0 || ^11.0.0",
|
|
29
|
+
"@nestjs/core": "10.0.0 || ^11.0.0",
|
|
30
|
+
"@nestjs/swagger": "10.0.0 || ^11.0.0",
|
|
31
|
+
"class-validator": "0.14.0",
|
|
32
|
+
"class-transformer": "0.5.0"
|
|
26
33
|
},
|
|
27
34
|
"peerDependenciesMeta": {
|
|
28
35
|
"@nestjs/common": {
|
|
@@ -34,12 +41,6 @@
|
|
|
34
41
|
"@nestjs/swagger": {
|
|
35
42
|
"optional": false
|
|
36
43
|
},
|
|
37
|
-
"dismissible/nestjs-dismissible-item": {
|
|
38
|
-
"optional": false
|
|
39
|
-
},
|
|
40
|
-
"@dismissible/nestjs-storage": {
|
|
41
|
-
"optional": false
|
|
42
|
-
},
|
|
43
44
|
"class-validator": {
|
|
44
45
|
"optional": false
|
|
45
46
|
},
|
|
@@ -62,5 +63,6 @@
|
|
|
62
63
|
},
|
|
63
64
|
"publishConfig": {
|
|
64
65
|
"access": "public"
|
|
65
|
-
}
|
|
66
|
+
},
|
|
67
|
+
"type": "commonjs"
|
|
66
68
|
}
|
|
@@ -0,0 +1,40 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
+
exports.DismissibleItemResponseDto = void 0;
|
|
4
|
+
const tslib_1 = require("tslib");
|
|
5
|
+
const swagger_1 = require("@nestjs/swagger");
|
|
6
|
+
/**
|
|
7
|
+
* Response DTO for a dismissible item.
|
|
8
|
+
*/
|
|
9
|
+
class DismissibleItemResponseDto {
|
|
10
|
+
}
|
|
11
|
+
exports.DismissibleItemResponseDto = DismissibleItemResponseDto;
|
|
12
|
+
tslib_1.__decorate([
|
|
13
|
+
(0, swagger_1.ApiProperty)({
|
|
14
|
+
description: 'Unique identifier for the item',
|
|
15
|
+
example: 'welcome-banner-v2',
|
|
16
|
+
}),
|
|
17
|
+
tslib_1.__metadata("design:type", String)
|
|
18
|
+
], DismissibleItemResponseDto.prototype, "itemId", void 0);
|
|
19
|
+
tslib_1.__decorate([
|
|
20
|
+
(0, swagger_1.ApiProperty)({
|
|
21
|
+
description: 'User identifier who created the item',
|
|
22
|
+
example: 'user-123',
|
|
23
|
+
}),
|
|
24
|
+
tslib_1.__metadata("design:type", String)
|
|
25
|
+
], DismissibleItemResponseDto.prototype, "userId", void 0);
|
|
26
|
+
tslib_1.__decorate([
|
|
27
|
+
(0, swagger_1.ApiProperty)({
|
|
28
|
+
description: 'When the item was created (ISO 8601)',
|
|
29
|
+
example: '2024-01-15T10:30:00.000Z',
|
|
30
|
+
}),
|
|
31
|
+
tslib_1.__metadata("design:type", String)
|
|
32
|
+
], DismissibleItemResponseDto.prototype, "createdAt", void 0);
|
|
33
|
+
tslib_1.__decorate([
|
|
34
|
+
(0, swagger_1.ApiPropertyOptional)({
|
|
35
|
+
description: 'When the item was dismissed (ISO 8601)',
|
|
36
|
+
example: '2024-01-15T12:00:00.000Z',
|
|
37
|
+
}),
|
|
38
|
+
tslib_1.__metadata("design:type", String)
|
|
39
|
+
], DismissibleItemResponseDto.prototype, "dismissedAt", void 0);
|
|
40
|
+
//# sourceMappingURL=dismissible-item-response.dto.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"dismissible-item-response.dto.js","sourceRoot":"","sources":["../../../../../libs/dismissible/src/api/dismissible-item-response.dto.ts"],"names":[],"mappings":";;;;AAAA,6CAAmE;AAEnE;;GAEG;AACH,MAAa,0BAA0B;CAwBtC;AAxBD,gEAwBC;AAnBC;IAJC,IAAA,qBAAW,EAAC;QACX,WAAW,EAAE,gCAAgC;QAC7C,OAAO,EAAE,mBAAmB;KAC7B,CAAC;;0DACc;AAMhB;IAJC,IAAA,qBAAW,EAAC;QACX,WAAW,EAAE,sCAAsC;QACnD,OAAO,EAAE,UAAU;KACpB,CAAC;;0DACc;AAMhB;IAJC,IAAA,qBAAW,EAAC;QACX,WAAW,EAAE,sCAAsC;QACnD,OAAO,EAAE,0BAA0B;KACpC,CAAC;;6DACiB;AAMnB;IAJC,IAAA,6BAAmB,EAAC;QACnB,WAAW,EAAE,wCAAwC;QACrD,OAAO,EAAE,0BAA0B;KACpC,CAAC;;+DACmB"}
|
|
@@ -0,0 +1,12 @@
|
|
|
1
|
+
import { DismissibleItemDto } from '@dismissible/nestjs-dismissible-item';
|
|
2
|
+
import { DismissibleItemResponseDto } from './dismissible-item-response.dto';
|
|
3
|
+
/**
|
|
4
|
+
* Mapper for converting domain objects to DTOs.
|
|
5
|
+
*/
|
|
6
|
+
export declare class DismissibleItemMapper {
|
|
7
|
+
/**
|
|
8
|
+
* Convert a dismissible item to a response DTO.
|
|
9
|
+
* Converts Date objects to ISO 8601 strings.
|
|
10
|
+
*/
|
|
11
|
+
toResponseDto(item: DismissibleItemDto): DismissibleItemResponseDto;
|
|
12
|
+
}
|
|
@@ -0,0 +1,30 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
+
exports.DismissibleItemMapper = void 0;
|
|
4
|
+
const tslib_1 = require("tslib");
|
|
5
|
+
const common_1 = require("@nestjs/common");
|
|
6
|
+
const dismissible_item_response_dto_1 = require("./dismissible-item-response.dto");
|
|
7
|
+
/**
|
|
8
|
+
* Mapper for converting domain objects to DTOs.
|
|
9
|
+
*/
|
|
10
|
+
let DismissibleItemMapper = class DismissibleItemMapper {
|
|
11
|
+
/**
|
|
12
|
+
* Convert a dismissible item to a response DTO.
|
|
13
|
+
* Converts Date objects to ISO 8601 strings.
|
|
14
|
+
*/
|
|
15
|
+
toResponseDto(item) {
|
|
16
|
+
const dto = new dismissible_item_response_dto_1.DismissibleItemResponseDto();
|
|
17
|
+
dto.itemId = item.id;
|
|
18
|
+
dto.userId = item.userId;
|
|
19
|
+
dto.createdAt = item.createdAt.toISOString();
|
|
20
|
+
if (item.dismissedAt) {
|
|
21
|
+
dto.dismissedAt = item.dismissedAt.toISOString();
|
|
22
|
+
}
|
|
23
|
+
return dto;
|
|
24
|
+
}
|
|
25
|
+
};
|
|
26
|
+
exports.DismissibleItemMapper = DismissibleItemMapper;
|
|
27
|
+
exports.DismissibleItemMapper = DismissibleItemMapper = tslib_1.__decorate([
|
|
28
|
+
(0, common_1.Injectable)()
|
|
29
|
+
], DismissibleItemMapper);
|
|
30
|
+
//# sourceMappingURL=dismissible-item.mapper.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"dismissible-item.mapper.js","sourceRoot":"","sources":["../../../../../libs/dismissible/src/api/dismissible-item.mapper.ts"],"names":[],"mappings":";;;;AAAA,2CAA4C;AAE5C,mFAA6E;AAE7E;;GAEG;AAEI,IAAM,qBAAqB,GAA3B,MAAM,qBAAqB;IAChC;;;OAGG;IACH,aAAa,CAAC,IAAwB;QACpC,MAAM,GAAG,GAAG,IAAI,0DAA0B,EAAE,CAAC;QAE7C,GAAG,CAAC,MAAM,GAAG,IAAI,CAAC,EAAE,CAAC;QACrB,GAAG,CAAC,MAAM,GAAG,IAAI,CAAC,MAAM,CAAC;QACzB,GAAG,CAAC,SAAS,GAAG,IAAI,CAAC,SAAS,CAAC,WAAW,EAAE,CAAC;QAE7C,IAAI,IAAI,CAAC,WAAW,EAAE,CAAC;YACrB,GAAG,CAAC,WAAW,GAAG,IAAI,CAAC,WAAW,CAAC,WAAW,EAAE,CAAC;QACnD,CAAC;QAED,OAAO,GAAG,CAAC;IACb,CAAC;CACF,CAAA;AAlBY,sDAAqB;gCAArB,qBAAqB;IADjC,IAAA,mBAAU,GAAE;GACA,qBAAqB,CAkBjC"}
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
export {};
|
|
@@ -0,0 +1,43 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
+
const dismissible_item_mapper_1 = require("./dismissible-item.mapper");
|
|
4
|
+
const factories_1 = require("../testing/factories");
|
|
5
|
+
describe('DismissibleItemMapper', () => {
|
|
6
|
+
let mapper;
|
|
7
|
+
beforeEach(() => {
|
|
8
|
+
mapper = new dismissible_item_mapper_1.DismissibleItemMapper();
|
|
9
|
+
});
|
|
10
|
+
describe('toResponseDto', () => {
|
|
11
|
+
it('should convert basic item to DTO', () => {
|
|
12
|
+
const item = (0, factories_1.createTestItem)({
|
|
13
|
+
id: 'test-item',
|
|
14
|
+
userId: 'test-user-id',
|
|
15
|
+
createdAt: new Date('2024-01-15T10:00:00.000Z'),
|
|
16
|
+
});
|
|
17
|
+
const dto = mapper.toResponseDto(item);
|
|
18
|
+
expect(dto.itemId).toBe('test-item');
|
|
19
|
+
expect(dto.userId).toBe('test-user-id');
|
|
20
|
+
expect(dto.createdAt).toBe('2024-01-15T10:00:00.000Z');
|
|
21
|
+
expect(dto.dismissedAt).toBeUndefined();
|
|
22
|
+
});
|
|
23
|
+
it('should convert dates to ISO strings', () => {
|
|
24
|
+
const item = (0, factories_1.createDismissedTestItem)({
|
|
25
|
+
id: 'test-item',
|
|
26
|
+
createdAt: new Date('2024-01-15T10:00:00.000Z'),
|
|
27
|
+
dismissedAt: new Date('2024-01-15T12:00:00.000Z'),
|
|
28
|
+
});
|
|
29
|
+
const dto = mapper.toResponseDto(item);
|
|
30
|
+
expect(dto.createdAt).toBe('2024-01-15T10:00:00.000Z');
|
|
31
|
+
expect(dto.dismissedAt).toBe('2024-01-15T12:00:00.000Z');
|
|
32
|
+
});
|
|
33
|
+
it('should include userId in DTO', () => {
|
|
34
|
+
const item = (0, factories_1.createTestItem)({
|
|
35
|
+
id: 'test-item',
|
|
36
|
+
userId: 'user-123',
|
|
37
|
+
});
|
|
38
|
+
const dto = mapper.toResponseDto(item);
|
|
39
|
+
expect(dto.userId).toBe('user-123');
|
|
40
|
+
});
|
|
41
|
+
});
|
|
42
|
+
});
|
|
43
|
+
//# sourceMappingURL=dismissible-item.mapper.spec.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"dismissible-item.mapper.spec.js","sourceRoot":"","sources":["../../../../../libs/dismissible/src/api/dismissible-item.mapper.spec.ts"],"names":[],"mappings":";;AAAA,uEAAkE;AAClE,oDAA+E;AAE/E,QAAQ,CAAC,uBAAuB,EAAE,GAAG,EAAE;IACrC,IAAI,MAA6B,CAAC;IAElC,UAAU,CAAC,GAAG,EAAE;QACd,MAAM,GAAG,IAAI,+CAAqB,EAAE,CAAC;IACvC,CAAC,CAAC,CAAC;IAEH,QAAQ,CAAC,eAAe,EAAE,GAAG,EAAE;QAC7B,EAAE,CAAC,kCAAkC,EAAE,GAAG,EAAE;YAC1C,MAAM,IAAI,GAAG,IAAA,0BAAc,EAAC;gBAC1B,EAAE,EAAE,WAAW;gBACf,MAAM,EAAE,cAAc;gBACtB,SAAS,EAAE,IAAI,IAAI,CAAC,0BAA0B,CAAC;aAChD,CAAC,CAAC;YAEH,MAAM,GAAG,GAAG,MAAM,CAAC,aAAa,CAAC,IAAI,CAAC,CAAC;YAEvC,MAAM,CAAC,GAAG,CAAC,MAAM,CAAC,CAAC,IAAI,CAAC,WAAW,CAAC,CAAC;YACrC,MAAM,CAAC,GAAG,CAAC,MAAM,CAAC,CAAC,IAAI,CAAC,cAAc,CAAC,CAAC;YACxC,MAAM,CAAC,GAAG,CAAC,SAAS,CAAC,CAAC,IAAI,CAAC,0BAA0B,CAAC,CAAC;YACvD,MAAM,CAAC,GAAG,CAAC,WAAW,CAAC,CAAC,aAAa,EAAE,CAAC;QAC1C,CAAC,CAAC,CAAC;QAEH,EAAE,CAAC,qCAAqC,EAAE,GAAG,EAAE;YAC7C,MAAM,IAAI,GAAG,IAAA,mCAAuB,EAAC;gBACnC,EAAE,EAAE,WAAW;gBACf,SAAS,EAAE,IAAI,IAAI,CAAC,0BAA0B,CAAC;gBAC/C,WAAW,EAAE,IAAI,IAAI,CAAC,0BAA0B,CAAC;aAClD,CAAC,CAAC;YAEH,MAAM,GAAG,GAAG,MAAM,CAAC,aAAa,CAAC,IAAI,CAAC,CAAC;YAEvC,MAAM,CAAC,GAAG,CAAC,SAAS,CAAC,CAAC,IAAI,CAAC,0BAA0B,CAAC,CAAC;YACvD,MAAM,CAAC,GAAG,CAAC,WAAW,CAAC,CAAC,IAAI,CAAC,0BAA0B,CAAC,CAAC;QAC3D,CAAC,CAAC,CAAC;QAEH,EAAE,CAAC,8BAA8B,EAAE,GAAG,EAAE;YACtC,MAAM,IAAI,GAAG,IAAA,0BAAc,EAAC;gBAC1B,EAAE,EAAE,WAAW;gBACf,MAAM,EAAE,UAAU;aACnB,CAAC,CAAC;YAEH,MAAM,GAAG,GAAG,MAAM,CAAC,aAAa,CAAC,IAAI,CAAC,CAAC;YAEvC,MAAM,CAAC,GAAG,CAAC,MAAM,CAAC,CAAC,IAAI,CAAC,UAAU,CAAC,CAAC;QACtC,CAAC,CAAC,CAAC;IACL,CAAC,CAAC,CAAC;AACL,CAAC,CAAC,CAAC"}
|
package/src/api/index.js
ADDED
|
@@ -0,0 +1,8 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
+
const tslib_1 = require("tslib");
|
|
4
|
+
tslib_1.__exportStar(require("./use-cases"), exports);
|
|
5
|
+
tslib_1.__exportStar(require("./validation"), exports);
|
|
6
|
+
tslib_1.__exportStar(require("./dismissible-item.mapper"), exports);
|
|
7
|
+
tslib_1.__exportStar(require("./dismissible-item-response.dto"), exports);
|
|
8
|
+
//# sourceMappingURL=index.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"index.js","sourceRoot":"","sources":["../../../../../libs/dismissible/src/api/index.ts"],"names":[],"mappings":";;;AAAA,sDAA4B;AAE5B,uDAA6B;AAE7B,oEAA0C;AAC1C,0EAAgD"}
|
|
@@ -0,0 +1,8 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
+
exports.API_TAG_DISMISSIBLE = void 0;
|
|
4
|
+
/**
|
|
5
|
+
* API tag constants for Swagger/OpenAPI documentation.
|
|
6
|
+
*/
|
|
7
|
+
exports.API_TAG_DISMISSIBLE = 'Dismissible';
|
|
8
|
+
//# sourceMappingURL=api-tags.constants.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"api-tags.constants.js","sourceRoot":"","sources":["../../../../../../libs/dismissible/src/api/use-cases/api-tags.constants.ts"],"names":[],"mappings":";;;AAAA;;GAEG;AACU,QAAA,mBAAmB,GAAG,aAAa,CAAC"}
|
|
@@ -0,0 +1,15 @@
|
|
|
1
|
+
import { DismissibleService } from '../../../core/dismissible.service';
|
|
2
|
+
import { DismissibleItemMapper } from '../../dismissible-item.mapper';
|
|
3
|
+
import { IRequestContext } from '@dismissible/nestjs-dismissible-request';
|
|
4
|
+
import { DismissResponseDto } from './dismiss.response.dto';
|
|
5
|
+
import { ResponseService } from '../../../response/response.service';
|
|
6
|
+
/**
|
|
7
|
+
* Controller for dismiss dismissible item operations.
|
|
8
|
+
*/
|
|
9
|
+
export declare class DismissController {
|
|
10
|
+
private readonly dismissibleService;
|
|
11
|
+
private readonly mapper;
|
|
12
|
+
private readonly responseService;
|
|
13
|
+
constructor(dismissibleService: DismissibleService, mapper: DismissibleItemMapper, responseService: ResponseService);
|
|
14
|
+
dismiss(userId: string, itemId: string, context: IRequestContext): Promise<DismissResponseDto>;
|
|
15
|
+
}
|
|
@@ -0,0 +1,74 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
+
exports.DismissController = void 0;
|
|
4
|
+
const tslib_1 = require("tslib");
|
|
5
|
+
const common_1 = require("@nestjs/common");
|
|
6
|
+
const swagger_1 = require("@nestjs/swagger");
|
|
7
|
+
const dismissible_service_1 = require("../../../core/dismissible.service");
|
|
8
|
+
const dismissible_item_mapper_1 = require("../../dismissible-item.mapper");
|
|
9
|
+
const nestjs_dismissible_request_1 = require("@dismissible/nestjs-dismissible-request");
|
|
10
|
+
const dismiss_response_dto_1 = require("./dismiss.response.dto");
|
|
11
|
+
const response_service_1 = require("../../../response/response.service");
|
|
12
|
+
const http_exception_filter_1 = require("../../../response/http-exception-filter");
|
|
13
|
+
const api_tags_constants_1 = require("../api-tags.constants");
|
|
14
|
+
const validation_1 = require("../../validation");
|
|
15
|
+
/**
|
|
16
|
+
* Controller for dismiss dismissible item operations.
|
|
17
|
+
*/
|
|
18
|
+
let DismissController = class DismissController {
|
|
19
|
+
constructor(dismissibleService, mapper, responseService) {
|
|
20
|
+
this.dismissibleService = dismissibleService;
|
|
21
|
+
this.mapper = mapper;
|
|
22
|
+
this.responseService = responseService;
|
|
23
|
+
}
|
|
24
|
+
async dismiss(userId, itemId, context) {
|
|
25
|
+
const result = await this.dismissibleService.dismiss(itemId, userId, context);
|
|
26
|
+
return this.responseService.success(this.mapper.toResponseDto(result.item));
|
|
27
|
+
}
|
|
28
|
+
};
|
|
29
|
+
exports.DismissController = DismissController;
|
|
30
|
+
tslib_1.__decorate([
|
|
31
|
+
(0, common_1.Delete)(':itemId'),
|
|
32
|
+
(0, swagger_1.ApiOperation)({
|
|
33
|
+
summary: 'Dismiss an item',
|
|
34
|
+
description: 'Marks a dismissible item as dismissed.',
|
|
35
|
+
}),
|
|
36
|
+
(0, swagger_1.ApiParam)({
|
|
37
|
+
name: 'userId',
|
|
38
|
+
description: 'User identifier (max length: 32 characters)',
|
|
39
|
+
example: 'user-123',
|
|
40
|
+
}),
|
|
41
|
+
(0, swagger_1.ApiParam)({
|
|
42
|
+
name: 'itemId',
|
|
43
|
+
description: 'Unique identifier for the dismissible item (max length: 32 characters)',
|
|
44
|
+
example: 'welcome-banner-v2',
|
|
45
|
+
}),
|
|
46
|
+
(0, swagger_1.ApiResponse)({
|
|
47
|
+
status: 200,
|
|
48
|
+
description: 'The dismissed item',
|
|
49
|
+
type: dismiss_response_dto_1.DismissResponseDto,
|
|
50
|
+
}),
|
|
51
|
+
(0, swagger_1.ApiResponse)({
|
|
52
|
+
status: 400,
|
|
53
|
+
description: 'Item not found or already dismissed',
|
|
54
|
+
}),
|
|
55
|
+
(0, swagger_1.ApiResponse)({
|
|
56
|
+
status: 403,
|
|
57
|
+
description: 'Operation blocked by lifecycle hook',
|
|
58
|
+
}),
|
|
59
|
+
(0, common_1.UseFilters)(http_exception_filter_1.HttpExceptionFilter),
|
|
60
|
+
tslib_1.__param(0, (0, validation_1.UserId)()),
|
|
61
|
+
tslib_1.__param(1, (0, validation_1.ItemId)()),
|
|
62
|
+
tslib_1.__param(2, (0, nestjs_dismissible_request_1.RequestContext)()),
|
|
63
|
+
tslib_1.__metadata("design:type", Function),
|
|
64
|
+
tslib_1.__metadata("design:paramtypes", [String, String, Object]),
|
|
65
|
+
tslib_1.__metadata("design:returntype", Promise)
|
|
66
|
+
], DismissController.prototype, "dismiss", null);
|
|
67
|
+
exports.DismissController = DismissController = tslib_1.__decorate([
|
|
68
|
+
(0, swagger_1.ApiTags)(api_tags_constants_1.API_TAG_DISMISSIBLE),
|
|
69
|
+
(0, common_1.Controller)('v1/users/:userId/items'),
|
|
70
|
+
tslib_1.__metadata("design:paramtypes", [dismissible_service_1.DismissibleService,
|
|
71
|
+
dismissible_item_mapper_1.DismissibleItemMapper,
|
|
72
|
+
response_service_1.ResponseService])
|
|
73
|
+
], DismissController);
|
|
74
|
+
//# sourceMappingURL=dismiss.controller.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"dismiss.controller.js","sourceRoot":"","sources":["../../../../../../../libs/dismissible/src/api/use-cases/dismiss/dismiss.controller.ts"],"names":[],"mappings":";;;;AAAA,2CAAgE;AAChE,6CAA+E;AAC/E,2EAAuE;AACvE,2EAAsE;AACtE,wFAA0F;AAC1F,iEAA4D;AAC5D,yEAAqE;AACrE,mFAA8E;AAC9E,8DAA4D;AAC5D,iDAAkD;AAElD;;GAEG;AAGI,IAAM,iBAAiB,GAAvB,MAAM,iBAAiB;IAC5B,YACmB,kBAAsC,EACtC,MAA6B,EAC7B,eAAgC;QAFhC,uBAAkB,GAAlB,kBAAkB,CAAoB;QACtC,WAAM,GAAN,MAAM,CAAuB;QAC7B,oBAAe,GAAf,eAAe,CAAiB;IAChD,CAAC;IA+BE,AAAN,KAAK,CAAC,OAAO,CACD,MAAc,EACd,MAAc,EACN,OAAwB;QAE1C,MAAM,MAAM,GAAG,MAAM,IAAI,CAAC,kBAAkB,CAAC,OAAO,CAAC,MAAM,EAAE,MAAM,EAAE,OAAO,CAAC,CAAC;QAE9E,OAAO,IAAI,CAAC,eAAe,CAAC,OAAO,CAAC,IAAI,CAAC,MAAM,CAAC,aAAa,CAAC,MAAM,CAAC,IAAI,CAAC,CAAC,CAAC;IAC9E,CAAC;CACF,CAAA;AA7CY,8CAAiB;AAoCtB;IA7BL,IAAA,eAAM,EAAC,SAAS,CAAC;IACjB,IAAA,sBAAY,EAAC;QACZ,OAAO,EAAE,iBAAiB;QAC1B,WAAW,EAAE,wCAAwC;KACtD,CAAC;IACD,IAAA,kBAAQ,EAAC;QACR,IAAI,EAAE,QAAQ;QACd,WAAW,EAAE,6CAA6C;QAC1D,OAAO,EAAE,UAAU;KACpB,CAAC;IACD,IAAA,kBAAQ,EAAC;QACR,IAAI,EAAE,QAAQ;QACd,WAAW,EAAE,wEAAwE;QACrF,OAAO,EAAE,mBAAmB;KAC7B,CAAC;IACD,IAAA,qBAAW,EAAC;QACX,MAAM,EAAE,GAAG;QACX,WAAW,EAAE,oBAAoB;QACjC,IAAI,EAAE,yCAAkB;KACzB,CAAC;IACD,IAAA,qBAAW,EAAC;QACX,MAAM,EAAE,GAAG;QACX,WAAW,EAAE,qCAAqC;KACnD,CAAC;IACD,IAAA,qBAAW,EAAC;QACX,MAAM,EAAE,GAAG;QACX,WAAW,EAAE,qCAAqC;KACnD,CAAC;IACD,IAAA,mBAAU,EAAC,2CAAmB,CAAC;IAE7B,mBAAA,IAAA,mBAAM,GAAE,CAAA;IACR,mBAAA,IAAA,mBAAM,GAAE,CAAA;IACR,mBAAA,IAAA,2CAAc,GAAE,CAAA;;;;gDAKlB;4BA5CU,iBAAiB;IAF7B,IAAA,iBAAO,EAAC,wCAAmB,CAAC;IAC5B,IAAA,mBAAU,EAAC,wBAAwB,CAAC;6CAGI,wCAAkB;QAC9B,+CAAqB;QACZ,kCAAe;GAJxC,iBAAiB,CA6C7B"}
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
export {};
|
|
@@ -0,0 +1,37 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
+
const ts_jest_mocker_1 = require("ts-jest-mocker");
|
|
4
|
+
const dismiss_controller_1 = require("./dismiss.controller");
|
|
5
|
+
const dismissible_service_1 = require("../../../core/dismissible.service");
|
|
6
|
+
const dismissible_item_mapper_1 = require("../../dismissible-item.mapper");
|
|
7
|
+
const factories_1 = require("../../../testing/factories");
|
|
8
|
+
const response_1 = require("../../../response");
|
|
9
|
+
describe('DismissController', () => {
|
|
10
|
+
let controller;
|
|
11
|
+
let mockService;
|
|
12
|
+
let mockResponseService;
|
|
13
|
+
let mapper;
|
|
14
|
+
beforeEach(() => {
|
|
15
|
+
mockService = (0, ts_jest_mocker_1.mock)(dismissible_service_1.DismissibleService);
|
|
16
|
+
mockResponseService = (0, ts_jest_mocker_1.mock)(response_1.ResponseService, { failIfMockNotProvided: false });
|
|
17
|
+
mockResponseService.success.mockImplementation((data) => ({ data }));
|
|
18
|
+
mapper = new dismissible_item_mapper_1.DismissibleItemMapper();
|
|
19
|
+
controller = new dismiss_controller_1.DismissController(mockService, mapper, mockResponseService);
|
|
20
|
+
});
|
|
21
|
+
describe('dismiss', () => {
|
|
22
|
+
it('should return dismissed item wrapped in data', async () => {
|
|
23
|
+
const item = (0, factories_1.createTestItem)({
|
|
24
|
+
id: 'test-item',
|
|
25
|
+
dismissedAt: new Date(),
|
|
26
|
+
});
|
|
27
|
+
const previousItem = (0, factories_1.createTestItem)({ id: 'test-item' });
|
|
28
|
+
const context = (0, factories_1.createTestContext)();
|
|
29
|
+
mockService.dismiss.mockResolvedValue({ item, previousItem });
|
|
30
|
+
const result = await controller.dismiss('test-user-id', 'test-item', context);
|
|
31
|
+
expect(result.data.itemId).toBe('test-item');
|
|
32
|
+
expect(mockService.dismiss).toHaveBeenCalledWith('test-item', 'test-user-id', context);
|
|
33
|
+
expect(mockResponseService.success).toHaveBeenCalled();
|
|
34
|
+
});
|
|
35
|
+
});
|
|
36
|
+
});
|
|
37
|
+
//# sourceMappingURL=dismiss.controller.spec.js.map
|