@lenne.tech/nest-server 2.0.0-alpha8 → 2.0.3

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (31) hide show
  1. package/dist/core/common/services/config.service.d.ts +1 -1
  2. package/dist/core/common/services/config.service.js +3 -3
  3. package/dist/core/common/services/config.service.js.map +1 -1
  4. package/dist/core/modules/auth/core-auth.module.js +5 -0
  5. package/dist/core/modules/auth/core-auth.module.js.map +1 -1
  6. package/dist/core/modules/auth/guards/auth.guard.js +7 -3
  7. package/dist/core/modules/auth/guards/auth.guard.js.map +1 -1
  8. package/dist/core/modules/user/core-user.service.js +2 -1
  9. package/dist/core/modules/user/core-user.service.js.map +1 -1
  10. package/dist/core.module.js +7 -0
  11. package/dist/core.module.js.map +1 -1
  12. package/dist/server/modules/user/user.module.js +10 -1
  13. package/dist/server/modules/user/user.module.js.map +1 -1
  14. package/dist/server/modules/user/user.resolver.d.ts +4 -2
  15. package/dist/server/modules/user/user.resolver.js +11 -8
  16. package/dist/server/modules/user/user.resolver.js.map +1 -1
  17. package/dist/server/modules/user/user.service.d.ts +3 -1
  18. package/dist/server/modules/user/user.service.js +9 -5
  19. package/dist/server/modules/user/user.service.js.map +1 -1
  20. package/dist/server/server.module.js.map +1 -1
  21. package/dist/tsconfig.build.tsbuildinfo +1 -1
  22. package/package.json +3 -3
  23. package/src/core/common/services/config.service.ts +7 -5
  24. package/src/core/modules/auth/core-auth.module.ts +5 -0
  25. package/src/core/modules/auth/guards/auth.guard.ts +5 -0
  26. package/src/core/modules/user/core-user.service.ts +2 -1
  27. package/src/core.module.ts +8 -0
  28. package/src/server/modules/user/user.module.ts +10 -1
  29. package/src/server/modules/user/user.resolver.ts +7 -8
  30. package/src/server/modules/user/user.service.ts +7 -7
  31. package/src/server/server.module.ts +1 -0
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@lenne.tech/nest-server",
3
- "version": "2.0.0-alpha8",
3
+ "version": "2.0.3",
4
4
  "description": "Modern, fast, powerful Node.js web framework in TypeScript based on Nest with a GraphQL API and a connection to MongoDB (or other databases).",
5
5
  "keywords": [
6
6
  "node",
@@ -114,8 +114,7 @@
114
114
  "supertest": "6.1.6",
115
115
  "ts-morph": "11.0.3",
116
116
  "ts-node": "9.1.1",
117
- "tsconfig-paths": "3.10.1",
118
- "ts-jest": "27.0.5"
117
+ "tsconfig-paths": "3.10.1"
119
118
  },
120
119
  "devDependencies": {
121
120
  "eslint": "7.32.0",
@@ -124,6 +123,7 @@
124
123
  "pm2": "5.1.0",
125
124
  "prettier": "2.3.2",
126
125
  "pretty-quick": "3.1.1",
126
+ "ts-jest": "27.0.5",
127
127
  "typescript": "4.3.5"
128
128
  },
129
129
  "jest": {
@@ -14,20 +14,22 @@ export class ConfigService {
14
14
  * Create config service
15
15
  */
16
16
  constructor(config: { [key: string]: any } & Partial<IServerOptions>) {
17
- this._config = config;
17
+ this._config = config || {};
18
18
  }
19
19
 
20
20
  /**
21
- * Get config
21
+ * Get config (deep cloned to avoid unwanted side effects)
22
22
  */
23
23
  get config() {
24
24
  return _.cloneDeep(this._config);
25
25
  }
26
26
 
27
27
  /**
28
- * Get data from config
28
+ * Get data from config (deep cloned to avoid unwanted side effects)
29
+ * @param key Property name of config object, which is to be returned
30
+ * @param defaultValue Default value which is to be returned if property doesn't exist
29
31
  */
30
- get(key: string) {
31
- return _.cloneDeep(_.get(this._config, key, undefined));
32
+ get(key: string, defaultValue: any = undefined) {
33
+ return _.cloneDeep(_.get(this._config, key, defaultValue));
32
34
  }
33
35
  }
@@ -6,6 +6,7 @@ import { RolesGuard } from './guards/roles.guard';
6
6
  import { JwtStrategy } from './jwt.strategy';
7
7
  import { CoreAuthUserService } from './services/core-auth-user.service';
8
8
  import { CoreAuthService } from './services/core-auth.service';
9
+ import { PubSub } from 'graphql-subscriptions';
9
10
 
10
11
  /**
11
12
  * CoreAuthModule to handle user authentication and enables Roles
@@ -34,6 +35,10 @@ export class CoreAuthModule {
34
35
  provide: CoreAuthUserService,
35
36
  useClass: UserService,
36
37
  },
38
+ {
39
+ provide: 'PUB_SUB',
40
+ useValue: new PubSub(),
41
+ },
37
42
 
38
43
  // Standard services
39
44
  CoreAuthService,
@@ -58,6 +58,11 @@ function createAuthGuard(type?: string): Type<CanActivate> {
58
58
  * Integrate options
59
59
  */
60
60
  async canActivate(context: ExecutionContext): Promise<boolean> {
61
+ const args = context.getArgs();
62
+ if (args.length > 0 && args[args.length - 1]?.operation?.operation === 'subscription') {
63
+ return true;
64
+ }
65
+
61
66
  const options = { ...defaultOptions, ...this.options };
62
67
  const response = context?.switchToHttp()?.getResponse();
63
68
  let request = this.getRequest(context);
@@ -97,10 +97,11 @@ export abstract class CoreUserService<
97
97
  * Get users via filter
98
98
  */
99
99
  async find(filterArgs?: FilterArgs, ...args: any[]): Promise<TUser[]> {
100
+ const filterQuery = Filter.convertFilterArgsToQuery(filterArgs);
100
101
  // Return found users
101
102
  return await Promise.all(
102
103
  (
103
- await this.userModel.find(...Filter.convertFilterArgsToQuery(filterArgs))
104
+ await this.userModel.find(filterQuery[0], null, filterQuery[1]).exec()
104
105
  ).map((user) => {
105
106
  return this.prepareOutput(user, args[0]);
106
107
  })
@@ -41,6 +41,14 @@ export class CoreModule {
41
41
  autoSchemaFile: 'schema.gql',
42
42
  context: ({ req }) => ({ req }),
43
43
  installSubscriptionHandlers: true,
44
+ subscriptions: {
45
+ 'subscriptions-transport-ws': {
46
+ onConnect: (connectionParams) => {
47
+ // TODO: Handle Authorization
48
+ const authToken = connectionParams.Authorization;
49
+ },
50
+ },
51
+ },
44
52
  },
45
53
  port: 3000,
46
54
  mongoose: {
@@ -5,6 +5,7 @@ import { User, UserSchema } from './user.model';
5
5
  import { UserResolver } from './user.resolver';
6
6
  import { UserService } from './user.service';
7
7
  import { MongooseModule } from '@nestjs/mongoose';
8
+ import { PubSub } from 'graphql-subscriptions';
8
9
 
9
10
  /**
10
11
  * User module
@@ -12,7 +13,15 @@ import { MongooseModule } from '@nestjs/mongoose';
12
13
  @Module({
13
14
  imports: [MongooseModule.forFeature([{ name: User.name, schema: UserSchema }])],
14
15
  controllers: [AvatarController],
15
- providers: [JSON, UserResolver, UserService],
16
+ providers: [
17
+ JSON,
18
+ UserResolver,
19
+ UserService,
20
+ {
21
+ provide: 'PUB_SUB',
22
+ useValue: new PubSub(),
23
+ },
24
+ ],
16
25
  exports: [MongooseModule, UserResolver, UserService],
17
26
  })
18
27
  export class UserModule {}
@@ -10,9 +10,7 @@ import { UserCreateInput } from './inputs/user-create.input';
10
10
  import { UserInput } from './inputs/user.input';
11
11
  import { User } from './user.model';
12
12
  import { UserService } from './user.service';
13
-
14
- // Subscription
15
- const pubSub = new PubSub();
13
+ import { Inject } from '@nestjs/common';
16
14
 
17
15
  /**
18
16
  * Resolver to process with user data
@@ -22,7 +20,7 @@ export class UserResolver {
22
20
  /**
23
21
  * Import services
24
22
  */
25
- constructor(protected readonly usersService: UserService) {}
23
+ constructor(protected readonly usersService: UserService, @Inject('PUB_SUB') protected readonly pubSub: PubSub) {}
26
24
 
27
25
  // ===========================================================================
28
26
  // Queries
@@ -96,9 +94,10 @@ export class UserResolver {
96
94
  /**
97
95
  * Subscritption for create user
98
96
  */
99
- @Roles(RoleEnum.ADMIN)
100
- @Subscription((returns) => User)
101
- userCreated() {
102
- return pubSub.asyncIterator('userCreated');
97
+ @Subscription((returns) => User, {
98
+ resolve: (value) => value,
99
+ })
100
+ async userCreated() {
101
+ return this.pubSub.asyncIterator('userCreated');
103
102
  }
104
103
  }
@@ -1,7 +1,6 @@
1
- import { Injectable, UnauthorizedException, UnprocessableEntityException } from '@nestjs/common';
1
+ import { Inject, Injectable, UnauthorizedException, UnprocessableEntityException } from '@nestjs/common';
2
2
  import * as fs from 'fs';
3
3
  import { GraphQLResolveInfo } from 'graphql';
4
- import { PubSub } from 'graphql-subscriptions';
5
4
  import envConfig from '../../../config.env';
6
5
  import { FilterArgs } from '../../../core/common/args/filter.args';
7
6
  import { Filter } from '../../../core/common/helpers/filter.helper';
@@ -15,9 +14,7 @@ import { User } from './user.model';
15
14
  import { InjectModel } from '@nestjs/mongoose';
16
15
  import { Model } from 'mongoose';
17
16
  import { ICorePersistenceModel } from '../../../core/common/interfaces/core-persistence-model.interface';
18
-
19
- // Subscription
20
- const pubSub = new PubSub();
17
+ import { PubSub } from 'graphql-subscriptions';
21
18
 
22
19
  /**
23
20
  * User service
@@ -42,7 +39,8 @@ export class UserService extends CoreUserService<User, UserInput, UserCreateInpu
42
39
  constructor(
43
40
  protected readonly configService: ConfigService,
44
41
  protected readonly emailService: EmailService,
45
- @InjectModel('User') protected readonly userModel: Model<User>
42
+ @InjectModel('User') protected readonly userModel: Model<User>,
43
+ @Inject('PUB_SUB') protected readonly pubSub: PubSub
46
44
  ) {
47
45
  super(userModel);
48
46
  this.model = User;
@@ -58,6 +56,7 @@ export class UserService extends CoreUserService<User, UserInput, UserCreateInpu
58
56
  async create(input: UserCreateInput, currentUser?: User, ...args: any[]): Promise<User> {
59
57
  const user = await super.create(input, currentUser);
60
58
  const text = `Welcome ${user.firstName}, this is plain text from server.`;
59
+ await this.pubSub.publish('userCreated', User.map(user));
61
60
  await this.emailService.sendMail(user.email, 'Welcome', {
62
61
  htmlTemplate: 'welcome',
63
62
  templateData: user,
@@ -71,8 +70,9 @@ export class UserService extends CoreUserService<User, UserInput, UserCreateInpu
71
70
  * Get users via filter
72
71
  */
73
72
  find(filterArgs?: FilterArgs, ...args: any[]): Promise<User[]> {
73
+ const filterQuery = Filter.convertFilterArgsToQuery(filterArgs);
74
74
  // Return found users
75
- return this.userModel.find(...Filter.convertFilterArgsToQuery(filterArgs)).exec();
75
+ return this.userModel.find(filterQuery[0], null, filterQuery[1]).exec();
76
76
  }
77
77
 
78
78
  /**
@@ -4,6 +4,7 @@ import { CoreModule } from '../core.module';
4
4
  import { AuthModule } from './modules/auth/auth.module';
5
5
  import { FileController } from './modules/file/file.controller';
6
6
  import { ServerController } from './server.controller';
7
+ import { PubSub } from 'graphql-subscriptions';
7
8
 
8
9
  /**
9
10
  * Server module (dynamic)