@lenne.tech/nest-server 11.21.2 → 11.22.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.
Files changed (71) hide show
  1. package/.claude/rules/architecture.md +79 -0
  2. package/.claude/rules/better-auth.md +262 -0
  3. package/.claude/rules/configurable-features.md +308 -0
  4. package/.claude/rules/core-modules.md +205 -0
  5. package/.claude/rules/migration-guides.md +149 -0
  6. package/.claude/rules/module-deprecation.md +214 -0
  7. package/.claude/rules/module-inheritance.md +97 -0
  8. package/.claude/rules/package-management.md +112 -0
  9. package/.claude/rules/role-system.md +146 -0
  10. package/.claude/rules/testing.md +120 -0
  11. package/.claude/rules/versioning.md +53 -0
  12. package/CLAUDE.md +172 -0
  13. package/dist/core/common/interfaces/server-options.interface.d.ts +10 -0
  14. package/dist/core/modules/better-auth/core-better-auth-user.mapper.js +25 -25
  15. package/dist/core/modules/better-auth/core-better-auth-user.mapper.js.map +1 -1
  16. package/dist/core/modules/better-auth/core-better-auth.service.js +8 -4
  17. package/dist/core/modules/better-auth/core-better-auth.service.js.map +1 -1
  18. package/dist/core/modules/error-code/error-code.module.js.map +1 -1
  19. package/dist/core/modules/tenant/core-tenant.guard.d.ts +1 -0
  20. package/dist/core/modules/tenant/core-tenant.guard.js +59 -4
  21. package/dist/core/modules/tenant/core-tenant.guard.js.map +1 -1
  22. package/dist/core/modules/tenant/core-tenant.helpers.js.map +1 -1
  23. package/dist/core.module.d.ts +3 -3
  24. package/dist/core.module.js +17 -4
  25. package/dist/core.module.js.map +1 -1
  26. package/dist/server/server.module.js +6 -6
  27. package/dist/server/server.module.js.map +1 -1
  28. package/dist/test/test.helper.d.ts +6 -2
  29. package/dist/test/test.helper.js +28 -6
  30. package/dist/test/test.helper.js.map +1 -1
  31. package/dist/tsconfig.build.tsbuildinfo +1 -1
  32. package/docs/REQUEST-LIFECYCLE.md +1256 -0
  33. package/docs/error-codes.md +446 -0
  34. package/migration-guides/11.10.x-to-11.11.x.md +266 -0
  35. package/migration-guides/11.11.x-to-11.12.x.md +323 -0
  36. package/migration-guides/11.12.x-to-11.13.0.md +612 -0
  37. package/migration-guides/11.13.x-to-11.14.0.md +348 -0
  38. package/migration-guides/11.14.x-to-11.15.0.md +262 -0
  39. package/migration-guides/11.15.0-to-11.15.3.md +118 -0
  40. package/migration-guides/11.15.x-to-11.16.0.md +497 -0
  41. package/migration-guides/11.16.x-to-11.17.0.md +130 -0
  42. package/migration-guides/11.17.x-to-11.18.0.md +393 -0
  43. package/migration-guides/11.18.x-to-11.19.0.md +151 -0
  44. package/migration-guides/11.19.x-to-11.20.0.md +170 -0
  45. package/migration-guides/11.20.x-to-11.21.0.md +216 -0
  46. package/migration-guides/11.21.0-to-11.21.1.md +194 -0
  47. package/migration-guides/11.21.1-to-11.21.2.md +114 -0
  48. package/migration-guides/11.21.2-to-11.21.3.md +175 -0
  49. package/migration-guides/11.21.x-to-11.22.0.md +224 -0
  50. package/migration-guides/11.3.x-to-11.4.x.md +233 -0
  51. package/migration-guides/11.6.x-to-11.7.x.md +394 -0
  52. package/migration-guides/11.7.x-to-11.8.x.md +318 -0
  53. package/migration-guides/11.8.x-to-11.9.x.md +322 -0
  54. package/migration-guides/11.9.x-to-11.10.x.md +571 -0
  55. package/migration-guides/TEMPLATE.md +113 -0
  56. package/package.json +8 -3
  57. package/src/core/common/interfaces/server-options.interface.ts +83 -16
  58. package/src/core/modules/better-auth/CUSTOMIZATION.md +24 -17
  59. package/src/core/modules/better-auth/INTEGRATION-CHECKLIST.md +5 -5
  60. package/src/core/modules/better-auth/core-better-auth-user.mapper.ts +29 -25
  61. package/src/core/modules/better-auth/core-better-auth.service.ts +13 -9
  62. package/src/core/modules/error-code/INTEGRATION-CHECKLIST.md +42 -12
  63. package/src/core/modules/error-code/error-code.module.ts +4 -9
  64. package/src/core/modules/tenant/INTEGRATION-CHECKLIST.md +13 -2
  65. package/src/core/modules/tenant/README.md +26 -1
  66. package/src/core/modules/tenant/core-tenant.guard.ts +142 -11
  67. package/src/core/modules/tenant/core-tenant.helpers.ts +6 -2
  68. package/src/core.module.ts +52 -10
  69. package/src/server/server.module.ts +7 -9
  70. package/src/test/README.md +47 -0
  71. package/src/test/test.helper.ts +55 -6
@@ -0,0 +1,394 @@
1
+ # Migration Guide: 11.6.x → 11.7.x
2
+
3
+ ## TL;DR
4
+
5
+ ```bash
6
+ npm install @lenne.tech/nest-server@11.7.x
7
+ npm run build && npm test # Done! No breaking changes.
8
+ ```
9
+
10
+ **New in 11.7.x:** Simplified `CoreModule.forRoot(envConfig)` for IAM-only projects.
11
+
12
+ ---
13
+
14
+ ## Overview
15
+
16
+ | Category | Details |
17
+ |----------|---------|
18
+ | **Breaking Changes** | None |
19
+ | **New Features** | Simplified CoreModule signature, Legacy endpoint control, IAuthProvider interface, Migration status query, Bidirectional password sync |
20
+ | **Bugfixes** | Improved module inheritance pattern for BetterAuth |
21
+ | **Migration Effort** | ~5 minutes (package update only) |
22
+
23
+ ---
24
+
25
+ ## Choose Your Scenario
26
+
27
+ | Scenario | Use When | CoreModule Signature | Path |
28
+ |----------|----------|---------------------|------|
29
+ | **Legacy Only** | Existing project, no BetterAuth needed | `CoreModule.forRoot(AuthService, AuthModule, envConfig)` | [Path A](#path-a-keep-legacy-auth-no-changes-required) |
30
+ | **Legacy + IAM** | Existing project, migrating to BetterAuth | `CoreModule.forRoot(AuthService, AuthModule, envConfig)` | [Path B](#path-b-add-betterauth-migration-scenario) |
31
+ | **IAM Only** | New project, BetterAuth from start | `CoreModule.forRoot(envConfig)` *(New!)* | [Path C](#path-c-new-project-with-iam-only) |
32
+
33
+ ---
34
+
35
+ ## Quick Migration (No Breaking Changes)
36
+
37
+ Since there are no breaking changes, the migration is straightforward:
38
+
39
+ ```bash
40
+ # Update package
41
+ npm install @lenne.tech/nest-server@11.7.x
42
+
43
+ # Verify build
44
+ npm run build
45
+
46
+ # Run tests
47
+ npm test
48
+ ```
49
+
50
+ **Done!** All existing code continues to work without modifications.
51
+
52
+ ---
53
+
54
+ ## What's New in 11.7.x
55
+
56
+ ### 1. Simplified CoreModule Signature (IAM-Only)
57
+
58
+ New single-parameter signature for projects that only use BetterAuth:
59
+
60
+ ```typescript
61
+ // server.module.ts - NEW: IAM-only (recommended for new projects)
62
+ @Module({
63
+ imports: [
64
+ CoreModule.forRoot(envConfig), // Simple! No AuthService/AuthModule needed
65
+ BetterAuthModule.forRoot({
66
+ config: envConfig.betterAuth,
67
+ fallbackSecrets: [envConfig.jwt?.secret],
68
+ }),
69
+ // ... other modules
70
+ ],
71
+ })
72
+ export class ServerModule {}
73
+ ```
74
+
75
+ **Benefits:**
76
+ - No need to create AuthService or AuthModule for new projects
77
+ - GraphQL subscriptions authenticate via BetterAuth sessions
78
+ - Cleaner setup for modern projects
79
+
80
+ **The 3-parameter signature is now `@deprecated` for new projects** but remains fully functional for existing projects during migration.
81
+
82
+ ### 2. Legacy Endpoint Control (`auth.legacyEndpoints`)
83
+
84
+ New configuration option to disable legacy auth endpoints after BetterAuth migration:
85
+
86
+ ```typescript
87
+ // config.env.ts
88
+ {
89
+ auth: {
90
+ legacyEndpoints: {
91
+ enabled: true, // Default: true
92
+ graphql: true, // Control GraphQL endpoints separately
93
+ rest: true, // Control REST endpoints separately
94
+ }
95
+ }
96
+ }
97
+ ```
98
+
99
+ When disabled, legacy endpoints return HTTP 410 Gone with `LegacyAuthDisabledException`.
100
+
101
+ **Affected Endpoints:**
102
+ - GraphQL: `signIn`, `signUp`, `logout`, `refreshToken`
103
+ - REST: `POST /auth/signin`, `POST /auth/signup`, `GET /auth/logout`, `GET /auth/refresh-token`
104
+
105
+ ### 3. Bidirectional Password Synchronization
106
+
107
+ Passwords are now synchronized between Legacy Auth and BetterAuth:
108
+
109
+ | Direction | Flow | Password Storage |
110
+ |-----------|------|------------------|
111
+ | Legacy → IAM | User signs up via Legacy | `bcrypt(sha256(pw))` + `scrypt(sha256(pw))` |
112
+ | IAM → Legacy | User signs up via BetterAuth | `scrypt(sha256(pw))` + `bcrypt(sha256(pw))` |
113
+
114
+ **Requirement:** Inject `BetterAuthUserMapper` in your `UserService`:
115
+
116
+ ```typescript
117
+ // user.service.ts
118
+ constructor(
119
+ // ... other params ...
120
+ @Optional() private readonly betterAuthUserMapper?: BetterAuthUserMapper,
121
+ ) {
122
+ super(configService, emailService, mainDbModel, mainModelConstructor, { betterAuthUserMapper });
123
+ }
124
+ ```
125
+
126
+ ### 4. IAuthProvider Interface
127
+
128
+ New abstraction layer for authentication providers (preparation for future version):
129
+
130
+ ```typescript
131
+ interface IAuthProvider {
132
+ decodeJwt(token: string): JwtPayload;
133
+ validateUser(payload: JwtPayload): Promise<any>;
134
+ signToken(user: any, expiresIn?: string): string;
135
+ }
136
+ ```
137
+
138
+ ### 5. Migration Status Query
139
+
140
+ GraphQL query for monitoring BetterAuth migration progress (admin only):
141
+
142
+ ```graphql
143
+ query {
144
+ betterAuthMigrationStatus {
145
+ totalUsers
146
+ fullyMigratedUsers
147
+ pendingMigrationUsers
148
+ migrationPercentage
149
+ canDisableLegacyAuth
150
+ pendingUserEmails
151
+ }
152
+ }
153
+ ```
154
+
155
+ ### 6. Deprecation Warnings
156
+
157
+ JSDoc `@deprecated` comments added to legacy auth endpoints and the 3-parameter CoreModule signature.
158
+
159
+ ---
160
+
161
+ ## Detailed Migration Paths
162
+
163
+ ### Path A: Keep Legacy Auth (No Changes Required)
164
+
165
+ If you're not using BetterAuth:
166
+
167
+ ```bash
168
+ npm install @lenne.tech/nest-server@11.7.x
169
+ npm run build && npm test
170
+ ```
171
+
172
+ Your existing code continues to work unchanged.
173
+
174
+ ### Path B: Add BetterAuth (Migration Scenario)
175
+
176
+ For existing projects adding BetterAuth alongside Legacy Auth:
177
+
178
+ 1. **Update Package**
179
+ ```bash
180
+ npm install @lenne.tech/nest-server@11.7.x
181
+ ```
182
+
183
+ 2. **Keep Existing CoreModule Signature**
184
+ ```typescript
185
+ // server.module.ts - Keep your existing setup
186
+ CoreModule.forRoot(AuthService, AuthModule.forRoot(envConfig.jwt), envConfig)
187
+ ```
188
+
189
+ 3. **Add BetterAuth Module**
190
+ Follow the [BetterAuth Integration Checklist](../src/core/modules/better-auth/INTEGRATION-CHECKLIST.md)
191
+
192
+ 4. **Configure Legacy Endpoints**
193
+ ```typescript
194
+ // config.env.ts
195
+ auth: {
196
+ legacyEndpoints: { enabled: true } // Keep during migration
197
+ }
198
+ ```
199
+
200
+ 5. **Monitor Migration Progress**
201
+ ```graphql
202
+ query { betterAuthMigrationStatus { migrationPercentage, canDisableLegacyAuth } }
203
+ ```
204
+
205
+ 6. **Disable Legacy When Ready**
206
+ ```typescript
207
+ auth: {
208
+ legacyEndpoints: { enabled: false } // After all users migrated
209
+ }
210
+ ```
211
+
212
+ ### Path C: New Project with IAM Only
213
+
214
+ For new projects starting fresh with BetterAuth:
215
+
216
+ 1. **Install Package**
217
+ ```bash
218
+ npm install @lenne.tech/nest-server@11.7.x
219
+ ```
220
+
221
+ 2. **Configure ServerModule**
222
+ ```typescript
223
+ // server.module.ts
224
+ @Module({
225
+ imports: [
226
+ CoreModule.forRoot(envConfig), // Simplified! No AuthService/AuthModule needed
227
+ BetterAuthModule.forRoot({
228
+ config: envConfig.betterAuth,
229
+ fallbackSecrets: [envConfig.jwt?.secret],
230
+ }),
231
+ // ... other modules
232
+ ],
233
+ })
234
+ export class ServerModule {}
235
+ ```
236
+
237
+ 3. **Configure config.env.ts**
238
+ ```typescript
239
+ // config.env.ts
240
+ auth: {
241
+ legacyEndpoints: { enabled: false } // Disable Legacy endpoints
242
+ },
243
+ betterAuth: {
244
+ jwt: {}, // Enable JWT tokens
245
+ twoFactor: {}, // Enable 2FA (optional)
246
+ passkey: {}, // Enable Passkeys (optional)
247
+ }
248
+ ```
249
+
250
+ 4. **Follow Integration Checklist**
251
+ See [BetterAuth Integration Checklist](../src/core/modules/better-auth/INTEGRATION-CHECKLIST.md) for required files.
252
+
253
+ ---
254
+
255
+ ## Compatibility Notes
256
+
257
+ ### Module Inheritance Pattern
258
+
259
+ Projects extending `CoreAuthResolver` and `CoreAuthController` continue to work seamlessly. Common patterns observed:
260
+
261
+ **Pattern 1: Override with authService call (common) - MUST call check method**
262
+ ```typescript
263
+ @Resolver()
264
+ export class AuthResolver extends CoreAuthResolver {
265
+ override async signIn(input: SignInInput, ...): Promise<Auth> {
266
+ this.checkLegacyGraphQLEnabled('signIn'); // Required!
267
+ return this.authService.signIn(input, ...);
268
+ }
269
+ }
270
+ ```
271
+ ⚠️ **Important:** When overriding `signIn`, `signUp`, `logout`, or `refreshToken`, you MUST call the protected `checkLegacyGraphQLEnabled()` method. Otherwise, the `auth.legacyEndpoints.enabled: false` configuration will be ignored and legacy endpoints remain accessible.
272
+
273
+ **Pattern 2: Simple extension (no overrides)**
274
+ ```typescript
275
+ @Resolver()
276
+ export class AuthResolver extends CoreAuthResolver {}
277
+ ```
278
+ This pattern benefits from the new deprecation warnings in IDE.
279
+
280
+ ### Custom Role Enums
281
+
282
+ Projects using custom role enums (e.g., `CompanyRoles`) instead of `RoleEnum` continue to work without changes.
283
+
284
+ ### Additional Auth Methods
285
+
286
+ Custom methods like `loginAsCompany`, `getCurrentUser`, or `sendVerificationMail` are unaffected.
287
+
288
+ ---
289
+
290
+ ## Client Configuration
291
+
292
+ New clients should hash passwords with SHA256 before sending:
293
+
294
+ ```typescript
295
+ // auth-client.ts (Nuxt/Vue example)
296
+ import { createAuthClient } from 'better-auth/vue';
297
+
298
+ const baseClient = createAuthClient({
299
+ baseURL: import.meta.env.VITE_API_URL,
300
+ basePath: '/iam', // Must match server config
301
+ plugins: [/* ... */],
302
+ });
303
+
304
+ // Wrap signIn/signUp to hash passwords
305
+ export const authClient = {
306
+ ...baseClient,
307
+ signIn: {
308
+ ...baseClient.signIn,
309
+ email: async (params) => {
310
+ const hashedPassword = await sha256(params.password);
311
+ return baseClient.signIn.email({ ...params, password: hashedPassword });
312
+ },
313
+ },
314
+ // ... same for signUp, resetPassword, etc.
315
+ };
316
+ ```
317
+
318
+ The server accepts both plain and SHA256-hashed passwords but **new clients should always hash**.
319
+
320
+ ---
321
+
322
+ ## Troubleshooting
323
+
324
+ ### Build Errors
325
+
326
+ If type errors occur related to `auth` configuration:
327
+
328
+ ```bash
329
+ rm -rf node_modules package-lock.json
330
+ npm install
331
+ npm run build
332
+ ```
333
+
334
+ ### Legacy Endpoints Return 410
335
+
336
+ If legacy endpoints unexpectedly return 410 Gone:
337
+ 1. Check `config.auth.legacyEndpoints.enabled` is not `false`
338
+ 2. Remove the `auth` configuration block to use defaults
339
+
340
+ ### Tests Fail
341
+
342
+ 1. Ensure MongoDB is running
343
+ 2. Run with debug: `npm run test:e2e-doh`
344
+ 3. Check configuration matches test environment expectations
345
+
346
+ ### GraphQL Subscriptions in IAM-Only Mode
347
+
348
+ GraphQL Subscriptions are fully supported in IAM-only mode. If authentication fails, check:
349
+ 1. Client sends `Authorization: Bearer <session-token>` in WebSocket connection params
350
+ 2. BetterAuth is configured: `betterAuth: { jwt: {} }` (JWT plugin enables token validation)
351
+ 3. Session is valid and not expired
352
+
353
+ ---
354
+
355
+ ## Version Comparison
356
+
357
+ | Version | Feature | Status |
358
+ |---------|---------|--------|
359
+ | 11.6.x | BetterAuth module | Introduced |
360
+ | 11.7.x | Simplified CoreModule signature | New |
361
+ | 11.7.x | IAM-only GraphQL Subscriptions | New |
362
+ | 11.7.x | Legacy endpoint control | New |
363
+ | 11.7.x | Bidirectional password sync | New |
364
+ | 11.7.x | IAuthProvider interface | New |
365
+ | 11.7.x | Migration status query | New |
366
+ | Future | BetterAuth default | Planned |
367
+
368
+ ---
369
+
370
+ ## Module Documentation
371
+
372
+ For detailed information about affected modules, see:
373
+
374
+ ### Auth Module (Legacy Auth)
375
+
376
+ - **Location:** `src/core/modules/auth/`
377
+ - **Key Files:**
378
+ - `core-auth.resolver.ts` - GraphQL endpoints with deprecation warnings
379
+ - `core-auth.controller.ts` - REST endpoints with deprecation warnings
380
+ - `interfaces/auth-provider.interface.ts` - New IAuthProvider interface
381
+
382
+ ### BetterAuth Module (IAM)
383
+
384
+ - **README:** [src/core/modules/better-auth/README.md](../src/core/modules/better-auth/README.md)
385
+ - **Integration Checklist:** [src/core/modules/better-auth/INTEGRATION-CHECKLIST.md](../src/core/modules/better-auth/INTEGRATION-CHECKLIST.md)
386
+ - **Reference Implementation:** `src/server/modules/better-auth/`
387
+
388
+ ---
389
+
390
+ ## References
391
+
392
+ - [Module Deprecation Roadmap](../.claude/rules/module-deprecation.md)
393
+ - [nest-server-starter](https://github.com/lenneTech/nest-server-starter) (reference implementation)
394
+ - [BetterAuth README](../src/core/modules/better-auth/README.md)
@@ -0,0 +1,318 @@
1
+ # Migration Guide: 11.7.x → 11.8.x
2
+
3
+ ## Overview
4
+
5
+ | Category | Details |
6
+ |----------|---------|
7
+ | **Breaking Changes** | 1 (File download endpoint) |
8
+ | **New Features** | 2 (TUS Module, CoreFileController) |
9
+ | **Bugfixes** | None |
10
+ | **Migration Effort** | ~10 minutes |
11
+
12
+ ---
13
+
14
+ ## Prerequisites
15
+
16
+ ### Node.js Version
17
+
18
+ **Node.js >= 20.19.0 is required** for `@tus/server` support.
19
+
20
+ ```bash
21
+ # Check your version
22
+ node --version
23
+
24
+ # Should output v20.19.0 or higher
25
+ ```
26
+
27
+ ### New Dependencies
28
+
29
+ The following packages are automatically installed with nest-server 11.8.x:
30
+
31
+ | Package | Version | Purpose |
32
+ |---------|---------|---------|
33
+ | `@tus/server` | 2.3.0 | TUS protocol server implementation |
34
+ | `@tus/file-store` | 2.0.0 | File storage backend for TUS uploads |
35
+
36
+ These are production dependencies and will be installed automatically when updating nest-server.
37
+
38
+ ---
39
+
40
+ ## Quick Migration
41
+
42
+ ```bash
43
+ # Update package
44
+ npm install @lenne.tech/nest-server@11.8.x
45
+
46
+ # Install new TUS dependencies (automatically included)
47
+ npm install
48
+
49
+ # Verify build
50
+ npm run build
51
+
52
+ # Run tests
53
+ npm test
54
+ ```
55
+
56
+ **Important:** If your project uses file downloads, see [Breaking Changes](#breaking-changes) below.
57
+
58
+ ---
59
+
60
+ ## What's New in 11.8.x
61
+
62
+ ### 1. TUS Module (Resumable Uploads)
63
+
64
+ TUS is **enabled by default** - no configuration required! The module provides resumable file uploads using the [tus.io](https://tus.io) protocol.
65
+
66
+ **Endpoints (automatically available):**
67
+
68
+ | Method | Endpoint | Description |
69
+ |--------|----------|-------------|
70
+ | OPTIONS | `/tus` | Get server capabilities |
71
+ | POST | `/tus` | Create new upload |
72
+ | HEAD | `/tus/:id` | Get upload status |
73
+ | PATCH | `/tus/:id` | Continue upload |
74
+ | DELETE | `/tus/:id` | Terminate upload |
75
+
76
+ **Default Configuration:**
77
+ ```typescript
78
+ {
79
+ enabled: true,
80
+ path: '/tus',
81
+ maxSize: 50 * 1024 * 1024 * 1024, // 50 GB
82
+ expiration: { expiresIn: '24h' },
83
+ }
84
+ ```
85
+
86
+ > **Note:** `@tus/server` already includes all TUS protocol headers (Authorization, Content-Type, Tus-Resumable, Upload-Length, Upload-Metadata, Upload-Offset, etc.). The `allowedHeaders` option is only for project-specific custom headers.
87
+
88
+ **Add custom headers (if needed):**
89
+ ```typescript
90
+ // config.env.ts
91
+ tus: {
92
+ allowedHeaders: ['X-Custom-Header'], // Only additional project-specific headers
93
+ }
94
+ ```
95
+
96
+ **Disable TUS (if needed):**
97
+ ```typescript
98
+ // server.module.ts
99
+ TusModule.forRoot({ config: false })
100
+ ```
101
+
102
+ **Client Usage:**
103
+ ```typescript
104
+ import { Upload } from 'tus-js-client';
105
+
106
+ const upload = new Upload(file, {
107
+ endpoint: 'http://localhost:3000/tus',
108
+ metadata: { filename: file.name, filetype: file.type },
109
+ onSuccess: () => console.log('Upload complete!'),
110
+ });
111
+ upload.start();
112
+ ```
113
+
114
+ ### 2. CoreFileController (Public Download Endpoints)
115
+
116
+ New abstract controller providing public file download endpoints:
117
+
118
+ | Endpoint | Description | Permission |
119
+ |----------|-------------|------------|
120
+ | `GET /files/id/:id` | Download by ID | S_EVERYONE |
121
+ | `GET /files/:filename` | Download by filename | S_EVERYONE |
122
+
123
+ Projects extending `CoreFileController` automatically get these endpoints.
124
+
125
+ ---
126
+
127
+ ## Breaking Changes
128
+
129
+ ### Change 1: File Download Endpoint Pattern
130
+
131
+ The file download by ID endpoint has changed from `/files/:id` to `/files/id/:id`.
132
+
133
+ **Before (11.7.x):**
134
+ ```typescript
135
+ // FileController with custom download endpoint
136
+ @Get(':id')
137
+ @Roles(RoleEnum.ADMIN)
138
+ async getFile(@Param('id') id: string, @Res() res: Response) { }
139
+
140
+ // Client usage
141
+ GET /files/abc123 → Downloads file by ID (admin only)
142
+ ```
143
+
144
+ **After (11.8.x):**
145
+ ```typescript
146
+ // FileController extends CoreFileController
147
+ export class FileController extends CoreFileController {
148
+ constructor(protected override readonly fileService: FileService) {
149
+ super(fileService);
150
+ }
151
+ // Inherited: GET /files/id/:id (public)
152
+ // Inherited: GET /files/:filename (public)
153
+ }
154
+
155
+ // Client usage
156
+ GET /files/id/abc123 → Downloads file by ID (public)
157
+ GET /files/example.pdf → Downloads file by filename (public)
158
+ ```
159
+
160
+ **Migration Steps:**
161
+
162
+ 1. **Update FileController** to extend `CoreFileController`:
163
+
164
+ ```typescript
165
+ // src/server/modules/file/file.controller.ts
166
+ import { Controller, Delete, Get, Param, Post, UploadedFile, UseInterceptors } from '@nestjs/common';
167
+ import { CoreFileController, Roles, RoleEnum } from '@lenne.tech/nest-server';
168
+ import { FileService } from './file.service';
169
+
170
+ @Controller('files')
171
+ @Roles(RoleEnum.ADMIN)
172
+ export class FileController extends CoreFileController {
173
+ constructor(protected override readonly fileService: FileService) {
174
+ super(fileService);
175
+ }
176
+
177
+ // Keep your admin-only endpoints (upload, info, delete)
178
+ @Post('upload')
179
+ @Roles(RoleEnum.ADMIN)
180
+ @UseInterceptors(FileInterceptor('file'))
181
+ async uploadFile(@UploadedFile() file: Express.Multer.File) { /* ... */ }
182
+
183
+ @Get('info/:id')
184
+ @Roles(RoleEnum.ADMIN)
185
+ async getFileInfo(@Param('id') id: string) { /* ... */ }
186
+
187
+ @Delete(':id')
188
+ @Roles(RoleEnum.ADMIN)
189
+ async deleteFile(@Param('id') id: string) { /* ... */ }
190
+
191
+ // REMOVE your old getFile() method - CoreFileController handles downloads
192
+ }
193
+ ```
194
+
195
+ 2. **Update client-side download URLs:**
196
+
197
+ ```typescript
198
+ // Before
199
+ const downloadUrl = `/files/${fileId}`;
200
+
201
+ // After
202
+ const downloadUrl = `/files/id/${fileId}`;
203
+ // Or by filename:
204
+ const downloadUrl = `/files/${filename}`;
205
+ ```
206
+
207
+ 3. **Optional: Restrict download access** (if you need authentication):
208
+
209
+ ```typescript
210
+ @Controller('files')
211
+ @Roles(RoleEnum.ADMIN)
212
+ export class FileController extends CoreFileController {
213
+ // Override to require authentication
214
+ @Get('id/:id')
215
+ @Roles(RoleEnum.S_USER) // Require logged-in user
216
+ override async getFileById(@Param('id') id: string, @Res() res: Response) {
217
+ return super.getFileById(id, res);
218
+ }
219
+
220
+ @Get(':filename')
221
+ @Roles(RoleEnum.S_USER)
222
+ override async getFile(@Param('filename') filename: string, @Res() res: Response) {
223
+ return super.getFile(filename, res);
224
+ }
225
+ }
226
+ ```
227
+
228
+ ---
229
+
230
+ ## Compatibility Notes
231
+
232
+ ### Pattern: Custom FileController without CoreFileController
233
+
234
+ If you want to keep the old behavior exactly:
235
+
236
+ ```typescript
237
+ // This still works - don't extend CoreFileController
238
+ @Controller('files')
239
+ @Roles(RoleEnum.ADMIN)
240
+ export class FileController {
241
+ constructor(private readonly fileService: FileService) {}
242
+
243
+ @Get(':id')
244
+ @Roles(RoleEnum.ADMIN)
245
+ async getFile(@Param('id') id: string, @Res() res: Response) {
246
+ // Your existing implementation
247
+ }
248
+ }
249
+ ```
250
+
251
+ ### Pattern: TUS with Authentication
252
+
253
+ By default, TUS allows everyone to upload. To require authentication:
254
+
255
+ ```typescript
256
+ // src/server/modules/tus/tus.controller.ts
257
+ import { Controller } from '@nestjs/common';
258
+ import { CoreTusController, Roles, RoleEnum } from '@lenne.tech/nest-server';
259
+
260
+ @Controller('tus')
261
+ @Roles(RoleEnum.S_USER) // Require logged-in user
262
+ export class TusController extends CoreTusController {}
263
+
264
+ // server.module.ts
265
+ TusModule.forRoot({ controller: TusController })
266
+ ```
267
+
268
+ ---
269
+
270
+ ## Troubleshooting
271
+
272
+ ### Download returns 404 after migration
273
+
274
+ **Cause:** Using old endpoint pattern `/files/:id` instead of `/files/id/:id`
275
+
276
+ **Solution:** Update client to use `/files/id/:id` or `/files/:filename`
277
+
278
+ ### TUS uploads not working
279
+
280
+ **Cause:** TUS might be disabled in config
281
+
282
+ **Solution:** Check that `tus: false` is not set in your config. TUS is enabled by default.
283
+
284
+ ### TypeScript error: "must have an 'override' modifier"
285
+
286
+ **Cause:** `fileService` in constructor needs `override` when extending CoreFileController
287
+
288
+ **Solution:**
289
+ ```typescript
290
+ // Add 'override' keyword
291
+ constructor(protected override readonly fileService: FileService) {
292
+ super(fileService);
293
+ }
294
+ ```
295
+
296
+ ---
297
+
298
+ ## Module Documentation
299
+
300
+ ### TUS Module
301
+
302
+ - **README:** [src/core/modules/tus/README.md](../src/core/modules/tus/README.md)
303
+ - **Integration Checklist:** [src/core/modules/tus/INTEGRATION-CHECKLIST.md](../src/core/modules/tus/INTEGRATION-CHECKLIST.md)
304
+ - **Reference Implementation:** `src/server/server.module.ts`
305
+
306
+ ### File Module
307
+
308
+ - **README:** [src/core/modules/file/README.md](../src/core/modules/file/README.md)
309
+ - **Reference Implementation:** `src/server/modules/file/file.controller.ts`
310
+
311
+ ---
312
+
313
+ ## References
314
+
315
+ - [TUS Protocol](https://tus.io/protocols/resumable-upload)
316
+ - [tus-js-client](https://github.com/tus/tus-js-client)
317
+ - [@tus/server](https://github.com/tus/tus-node-server)
318
+ - [nest-server-starter](https://github.com/lenneTech/nest-server-starter) (reference implementation)