Skip to content

Commit e83c3e0

Browse files
author
hirsch88
committed
✨ Add hashing password
1 parent f2209d0 commit e83c3e0

File tree

6 files changed

+66
-27
lines changed

6 files changed

+66
-27
lines changed

package.json

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -38,6 +38,7 @@
3838
}
3939
],
4040
"dependencies": {
41+
"@types/bcrypt": "^2.0.0",
4142
"@types/bluebird": "^3.5.18",
4243
"@types/body-parser": "^1.16.7",
4344
"@types/chalk": "^2.2.0",
@@ -55,6 +56,7 @@
5556
"@types/supertest": "^2.0.4",
5657
"@types/uuid": "^3.4.3",
5758
"@types/winston": "^2.3.7",
59+
"bcrypt": "^2.0.1",
5860
"body-parser": "^1.18.2",
5961
"chalk": "^2.3.0",
6062
"class-validator": "^0.8.5",

src/api/models/User.ts

Lines changed: 24 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -1,12 +1,32 @@
1+
import * as bcrypt from 'bcrypt';
12
import { Exclude } from 'class-transformer';
23
import { IsNotEmpty } from 'class-validator';
3-
import { Column, Entity, OneToMany, PrimaryGeneratedColumn } from 'typeorm';
4+
import { BeforeInsert, Column, Entity, OneToMany, PrimaryGeneratedColumn } from 'typeorm';
45

56
import { Pet } from './Pet';
67

78
@Entity()
89
export class User {
910

11+
public static hashPassword(password: string): Promise<string> {
12+
return new Promise((resolve, reject) => {
13+
bcrypt.hash(password, 10, (err, hash) => {
14+
if (err) {
15+
return reject(err);
16+
}
17+
resolve(hash);
18+
});
19+
});
20+
}
21+
22+
public static comparePassword(user: User, password: string): Promise<boolean> {
23+
return new Promise((resolve, reject) => {
24+
bcrypt.compare(password, user.password, (err, res) => {
25+
resolve(res === true);
26+
});
27+
});
28+
}
29+
1030
@PrimaryGeneratedColumn('uuid')
1131
public id: string;
1232

@@ -38,8 +58,9 @@ export class User {
3858
return `${this.firstName} ${this.lastName} (${this.email})`;
3959
}
4060

41-
public toBase64(): string {
42-
return Buffer.from(`${this.username}:${this.password}`).toString('base64');
61+
@BeforeInsert()
62+
public async hashPassword(): Promise<void> {
63+
this.password = await User.hashPassword(this.password);
4364
}
4465

4566
}

src/auth/AuthService.ts

Lines changed: 13 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -17,28 +17,32 @@ export class AuthService {
1717
public parseBasicAuthFromRequest(req: express.Request): { username: string, password: string } {
1818
const authorization = req.header('authorization');
1919

20-
// Retrieve the token form the Authorization header
2120
if (authorization && authorization.split(' ')[0] === 'Basic') {
22-
this.log.info('Token provided by the client');
23-
const decodedToken = Buffer.from(authorization.split(' ')[1], 'base64').toString('ascii');
24-
const username = decodedToken.split(':')[0];
25-
const password = decodedToken.split(':')[1];
21+
this.log.info('Credentials provided by the client');
22+
const decodedBase64 = Buffer.from(authorization.split(' ')[1], 'base64').toString('ascii');
23+
const username = decodedBase64.split(':')[0];
24+
const password = decodedBase64.split(':')[1];
2625
if (username && password) {
2726
return { username, password };
2827
}
2928
}
3029

31-
this.log.info('No Token provided by the client');
30+
this.log.info('No Credentials provided by the client');
3231
return undefined;
3332
}
3433

35-
public async findUserByUsernameAndPassword(username: string, password: string): Promise<User> {
36-
return this.userRepository.findOne({
34+
public async validateUser(username: string, password: string): Promise<User> {
35+
const user = await this.userRepository.findOne({
3736
where: {
3837
username,
39-
password,
4038
},
4139
});
40+
41+
if (await User.comparePassword(user, password)) {
42+
return user;
43+
}
44+
45+
return undefined;
4246
}
4347

4448
}

src/auth/authorizationChecker.ts

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -22,7 +22,7 @@ export function authorizationChecker(connection: Connection): (action: Action, r
2222
return false;
2323
}
2424

25-
action.request.user = await authService.findUserByUsernameAndPassword(credentials.username, credentials.password);
25+
action.request.user = await authService.validateUser(credentials.username, credentials.password);
2626
if (action.request.user === undefined) {
2727
log.warn('Invalid credentials given');
2828
return false;

src/database/seeds/CreateBruce.ts

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,3 +1,4 @@
1+
import { hash } from 'bcrypt';
12
import { Connection } from 'typeorm';
23

34
import { User } from '../../../src/api/models/User';

yarn.lock

Lines changed: 25 additions & 14 deletions
Original file line numberDiff line numberDiff line change
@@ -16,6 +16,10 @@
1616
esutils "^2.0.2"
1717
js-tokens "^3.0.0"
1818

19+
"@types/bcrypt@^2.0.0":
20+
version "2.0.0"
21+
resolved "https://registry.yarnpkg.com/@types/bcrypt/-/bcrypt-2.0.0.tgz#74cccef82026341fd786cf2eb9c912c7f9107c55"
22+
1923
"@types/bluebird@^3.5.18":
2024
version "3.5.20"
2125
resolved "https://registry.yarnpkg.com/@types/bluebird/-/bluebird-3.5.20.tgz#f6363172add6f4eabb8cada53ca9af2781e8d6a1"
@@ -703,6 +707,13 @@ bcrypt-pbkdf@^1.0.0:
703707
dependencies:
704708
tweetnacl "^0.14.3"
705709

710+
bcrypt@^2.0.1:
711+
version "2.0.1"
712+
resolved "https://registry.yarnpkg.com/bcrypt/-/bcrypt-2.0.1.tgz#229c5afe09379789f918efe86e5e5b682e509f85"
713+
dependencies:
714+
nan "2.10.0"
715+
node-pre-gyp "0.9.1"
716+
706717
better-assert@~1.0.0:
707718
version "1.0.2"
708719
resolved "https://registry.yarnpkg.com/better-assert/-/better-assert-1.0.2.tgz#40866b9e1b9e0b55b481894311e68faffaebc522"
@@ -3564,7 +3575,7 @@ mz@^2.4.0:
35643575
object-assign "^4.0.1"
35653576
thenify-all "^1.0.0"
35663577

3567-
nan@^2.3.0, nan@^2.9.2:
3578+
nan@2.10.0, nan@^2.3.0, nan@^2.9.2:
35683579
version "2.10.0"
35693580
resolved "https://registry.yarnpkg.com/nan/-/nan-2.10.0.tgz#96d0cd610ebd58d4b4de9cc0c6828cda99c7548f"
35703581

@@ -3646,36 +3657,36 @@ node-notifier@^5.2.1:
36463657
shellwords "^0.1.1"
36473658
which "^1.3.0"
36483659

3649-
node-pre-gyp@^0.6.39:
3650-
version "0.6.39"
3651-
resolved "https://registry.yarnpkg.com/node-pre-gyp/-/node-pre-gyp-0.6.39.tgz#c00e96860b23c0e1420ac7befc5044e1d78d8649"
3660+
node-pre-gyp@0.9.1, node-pre-gyp@^0.9.0, node-pre-gyp@~0.9.0:
3661+
version "0.9.1"
3662+
resolved "https://registry.yarnpkg.com/node-pre-gyp/-/node-pre-gyp-0.9.1.tgz#f11c07516dd92f87199dbc7e1838eab7cd56c9e0"
36523663
dependencies:
36533664
detect-libc "^1.0.2"
3654-
hawk "3.1.3"
36553665
mkdirp "^0.5.1"
3666+
needle "^2.2.0"
36563667
nopt "^4.0.1"
3668+
npm-packlist "^1.1.6"
36573669
npmlog "^4.0.2"
36583670
rc "^1.1.7"
3659-
request "2.81.0"
36603671
rimraf "^2.6.1"
36613672
semver "^5.3.0"
3662-
tar "^2.2.1"
3663-
tar-pack "^3.4.0"
3673+
tar "^4"
36643674

3665-
node-pre-gyp@^0.9.0, node-pre-gyp@~0.9.0:
3666-
version "0.9.1"
3667-
resolved "https://registry.yarnpkg.com/node-pre-gyp/-/node-pre-gyp-0.9.1.tgz#f11c07516dd92f87199dbc7e1838eab7cd56c9e0"
3675+
node-pre-gyp@^0.6.39:
3676+
version "0.6.39"
3677+
resolved "https://registry.yarnpkg.com/node-pre-gyp/-/node-pre-gyp-0.6.39.tgz#c00e96860b23c0e1420ac7befc5044e1d78d8649"
36683678
dependencies:
36693679
detect-libc "^1.0.2"
3680+
hawk "3.1.3"
36703681
mkdirp "^0.5.1"
3671-
needle "^2.2.0"
36723682
nopt "^4.0.1"
3673-
npm-packlist "^1.1.6"
36743683
npmlog "^4.0.2"
36753684
rc "^1.1.7"
3685+
request "2.81.0"
36763686
rimraf "^2.6.1"
36773687
semver "^5.3.0"
3678-
tar "^4"
3688+
tar "^2.2.1"
3689+
tar-pack "^3.4.0"
36793690

36803691
nodemon@^1.12.1:
36813692
version "1.17.4"

0 commit comments

Comments
 (0)