@solidxai/core 0.1.9-beta.7 → 0.1.9-beta.8

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 (172) hide show
  1. package/dist/constants/chatter-message.constants.d.ts +6 -0
  2. package/dist/constants/chatter-message.constants.d.ts.map +1 -1
  3. package/dist/constants/chatter-message.constants.js +7 -1
  4. package/dist/constants/chatter-message.constants.js.map +1 -1
  5. package/dist/controllers/authentication.controller.d.ts +12 -0
  6. package/dist/controllers/authentication.controller.d.ts.map +1 -1
  7. package/dist/controllers/authentication.controller.js +13 -0
  8. package/dist/controllers/authentication.controller.js.map +1 -1
  9. package/dist/controllers/chatter-message.controller.d.ts +1 -0
  10. package/dist/controllers/chatter-message.controller.d.ts.map +1 -1
  11. package/dist/controllers/chatter-message.controller.js +12 -0
  12. package/dist/controllers/chatter-message.controller.js.map +1 -1
  13. package/dist/controllers/facebook-authentication.controller.d.ts +27 -0
  14. package/dist/controllers/facebook-authentication.controller.d.ts.map +1 -0
  15. package/dist/controllers/facebook-authentication.controller.js +117 -0
  16. package/dist/controllers/facebook-authentication.controller.js.map +1 -0
  17. package/dist/controllers/menu-item-metadata.controller.d.ts +1 -0
  18. package/dist/controllers/menu-item-metadata.controller.d.ts.map +1 -1
  19. package/dist/controllers/menu-item-metadata.controller.js +15 -0
  20. package/dist/controllers/menu-item-metadata.controller.js.map +1 -1
  21. package/dist/controllers/microsoft-authentication.controller.d.ts +27 -0
  22. package/dist/controllers/microsoft-authentication.controller.d.ts.map +1 -0
  23. package/dist/controllers/microsoft-authentication.controller.js +118 -0
  24. package/dist/controllers/microsoft-authentication.controller.js.map +1 -0
  25. package/dist/controllers/setting.controller.d.ts +2 -2
  26. package/dist/controllers/setting.controller.js +2 -2
  27. package/dist/decorators/auth.decorator.d.ts.map +1 -1
  28. package/dist/decorators/computed-field-provider.decorator.d.ts.map +1 -1
  29. package/dist/decorators/dashboard-question-data-provider.decorator.d.ts.map +1 -1
  30. package/dist/decorators/dashboard-selection-provider.decorator.d.ts.map +1 -1
  31. package/dist/decorators/disallow-in-production.decorator.d.ts.map +1 -1
  32. package/dist/decorators/error-codes-provider.decorator.d.ts.map +1 -1
  33. package/dist/decorators/extension-user-creation-provider.decorator.d.ts.map +1 -1
  34. package/dist/decorators/is-not-in-enum.decorator.d.ts.map +1 -1
  35. package/dist/decorators/mail-provider.decorator.d.ts.map +1 -1
  36. package/dist/decorators/roles.decorator.d.ts.map +1 -1
  37. package/dist/decorators/scheduled-job-provider.decorator.d.ts.map +1 -1
  38. package/dist/decorators/security-rule-config-provider.decorator.d.ts.map +1 -1
  39. package/dist/decorators/selection-provider.decorator.d.ts.map +1 -1
  40. package/dist/decorators/sms-provider.decorator.d.ts.map +1 -1
  41. package/dist/decorators/solid-database-module.decorator.d.ts.map +1 -1
  42. package/dist/decorators/whatsapp-provider.decorator.d.ts.map +1 -1
  43. package/dist/dtos/create-chatter-message.dto.d.ts +1 -0
  44. package/dist/dtos/create-chatter-message.dto.d.ts.map +1 -1
  45. package/dist/dtos/create-chatter-message.dto.js +7 -1
  46. package/dist/dtos/create-chatter-message.dto.js.map +1 -1
  47. package/dist/dtos/post-chatter-message.dto.d.ts +1 -0
  48. package/dist/dtos/post-chatter-message.dto.d.ts.map +1 -1
  49. package/dist/dtos/post-chatter-message.dto.js +6 -1
  50. package/dist/dtos/post-chatter-message.dto.js.map +1 -1
  51. package/dist/dtos/update-chatter-message.dto.d.ts +1 -0
  52. package/dist/dtos/update-chatter-message.dto.d.ts.map +1 -1
  53. package/dist/dtos/update-chatter-message.dto.js +7 -1
  54. package/dist/dtos/update-chatter-message.dto.js.map +1 -1
  55. package/dist/entities/chatter-message.entity.d.ts +1 -0
  56. package/dist/entities/chatter-message.entity.d.ts.map +1 -1
  57. package/dist/entities/chatter-message.entity.js +5 -1
  58. package/dist/entities/chatter-message.entity.js.map +1 -1
  59. package/dist/entities/user.entity.d.ts +8 -0
  60. package/dist/entities/user.entity.d.ts.map +1 -1
  61. package/dist/entities/user.entity.js +33 -1
  62. package/dist/entities/user.entity.js.map +1 -1
  63. package/dist/helpers/cors.helper.js +1 -1
  64. package/dist/helpers/cors.helper.js.map +1 -1
  65. package/dist/helpers/facebook-oauth.helper.d.ts +8 -0
  66. package/dist/helpers/facebook-oauth.helper.d.ts.map +1 -0
  67. package/dist/helpers/facebook-oauth.helper.js +11 -0
  68. package/dist/helpers/facebook-oauth.helper.js.map +1 -0
  69. package/dist/helpers/microsoft-oauth.helper.d.ts +9 -0
  70. package/dist/helpers/microsoft-oauth.helper.d.ts.map +1 -0
  71. package/dist/helpers/microsoft-oauth.helper.js +12 -0
  72. package/dist/helpers/microsoft-oauth.helper.js.map +1 -0
  73. package/dist/helpers/security.helper.d.ts.map +1 -1
  74. package/dist/helpers/string.helper.d.ts.map +1 -1
  75. package/dist/helpers/user-helper.d.ts.map +1 -1
  76. package/dist/helpers/user-helper.js +4 -0
  77. package/dist/helpers/user-helper.js.map +1 -1
  78. package/dist/index.d.ts +2 -0
  79. package/dist/index.d.ts.map +1 -1
  80. package/dist/index.js +2 -0
  81. package/dist/index.js.map +1 -1
  82. package/dist/interfaces.d.ts +19 -0
  83. package/dist/interfaces.d.ts.map +1 -1
  84. package/dist/interfaces.js.map +1 -1
  85. package/dist/passport-strategies/facebook-oauth.strategy.d.ts +14 -0
  86. package/dist/passport-strategies/facebook-oauth.strategy.d.ts.map +1 -0
  87. package/dist/passport-strategies/facebook-oauth.strategy.js +73 -0
  88. package/dist/passport-strategies/facebook-oauth.strategy.js.map +1 -0
  89. package/dist/passport-strategies/microsoft-oauth.strategy.d.ts +14 -0
  90. package/dist/passport-strategies/microsoft-oauth.strategy.d.ts.map +1 -0
  91. package/dist/passport-strategies/microsoft-oauth.strategy.js +77 -0
  92. package/dist/passport-strategies/microsoft-oauth.strategy.js.map +1 -0
  93. package/dist/seeders/seed-data/solid-core-metadata.json +27 -58
  94. package/dist/services/api-key.service.d.ts +17 -1
  95. package/dist/services/api-key.service.d.ts.map +1 -1
  96. package/dist/services/api-key.service.js +38 -2
  97. package/dist/services/api-key.service.js.map +1 -1
  98. package/dist/services/authentication.service.d.ts +51 -16
  99. package/dist/services/authentication.service.d.ts.map +1 -1
  100. package/dist/services/authentication.service.js +318 -150
  101. package/dist/services/authentication.service.js.map +1 -1
  102. package/dist/services/chatter-message.service.d.ts +1 -0
  103. package/dist/services/chatter-message.service.d.ts.map +1 -1
  104. package/dist/services/chatter-message.service.js +24 -7
  105. package/dist/services/chatter-message.service.js.map +1 -1
  106. package/dist/services/crud-helper.service.d.ts.map +1 -1
  107. package/dist/services/model-metadata.service.js +1 -1
  108. package/dist/services/model-metadata.service.js.map +1 -1
  109. package/dist/services/setting.service.d.ts +5 -2
  110. package/dist/services/setting.service.d.ts.map +1 -1
  111. package/dist/services/setting.service.js +51 -6
  112. package/dist/services/setting.service.js.map +1 -1
  113. package/dist/services/settings/default-settings-provider.service.d.ts +830 -0
  114. package/dist/services/settings/default-settings-provider.service.d.ts.map +1 -1
  115. package/dist/services/settings/default-settings-provider.service.js +1033 -117
  116. package/dist/services/settings/default-settings-provider.service.js.map +1 -1
  117. package/dist/services/user.service.d.ts +2 -0
  118. package/dist/services/user.service.d.ts.map +1 -1
  119. package/dist/services/user.service.js +72 -0
  120. package/dist/services/user.service.js.map +1 -1
  121. package/dist/solid-core.module.d.ts.map +1 -1
  122. package/dist/solid-core.module.js +11 -3
  123. package/dist/solid-core.module.js.map +1 -1
  124. package/dist/transformers/array-transformer.d.ts.map +1 -1
  125. package/dist/transformers/boolean-transformer.d.ts.map +1 -1
  126. package/dist/transformers/datetime-transformer.d.ts.map +1 -1
  127. package/dist/transformers/integer-transformer.d.ts.map +1 -1
  128. package/dist/validators/is-parsable-int.d.ts.map +1 -1
  129. package/dist-tests/api/authenticate.spec.js +119 -0
  130. package/dist-tests/api/authenticate.spec.js.map +1 -0
  131. package/dist-tests/api/crud-service.findOne.cityMaster.spec.js +97 -0
  132. package/dist-tests/api/crud-service.findOne.cityMaster.spec.js.map +1 -0
  133. package/dist-tests/api/ping.spec.js +21 -0
  134. package/dist-tests/api/ping.spec.js.map +1 -0
  135. package/dist-tests/helpers/auth.js +41 -0
  136. package/dist-tests/helpers/auth.js.map +1 -0
  137. package/dist-tests/helpers/env.js +11 -0
  138. package/dist-tests/helpers/env.js.map +1 -0
  139. package/docs/java-spring/README.md +3 -0
  140. package/docs/java-spring/solid-core-module-deep-dive-report.md +1317 -0
  141. package/nest +0 -0
  142. package/package.json +7 -1
  143. package/src/constants/chatter-message.constants.ts +7 -0
  144. package/src/controllers/authentication.controller.ts +8 -1
  145. package/src/controllers/chatter-message.controller.ts +6 -0
  146. package/src/controllers/facebook-authentication.controller.ts +113 -0
  147. package/src/controllers/menu-item-metadata.controller.ts +21 -15
  148. package/src/controllers/microsoft-authentication.controller.ts +116 -0
  149. package/src/dtos/create-chatter-message.dto.ts +11 -0
  150. package/src/dtos/post-chatter-message.dto.ts +4 -0
  151. package/src/dtos/update-chatter-message.dto.ts +13 -1
  152. package/src/entities/chatter-message.entity.ts +4 -1
  153. package/src/entities/user.entity.ts +32 -0
  154. package/src/helpers/cors.helper.ts +1 -1
  155. package/src/helpers/facebook-oauth.helper.ts +17 -0
  156. package/src/helpers/microsoft-oauth.helper.ts +19 -0
  157. package/src/helpers/user-helper.ts +4 -0
  158. package/src/index.ts +2 -0
  159. package/src/interfaces.ts +32 -1
  160. package/src/passport-strategies/facebook-oauth.strategy.ts +64 -0
  161. package/src/passport-strategies/microsoft-oauth.strategy.ts +70 -0
  162. package/src/seeders/seed-data/solid-core-metadata.json +27 -58
  163. package/src/services/api-key.service.ts +77 -35
  164. package/src/services/authentication.service.ts +1717 -1278
  165. package/src/services/chatter-message.service.ts +23 -3
  166. package/src/services/model-metadata.service.ts +1 -1
  167. package/src/services/setting.service.ts +64 -8
  168. package/src/services/settings/default-settings-provider.service.ts +1104 -155
  169. package/src/services/user.service.ts +87 -0
  170. package/src/solid-core.module.ts +25 -8
  171. package/.claude/settings.local.json +0 -15
  172. package/src/services/1.js +0 -6
package/nest ADDED
File without changes
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@solidxai/core",
3
- "version": "0.1.9-beta.7",
3
+ "version": "0.1.9-beta.8",
4
4
  "description": "This module is a NestJS module containing all the required core providers required by a Solid application",
5
5
  "main": "dist/index.js",
6
6
  "types": "dist/index.d.ts",
@@ -38,6 +38,7 @@
38
38
  "@nest-lab/throttler-storage-redis": "^1.1.0",
39
39
  "@nestjs/schedule": "^6.0.0",
40
40
  "@nestjs/throttler": "^6.4.0",
41
+ "@types/passport-apple": "^2.0.3",
41
42
  "amqplib": "^0.10.4",
42
43
  "axios": "^1.7.0",
43
44
  "bcrypt": "^5.1.1",
@@ -62,9 +63,12 @@
62
63
  "mysql2": "^3.13.0",
63
64
  "nodemailer": "^6.9.13",
64
65
  "passport": "^0.7.0",
66
+ "passport-apple": "^2.0.2",
67
+ "passport-facebook": "^3.0.0",
65
68
  "passport-google-oauth2": "^0.2.0",
66
69
  "passport-jwt": "^4.0.1",
67
70
  "passport-local": "^1.0.0",
71
+ "passport-microsoft": "^2.1.0",
68
72
  "pg": "^8.11.3",
69
73
  "pluralize": "^8.0.0",
70
74
  "puppeteer": "^23.2.0",
@@ -134,9 +138,11 @@
134
138
  "@types/multer": "^1.4.11",
135
139
  "@types/node": "^20.3.1",
136
140
  "@types/nodemailer": "^6.4.15",
141
+ "@types/passport-facebook": "^3.0.3",
137
142
  "@types/passport-google-oauth2": "^0.1.8",
138
143
  "@types/passport-jwt": "^4.0.1",
139
144
  "@types/passport-local": "^1.0.38",
145
+ "@types/passport-microsoft": "^2.1.1",
140
146
  "@types/pluralize": "^0.0.33",
141
147
  "@types/qs": "^6.9.15",
142
148
  "@types/supertest": "^2.0.12",
@@ -8,4 +8,11 @@ export const CHATTER_MESSAGE_SUBTYPE = {
8
8
  AUDIT_UPDATE: 'audit_update',
9
9
  AUDIT_DELETE: 'audit_delete',
10
10
  CUSTOM: 'custom',
11
+ NOTE: 'note',
12
+ TASK: 'task',
13
+ } as const;
14
+
15
+ export const CHATTER_MESSAGE_STATUS = {
16
+ PENDING: 'pending',
17
+ COMPLETED: 'completed',
11
18
  } as const;
@@ -1,5 +1,5 @@
1
1
  import { Body, Controller, Get, HttpCode, HttpStatus, Logger, Param, ParseIntPipe, Patch, Post, Res, Headers } from '@nestjs/common';
2
- import { ApiBearerAuth, ApiTags } from '@nestjs/swagger';
2
+ import { ApiBearerAuth, ApiHeader, ApiTags } from '@nestjs/swagger';
3
3
  import { Response } from 'express';
4
4
  import { ActiveUser } from "../decorators/active-user.decorator";
5
5
  import { Public } from '../decorators/public.decorator';
@@ -142,6 +142,13 @@ export class AuthenticationController {
142
142
  return this.apiKeyService.updateKey(id, activeUser.sub, dto);
143
143
  }
144
144
 
145
+ @Public()
146
+ @ApiHeader({ name: 'solidx-api-key', required: true, description: 'API key for authenticating the request' })
147
+ @Get('api-keys/me')
148
+ async apiKeyMe(@Headers('solidx-api-key') apiKey: string) {
149
+ return this.apiKeyService.apiKeyMe(apiKey);
150
+ }
151
+
145
152
  @Post('sso/code')
146
153
  @HttpCode(HttpStatus.OK)
147
154
  generateSsoCode(
@@ -121,4 +121,10 @@ export class ChatterMessageController {
121
121
  ) {
122
122
  return this.service.postMessage(postDto, files);
123
123
  }
124
+
125
+ @ApiBearerAuth("jwt")
126
+ @Patch(':id/complete')
127
+ async markCompleted(@Param('id') id: string) {
128
+ return this.service.markCompleted(+id);
129
+ }
124
130
  }
@@ -0,0 +1,113 @@
1
+ import {
2
+ Controller,
3
+ Get,
4
+ Inject,
5
+ InternalServerErrorException,
6
+ Query,
7
+ Req,
8
+ Res,
9
+ UseGuards,
10
+ } from "@nestjs/common";
11
+ import { ApiQuery, ApiTags } from "@nestjs/swagger";
12
+ import { Request, Response } from "express";
13
+ import {
14
+ FacebookAuthConfiguration,
15
+ isFacebookOAuthConfigured,
16
+ } from "../helpers/facebook-oauth.helper";
17
+ import { AuthenticationService } from "../services/authentication.service";
18
+ import { SettingService } from "../services/setting.service";
19
+ import { Public } from "src/decorators/public.decorator";
20
+ import { Auth } from "../decorators/auth.decorator";
21
+ import { AuthType } from "../enums/auth-type.enum";
22
+ import { FacebookOauthGuard } from "../passport-strategies/facebook-oauth.strategy";
23
+ import { UserService } from "../services/user.service";
24
+ import type { SolidCoreSetting } from "../services/settings/default-settings-provider.service";
25
+
26
+ @Auth(AuthType.None)
27
+ @ApiTags("Iam")
28
+ @Controller("iam/facebook")
29
+ export class FacebookAuthenticationController {
30
+ constructor(
31
+ private readonly userService: UserService,
32
+ private readonly authService: AuthenticationService,
33
+ private readonly settingService: SettingService,
34
+ ) {}
35
+
36
+ private async getConfiguration(): Promise<FacebookAuthConfiguration> {
37
+ return {
38
+ clientID:
39
+ await this.settingService.getConfigValue<SolidCoreSetting>(
40
+ "FACEBOOK_CLIENT_ID",
41
+ ),
42
+ clientSecret: await this.settingService.getConfigValue<SolidCoreSetting>(
43
+ "FACEBOOK_CLIENT_SECRET",
44
+ ),
45
+ callbackURL: await this.settingService.getConfigValue<SolidCoreSetting>(
46
+ "FACEBOOK_CALLBACK_URL",
47
+ ),
48
+ redirectURL: await this.settingService.getConfigValue<SolidCoreSetting>(
49
+ "FACEBOOK_REDIRECT_URL",
50
+ ),
51
+ };
52
+ }
53
+
54
+ private async validateConfiguration() {
55
+ const config = await this.getConfiguration();
56
+ if (!isFacebookOAuthConfigured(config)) {
57
+ throw new InternalServerErrorException(
58
+ "Facebook OAuth is not configured",
59
+ );
60
+ }
61
+ return config;
62
+ }
63
+
64
+ @Public()
65
+ @UseGuards(FacebookOauthGuard)
66
+ @Get("connect")
67
+ async connect() {
68
+ await this.validateConfiguration();
69
+ }
70
+
71
+ @Public()
72
+ @Get("connect/callback")
73
+ @UseGuards(FacebookOauthGuard)
74
+ async facebookAuthCallback(@Req() req: Request, @Res() res: Response) {
75
+ const config = await this.validateConfiguration();
76
+ const user = req.user;
77
+ return res.redirect(`${config.redirectURL}?accessCode=${user['accessCode']}`);
78
+ }
79
+
80
+ /**
81
+ * This is just a dummy endpoint where we are passing in the accessCode, this will be configured in the .env as an environment variable and
82
+ * will be passed the accessCode, using the accessCode the UI code on this page will mostly invoke the /iam/facebook/auth endpoint which will finally generate the JWT token.
83
+ *
84
+ * @param accessCode
85
+ * @returns
86
+ */
87
+ @Public()
88
+ @Get('dummy-redirect')
89
+ async dummyFacebookAuthRedirect(@Query('accessCode') accessCode) {
90
+ await this.validateConfiguration();
91
+ const user = await this.userService.findOneByAccessCode(accessCode);
92
+
93
+ if (user) {
94
+ delete user['password'];
95
+ }
96
+
97
+ return user;
98
+ }
99
+
100
+ /**
101
+ * Use this endpoint to authenticate using an accessCode with Facebook.
102
+ *
103
+ * @param accessCode
104
+ * @returns
105
+ */
106
+ @Public()
107
+ @Get("authenticate")
108
+ @ApiQuery({ name: "accessCode", required: true, type: String })
109
+ async facebookAuth(@Query("accessCode") accessCode: string) {
110
+ await this.validateConfiguration();
111
+ return this.authService.signInUsingFacebook(accessCode);
112
+ }
113
+ }
@@ -1,4 +1,4 @@
1
- import { Controller, Post, Body, Param, UploadedFiles, UseInterceptors, Put, Get, Query, Delete } from '@nestjs/common';
1
+ import { Controller, Post, Body, Param, UploadedFiles, UseInterceptors, Put, Get, Query, Delete, Patch } from '@nestjs/common';
2
2
  import { AnyFilesInterceptor } from "@nestjs/platform-express";
3
3
  import { ApiBearerAuth, ApiForbiddenResponse, ApiQuery, ApiTags } from '@nestjs/swagger';
4
4
  import { MenuItemMetadataService } from '../services/menu-item-metadata.service';
@@ -17,23 +17,23 @@ export class MenuItemMetadataController {
17
17
  @ApiBearerAuth("jwt")
18
18
  @Post()
19
19
  @UseInterceptors(AnyFilesInterceptor())
20
- create(@Body() createDto: CreateMenuItemMetadataDto, @UploadedFiles() files: Array<Express.Multer.File>,@SolidRequestContextDecorator() solidRequestContext:SolidRequestContextDto) {
21
- return this.service.create(createDto, files,solidRequestContext);
20
+ create(@Body() createDto: CreateMenuItemMetadataDto, @UploadedFiles() files: Array<Express.Multer.File>, @SolidRequestContextDecorator() solidRequestContext: SolidRequestContextDto) {
21
+ return this.service.create(createDto, files, solidRequestContext);
22
22
  }
23
23
 
24
24
  @ApiBearerAuth("jwt")
25
25
  @Post('/bulk')
26
26
  @UseInterceptors(AnyFilesInterceptor())
27
- insertMany(@Body() createDtos: CreateMenuItemMetadataDto[], @UploadedFiles() filesArray: Express.Multer.File[][] = [],@SolidRequestContextDecorator() solidRequestContext:SolidRequestContextDto) {
28
- return this.service.insertMany(createDtos, filesArray,solidRequestContext);
27
+ insertMany(@Body() createDtos: CreateMenuItemMetadataDto[], @UploadedFiles() filesArray: Express.Multer.File[][] = [], @SolidRequestContextDecorator() solidRequestContext: SolidRequestContextDto) {
28
+ return this.service.insertMany(createDtos, filesArray, solidRequestContext);
29
29
  }
30
30
 
31
31
 
32
32
  @ApiBearerAuth("jwt")
33
33
  @Put(':id')
34
34
  @UseInterceptors(AnyFilesInterceptor())
35
- update(@Param('id') id: number, @Body() updateDto: UpdateMenuItemMetadataDto, @UploadedFiles() files: Array<Express.Multer.File>,@SolidRequestContextDecorator() solidRequestContext:SolidRequestContextDto) {
36
- return this.service.update(id, updateDto, files,false,solidRequestContext);
35
+ update(@Param('id') id: number, @Body() updateDto: UpdateMenuItemMetadataDto, @UploadedFiles() files: Array<Express.Multer.File>, @SolidRequestContextDecorator() solidRequestContext: SolidRequestContextDto) {
36
+ return this.service.update(id, updateDto, files, false, solidRequestContext);
37
37
  }
38
38
 
39
39
  @ApiBearerAuth("jwt")
@@ -48,8 +48,8 @@ export class MenuItemMetadataController {
48
48
  @ApiQuery({ name: 'populateMedia', required: false, type: Array })
49
49
  @ApiQuery({ name: 'filters', required: false, type: Array })
50
50
  @Get()
51
- async findMany(@Query() query: any,@SolidRequestContextDecorator() solidRequestContext:SolidRequestContextDto) {
52
- return this.service.find(query,solidRequestContext);
51
+ async findMany(@Query() query: any, @SolidRequestContextDecorator() solidRequestContext: SolidRequestContextDto) {
52
+ return this.service.find(query, solidRequestContext);
53
53
  }
54
54
 
55
55
  // /api/solid-menu-item/me
@@ -63,19 +63,25 @@ export class MenuItemMetadataController {
63
63
 
64
64
  @ApiBearerAuth("jwt")
65
65
  @Get(':id')
66
- async findOne(@Param('id') id: string, @Query() query: any,@SolidRequestContextDecorator() solidRequestContext:SolidRequestContextDto) {
67
- return this.service.findOne(+id, query,solidRequestContext);
66
+ async findOne(@Param('id') id: string, @Query() query: any, @SolidRequestContextDecorator() solidRequestContext: SolidRequestContextDto) {
67
+ return this.service.findOne(+id, query, solidRequestContext);
68
68
  }
69
69
 
70
70
  @Delete('/bulk')
71
- async deleteMany(@Body() ids: number[],@SolidRequestContextDecorator() solidRequestContext:SolidRequestContextDto) {
72
- return this.service.deleteMany(ids,solidRequestContext);
71
+ async deleteMany(@Body() ids: number[], @SolidRequestContextDecorator() solidRequestContext: SolidRequestContextDto) {
72
+ return this.service.deleteMany(ids, solidRequestContext);
73
73
  }
74
74
 
75
75
  @ApiBearerAuth("jwt")
76
76
  @Delete(':id')
77
- async delete(@Param('id') id: number,@SolidRequestContextDecorator() solidRequestContext:SolidRequestContextDto) {
78
- return this.service.delete(id,solidRequestContext);
77
+ async delete(@Param('id') id: number, @SolidRequestContextDecorator() solidRequestContext: SolidRequestContextDto) {
78
+ return this.service.delete(id, solidRequestContext);
79
79
  }
80
80
 
81
+ @ApiBearerAuth('jwt')
82
+ @Patch(':id')
83
+ @UseInterceptors(AnyFilesInterceptor())
84
+ partialUpdate(@Param('id') id: number, @Body() updateDto: UpdateMenuItemMetadataDto, @UploadedFiles() files: Array<Express.Multer.File>) {
85
+ return this.service.update(id, updateDto, files, true);
86
+ }
81
87
  }
@@ -0,0 +1,116 @@
1
+ import {
2
+ Controller,
3
+ Get,
4
+ Inject,
5
+ InternalServerErrorException,
6
+ Query,
7
+ Req,
8
+ Res,
9
+ UseGuards,
10
+ } from "@nestjs/common";
11
+ import { ApiQuery, ApiTags } from "@nestjs/swagger";
12
+ import { Request, Response } from "express";
13
+ import {
14
+ MicrosoftAuthConfiguration,
15
+ isMicrosoftOAuthConfigured,
16
+ } from "../helpers/microsoft-oauth.helper";
17
+ import { AuthenticationService } from "../services/authentication.service";
18
+ import { SettingService } from "../services/setting.service";
19
+ import { Public } from "src/decorators/public.decorator";
20
+ import { Auth } from "../decorators/auth.decorator";
21
+ import { AuthType } from "../enums/auth-type.enum";
22
+ import { MicrosoftOauthGuard } from "../passport-strategies/microsoft-oauth.strategy";
23
+ import { UserService } from "../services/user.service";
24
+ import type { SolidCoreSetting } from "../services/settings/default-settings-provider.service";
25
+
26
+ @Auth(AuthType.None)
27
+ @ApiTags("Iam")
28
+ @Controller("iam/microsoft")
29
+ export class MicrosoftAuthenticationController {
30
+ constructor(
31
+ private readonly userService: UserService,
32
+ private readonly authService: AuthenticationService,
33
+ private readonly settingService: SettingService,
34
+ ) {}
35
+
36
+ private async getConfiguration(): Promise<MicrosoftAuthConfiguration> {
37
+ return {
38
+ clientID:
39
+ await this.settingService.getConfigValue<SolidCoreSetting>(
40
+ "MICROSOFT_CLIENT_ID" as any,
41
+ ),
42
+ clientSecret: await this.settingService.getConfigValue<SolidCoreSetting>(
43
+ "MICROSOFT_CLIENT_SECRET" as any,
44
+ ),
45
+ tenant: await this.settingService.getConfigValue<SolidCoreSetting>(
46
+ "MICROSOFT_TENANT_ID" as any,
47
+ ),
48
+ callbackURL: await this.settingService.getConfigValue<SolidCoreSetting>(
49
+ "MICROSOFT_CALLBACK_URL" as any,
50
+ ),
51
+ redirectURL: await this.settingService.getConfigValue<SolidCoreSetting>(
52
+ "MICROSOFT_REDIRECT_URL" as any,
53
+ ),
54
+ };
55
+ }
56
+
57
+ private async validateConfiguration() {
58
+ const config = await this.getConfiguration();
59
+ if (!isMicrosoftOAuthConfigured(config)) {
60
+ throw new InternalServerErrorException(
61
+ "Microsoft OAuth is not configured",
62
+ );
63
+ }
64
+ return config;
65
+ }
66
+
67
+ @Public()
68
+ @UseGuards(MicrosoftOauthGuard)
69
+ @Get("connect")
70
+ async connect() {
71
+ await this.validateConfiguration();
72
+ }
73
+
74
+ @Public()
75
+ @Get("connect/callback")
76
+ @UseGuards(MicrosoftOauthGuard)
77
+ async microsoftAuthCallback(@Req() req: Request, @Res() res: Response) {
78
+ const config = await this.validateConfiguration();
79
+ const user = req.user;
80
+ return res.redirect(`${config.redirectURL}?accessCode=${user['accessCode']}`);
81
+ }
82
+
83
+ /**
84
+ * This is just a dummy endpoint where we are passing in the accessCode, this will be configured in the .env as an environment variable and
85
+ * will be passed the accessCode, using the accessCode the UI code on this page will mostly invoke the /iam/microsoft/auth endpoint which will finally generate the JWT token.
86
+ *
87
+ * @param accessCode
88
+ * @returns
89
+ */
90
+ @Public()
91
+ @Get('dummy-redirect')
92
+ async dummyMicrosoftAuthRedirect(@Query('accessCode') accessCode) {
93
+ await this.validateConfiguration();
94
+ const user = await this.userService.findOneByAccessCode(accessCode);
95
+
96
+ if (user) {
97
+ delete user['password'];
98
+ }
99
+
100
+ return user;
101
+ }
102
+
103
+ /**
104
+ * Use this endpoint to authenticate using an accessCode with Microsoft.
105
+ *
106
+ * @param accessCode
107
+ * @returns
108
+ */
109
+ @Public()
110
+ @Get("authenticate")
111
+ @ApiQuery({ name: "accessCode", required: true, type: String })
112
+ async microsoftAuth(@Query("accessCode") accessCode: string) {
113
+ await this.validateConfiguration();
114
+ return this.authService.signInUsingMicrosoft(accessCode);
115
+ }
116
+ }
@@ -7,28 +7,39 @@ export class CreateChatterMessageDto {
7
7
  @IsString()
8
8
  @ApiProperty()
9
9
  messageType: string;
10
+
10
11
  @IsNotEmpty()
11
12
  @IsString()
12
13
  @ApiProperty()
13
14
  messageSubType: string;
15
+
14
16
  @IsOptional()
15
17
  @IsString()
16
18
  @ApiProperty()
17
19
  messageBody: string;
20
+
18
21
  @IsNotEmpty()
19
22
  @IsInt()
20
23
  @ApiProperty()
21
24
  coModelEntityId: number;
25
+
22
26
  @IsNotEmpty()
23
27
  @IsString()
24
28
  @ApiProperty()
25
29
  coModelName: string;
30
+
26
31
  @IsOptional()
27
32
  @IsInt()
28
33
  @ApiProperty()
29
34
  userId: number;
35
+
30
36
  @IsString()
31
37
  @IsOptional()
32
38
  @ApiProperty()
33
39
  userUserKey: string;
40
+
41
+ @IsString()
42
+ @IsOptional()
43
+ @ApiProperty()
44
+ status: string;
34
45
  }
@@ -20,4 +20,8 @@ export class PostChatterMessageDto {
20
20
  @IsString()
21
21
  @IsOptional()
22
22
  modelUserKey?: string;
23
+
24
+ @IsString()
25
+ @IsOptional()
26
+ status?: string;
23
27
  }
@@ -1,41 +1,53 @@
1
- import { IsInt,IsOptional, IsString, IsNotEmpty } from 'class-validator';
1
+ import { IsInt, IsOptional, IsString, IsNotEmpty } from 'class-validator';
2
2
  import { ApiProperty } from '@nestjs/swagger';
3
3
 
4
4
  export class UpdateChatterMessageDto {
5
5
  @IsOptional()
6
6
  @IsInt()
7
7
  id: number;
8
+
8
9
  @IsNotEmpty()
9
10
  @IsOptional()
10
11
  @IsString()
11
12
  @ApiProperty()
12
13
  messageType: string;
14
+
13
15
  @IsNotEmpty()
14
16
  @IsOptional()
15
17
  @IsString()
16
18
  @ApiProperty()
17
19
  messageSubType: string;
20
+
18
21
  @IsNotEmpty()
19
22
  @IsOptional()
20
23
  @IsString()
21
24
  @ApiProperty()
22
25
  messageBody: string;
26
+
23
27
  @IsNotEmpty()
24
28
  @IsOptional()
25
29
  @IsInt()
26
30
  @ApiProperty()
27
31
  coModelEntityId: number;
32
+
28
33
  @IsNotEmpty()
29
34
  @IsOptional()
30
35
  @IsString()
31
36
  @ApiProperty()
32
37
  coModelName: string;
38
+
33
39
  @IsOptional()
34
40
  @IsInt()
35
41
  @ApiProperty()
36
42
  userId: number;
43
+
37
44
  @IsString()
38
45
  @IsOptional()
39
46
  @ApiProperty()
40
47
  userUserKey: string;
48
+
49
+ @IsOptional()
50
+ @IsString()
51
+ @ApiProperty()
52
+ status: string;
41
53
  }
@@ -12,7 +12,7 @@ export class ChatterMessage extends CommonEntity {
12
12
  messageType: string; // audit | custom
13
13
 
14
14
  @Column({ type: "varchar" })
15
- messageSubType: string; // audit_update | audit_insert | audit_delete | custom
15
+ messageSubType: string; // audit_update | audit_insert | audit_delete | custom | note | task
16
16
 
17
17
  @Column({ nullable: true, ...getColumnType('longText') })
18
18
  messageBody: string;
@@ -38,4 +38,7 @@ export class ChatterMessage extends CommonEntity {
38
38
 
39
39
  @Column({ nullable: true })
40
40
  modelUserKey: string;
41
+
42
+ @Column({ default: 'pending' })
43
+ status: string; // pending | completed
41
44
  }
@@ -56,6 +56,38 @@ export class User extends CommonEntity {
56
56
  // don't send to client
57
57
  googleProfilePicture: string;
58
58
 
59
+ @Column({ type: "varchar", nullable: true })
60
+ // don't send to client
61
+ facebookId: string;
62
+
63
+ @Column({ type: "varchar", nullable: true })
64
+ // don't send to client
65
+ facebookAccessToken: string;
66
+
67
+ @Column({ type: "varchar", nullable: true })
68
+ // don't send to client
69
+ facebookProfilePicture: string;
70
+
71
+ @Column({ type: "varchar", nullable: true })
72
+ // don't send to client
73
+ appleId: string;
74
+
75
+ @Column({ type: "varchar", nullable: true })
76
+ // don't send to client
77
+ appleAccessToken: string;
78
+
79
+ @Column({ type: "varchar", nullable: true })
80
+ // don't send to client
81
+ microsoftId: string;
82
+
83
+ @Column({ type: "varchar", nullable: true })
84
+ // don't send to client
85
+ microsoftAccessToken: string;
86
+
87
+ @Column({ type: "varchar", nullable: true })
88
+ // don't send to client
89
+ microsoftProfilePicture: string;
90
+
59
91
  @Column({ default: true })
60
92
  @Expose()
61
93
  active: boolean = true;
@@ -42,7 +42,7 @@ export function buildDefaultCorsOptions(): CorsOptions {
42
42
  return cb(new Error(`Origin ${origin} not allowed by CORS. Allowed origins: ${allowed.join(', ')}`), false);
43
43
  },
44
44
  methods: ['GET', 'POST', 'PUT', 'PATCH', 'DELETE', 'OPTIONS'],
45
- allowedHeaders: ['Content-Type', 'Authorization'],
45
+ allowedHeaders: ['Content-Type', 'Authorization','solidx-api-key'],
46
46
  credentials: true,
47
47
  };
48
48
  }
@@ -0,0 +1,17 @@
1
+ export type FacebookAuthConfiguration = {
2
+ clientID: string;
3
+ clientSecret: string;
4
+ callbackURL: string;
5
+ redirectURL: string;
6
+ };
7
+
8
+ export const isFacebookOAuthConfigured = (
9
+ config: FacebookAuthConfiguration,
10
+ ): boolean => {
11
+ return !!(
12
+ config.clientID &&
13
+ config.clientSecret &&
14
+ config.callbackURL &&
15
+ config.redirectURL
16
+ );
17
+ };
@@ -0,0 +1,19 @@
1
+ export type MicrosoftAuthConfiguration = {
2
+ clientID: string;
3
+ clientSecret: string;
4
+ tenant: string;
5
+ callbackURL: string;
6
+ redirectURL: string;
7
+ };
8
+
9
+ export const isMicrosoftOAuthConfigured = (
10
+ config: MicrosoftAuthConfiguration,
11
+ ): boolean => {
12
+ return !!(
13
+ config.clientID &&
14
+ config.clientSecret &&
15
+ config.tenant &&
16
+ config.callbackURL &&
17
+ config.redirectURL
18
+ );
19
+ };
@@ -11,6 +11,10 @@ export function getUserExcludedFields(): string[] {
11
11
  "forcePasswordChange",
12
12
  "lastLoginProvider",
13
13
  "googleProfilePicture",
14
+ "facebookAccessToken",
15
+ "facebookId",
16
+ "microsoftAccessToken",
17
+ "microsoftId",
14
18
  "forgotPasswordConfirmedAt",
15
19
  "verificationTokenOnForgotPassword",
16
20
  "verificationTokenOnForgotPasswordExpiresAt",
package/src/index.ts CHANGED
@@ -261,6 +261,8 @@ export * from './jobs/redis/twilio-sms-subscriber-redis.service'
261
261
  export * from './listeners/user-registration.listener'
262
262
 
263
263
  export * from './passport-strategies/google-oauth.strategy'
264
+ export * from './passport-strategies/facebook-oauth.strategy'
265
+ export * from './passport-strategies/microsoft-oauth.strategy'
264
266
 
265
267
  export * from './services/selection-providers/list-of-values-selection-providers.service'
266
268
 
package/src/interfaces.ts CHANGED
@@ -68,12 +68,44 @@ export enum SettingLevel {
68
68
  InternalUser = "internal-user"
69
69
  }
70
70
 
71
+ export type SettingControlType =
72
+ | 'shortText'
73
+ | 'longText'
74
+ | 'numeric'
75
+ | 'boolean'
76
+ | 'date'
77
+ | 'datetime'
78
+ | 'mediaSingle'
79
+ | 'selectionStatic'
80
+ | 'custom';
81
+
82
+ export interface SettingOption {
83
+ label: string;
84
+ value: string | number | boolean;
85
+ }
86
+
71
87
  export interface SettingDefinition<T = any> {
72
88
  moduleName: string;
73
89
  key: string;
74
90
  value: T;
75
91
  level: SettingLevel;
76
92
  encrypted?: boolean;
93
+ label?: string;
94
+ description?: string;
95
+ placeholder?: string;
96
+ group?: string;
97
+ sortOrder?: number;
98
+ controlType?: SettingControlType;
99
+ options?: SettingOption[];
100
+ settingsWidget?: string; // for custom controlType, specify the frontend widget to use
101
+ }
102
+
103
+ export interface AdminSettingDefinition<T = any> extends SettingDefinition<T> {
104
+ editable: boolean;
105
+ }
106
+
107
+ export interface AdminSettingsResponse<T = any> {
108
+ data: AdminSettingDefinition<T>[];
77
109
  }
78
110
 
79
111
  // solid-core/settings/settings-provider.interface.ts
@@ -419,4 +451,3 @@ export interface AuditQueuePayload {
419
451
  userId?: number | null;
420
452
  }
421
453
 
422
-