@skroz/profile-api 1.0.7 → 1.0.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.
- package/dist/dto/ConfirmEmailInput.d.ts +1 -1
- package/dist/dto/ConfirmEmailInput.js +3 -3
- package/dist/dto/ForgotPasswordInput.d.ts +1 -1
- package/dist/dto/ForgotPasswordInput.js +3 -3
- package/dist/dto/LoginInput.d.ts +2 -2
- package/dist/dto/LoginInput.js +38 -5
- package/dist/dto/PasswordInput.d.ts +1 -1
- package/dist/dto/PasswordInput.js +3 -3
- package/dist/dto/RecoverPasswordInput.d.ts +2 -2
- package/dist/dto/RecoverPasswordInput.js +38 -5
- package/dist/dto/RegisterInput.d.ts +2 -2
- package/dist/dto/RegisterInput.js +38 -5
- package/dist/dto/SendTokenPayload.d.ts +2 -2
- package/dist/dto/SendTokenPayload.js +3 -4
- package/dist/dto/StatusPayload.d.ts +1 -1
- package/dist/dto/StatusPayload.js +2 -3
- package/dist/dto/UpdateEmailInput.d.ts +1 -1
- package/dist/dto/UpdateEmailInput.js +3 -3
- package/dist/dto/UpdatePasswordInput.d.ts +2 -2
- package/dist/dto/UpdatePasswordInput.js +38 -5
- package/dist/dto/UpdateProfileInput.d.ts +1 -1
- package/dist/dto/UpdateProfileInput.js +3 -3
- package/dist/dto/index.d.ts +11 -11
- package/dist/dto/index.js +42 -24
- package/dist/email-templates/base/content.pug +32 -0
- package/dist/email-templates/base/header.pug +28 -0
- package/dist/email-templates/base/layout.pug +34 -0
- package/dist/email-templates/base/mixins.pug +16 -0
- package/dist/email-templates/confirmEmail.pug +16 -0
- package/dist/email-templates/forgotPassword.pug +16 -0
- package/dist/email-templates/notification.pug +14 -0
- package/dist/email-templates/tempPassword.pug +14 -0
- package/dist/resolvers/AuthResolver.d.ts +1 -24
- package/dist/resolvers/AuthResolver.js +6 -3
- package/dist/resolvers/ProfileResolver.d.ts +1 -18
- package/dist/resolvers/ProfileResolver.js +8 -2
- package/dist/services/ProfileEmailService.js +2 -2
- package/dist/types/index.d.ts +1 -1
- package/package.json +3 -3
- package/src/dto/ConfirmEmailInput.ts +1 -1
- package/src/dto/ForgotPasswordInput.ts +1 -1
- package/src/dto/LoginInput.ts +2 -2
- package/src/dto/PasswordInput.ts +1 -1
- package/src/dto/RecoverPasswordInput.ts +2 -2
- package/src/dto/RegisterInput.ts +2 -2
- package/src/dto/SendTokenPayload.ts +2 -2
- package/src/dto/StatusPayload.ts +1 -1
- package/src/dto/UpdateEmailInput.ts +1 -1
- package/src/dto/UpdatePasswordInput.ts +2 -2
- package/src/dto/UpdateProfileInput.ts +1 -1
- package/src/dto/index.ts +11 -11
- package/src/email-templates/base/content.pug +32 -0
- package/src/email-templates/base/header.pug +28 -0
- package/src/email-templates/base/layout.pug +34 -0
- package/src/email-templates/base/mixins.pug +16 -0
- package/src/email-templates/confirmEmail.pug +16 -0
- package/src/email-templates/forgotPassword.pug +16 -0
- package/src/email-templates/notification.pug +14 -0
- package/src/email-templates/tempPassword.pug +14 -0
- package/src/resolvers/AuthResolver.ts +76 -30
- package/src/resolvers/ProfileResolver.ts +125 -98
- package/src/services/ProfileEmailService.ts +147 -147
- package/src/types/index.ts +1 -1
|
@@ -0,0 +1,14 @@
|
|
|
1
|
+
extends base/layout
|
|
2
|
+
include base/mixins
|
|
3
|
+
|
|
4
|
+
block content
|
|
5
|
+
+header(header)
|
|
6
|
+
p #{' ' + text}
|
|
7
|
+
if (link)
|
|
8
|
+
+link(link.href, link.label)
|
|
9
|
+
div(style='margin-top: 30px;')
|
|
10
|
+
strong #{mistakeHeader}
|
|
11
|
+
a(href=unsubscribeLink)
|
|
12
|
+
strong Отписаться
|
|
13
|
+
br
|
|
14
|
+
| #{mistakeText}
|
|
@@ -0,0 +1,14 @@
|
|
|
1
|
+
extends base/layout
|
|
2
|
+
include base/mixins
|
|
3
|
+
|
|
4
|
+
block content
|
|
5
|
+
+header(header)
|
|
6
|
+
p #{' ' + text}
|
|
7
|
+
if (link)
|
|
8
|
+
+link(link.href, link.label)
|
|
9
|
+
div(style='margin-top: 30px;')
|
|
10
|
+
strong #{mistakeHeader}
|
|
11
|
+
a(href=unsubscribeLink)
|
|
12
|
+
strong Отписаться
|
|
13
|
+
br
|
|
14
|
+
| #{mistakeText}
|
|
@@ -1,26 +1,34 @@
|
|
|
1
|
-
import {
|
|
2
|
-
Arg,
|
|
3
|
-
Authorized,
|
|
4
|
-
Ctx,
|
|
5
|
-
Mutation,
|
|
6
|
-
Resolver,
|
|
7
|
-
} from 'type-graphql';
|
|
1
|
+
import { Arg, Authorized, Ctx, Mutation, Resolver } from 'type-graphql';
|
|
8
2
|
import { StatusPayload } from '@os-team/graphql-utils';
|
|
9
3
|
import { TransformArgs } from '@os-team/graphql-transformers';
|
|
10
4
|
import { ValidateArgs } from '@os-team/graphql-validators';
|
|
11
|
-
import {
|
|
5
|
+
import {
|
|
6
|
+
ProfileAuthService,
|
|
7
|
+
CONFIRMATION_REDIS_PREFIX,
|
|
8
|
+
RECOVERY_REDIS_PREFIX,
|
|
9
|
+
} from '../services/ProfileAuthService';
|
|
12
10
|
import { ProfileContext } from '../types';
|
|
13
11
|
import {
|
|
14
|
-
RegisterInput,
|
|
15
|
-
|
|
12
|
+
RegisterInput,
|
|
13
|
+
registerTransformers,
|
|
14
|
+
registerValidators,
|
|
15
|
+
LoginInput,
|
|
16
|
+
loginTransformers,
|
|
17
|
+
loginValidators,
|
|
16
18
|
ConfirmEmailInput,
|
|
17
|
-
ForgotPasswordInput,
|
|
18
|
-
|
|
19
|
+
ForgotPasswordInput,
|
|
20
|
+
forgotPasswordTransformers,
|
|
21
|
+
forgotPasswordValidators,
|
|
22
|
+
RecoverPasswordInput,
|
|
23
|
+
recoverPasswordTransformers,
|
|
24
|
+
recoverPasswordValidators,
|
|
19
25
|
SendTokenPayload,
|
|
20
|
-
confirmEmailValidators
|
|
26
|
+
confirmEmailValidators,
|
|
21
27
|
} from '../dto';
|
|
22
28
|
|
|
23
|
-
export interface AuthResolverDependencies<
|
|
29
|
+
export interface AuthResolverDependencies<
|
|
30
|
+
TContext extends ProfileContext = ProfileContext
|
|
31
|
+
> {
|
|
24
32
|
authService: ProfileAuthService | (() => ProfileAuthService);
|
|
25
33
|
userType: any;
|
|
26
34
|
onUserCreated?: (user: any, ctx: TContext) => Promise<void>;
|
|
@@ -31,7 +39,9 @@ export interface AuthResolverDependencies<TContext extends ProfileContext = Prof
|
|
|
31
39
|
logTelegramBot?: { sendError: (msg: string) => Promise<any> };
|
|
32
40
|
}
|
|
33
41
|
|
|
34
|
-
export function createAuthResolver<
|
|
42
|
+
export function createAuthResolver<
|
|
43
|
+
TContext extends ProfileContext = ProfileContext
|
|
44
|
+
>(deps: AuthResolverDependencies<TContext>): any {
|
|
35
45
|
const {
|
|
36
46
|
authService,
|
|
37
47
|
onUserCreated,
|
|
@@ -40,7 +50,7 @@ export function createAuthResolver<TContext extends ProfileContext = ProfileCont
|
|
|
40
50
|
onEmailConfirmed,
|
|
41
51
|
onPasswordRecovered,
|
|
42
52
|
logTelegramBot,
|
|
43
|
-
userType
|
|
53
|
+
userType,
|
|
44
54
|
} = deps;
|
|
45
55
|
|
|
46
56
|
const getAuthService = (): ProfileAuthService => {
|
|
@@ -67,7 +77,8 @@ export function createAuthResolver<TContext extends ProfileContext = ProfileCont
|
|
|
67
77
|
});
|
|
68
78
|
|
|
69
79
|
if (onUserCreated) await onUserCreated(user, ctx);
|
|
70
|
-
if (logTelegramBot)
|
|
80
|
+
if (logTelegramBot)
|
|
81
|
+
await logTelegramBot.sendError(`Новый пользователь ${input.email}`);
|
|
71
82
|
|
|
72
83
|
// Создаем сессию
|
|
73
84
|
const userAgent = decodeURI(ctx.req.get('user-agent') || '');
|
|
@@ -91,7 +102,10 @@ export function createAuthResolver<TContext extends ProfileContext = ProfileCont
|
|
|
91
102
|
|
|
92
103
|
if (user.isBanned) throw new Error(t('validation:user.banned'));
|
|
93
104
|
|
|
94
|
-
const isPasswordOk = await service.verifyPassword(
|
|
105
|
+
const isPasswordOk = await service.verifyPassword(
|
|
106
|
+
user.password!,
|
|
107
|
+
input.password
|
|
108
|
+
);
|
|
95
109
|
if (!isPasswordOk) throw new Error(t('validation:login.wrongPassword'));
|
|
96
110
|
|
|
97
111
|
const userAgent = decodeURI(ctx.req.get('user-agent') || '');
|
|
@@ -125,16 +139,29 @@ export function createAuthResolver<TContext extends ProfileContext = ProfileCont
|
|
|
125
139
|
return { ok: true };
|
|
126
140
|
}
|
|
127
141
|
|
|
128
|
-
@ValidateArgs(confirmEmailValidators, {
|
|
142
|
+
@ValidateArgs(confirmEmailValidators, {
|
|
143
|
+
arg: 'input',
|
|
144
|
+
tKey: 'confirmEmail',
|
|
145
|
+
})
|
|
129
146
|
@Mutation(() => StatusPayload)
|
|
130
|
-
async confirmEmail(
|
|
147
|
+
async confirmEmail(
|
|
148
|
+
@Arg('input') input: ConfirmEmailInput,
|
|
149
|
+
@Ctx() ctx: TContext
|
|
150
|
+
) {
|
|
131
151
|
const service = getAuthService();
|
|
132
|
-
const user = await service.getUserByToken(
|
|
152
|
+
const user = await service.getUserByToken(
|
|
153
|
+
CONFIRMATION_REDIS_PREFIX,
|
|
154
|
+
input.token
|
|
155
|
+
);
|
|
133
156
|
if (!user) throw new Error(ctx.t('validation:error.wrongCode'));
|
|
134
157
|
|
|
135
158
|
user.isEmailConfirmed = true;
|
|
136
159
|
await user.save();
|
|
137
|
-
await service.removeTokenFromRedis(
|
|
160
|
+
await service.removeTokenFromRedis(
|
|
161
|
+
CONFIRMATION_REDIS_PREFIX,
|
|
162
|
+
user,
|
|
163
|
+
input.token
|
|
164
|
+
);
|
|
138
165
|
|
|
139
166
|
const userAgent = decodeURI(ctx.req.get('user-agent') || '');
|
|
140
167
|
await ctx.req.session.create({
|
|
@@ -145,7 +172,9 @@ export function createAuthResolver<TContext extends ProfileContext = ProfileCont
|
|
|
145
172
|
|
|
146
173
|
if (onEmailConfirmed) await onEmailConfirmed(user, ctx);
|
|
147
174
|
if (logTelegramBot) {
|
|
148
|
-
await logTelegramBot.sendError(
|
|
175
|
+
await logTelegramBot.sendError(
|
|
176
|
+
`${user.email || user.urlSlug} подтвердил(а) email`
|
|
177
|
+
);
|
|
149
178
|
}
|
|
150
179
|
|
|
151
180
|
return { ok: true };
|
|
@@ -154,7 +183,10 @@ export function createAuthResolver<TContext extends ProfileContext = ProfileCont
|
|
|
154
183
|
@TransformArgs(forgotPasswordTransformers, { arg: 'input' })
|
|
155
184
|
@ValidateArgs(forgotPasswordValidators, { arg: 'input', tKey: 'forgot' })
|
|
156
185
|
@Mutation(() => SendTokenPayload)
|
|
157
|
-
async forgotPassword(
|
|
186
|
+
async forgotPassword(
|
|
187
|
+
@Arg('input') input: ForgotPasswordInput,
|
|
188
|
+
@Ctx() ctx: TContext
|
|
189
|
+
) {
|
|
158
190
|
const { t } = ctx;
|
|
159
191
|
const service = getAuthService();
|
|
160
192
|
const user = await service.db.findUserByEmail(input.email);
|
|
@@ -163,11 +195,13 @@ export function createAuthResolver<TContext extends ProfileContext = ProfileCont
|
|
|
163
195
|
const res = await service.sendLink(user, 'recovery');
|
|
164
196
|
|
|
165
197
|
if (logTelegramBot) {
|
|
166
|
-
await logTelegramBot.sendError(
|
|
198
|
+
await logTelegramBot.sendError(
|
|
199
|
+
`${user.email || user.urlSlug} запросил(а) восстановление пароля`
|
|
200
|
+
);
|
|
167
201
|
}
|
|
168
202
|
|
|
169
203
|
return {
|
|
170
|
-
|
|
204
|
+
recoveryLinkIsSent: res.ok,
|
|
171
205
|
limitExpiresAt: res.limitExpiresAt,
|
|
172
206
|
};
|
|
173
207
|
}
|
|
@@ -175,15 +209,25 @@ export function createAuthResolver<TContext extends ProfileContext = ProfileCont
|
|
|
175
209
|
@TransformArgs(recoverPasswordTransformers, { arg: 'input' })
|
|
176
210
|
@ValidateArgs(recoverPasswordValidators, { arg: 'input', tKey: 'recover' })
|
|
177
211
|
@Mutation(() => StatusPayload)
|
|
178
|
-
async recoverPassword(
|
|
212
|
+
async recoverPassword(
|
|
213
|
+
@Arg('input') input: RecoverPasswordInput,
|
|
214
|
+
@Ctx() ctx: TContext
|
|
215
|
+
) {
|
|
179
216
|
const service = getAuthService();
|
|
180
|
-
const user = await service.getUserByToken(
|
|
217
|
+
const user = await service.getUserByToken(
|
|
218
|
+
RECOVERY_REDIS_PREFIX,
|
|
219
|
+
input.token
|
|
220
|
+
);
|
|
181
221
|
if (!user) throw new Error(ctx.t('validation:error.wrongCode'));
|
|
182
222
|
|
|
183
223
|
user.password = await service.hashPassword(input.password);
|
|
184
224
|
user.isTempPassword = false;
|
|
185
225
|
await user.save();
|
|
186
|
-
await service.removeTokenFromRedis(
|
|
226
|
+
await service.removeTokenFromRedis(
|
|
227
|
+
RECOVERY_REDIS_PREFIX,
|
|
228
|
+
user,
|
|
229
|
+
input.token
|
|
230
|
+
);
|
|
187
231
|
|
|
188
232
|
const userAgent = decodeURI(ctx.req.get('user-agent') || '');
|
|
189
233
|
await ctx.req.session.create({
|
|
@@ -194,7 +238,9 @@ export function createAuthResolver<TContext extends ProfileContext = ProfileCont
|
|
|
194
238
|
|
|
195
239
|
if (onPasswordRecovered) await onPasswordRecovered(user, ctx);
|
|
196
240
|
if (logTelegramBot) {
|
|
197
|
-
await logTelegramBot.sendError(
|
|
241
|
+
await logTelegramBot.sendError(
|
|
242
|
+
`${user.email || user.urlSlug} восстановил(а) пароль`
|
|
243
|
+
);
|
|
198
244
|
}
|
|
199
245
|
|
|
200
246
|
return { ok: true };
|
|
@@ -1,10 +1,10 @@
|
|
|
1
1
|
import {
|
|
2
|
-
|
|
3
|
-
|
|
4
|
-
|
|
5
|
-
|
|
6
|
-
|
|
7
|
-
|
|
2
|
+
Arg,
|
|
3
|
+
Authorized,
|
|
4
|
+
Ctx,
|
|
5
|
+
Mutation,
|
|
6
|
+
Resolver,
|
|
7
|
+
UnauthorizedError,
|
|
8
8
|
} from 'type-graphql';
|
|
9
9
|
import { StatusPayload } from '@os-team/graphql-utils';
|
|
10
10
|
import { TransformArgs } from '@os-team/graphql-transformers';
|
|
@@ -12,103 +12,130 @@ import { ValidateArgs } from '@os-team/graphql-validators';
|
|
|
12
12
|
import { ProfileAuthService } from '../services/ProfileAuthService';
|
|
13
13
|
import { ProfileContext } from '../types';
|
|
14
14
|
import {
|
|
15
|
-
|
|
16
|
-
|
|
17
|
-
|
|
15
|
+
UpdateEmailInput,
|
|
16
|
+
updateEmailTransformers,
|
|
17
|
+
updateEmailValidators,
|
|
18
|
+
UpdatePasswordInput,
|
|
19
|
+
updatePasswordTransformers,
|
|
20
|
+
updatePasswordValidators,
|
|
21
|
+
UpdateProfileInput,
|
|
22
|
+
updateProfileTransformers,
|
|
23
|
+
updateProfileValidators,
|
|
18
24
|
} from '../dto';
|
|
19
25
|
|
|
20
26
|
export interface ProfileResolverDependencies {
|
|
21
|
-
|
|
22
|
-
|
|
27
|
+
authService: ProfileAuthService | (() => ProfileAuthService);
|
|
28
|
+
userType: any;
|
|
23
29
|
}
|
|
24
30
|
|
|
25
|
-
export function createProfileResolver<
|
|
26
|
-
|
|
27
|
-
|
|
28
|
-
|
|
29
|
-
|
|
30
|
-
|
|
31
|
-
|
|
32
|
-
|
|
33
|
-
|
|
34
|
-
|
|
35
|
-
|
|
36
|
-
|
|
37
|
-
|
|
38
|
-
|
|
39
|
-
|
|
40
|
-
|
|
41
|
-
|
|
42
|
-
|
|
43
|
-
|
|
44
|
-
|
|
45
|
-
|
|
46
|
-
|
|
47
|
-
|
|
48
|
-
|
|
49
|
-
|
|
50
|
-
|
|
51
|
-
|
|
52
|
-
|
|
53
|
-
|
|
54
|
-
|
|
55
|
-
|
|
56
|
-
|
|
57
|
-
|
|
58
|
-
@Mutation(() => StatusPayload)
|
|
59
|
-
async updatePassword(@Arg('input') input: UpdatePasswordInput, @Ctx() ctx: TContext) {
|
|
60
|
-
const { user, t } = ctx;
|
|
61
|
-
if (!user) throw new UnauthorizedError();
|
|
62
|
-
|
|
63
|
-
const service = getAuthService();
|
|
64
|
-
const isOldPasswordOk = await service.verifyPassword(user.password!, input.oldPassword);
|
|
65
|
-
if (!isOldPasswordOk) throw new Error(t('validation:updatePassword.wrongPassword'));
|
|
66
|
-
|
|
67
|
-
user.password = await service.hashPassword(input.password);
|
|
68
|
-
user.isTempPassword = false;
|
|
69
|
-
await user.save();
|
|
70
|
-
|
|
71
|
-
return { ok: true };
|
|
72
|
-
}
|
|
73
|
-
|
|
74
|
-
@Authorized()
|
|
75
|
-
@TransformArgs(updateProfileTransformers, { arg: 'input' })
|
|
76
|
-
@ValidateArgs(updateProfileValidators, { arg: 'input', tKey: 'updateProfile' })
|
|
77
|
-
@Mutation(() => userType)
|
|
78
|
-
async updateProfile(@Arg('input') input: UpdateProfileInput, @Ctx() ctx: TContext) {
|
|
79
|
-
const { user } = ctx;
|
|
80
|
-
if (!user) throw new UnauthorizedError();
|
|
81
|
-
|
|
82
|
-
user.name = input.name;
|
|
83
|
-
await user.save();
|
|
84
|
-
|
|
85
|
-
return user;
|
|
86
|
-
}
|
|
87
|
-
|
|
88
|
-
@Authorized()
|
|
89
|
-
@Mutation(() => StatusPayload)
|
|
90
|
-
async toggleEmailNotification(@Ctx() ctx: TContext) {
|
|
91
|
-
const { user } = ctx;
|
|
92
|
-
if (!user) throw new UnauthorizedError();
|
|
93
|
-
|
|
94
|
-
user.isEmailNotificationEnabled = !user.isEmailNotificationEnabled;
|
|
95
|
-
await user.save();
|
|
96
|
-
|
|
97
|
-
return { ok: true };
|
|
98
|
-
}
|
|
99
|
-
|
|
100
|
-
@Authorized()
|
|
101
|
-
@Mutation(() => StatusPayload)
|
|
102
|
-
async toggleTelegramNotification(@Ctx() ctx: TContext) {
|
|
103
|
-
const { user } = ctx;
|
|
104
|
-
if (!user) throw new UnauthorizedError();
|
|
105
|
-
|
|
106
|
-
user.isTelegramNotificationEnabled = !user.isTelegramNotificationEnabled;
|
|
107
|
-
await user.save();
|
|
108
|
-
|
|
109
|
-
return { ok: true };
|
|
110
|
-
}
|
|
31
|
+
export function createProfileResolver<
|
|
32
|
+
TContext extends ProfileContext = ProfileContext
|
|
33
|
+
>(deps: ProfileResolverDependencies): any {
|
|
34
|
+
const { authService, userType } = deps;
|
|
35
|
+
|
|
36
|
+
const getAuthService = (): ProfileAuthService => {
|
|
37
|
+
if (typeof authService === 'function') return authService();
|
|
38
|
+
return authService;
|
|
39
|
+
};
|
|
40
|
+
|
|
41
|
+
@Resolver(() => userType)
|
|
42
|
+
class ProfileResolver {
|
|
43
|
+
@Authorized()
|
|
44
|
+
@TransformArgs(updateEmailTransformers, { arg: 'input' })
|
|
45
|
+
@ValidateArgs(updateEmailValidators, { arg: 'input', tKey: 'updateEmail' })
|
|
46
|
+
@Mutation(() => StatusPayload)
|
|
47
|
+
async updateEmail(
|
|
48
|
+
@Arg('input') input: UpdateEmailInput,
|
|
49
|
+
@Ctx() ctx: TContext
|
|
50
|
+
) {
|
|
51
|
+
const { user, t } = ctx;
|
|
52
|
+
if (!user) throw new UnauthorizedError();
|
|
53
|
+
|
|
54
|
+
const service = getAuthService();
|
|
55
|
+
if (await service.db.isEmailTaken(input.email, user.id)) {
|
|
56
|
+
throw new Error(t('validation:updateEmail.emailExists'));
|
|
57
|
+
}
|
|
58
|
+
|
|
59
|
+
user.email = input.email;
|
|
60
|
+
user.isEmailConfirmed = false;
|
|
61
|
+
await user.save();
|
|
62
|
+
|
|
63
|
+
return { ok: true };
|
|
111
64
|
}
|
|
112
65
|
|
|
113
|
-
|
|
66
|
+
@Authorized()
|
|
67
|
+
@TransformArgs(updatePasswordTransformers, { arg: 'input' })
|
|
68
|
+
@ValidateArgs(updatePasswordValidators, {
|
|
69
|
+
arg: 'input',
|
|
70
|
+
tKey: 'updatePassword',
|
|
71
|
+
})
|
|
72
|
+
@Mutation(() => StatusPayload)
|
|
73
|
+
async updatePassword(
|
|
74
|
+
@Arg('input') input: UpdatePasswordInput,
|
|
75
|
+
@Ctx() ctx: TContext
|
|
76
|
+
) {
|
|
77
|
+
const { user, t } = ctx;
|
|
78
|
+
if (!user) throw new UnauthorizedError();
|
|
79
|
+
|
|
80
|
+
const service = getAuthService();
|
|
81
|
+
const isOldPasswordOk = await service.verifyPassword(
|
|
82
|
+
user.password!,
|
|
83
|
+
input.oldPassword
|
|
84
|
+
);
|
|
85
|
+
if (!isOldPasswordOk)
|
|
86
|
+
throw new Error(t('validation:updatePassword.wrongPassword'));
|
|
87
|
+
|
|
88
|
+
user.password = await service.hashPassword(input.password);
|
|
89
|
+
user.isTempPassword = false;
|
|
90
|
+
await user.save();
|
|
91
|
+
|
|
92
|
+
return { ok: true };
|
|
93
|
+
}
|
|
94
|
+
|
|
95
|
+
@Authorized()
|
|
96
|
+
@TransformArgs(updateProfileTransformers, { arg: 'input' })
|
|
97
|
+
@ValidateArgs(updateProfileValidators, {
|
|
98
|
+
arg: 'input',
|
|
99
|
+
tKey: 'updateProfile',
|
|
100
|
+
})
|
|
101
|
+
@Mutation(() => userType)
|
|
102
|
+
async updateProfile(
|
|
103
|
+
@Arg('input') input: UpdateProfileInput,
|
|
104
|
+
@Ctx() ctx: TContext
|
|
105
|
+
) {
|
|
106
|
+
const { user } = ctx;
|
|
107
|
+
if (!user) throw new UnauthorizedError();
|
|
108
|
+
|
|
109
|
+
user.name = input.name;
|
|
110
|
+
await user.save();
|
|
111
|
+
|
|
112
|
+
return user;
|
|
113
|
+
}
|
|
114
|
+
|
|
115
|
+
@Authorized()
|
|
116
|
+
@Mutation(() => StatusPayload)
|
|
117
|
+
async toggleEmailNotification(@Ctx() ctx: TContext) {
|
|
118
|
+
const { user } = ctx;
|
|
119
|
+
if (!user) throw new UnauthorizedError();
|
|
120
|
+
|
|
121
|
+
user.isEmailNotificationEnabled = !user.isEmailNotificationEnabled;
|
|
122
|
+
await user.save();
|
|
123
|
+
|
|
124
|
+
return { ok: true };
|
|
125
|
+
}
|
|
126
|
+
|
|
127
|
+
@Authorized()
|
|
128
|
+
@Mutation(() => StatusPayload)
|
|
129
|
+
async toggleTelegramNotification(@Ctx() ctx: TContext) {
|
|
130
|
+
const { user } = ctx;
|
|
131
|
+
if (!user) throw new UnauthorizedError();
|
|
132
|
+
|
|
133
|
+
user.isTelegramNotificationEnabled = !user.isTelegramNotificationEnabled;
|
|
134
|
+
await user.save();
|
|
135
|
+
|
|
136
|
+
return { ok: true };
|
|
137
|
+
}
|
|
138
|
+
}
|
|
139
|
+
|
|
140
|
+
return ProfileResolver;
|
|
114
141
|
}
|