@remit/auth-service 0.1.0 → 0.1.2
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/package.json +3 -2
- package/src/auth.ts +6 -0
- package/src/people.ts +11 -12
- package/src/signup.test.ts +24 -0
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@remit/auth-service",
|
|
3
|
-
"version": "0.1.
|
|
3
|
+
"version": "0.1.2",
|
|
4
4
|
"description": "better-auth identity service for the self-host stack",
|
|
5
5
|
"type": "module",
|
|
6
6
|
"main": "src/index.ts",
|
|
@@ -45,7 +45,8 @@
|
|
|
45
45
|
"@types/better-sqlite3": "^7.6.13",
|
|
46
46
|
"@remit/data-ports": "*",
|
|
47
47
|
"@remit/drizzle-sqlite-schema": "*",
|
|
48
|
-
"@remit/api-openapi-types": "*"
|
|
48
|
+
"@remit/api-openapi-types": "*",
|
|
49
|
+
"@remit/domain-enums": "*"
|
|
49
50
|
},
|
|
50
51
|
"license": "MIT",
|
|
51
52
|
"publishConfig": {
|
package/src/auth.ts
CHANGED
|
@@ -74,6 +74,10 @@ export const ACCOUNT_DISABLED = {
|
|
|
74
74
|
|
|
75
75
|
const RESET_TOKEN_TTL_SECONDS = 24 * 60 * 60;
|
|
76
76
|
|
|
77
|
+
const MIN_PASSWORD_LENGTH = 12;
|
|
78
|
+
|
|
79
|
+
const MAX_PASSWORD_LENGTH = 128;
|
|
80
|
+
|
|
77
81
|
const UNKNOWN = "unknown";
|
|
78
82
|
|
|
79
83
|
const clientIpOf = (ctx: GenericEndpointContext | null): string =>
|
|
@@ -180,6 +184,8 @@ export const createAuth = async (
|
|
|
180
184
|
enabled: true,
|
|
181
185
|
autoSignIn: true,
|
|
182
186
|
disableSignUp: !config.selfSignUpEnabled,
|
|
187
|
+
minPasswordLength: MIN_PASSWORD_LENGTH,
|
|
188
|
+
maxPasswordLength: MAX_PASSWORD_LENGTH,
|
|
183
189
|
resetPasswordTokenExpiresIn: RESET_TOKEN_TTL_SECONDS,
|
|
184
190
|
revokeSessionsOnPasswordReset: true,
|
|
185
191
|
onPasswordReset: async ({ user }, request) => {
|
package/src/people.ts
CHANGED
|
@@ -5,6 +5,7 @@ import type {
|
|
|
5
5
|
StepUpAction,
|
|
6
6
|
} from "@remit/api-openapi-types";
|
|
7
7
|
import { deriveAccountConfigId } from "@remit/data-ports/id";
|
|
8
|
+
import { PeopleErrorCode } from "@remit/domain-enums";
|
|
8
9
|
import { calendarFeedTokens } from "@remit/drizzle-sqlite-schema";
|
|
9
10
|
import { and, asc, count, eq, gt, lte, sql } from "drizzle-orm";
|
|
10
11
|
import type { Auth } from "./auth.js";
|
|
@@ -38,13 +39,10 @@ export interface PasswordReset {
|
|
|
38
39
|
expiresAt: number;
|
|
39
40
|
}
|
|
40
41
|
|
|
41
|
-
export type
|
|
42
|
-
|
|
43
|
-
|
|
44
|
-
|
|
45
|
-
| "wrong_password"
|
|
46
|
-
| "step_up_locked"
|
|
47
|
-
| "cannot_disable_self";
|
|
42
|
+
export type PeopleErrorCodeValue =
|
|
43
|
+
(typeof PeopleErrorCode)[keyof typeof PeopleErrorCode];
|
|
44
|
+
|
|
45
|
+
export type PeopleRefusal = PeopleErrorCodeValue | "not_found";
|
|
48
46
|
|
|
49
47
|
export interface Refused {
|
|
50
48
|
ok: false;
|
|
@@ -190,7 +188,7 @@ const callerRefusal = (
|
|
|
190
188
|
outcome: "RefusedCallerDisabled",
|
|
191
189
|
clientIp: request.clientIp,
|
|
192
190
|
});
|
|
193
|
-
return refused(
|
|
191
|
+
return refused(PeopleErrorCode.CallerDisabled);
|
|
194
192
|
};
|
|
195
193
|
|
|
196
194
|
const stepUpRefusal = (
|
|
@@ -218,7 +216,7 @@ const stepUpRefusal = (
|
|
|
218
216
|
outcome: "RefusedStepUp",
|
|
219
217
|
clientIp: request.clientIp,
|
|
220
218
|
});
|
|
221
|
-
return refused(
|
|
219
|
+
return refused(PeopleErrorCode.StepUpRequired);
|
|
222
220
|
};
|
|
223
221
|
|
|
224
222
|
const issueReset = (
|
|
@@ -327,7 +325,8 @@ export const createPeopleDirectory = async (
|
|
|
327
325
|
),
|
|
328
326
|
)
|
|
329
327
|
.get()?.failures ?? 0;
|
|
330
|
-
if (failures >= STEP_UP_MAX_FAILURES)
|
|
328
|
+
if (failures >= STEP_UP_MAX_FAILURES)
|
|
329
|
+
return refused(PeopleErrorCode.StepUpLocked);
|
|
331
330
|
return ok(
|
|
332
331
|
store.audit({
|
|
333
332
|
actor: request.callerId,
|
|
@@ -399,7 +398,7 @@ export const createPeopleDirectory = async (
|
|
|
399
398
|
const attempt = reserveAttempt(request);
|
|
400
399
|
if (!attempt.ok) return attempt;
|
|
401
400
|
if (!(await passwordMatches(request.callerId, request.password))) {
|
|
402
|
-
return refused(
|
|
401
|
+
return refused(PeopleErrorCode.WrongPassword);
|
|
403
402
|
}
|
|
404
403
|
return grantStepUp(request, attempt.value);
|
|
405
404
|
},
|
|
@@ -435,7 +434,7 @@ export const createPeopleDirectory = async (
|
|
|
435
434
|
outcome: "RefusedSelf",
|
|
436
435
|
clientIp: request.clientIp,
|
|
437
436
|
});
|
|
438
|
-
return refused(
|
|
437
|
+
return refused(PeopleErrorCode.CannotDisableSelf);
|
|
439
438
|
}
|
|
440
439
|
const stepUpRefused = stepUpRefusal(
|
|
441
440
|
store,
|
package/src/signup.test.ts
CHANGED
|
@@ -60,4 +60,28 @@ describe("createAuth self-signup gate", () => {
|
|
|
60
60
|
const body = (await response.json()) as { code?: string };
|
|
61
61
|
assert.equal(body.code, "EMAIL_PASSWORD_SIGN_UP_DISABLED");
|
|
62
62
|
});
|
|
63
|
+
|
|
64
|
+
it("refuses an 11-character password", async () => {
|
|
65
|
+
const auth = await createAuth(
|
|
66
|
+
{ ...baseConfig, selfSignUpEnabled: true, signInEnabled: true },
|
|
67
|
+
await openIdentityStore(baseConfig.connectionString),
|
|
68
|
+
);
|
|
69
|
+
const request = new Request(
|
|
70
|
+
"http://localhost:3000/api/auth/sign-up/email",
|
|
71
|
+
{
|
|
72
|
+
method: "POST",
|
|
73
|
+
headers: { "content-type": "application/json" },
|
|
74
|
+
body: JSON.stringify({
|
|
75
|
+
email: "short@example.com",
|
|
76
|
+
password: "elevenchars",
|
|
77
|
+
name: "Short",
|
|
78
|
+
}),
|
|
79
|
+
},
|
|
80
|
+
);
|
|
81
|
+
|
|
82
|
+
const response = await auth.handler(request);
|
|
83
|
+
|
|
84
|
+
const body = (await response.json()) as { code?: string };
|
|
85
|
+
assert.equal(body.code, "PASSWORD_TOO_SHORT");
|
|
86
|
+
});
|
|
63
87
|
});
|