@travetto/auth-model 7.1.3 → 8.0.0-alpha.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.
- package/README.md +4 -4
- package/package.json +4 -4
- package/src/model.ts +2 -2
- package/src/util.ts +23 -10
- package/support/test/model.ts +2 -2
package/README.md
CHANGED
|
@@ -132,7 +132,7 @@ class AuthConfig {
|
|
|
132
132
|
|
|
133
133
|
**Code: Sample usage**
|
|
134
134
|
```typescript
|
|
135
|
-
import {
|
|
135
|
+
import { RuntimeError } from '@travetto/runtime';
|
|
136
136
|
import { Injectable, Inject } from '@travetto/di';
|
|
137
137
|
import type { ModelAuthService } from '@travetto/auth-model';
|
|
138
138
|
|
|
@@ -148,7 +148,7 @@ class UserService {
|
|
|
148
148
|
try {
|
|
149
149
|
return await this.auth.authenticate(identity);
|
|
150
150
|
} catch (error) {
|
|
151
|
-
if (error instanceof
|
|
151
|
+
if (error instanceof RuntimeError && error.category === 'notfound') {
|
|
152
152
|
return await this.auth.register(identity);
|
|
153
153
|
} else {
|
|
154
154
|
throw error;
|
|
@@ -159,7 +159,7 @@ class UserService {
|
|
|
159
159
|
```
|
|
160
160
|
|
|
161
161
|
## Common Utilities
|
|
162
|
-
The [AuthModelUtil](https://github.com/travetto/travetto/tree/main/module/auth-model/src/util.ts#
|
|
162
|
+
The [AuthModelUtil](https://github.com/travetto/travetto/tree/main/module/auth-model/src/util.ts#L6) provides the following functionality:
|
|
163
163
|
|
|
164
164
|
**Code: Auth util structure**
|
|
165
165
|
```typescript
|
|
@@ -173,7 +173,7 @@ export class AuthModelUtil {
|
|
|
173
173
|
* @param keylen Length of hash
|
|
174
174
|
* @param digest Digest method
|
|
175
175
|
*/
|
|
176
|
-
static generateHash(value: string, salt: string, iterations = 25000, keylen = 256, digest = '
|
|
176
|
+
static async generateHash(value: string, salt: string, iterations = 25000, keylen = 256, digest = 'SHA-256'): Promise<string>;
|
|
177
177
|
/**
|
|
178
178
|
* Generate a salted password, with the ability to validate the password
|
|
179
179
|
*
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@travetto/auth-model",
|
|
3
|
-
"version": "
|
|
3
|
+
"version": "8.0.0-alpha.0",
|
|
4
4
|
"type": "module",
|
|
5
5
|
"description": "Authentication model support for the Travetto framework",
|
|
6
6
|
"keywords": [
|
|
@@ -26,11 +26,11 @@
|
|
|
26
26
|
"directory": "module/auth-model"
|
|
27
27
|
},
|
|
28
28
|
"dependencies": {
|
|
29
|
-
"@travetto/auth": "^
|
|
30
|
-
"@travetto/model": "^
|
|
29
|
+
"@travetto/auth": "^8.0.0-alpha.0",
|
|
30
|
+
"@travetto/model": "^8.0.0-alpha.0"
|
|
31
31
|
},
|
|
32
32
|
"peerDependencies": {
|
|
33
|
-
"@travetto/test": "^
|
|
33
|
+
"@travetto/test": "^8.0.0-alpha.0"
|
|
34
34
|
},
|
|
35
35
|
"peerDependenciesMeta": {
|
|
36
36
|
"@travetto/test": {
|
package/src/model.ts
CHANGED
|
@@ -153,10 +153,10 @@ export class ModelAuthService<T extends ModelType> implements Authenticator<T>,
|
|
|
153
153
|
async generateResetToken(userId: string): Promise<RegisteredPrincipal> {
|
|
154
154
|
const user = await this.#retrieve(userId);
|
|
155
155
|
const identity = this.toPrincipal(user);
|
|
156
|
-
const salt =
|
|
156
|
+
const salt = Util.uuid();
|
|
157
157
|
|
|
158
158
|
identity.resetToken = await AuthModelUtil.generateHash(Util.uuid(), salt, 25000, 32);
|
|
159
|
-
identity.resetExpires = TimeUtil.fromNow(
|
|
159
|
+
identity.resetExpires = TimeUtil.fromNow('1h');
|
|
160
160
|
|
|
161
161
|
const output: Partial<T> = { ...user, ...this.fromPrincipal(identity) };
|
|
162
162
|
await this.#modelService.update(this.#cls, this.#cls.from(castTo(output)));
|
package/src/util.ts
CHANGED
|
@@ -1,9 +1,4 @@
|
|
|
1
|
-
import
|
|
2
|
-
import util from 'node:util';
|
|
3
|
-
|
|
4
|
-
import { AppError, Util } from '@travetto/runtime';
|
|
5
|
-
|
|
6
|
-
const pbkdf2 = util.promisify(crypto.pbkdf2);
|
|
1
|
+
import { BinaryUtil, CodecUtil, RuntimeError, Util } from '@travetto/runtime';
|
|
7
2
|
|
|
8
3
|
/**
|
|
9
4
|
* Standard auth utilities
|
|
@@ -19,9 +14,27 @@ export class AuthModelUtil {
|
|
|
19
14
|
* @param keylen Length of hash
|
|
20
15
|
* @param digest Digest method
|
|
21
16
|
*/
|
|
22
|
-
static generateHash(value: string, salt: string, iterations = 25000, keylen = 256, digest = '
|
|
23
|
-
const
|
|
24
|
-
|
|
17
|
+
static async generateHash(value: string, salt: string, iterations = 25000, keylen = 256, digest = 'SHA-256'): Promise<string> {
|
|
18
|
+
const hashKey = await crypto.subtle.importKey(
|
|
19
|
+
'raw',
|
|
20
|
+
BinaryUtil.binaryArrayToBuffer(CodecUtil.fromUTF8String(value)),
|
|
21
|
+
{ name: 'PBKDF2' },
|
|
22
|
+
false,
|
|
23
|
+
['deriveBits']
|
|
24
|
+
);
|
|
25
|
+
|
|
26
|
+
const result = await crypto.subtle.deriveBits(
|
|
27
|
+
{
|
|
28
|
+
name: 'PBKDF2',
|
|
29
|
+
hash: { name: digest },
|
|
30
|
+
salt: BinaryUtil.binaryArrayToBuffer(CodecUtil.fromUTF8String(salt)),
|
|
31
|
+
iterations,
|
|
32
|
+
},
|
|
33
|
+
hashKey,
|
|
34
|
+
keylen * 8
|
|
35
|
+
);
|
|
36
|
+
|
|
37
|
+
return BinaryUtil.binaryArrayToUint8Array(result).toHex().substring(0, keylen);
|
|
25
38
|
}
|
|
26
39
|
|
|
27
40
|
/**
|
|
@@ -33,7 +46,7 @@ export class AuthModelUtil {
|
|
|
33
46
|
*/
|
|
34
47
|
static async generatePassword(password: string, salt: number | string = 32): Promise<{ salt: string, hash: string }> {
|
|
35
48
|
if (!password) {
|
|
36
|
-
throw new
|
|
49
|
+
throw new RuntimeError('Password is required', { category: 'data' });
|
|
37
50
|
}
|
|
38
51
|
|
|
39
52
|
salt = typeof salt === 'number' ? Util.uuid(salt) : salt;
|
package/support/test/model.ts
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
import assert from 'node:assert';
|
|
2
2
|
|
|
3
|
-
import {
|
|
3
|
+
import { RuntimeError, castTo, type Class } from '@travetto/runtime';
|
|
4
4
|
import { Suite, Test } from '@travetto/test';
|
|
5
5
|
import { Inject, InjectableFactory } from '@travetto/di';
|
|
6
6
|
import { type ModelCrudSupport, Model, Transient } from '@travetto/model';
|
|
@@ -76,7 +76,7 @@ export abstract class AuthModelServiceSuite {
|
|
|
76
76
|
await this.authService.authenticate(pre);
|
|
77
77
|
assert.fail('Should not have gotten here');
|
|
78
78
|
} catch (err) {
|
|
79
|
-
if (err instanceof
|
|
79
|
+
if (err instanceof RuntimeError && err.category === 'notfound') {
|
|
80
80
|
const user = await this.authService.register(pre);
|
|
81
81
|
assert.ok(user.hash);
|
|
82
82
|
assert.ok(user.id);
|