@crossauth/backend 0.0.35 → 0.0.37
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/auth.d.ts +5 -0
- package/dist/auth.d.ts.map +1 -1
- package/dist/authenticators/ldapauth.d.ts +1 -0
- package/dist/authenticators/ldapauth.d.ts.map +1 -1
- package/dist/index.cjs +1 -1
- package/dist/index.js +615 -590
- package/dist/session.d.ts.map +1 -1
- package/dist/storage/ldapstorage.d.ts.map +1 -1
- package/package.json +2 -2
package/dist/index.js
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
var Ae = Object.defineProperty;
|
|
2
2
|
var Ie = (S, s, e) => s in S ? Ae(S, s, { enumerable: !0, configurable: !0, writable: !0, value: e }) : S[s] = e;
|
|
3
|
-
var
|
|
3
|
+
var h = (S, s, e) => Ie(S, typeof s != "symbol" ? s + "" : s, e);
|
|
4
4
|
import { CrossauthError as o, ErrorCode as l, UserState as E, CrossauthLogger as u, j as f, OAuthFlows as b, KeyPrefix as U, OAuthTokenConsumerBase as Pe, OAuthClientBase as Ke } from "@crossauth/common";
|
|
5
5
|
import { PrismaClient as ce, Prisma as X } from "@prisma/client";
|
|
6
6
|
import ye from "@mbakereth/ldapjs";
|
|
@@ -71,10 +71,10 @@ class L {
|
|
|
71
71
|
* @param options See {@link UserStorageOptions}
|
|
72
72
|
*/
|
|
73
73
|
constructor(s = {}) {
|
|
74
|
-
|
|
75
|
-
|
|
76
|
-
|
|
77
|
-
|
|
74
|
+
h(this, "userEditableFields", []);
|
|
75
|
+
h(this, "adminEditableFields", []);
|
|
76
|
+
h(this, "normalizeUsername", !0);
|
|
77
|
+
h(this, "normalizeEmail", !0);
|
|
78
78
|
m("userEditableFields", g.JsonArray, this, s, "USER_EDITABLE_FIELDS"), m("adminEditableFields", g.JsonArray, this, s, "ADMIN_EDITABLE_FIELDS"), m("normalizeUsername", g.JsonArray, this, s, "NORMALIZE_USERNAME"), m("normalizeEmail", g.JsonArray, this, s, "NORMALIZE_EMAIL");
|
|
79
79
|
}
|
|
80
80
|
/**
|
|
@@ -173,14 +173,14 @@ class G extends L {
|
|
|
173
173
|
*/
|
|
174
174
|
constructor(e = {}) {
|
|
175
175
|
super(e);
|
|
176
|
-
|
|
177
|
-
|
|
178
|
-
|
|
179
|
-
|
|
180
|
-
|
|
181
|
-
|
|
182
|
-
|
|
183
|
-
|
|
176
|
+
h(this, "userTable", "user");
|
|
177
|
+
h(this, "userSecretsTable", "userSecrets");
|
|
178
|
+
h(this, "idColumn", "id");
|
|
179
|
+
h(this, "useridForeignKeyColumn", "userid");
|
|
180
|
+
h(this, "prismaClient");
|
|
181
|
+
h(this, "includes", ["secrets"]);
|
|
182
|
+
h(this, "includesObject", {});
|
|
183
|
+
h(this, "forceIdToNumber", !0);
|
|
184
184
|
m("userTable", g.String, this, e, "USER_TABLE"), m("userSecretsTable", g.String, this, e, "USER_SECRETS_TABLE"), m("idColumn", g.String, this, e, "USER_ID_COLUMN"), m("useridForeignKeyColumn", g.String, this, e, "USER_ID_FOREIGN_KEY_COLUMN"), m("includes", g.String, this, e, "USER_INCLUDES"), m("forceIdToNumber", g.String, this, e, "USER_FORCE_ID_TO_NUMBER"), this.includes.forEach((t) => {
|
|
185
185
|
this.includesObject[t] = !0;
|
|
186
186
|
}), e && e.prismaClient ? this.prismaClient = e.prismaClient : this.prismaClient = new ce();
|
|
@@ -279,16 +279,16 @@ class G extends L {
|
|
|
279
279
|
try {
|
|
280
280
|
let { id: r, ...i } = e, { userid: a, ...n } = t ?? {};
|
|
281
281
|
"email" in i && i.email && (i = { email_normalized: G.normalize(i.email), ...i }), "username" in i && i.username && (i = { username_normalized: G.normalize(i.username), ...i }), t ? await this.prismaClient.$transaction(async (c) => {
|
|
282
|
-
let
|
|
282
|
+
let d = {};
|
|
283
283
|
try {
|
|
284
|
-
|
|
284
|
+
d = await c[this.userSecretsTable].findUniqueOrThrow({
|
|
285
285
|
where: {
|
|
286
286
|
[this.useridForeignKeyColumn]: e.id
|
|
287
287
|
}
|
|
288
288
|
});
|
|
289
289
|
} catch {
|
|
290
290
|
}
|
|
291
|
-
let { userid: w, ...y } =
|
|
291
|
+
let { userid: w, ...y } = d ?? {};
|
|
292
292
|
n = { ...y, ...n }, await c[this.userTable].update({
|
|
293
293
|
where: {
|
|
294
294
|
[this.idColumn]: e.id
|
|
@@ -421,10 +421,10 @@ class kt extends x {
|
|
|
421
421
|
*/
|
|
422
422
|
constructor(e = {}) {
|
|
423
423
|
super();
|
|
424
|
-
|
|
425
|
-
|
|
426
|
-
|
|
427
|
-
|
|
424
|
+
h(this, "keyTable", "key");
|
|
425
|
+
h(this, "prismaClient");
|
|
426
|
+
h(this, "transactionTimeout", 5e3);
|
|
427
|
+
h(this, "useridForeignKeyColumn", "userid");
|
|
428
428
|
m("transactionTimeout", g.Number, this, e, "TRANSACTION_TIMEOUT"), m("useridForeignKeyColumn", g.Number, this, e, "USER_ID_FOREIGN_KEY_COLUMN"), e.keyTable && (this.keyTable = e.keyTable), e.prismaClient == null ? this.prismaClient = new ce() : this.prismaClient = e.prismaClient;
|
|
429
429
|
}
|
|
430
430
|
async getKey(e) {
|
|
@@ -468,7 +468,7 @@ class kt extends x {
|
|
|
468
468
|
async saveKey(e, t, r, i, a, n = {}) {
|
|
469
469
|
let c;
|
|
470
470
|
try {
|
|
471
|
-
let
|
|
471
|
+
let d = {
|
|
472
472
|
[this.useridForeignKeyColumn]: e,
|
|
473
473
|
value: t,
|
|
474
474
|
created: r,
|
|
@@ -477,10 +477,10 @@ class kt extends x {
|
|
|
477
477
|
...n
|
|
478
478
|
};
|
|
479
479
|
await this.prismaClient[this.keyTable].create({
|
|
480
|
-
data:
|
|
480
|
+
data: d
|
|
481
481
|
});
|
|
482
|
-
} catch (
|
|
483
|
-
|
|
482
|
+
} catch (d) {
|
|
483
|
+
d instanceof X.PrismaClientKnownRequestError || d instanceof Object && "code" in d ? d.code == "P2002" ? (u.logger.warn(f({ msg: "Attempt to create key that already exists. Stack trace follows" })), u.logger.debug(f({ err: d })), c = new o(l.KeyExists)) : (u.logger.debug(f({ err: d })), c = new o(l.Connection, "Error saving key")) : (u.logger.debug(f({ err: d })), c = new o(l.Connection, "Error saving key"));
|
|
484
484
|
}
|
|
485
485
|
if (c)
|
|
486
486
|
throw c;
|
|
@@ -691,14 +691,14 @@ class Et extends me {
|
|
|
691
691
|
*/
|
|
692
692
|
constructor(e = {}) {
|
|
693
693
|
super();
|
|
694
|
-
|
|
695
|
-
|
|
696
|
-
|
|
697
|
-
|
|
694
|
+
h(this, "clientTable", "oAuthClient");
|
|
695
|
+
h(this, "redirectUriTable", "OAuthClientRedirectUri");
|
|
696
|
+
h(this, "validFlowTable", "OAuthClientValidFlow");
|
|
697
|
+
h(this, "prismaClient");
|
|
698
698
|
// PrismaClient;
|
|
699
|
-
|
|
700
|
-
|
|
701
|
-
|
|
699
|
+
h(this, "transactionTimeout", 5e3);
|
|
700
|
+
h(this, "updateMode", "DeleteAndInsert");
|
|
701
|
+
h(this, "useridForeignKeyColumn", "userid");
|
|
702
702
|
m("clientTable", g.String, this, e, "OAUTH_CLIENT_TABLE"), m("redirectUriTable", g.String, this, e, "OAUTH_REDIRECTURI_TABLE"), m("validFlowTable", g.String, this, e, "OAUTH_VALID_FLOW_TABLE"), m("transactionTimeout", g.Number, this, e, "TRANSACTION_TIMEOUT"), m("updateMode", g.String, this, e, "OAUTHCLIENT_UPDATE_MODE"), m("useridForeignKeyColumn", g.String, this, e, "USER_ID_FOREIGN_KEY_COLUMN"), e.prismaClient == null ? this.prismaClient = new ce() : this.prismaClient = e.prismaClient;
|
|
703
703
|
}
|
|
704
704
|
async getClientById(e) {
|
|
@@ -717,14 +717,14 @@ class Et extends me {
|
|
|
717
717
|
...n
|
|
718
718
|
},
|
|
719
719
|
include: { redirect_uri: !0, valid_flow: !0 }
|
|
720
|
-
}),
|
|
720
|
+
}), d = c.redirect_uri, w = c.valid_flow;
|
|
721
721
|
let y = c[this.useridForeignKeyColumn];
|
|
722
722
|
return y === null && (y = void 0), this.useridForeignKeyColumn != "userid" && delete c[this.useridForeignKeyColumn], [{
|
|
723
723
|
...c,
|
|
724
724
|
userid: y,
|
|
725
725
|
client_secret: c.client_secret ?? void 0,
|
|
726
|
-
redirect_uri:
|
|
727
|
-
valid_flow: w.map((
|
|
726
|
+
redirect_uri: d.map((C) => C.uri),
|
|
727
|
+
valid_flow: w.map((C) => C.flow)
|
|
728
728
|
}];
|
|
729
729
|
} else {
|
|
730
730
|
const c = await r[this.clientTable].findMany({
|
|
@@ -734,10 +734,10 @@ class Et extends me {
|
|
|
734
734
|
},
|
|
735
735
|
include: { redirect_uri: !0, valid_flow: !0 }
|
|
736
736
|
});
|
|
737
|
-
for (let
|
|
738
|
-
const w =
|
|
739
|
-
let
|
|
740
|
-
|
|
737
|
+
for (let d of c) {
|
|
738
|
+
const w = d.redirect_uri, y = d.valid_flow;
|
|
739
|
+
let C = d[this.useridForeignKeyColumn];
|
|
740
|
+
C == null && (C = void 0), d.userid = C, this.useridForeignKeyColumn != "userid" && delete d[this.useridForeignKeyColumn], d.client_secret = d.client_secret ?? void 0, d.redirect_uri = w.map((v) => v.uri), d.valid_flow = y.map((v) => v.flow);
|
|
741
741
|
}
|
|
742
742
|
return c;
|
|
743
743
|
}
|
|
@@ -768,50 +768,50 @@ class Et extends me {
|
|
|
768
768
|
const { redirect_uri: r, valid_flow: i, userid: a, ...n } = e;
|
|
769
769
|
let c;
|
|
770
770
|
if (a && (n[this.useridForeignKeyColumn] = a), this.useridForeignKeyColumn != "userid" && delete e[this.useridForeignKeyColumn], r)
|
|
771
|
-
for (let
|
|
772
|
-
if (r[
|
|
771
|
+
for (let d = 0; d < r.length; ++d) {
|
|
772
|
+
if (r[d].includes("#")) throw new o(l.InvalidRedirectUri, "Redirect Uri's may not contain page fragments");
|
|
773
773
|
try {
|
|
774
|
-
new URL(r[
|
|
774
|
+
new URL(r[d]);
|
|
775
775
|
} catch {
|
|
776
|
-
throw new o(l.InvalidRedirectUri, `Redriect uri ${r[
|
|
776
|
+
throw new o(l.InvalidRedirectUri, `Redriect uri ${r[d]} is not valid`);
|
|
777
777
|
}
|
|
778
778
|
}
|
|
779
779
|
if (i) {
|
|
780
|
-
for (let
|
|
781
|
-
if (!b.isValidFlow(i[
|
|
780
|
+
for (let d = 0; d < i.length; ++d)
|
|
781
|
+
if (!b.isValidFlow(i[d])) throw new o(l.InvalidOAuthFlow, "Invalid flow " + i[d]);
|
|
782
782
|
}
|
|
783
783
|
try {
|
|
784
784
|
c = await t[this.clientTable].create({
|
|
785
785
|
data: n
|
|
786
786
|
});
|
|
787
|
-
} catch (
|
|
788
|
-
throw
|
|
787
|
+
} catch (d) {
|
|
788
|
+
throw d instanceof X.PrismaClientKnownRequestError || d instanceof Object && "code" in d ? d.code == "P2002" ? (u.logger.debug(f({ err: d })), new o(l.ClientExists, "Attempt to create an OAuth client with a client_id that already exists. Maximum attempts failed")) : (u.logger.debug(f({ err: d })), new o(l.Connection, "Error saving OAuth client")) : (u.logger.debug(f({ err: d })), new o(l.Connection, "Error saving OAuth client"));
|
|
789
789
|
}
|
|
790
790
|
if (!c)
|
|
791
791
|
throw u.logger.error(f({ msg: "Attempt to create key that already exists. Stack trace follows" })), new o(l.KeyExists);
|
|
792
792
|
if (r)
|
|
793
793
|
try {
|
|
794
|
-
for (let
|
|
794
|
+
for (let d = 0; d < r.length; ++d)
|
|
795
795
|
await t[this.redirectUriTable].create({
|
|
796
796
|
data: {
|
|
797
797
|
client_id: c.client_id,
|
|
798
|
-
uri: r[
|
|
798
|
+
uri: r[d]
|
|
799
799
|
}
|
|
800
800
|
});
|
|
801
|
-
} catch (
|
|
802
|
-
throw
|
|
801
|
+
} catch (d) {
|
|
802
|
+
throw d instanceof X.PrismaClientKnownRequestError || d instanceof Object && "code" in d ? d.code == "P2002" ? (u.logger.debug(f({ err: d })), new o(l.InvalidRedirectUri, "Attempt to create an OAuth client with a redirect uri that already belongs to another client")) : (u.logger.debug(f({ err: d })), new o(l.Connection, "Error saving OAuth client")) : (u.logger.debug(f({ err: d })), new o(l.Connection, "Error saving OAuth client"));
|
|
803
803
|
}
|
|
804
804
|
if (i)
|
|
805
805
|
try {
|
|
806
|
-
for (let
|
|
806
|
+
for (let d = 0; d < i.length; ++d)
|
|
807
807
|
await t[this.validFlowTable].create({
|
|
808
808
|
data: {
|
|
809
809
|
client_id: c.client_id,
|
|
810
|
-
flow: i[
|
|
810
|
+
flow: i[d]
|
|
811
811
|
}
|
|
812
812
|
});
|
|
813
|
-
} catch (
|
|
814
|
-
throw
|
|
813
|
+
} catch (d) {
|
|
814
|
+
throw d instanceof X.PrismaClientKnownRequestError || d instanceof Object && "code" in d ? (u.logger.debug(f({ err: d })), new o(l.Connection, "Error saving OAuth client")) : (u.logger.debug(f({ err: d })), new o(l.Connection, "Error saving OAuth client"));
|
|
815
815
|
}
|
|
816
816
|
return { ...c, redirect_uri: r, valid_flow: i };
|
|
817
817
|
}
|
|
@@ -954,11 +954,11 @@ class bt extends we {
|
|
|
954
954
|
*/
|
|
955
955
|
constructor(e = {}) {
|
|
956
956
|
super();
|
|
957
|
-
|
|
958
|
-
|
|
957
|
+
h(this, "authorizationTable", "oAuthAuthorization");
|
|
958
|
+
h(this, "prismaClient");
|
|
959
959
|
// PrismaClient;
|
|
960
|
-
|
|
961
|
-
|
|
960
|
+
h(this, "transactionTimeout", 5e3);
|
|
961
|
+
h(this, "useridForeignKeyColumn", "userid");
|
|
962
962
|
m("authorizationTable", g.String, this, e, "OAUTH_CLIENT_TABLE"), m("transactionTimeout", g.Number, this, e, "TRANSACTION_TIMEOUT"), m("useridForeignKeyColumn", g.String, this, e, "USER_ID_FOREIGN_KEY_COLUMN"), e.prismaClient == null ? this.prismaClient = new ce() : this.prismaClient = e.prismaClient;
|
|
963
963
|
}
|
|
964
964
|
async getAuthorizations(e, t) {
|
|
@@ -1018,10 +1018,10 @@ class Ut extends L {
|
|
|
1018
1018
|
*/
|
|
1019
1019
|
constructor(e = {}) {
|
|
1020
1020
|
super(e);
|
|
1021
|
-
|
|
1022
|
-
|
|
1023
|
-
|
|
1024
|
-
|
|
1021
|
+
h(this, "usersByUsername", {});
|
|
1022
|
+
h(this, "usersByEmail", {});
|
|
1023
|
+
h(this, "secretsByUsername", {});
|
|
1024
|
+
h(this, "secretsByEmail", {});
|
|
1025
1025
|
}
|
|
1026
1026
|
/**
|
|
1027
1027
|
* Create a user
|
|
@@ -1163,9 +1163,9 @@ class At extends x {
|
|
|
1163
1163
|
*/
|
|
1164
1164
|
constructor() {
|
|
1165
1165
|
super();
|
|
1166
|
-
|
|
1167
|
-
|
|
1168
|
-
|
|
1166
|
+
h(this, "keys", {});
|
|
1167
|
+
h(this, "keysByUserId", {});
|
|
1168
|
+
h(this, "nonUserKeys", []);
|
|
1169
1169
|
}
|
|
1170
1170
|
/**
|
|
1171
1171
|
* Returns the matching key recortd, with additional, or throws an exception.
|
|
@@ -1239,8 +1239,8 @@ class At extends x {
|
|
|
1239
1239
|
for (let i = 0; i < r.length; ++i) {
|
|
1240
1240
|
let a = !0, n = 0;
|
|
1241
1241
|
const c = r[i];
|
|
1242
|
-
for (let
|
|
1243
|
-
if (
|
|
1242
|
+
for (let d in e)
|
|
1243
|
+
if (d in c && c[d] != e[d]) {
|
|
1244
1244
|
a = !1, n = i;
|
|
1245
1245
|
break;
|
|
1246
1246
|
}
|
|
@@ -1316,8 +1316,8 @@ class It extends me {
|
|
|
1316
1316
|
*/
|
|
1317
1317
|
constructor(e = {}) {
|
|
1318
1318
|
super();
|
|
1319
|
-
|
|
1320
|
-
|
|
1319
|
+
h(this, "clients", {});
|
|
1320
|
+
h(this, "clientsByName", {});
|
|
1321
1321
|
}
|
|
1322
1322
|
/**
|
|
1323
1323
|
* Returns the matching client record or throws an exception.
|
|
@@ -1407,8 +1407,8 @@ class Pt extends we {
|
|
|
1407
1407
|
*/
|
|
1408
1408
|
constructor(e = {}) {
|
|
1409
1409
|
super();
|
|
1410
|
-
|
|
1411
|
-
|
|
1410
|
+
h(this, "byClientAndUser", {});
|
|
1411
|
+
h(this, "byClient", {});
|
|
1412
1412
|
}
|
|
1413
1413
|
async getAuthorizations(e, t) {
|
|
1414
1414
|
if (t) {
|
|
@@ -1447,11 +1447,11 @@ class oe extends L {
|
|
|
1447
1447
|
*/
|
|
1448
1448
|
constructor(e, t = {}) {
|
|
1449
1449
|
super(t);
|
|
1450
|
-
|
|
1451
|
-
|
|
1452
|
-
|
|
1453
|
-
|
|
1454
|
-
|
|
1450
|
+
h(this, "localStorage");
|
|
1451
|
+
h(this, "ldapUrls", []);
|
|
1452
|
+
h(this, "ldapUserSearchBase", "");
|
|
1453
|
+
h(this, "ldapUsernameAttribute", "cn");
|
|
1454
|
+
h(this, "createUserFn", $e);
|
|
1455
1455
|
this.localStorage = e, m("ldapUrls", g.JsonArray, this, t, "LDAP_URL", !0), m("ldapUserSearchBase", g.String, this, t, "LDAP_USER_SEARCH_BASE"), m("ldapUsernameAttribute", g.String, this, t, "LDAP_USENAME_ATTRIBUTE"), t.createUserFn && (this.createUserFn = t.createUserFn);
|
|
1456
1456
|
}
|
|
1457
1457
|
/**
|
|
@@ -1465,7 +1465,7 @@ class oe extends L {
|
|
|
1465
1465
|
async createUser(e, t) {
|
|
1466
1466
|
if (!(t != null && t.password)) throw new o(l.PasswordInvalid);
|
|
1467
1467
|
const r = await this.getLdapUser(e.username, t.password);
|
|
1468
|
-
return
|
|
1468
|
+
return e = this.createUserFn(e, r), await this.localStorage.createUser(e, { password: "pbkdf2:sha256:32:600000:0:DISABLED:DISABLED" });
|
|
1469
1469
|
}
|
|
1470
1470
|
/**
|
|
1471
1471
|
* Gets a user from the local storage. Does not check LDAP.
|
|
@@ -1590,17 +1590,17 @@ class oe extends L {
|
|
|
1590
1590
|
r && (n.attributes = r), e.search(
|
|
1591
1591
|
t,
|
|
1592
1592
|
n,
|
|
1593
|
-
function(c,
|
|
1593
|
+
function(c, d) {
|
|
1594
1594
|
let w;
|
|
1595
1595
|
if (c) {
|
|
1596
1596
|
a(c), e.unbind();
|
|
1597
1597
|
return;
|
|
1598
1598
|
}
|
|
1599
|
-
|
|
1599
|
+
d.on("searchEntry", function(y) {
|
|
1600
1600
|
w = oe.searchResultToUser(y.pojo);
|
|
1601
|
-
}),
|
|
1601
|
+
}), d.on("error", function(y) {
|
|
1602
1602
|
a(y), e.unbind();
|
|
1603
|
-
}),
|
|
1603
|
+
}), d.on("end", function(y) {
|
|
1604
1604
|
y.status != 0 ? a(new o(l.Connection, "LDAP onnection failed")) : w ? i(w) : a(new o(l.UsernameOrPasswordInvalid)), e.unbind();
|
|
1605
1605
|
});
|
|
1606
1606
|
}
|
|
@@ -1638,12 +1638,12 @@ class Y extends L {
|
|
|
1638
1638
|
*/
|
|
1639
1639
|
constructor(e, t = {}) {
|
|
1640
1640
|
super(t);
|
|
1641
|
-
|
|
1642
|
-
|
|
1643
|
-
|
|
1644
|
-
|
|
1645
|
-
|
|
1646
|
-
|
|
1641
|
+
h(this, "userTable", "users");
|
|
1642
|
+
h(this, "userSecretsTable", "usersecrets");
|
|
1643
|
+
h(this, "idColumn", "id");
|
|
1644
|
+
h(this, "useridForeignKeyColumn", "userid");
|
|
1645
|
+
h(this, "forceIdToNumber", !0);
|
|
1646
|
+
h(this, "dbPool");
|
|
1647
1647
|
this.dbPool = e, m("userTable", g.String, this, t, "USER_TABLE"), m("userSecretsTable", g.String, this, t, "USER_SECRETS_TABLE"), m("idColumn", g.String, this, t, "USER_ID_COLUMN"), m("forceIdToNumber", g.String, this, t, "USER_FORCE_ID_TO_NUMBER"), m("useridForeignKeyColumn", g.String, this, t, "USER_ID_FOREIGN_KEY_COLUMN");
|
|
1648
1648
|
}
|
|
1649
1649
|
/**
|
|
@@ -1696,23 +1696,23 @@ class Y extends L {
|
|
|
1696
1696
|
let i = await this.dbPool.connect(), a, n, c = this.dbPool.parameters();
|
|
1697
1697
|
try {
|
|
1698
1698
|
await i.startTransaction();
|
|
1699
|
-
let
|
|
1699
|
+
let d = `select * from ${this.userTable} where ${e} = ` + c.nextParameter(), w = await i.execute(d, [t]);
|
|
1700
1700
|
if (w.length == 0)
|
|
1701
1701
|
throw new o(l.UserNotExist);
|
|
1702
|
-
let y,
|
|
1702
|
+
let y, C, v;
|
|
1703
1703
|
if (this.idColumn in w[0]) y = w[0][this.idColumn];
|
|
1704
1704
|
else throw new o(l.Configuration, "ID column " + this.idColumn + " not present in user table");
|
|
1705
|
-
if ("username" in w[0])
|
|
1705
|
+
if ("username" in w[0]) C = w[0].username;
|
|
1706
1706
|
else throw new o(l.Configuration, "username column " + this.idColumn + " not present in user table");
|
|
1707
|
-
if ("state" in w[0])
|
|
1707
|
+
if ("state" in w[0]) v = w[0].state;
|
|
1708
1708
|
else throw new o(l.Configuration, "state column " + this.idColumn + " not present in user table");
|
|
1709
1709
|
if (a = {
|
|
1710
1710
|
...w[0],
|
|
1711
1711
|
id: y,
|
|
1712
|
-
username:
|
|
1713
|
-
state:
|
|
1712
|
+
username: C,
|
|
1713
|
+
state: v
|
|
1714
1714
|
}, !a) throw new o(l.UserNotExist);
|
|
1715
|
-
if (c = this.dbPool.parameters(),
|
|
1715
|
+
if (c = this.dbPool.parameters(), d = `select * from ${this.userSecretsTable} where ${this.useridForeignKeyColumn} = ` + c.nextParameter(), w = await i.execute(d, [a.id]), w.length == 0)
|
|
1716
1716
|
throw new o(l.UserNotExist);
|
|
1717
1717
|
if (w.length > 0 ? n = { userid: a.id, ...w[0] } : n = { userid: a.id }, !n) throw new o(l.UserNotExist);
|
|
1718
1718
|
if (this.useridForeignKeyColumn != "userid" && this.useridForeignKeyColumn in n && delete n[this.useridForeignKeyColumn], await i.commit(), (r == null ? void 0 : r.skipActiveCheck) != !0 && a.state == E.awaitingTwoFactorSetup)
|
|
@@ -1728,8 +1728,8 @@ class Y extends L {
|
|
|
1728
1728
|
if ((r == null ? void 0 : r.skipActiveCheck) != !0 && a.state == E.factor2ResetNeeded)
|
|
1729
1729
|
throw u.logger.debug(f({ msg: "2FA reset required" })), new o(l.Factor2ResetNeeded);
|
|
1730
1730
|
return { user: a, secrets: n };
|
|
1731
|
-
} catch (
|
|
1732
|
-
throw await i.rollback(),
|
|
1731
|
+
} catch (d) {
|
|
1732
|
+
throw await i.rollback(), d;
|
|
1733
1733
|
} finally {
|
|
1734
1734
|
i.release();
|
|
1735
1735
|
}
|
|
@@ -1742,24 +1742,24 @@ class Y extends L {
|
|
|
1742
1742
|
*/
|
|
1743
1743
|
async getUsers(e, t) {
|
|
1744
1744
|
const r = await this.dbPool.connect();
|
|
1745
|
-
let i = [], a = [], n = "", c = "",
|
|
1746
|
-
e && (c = "OFFSET " +
|
|
1745
|
+
let i = [], a = [], n = "", c = "", d = this.dbPool.parameters();
|
|
1746
|
+
e && (c = "OFFSET " + d.nextParameter()), t && (a.push(t), n = "LIMIT " + d.nextParameter());
|
|
1747
1747
|
try {
|
|
1748
1748
|
let w = `select * from ${this.userTable} ${n} ${c} order by username_normalized asc`, y = await r.execute(w, a);
|
|
1749
1749
|
if (y.length == 0)
|
|
1750
1750
|
throw new o(l.UserNotExist);
|
|
1751
|
-
for (let
|
|
1752
|
-
let
|
|
1753
|
-
if (this.idColumn in
|
|
1751
|
+
for (let C of y) {
|
|
1752
|
+
let v, p, T;
|
|
1753
|
+
if (this.idColumn in C) v = C[this.idColumn];
|
|
1754
1754
|
else throw new o(l.Configuration, "ID column " + this.idColumn + " not present in user table");
|
|
1755
|
-
if ("username" in
|
|
1755
|
+
if ("username" in C) p = C.username;
|
|
1756
1756
|
else throw new o(l.Configuration, "username column " + this.idColumn + " not present in user table");
|
|
1757
|
-
if ("state" in
|
|
1757
|
+
if ("state" in C) T = C.state;
|
|
1758
1758
|
else throw new o(l.Configuration, "state column " + this.idColumn + " not present in user table");
|
|
1759
1759
|
let k = {
|
|
1760
|
-
...
|
|
1761
|
-
id:
|
|
1762
|
-
username:
|
|
1760
|
+
...C,
|
|
1761
|
+
id: v,
|
|
1762
|
+
username: p,
|
|
1763
1763
|
state: T
|
|
1764
1764
|
};
|
|
1765
1765
|
i.push(k);
|
|
@@ -1789,26 +1789,26 @@ class Y extends L {
|
|
|
1789
1789
|
let i = this.dbPool.parameters(), a = `select * from ${this.userTable} where ${this.idColumn} = ` + i.nextParameter();
|
|
1790
1790
|
if ((await r.execute(a, [e.id])).length == 0)
|
|
1791
1791
|
throw new o(l.UserNotExist);
|
|
1792
|
-
let c = { ...e },
|
|
1792
|
+
let c = { ...e }, d = t ? { ...t } : void 0;
|
|
1793
1793
|
"email" in c && c.email && (c = { email_normalized: this.normalizeEmail ? Y.normalize(c.email) : c.email, ...c }), "username" in c && c.username && (c = { username_normalized: this.normalizeUsername ? Y.normalize(c.username) : c.username, ...c }), i = this.dbPool.parameters();
|
|
1794
1794
|
let w = [], y = [];
|
|
1795
|
-
for (let
|
|
1796
|
-
c[
|
|
1795
|
+
for (let C in c)
|
|
1796
|
+
c[C] != null && C != "id" && (w.push(C + "= " + i.nextParameter()), y.push(c[C]));
|
|
1797
1797
|
if (w.length > 0) {
|
|
1798
|
-
let
|
|
1798
|
+
let C = w.join(", ");
|
|
1799
1799
|
y.push(e.id);
|
|
1800
|
-
let
|
|
1801
|
-
await r.execute(
|
|
1800
|
+
let v = `update ${this.userTable} set ${C} where ${this.idColumn} = ` + i.nextParameter();
|
|
1801
|
+
await r.execute(v, y);
|
|
1802
1802
|
}
|
|
1803
1803
|
if (t) {
|
|
1804
1804
|
w = [], y = [], i = this.dbPool.parameters();
|
|
1805
|
-
for (let
|
|
1806
|
-
|
|
1805
|
+
for (let C in d)
|
|
1806
|
+
d[C] != null && C != "userid" && (w.push(C + "= " + i.nextParameter()), y.push(d[C]));
|
|
1807
1807
|
if (w.length > 0) {
|
|
1808
|
-
let
|
|
1808
|
+
let C = w.join(", ");
|
|
1809
1809
|
y.push(e.id);
|
|
1810
|
-
let
|
|
1811
|
-
await r.execute(
|
|
1810
|
+
let v = `update ${this.userSecretsTable} set ${C} where userid = ` + i.nextParameter();
|
|
1811
|
+
await r.execute(v, y);
|
|
1812
1812
|
}
|
|
1813
1813
|
}
|
|
1814
1814
|
await r.commit();
|
|
@@ -1836,26 +1836,26 @@ class Y extends L {
|
|
|
1836
1836
|
await r.startTransaction();
|
|
1837
1837
|
let a = { ...e }, n = t ? { ...t } : void 0;
|
|
1838
1838
|
"email" in a && a.email && (a = { email_normalized: this.normalizeEmail ? Y.normalize(a.email) : a.email, ...a }), "username" in a && a.username && (a = { username_normalized: this.normalizeUsername ? Y.normalize(a.username) : a.username, ...a });
|
|
1839
|
-
let c = [],
|
|
1839
|
+
let c = [], d = [], w = [];
|
|
1840
1840
|
const y = this.dbPool.parameters();
|
|
1841
|
-
for (let
|
|
1842
|
-
a[
|
|
1841
|
+
for (let v in a)
|
|
1842
|
+
a[v] != null && v != "id" && (c.push(v), d.push(y.nextParameter()), w.push(a[v]));
|
|
1843
1843
|
if (c.length > 0) {
|
|
1844
|
-
let
|
|
1845
|
-
const T = `insert into ${this.userTable} (${
|
|
1844
|
+
let v = c.join(", "), p = d.join(", ");
|
|
1845
|
+
const T = `insert into ${this.userTable} (${v}) values (${p}) returning ${this.idColumn}`, k = await r.execute(T, w);
|
|
1846
1846
|
if (k.length == 0 || !k[0][this.idColumn]) throw new o(l.Connection, "Couldn't create user");
|
|
1847
1847
|
i = k[0][this.idColumn];
|
|
1848
1848
|
}
|
|
1849
1849
|
if (!i) throw new o(l.Connection, "Couldn't create user");
|
|
1850
1850
|
if (t) {
|
|
1851
|
-
c = [],
|
|
1852
|
-
const
|
|
1853
|
-
c.push("userid"),
|
|
1854
|
-
for (let
|
|
1855
|
-
n[
|
|
1851
|
+
c = [], d = [], w = [];
|
|
1852
|
+
const v = this.dbPool.parameters();
|
|
1853
|
+
c.push("userid"), d.push(v.nextParameter()), w.push(i);
|
|
1854
|
+
for (let p in n)
|
|
1855
|
+
n[p] != null && p != "userid" && (c.push(p), d.push(v.nextParameter()), w.push(n[p]));
|
|
1856
1856
|
if (c.length > 0) {
|
|
1857
|
-
let
|
|
1858
|
-
const k = `insert into ${this.userSecretsTable} (${
|
|
1857
|
+
let p = c.join(", "), T = d.join(", ");
|
|
1858
|
+
const k = `insert into ${this.userSecretsTable} (${p}) values (${T})`;
|
|
1859
1859
|
u.logger.debug(f({ msg: "Executing query", query: k })), await r.execute(k, w);
|
|
1860
1860
|
}
|
|
1861
1861
|
}
|
|
@@ -1912,9 +1912,9 @@ class qe extends x {
|
|
|
1912
1912
|
*/
|
|
1913
1913
|
constructor(e, t = {}) {
|
|
1914
1914
|
super();
|
|
1915
|
-
|
|
1916
|
-
|
|
1917
|
-
|
|
1915
|
+
h(this, "keyTable", "keys");
|
|
1916
|
+
h(this, "dbPool");
|
|
1917
|
+
h(this, "useridForeignKeyColumn", "userid");
|
|
1918
1918
|
m("transactionTimeout", g.Number, this, t, "TRANSACTION_TIMEOUT"), m("useridForeignKeyColumn", g.String, this, t, "USER_ID_FOREIGN_KEY_COLUMN"), t.keyTable && (this.keyTable = t.keyTable), this.dbPool = e;
|
|
1919
1919
|
}
|
|
1920
1920
|
async getKey(e) {
|
|
@@ -1962,17 +1962,17 @@ class qe extends x {
|
|
|
1962
1962
|
* @throws {@link @crossauth/common!CrossauthError } if the key could not be stored.
|
|
1963
1963
|
*/
|
|
1964
1964
|
async saveKey(e, t, r, i, a, n = {}) {
|
|
1965
|
-
let c,
|
|
1965
|
+
let c, d = [this.useridForeignKeyColumn, "value", "created", "expires", "data"], w = this.dbPool.parameters(), y = [];
|
|
1966
1966
|
for (let k = 0; k < 5; ++k)
|
|
1967
1967
|
y.push(w.nextParameter());
|
|
1968
|
-
let
|
|
1968
|
+
let C = [e ?? null, t, r, i ?? null, a ?? ""];
|
|
1969
1969
|
for (let k in n)
|
|
1970
|
-
|
|
1971
|
-
let
|
|
1970
|
+
d.push(k), y.push(w.nextParameter()), C.push(n[k]);
|
|
1971
|
+
let v = d.join(", "), p = y.join(", ");
|
|
1972
1972
|
const T = await this.dbPool.connect();
|
|
1973
1973
|
try {
|
|
1974
|
-
const k = `insert into ${this.keyTable} (${
|
|
1975
|
-
await T.execute(k,
|
|
1974
|
+
const k = `insert into ${this.keyTable} (${v}) values (${p})`;
|
|
1975
|
+
await T.execute(k, C);
|
|
1976
1976
|
} catch (k) {
|
|
1977
1977
|
o.asCrossauthError(k).code == l.ConstraintViolation ? (u.logger.warn(f({ msg: "Attempt to create key that already exists. Stack trace follows" })), u.logger.debug(f({ err: k })), c = new o(l.KeyExists)) : (u.logger.debug(f({ err: k })), c = new o(l.Connection, "Error saving key"));
|
|
1978
1978
|
} finally {
|
|
@@ -1993,15 +1993,15 @@ class qe extends x {
|
|
|
1993
1993
|
async deleteAllForUser(e, t, r) {
|
|
1994
1994
|
const i = await this.dbPool.connect();
|
|
1995
1995
|
try {
|
|
1996
|
-
let a, n = [], c = "",
|
|
1996
|
+
let a, n = [], c = "", d = this.dbPool.parameters();
|
|
1997
1997
|
if (e) {
|
|
1998
|
-
const w =
|
|
1998
|
+
const w = d.nextParameter(), y = d.nextParameter();
|
|
1999
1999
|
a = `delete from ${this.keyTable} where ${this.useridForeignKeyColumn} = ${w} and value like ${y} `, n = [e];
|
|
2000
2000
|
} else {
|
|
2001
|
-
const w =
|
|
2001
|
+
const w = d.nextParameter();
|
|
2002
2002
|
a = `delete from ${this.keyTable} where ${this.useridForeignKeyColumn} is null and value like ${w}`;
|
|
2003
2003
|
}
|
|
2004
|
-
n.push(t + "%"), r && (c = "and value != " +
|
|
2004
|
+
n.push(t + "%"), r && (c = "and value != " + d.nextParameter(), n.push(r)), a += " " + c, u.logger.debug(f({ msg: "Executing query", query: a })), await i.execute(a, n);
|
|
2005
2005
|
} catch (a) {
|
|
2006
2006
|
throw a;
|
|
2007
2007
|
} finally {
|
|
@@ -2013,9 +2013,9 @@ class qe extends x {
|
|
|
2013
2013
|
try {
|
|
2014
2014
|
let r = [], i = [];
|
|
2015
2015
|
const a = this.dbPool.parameters();
|
|
2016
|
-
for (let
|
|
2017
|
-
let w =
|
|
2018
|
-
e[
|
|
2016
|
+
for (let d in e) {
|
|
2017
|
+
let w = d == "userid" ? this.useridForeignKeyColumn : d;
|
|
2018
|
+
e[d] == null ? r.push(w + " is null") : (r.push(w + " = " + a.nextParameter()), i.push(e[d]));
|
|
2019
2019
|
}
|
|
2020
2020
|
let n = r.join(" and "), c = `delete from ${this.keyTable} where ${n}`;
|
|
2021
2021
|
await t.execute(c, i);
|
|
@@ -2031,8 +2031,8 @@ class qe extends x {
|
|
|
2031
2031
|
let i, a = [];
|
|
2032
2032
|
const n = this.dbPool.parameters();
|
|
2033
2033
|
if (e) {
|
|
2034
|
-
let c = n.nextParameter(),
|
|
2035
|
-
i = `delete from ${this.keyTable} where ${this.useridForeignKeyColumn} = ${c} and value like ${
|
|
2034
|
+
let c = n.nextParameter(), d = n.nextParameter();
|
|
2035
|
+
i = `delete from ${this.keyTable} where ${this.useridForeignKeyColumn} = ${c} and value like ${d}`, a.push(e);
|
|
2036
2036
|
} else {
|
|
2037
2037
|
let c = n.nextParameter();
|
|
2038
2038
|
i = `delete from ${this.keyTable} where ${this.useridForeignKeyColumn} is null and value like ${c}`;
|
|
@@ -2053,8 +2053,8 @@ class qe extends x {
|
|
|
2053
2053
|
let c = await t.execute(i, a);
|
|
2054
2054
|
if (c.length == 0)
|
|
2055
2055
|
return [];
|
|
2056
|
-
for (let
|
|
2057
|
-
let w = this.makeKey(
|
|
2056
|
+
for (let d of c) {
|
|
2057
|
+
let w = this.makeKey(d);
|
|
2058
2058
|
this.useridForeignKeyColumn != "userid" && (w.userid = w[this.useridForeignKeyColumn], delete w[this.useridForeignKeyColumn]), r.push(w);
|
|
2059
2059
|
}
|
|
2060
2060
|
return r;
|
|
@@ -2086,12 +2086,12 @@ class qe extends x {
|
|
|
2086
2086
|
delete r.value;
|
|
2087
2087
|
let i = [], a = [], n = this.dbPool.parameters();
|
|
2088
2088
|
for (let c in r) {
|
|
2089
|
-
let
|
|
2090
|
-
r[c] != null && c == "userid" && this.useridForeignKeyColumn != "userid" && (
|
|
2089
|
+
let d = c;
|
|
2090
|
+
r[c] != null && c == "userid" && this.useridForeignKeyColumn != "userid" && (d = this.useridForeignKeyColumn), i.push(c + "= " + n.nextParameter()), a.push(r[d]);
|
|
2091
2091
|
}
|
|
2092
2092
|
if (a.push(t.value), i.length > 0) {
|
|
2093
|
-
let c = i.join(", "),
|
|
2094
|
-
u.logger.debug(f({ msg: "Executing query", query:
|
|
2093
|
+
let c = i.join(", "), d = `update ${this.keyTable} set ${c} where value = ` + n.nextParameter();
|
|
2094
|
+
u.logger.debug(f({ msg: "Executing query", query: d })), await e.execute(d, a);
|
|
2095
2095
|
}
|
|
2096
2096
|
}
|
|
2097
2097
|
/**
|
|
@@ -2162,11 +2162,11 @@ class We extends me {
|
|
|
2162
2162
|
*/
|
|
2163
2163
|
constructor(e, t = {}) {
|
|
2164
2164
|
super();
|
|
2165
|
-
|
|
2166
|
-
|
|
2167
|
-
|
|
2168
|
-
|
|
2169
|
-
|
|
2165
|
+
h(this, "clientTable", "oauthclient");
|
|
2166
|
+
h(this, "redirectUriTable", "oauthclientredirecturi");
|
|
2167
|
+
h(this, "validFlowTable", "oauthclientvalidflow");
|
|
2168
|
+
h(this, "dbPool");
|
|
2169
|
+
h(this, "useridForeignKeyColumn", "userid");
|
|
2170
2170
|
m("clientTable", g.String, this, t, "OAUTH_CLIENT_TABLE"), m("redirectUriTable", g.String, this, t, "OAUTH_REDIRECTURI_TABLE"), m("validFlowTable", g.String, this, t, "OAUTH_VALID_FLOW_TABLE"), m("updateMode", g.String, this, t, "OAUTHCLIENT_UPDATE_MODE"), m("useridForeignKeyColumn", g.String, this, t, "USER_ID_FOREIGN_KEY_COLUMN"), this.dbPool = e;
|
|
2171
2171
|
}
|
|
2172
2172
|
async getClientById(e) {
|
|
@@ -2210,11 +2210,11 @@ class We extends me {
|
|
|
2210
2210
|
};
|
|
2211
2211
|
}
|
|
2212
2212
|
async getClientWithTransaction(e, t, r, i, a, n) {
|
|
2213
|
-
let c = [],
|
|
2214
|
-
t && r && (
|
|
2215
|
-
let
|
|
2216
|
-
t && r && (
|
|
2217
|
-
let T = y + " union " +
|
|
2213
|
+
let c = [], d = this.dbPool.parameters(), w = [], y = `select c.*, r.uri as uri, null as flow from ${this.clientTable} as c left join ${this.redirectUriTable} r on c.client_id = r.client_id `, C = "";
|
|
2214
|
+
t && r && (C = `where c.${t} = ` + d.nextParameter(), w.push(r)), i !== null && i == null || (C == "" ? C = "where " : C += " and ", i == null ? C += "userid is null" : (C += `${this.useridForeignKeyColumn} = ` + d.nextParameter(), w.push(i)));
|
|
2215
|
+
let v = `select c.*, null as uri, f.flow as flow from ${this.clientTable} as c left join ${this.validFlowTable} f on c.client_id = f.client_id `, p = "";
|
|
2216
|
+
t && r && (p = `where c.${t} = ` + d.nextParameter(), w.push(r)), i !== null && i == null || (p == "" ? p = "where " : p += " and ", i == null ? p += "userid is null" : (p += `${this.useridForeignKeyColumn} = ` + d.nextParameter(), w.push(i))), n && (a || (a = 0), a = Number(a), n = Number(n), C == "" ? C = "where " : C += " and ", C += ` c.client_id in (select client_id from ${this.clientTable} limit ${n} offset ${a})`, p == "" ? p = "where " : p += " and ", p += ` c.client_id in (select client_id from ${this.clientTable} limit ${n} offset ${a})`), y += C, v += p;
|
|
2217
|
+
let T = y + " union " + v + " order by client_id";
|
|
2218
2218
|
const k = await e.execute(T, w);
|
|
2219
2219
|
let A;
|
|
2220
2220
|
for (let z of k)
|
|
@@ -2243,47 +2243,47 @@ class We extends me {
|
|
|
2243
2243
|
async createClientWithTransaction(e, t) {
|
|
2244
2244
|
const { redirect_uri: r, valid_flow: i, userid: a, ...n } = t;
|
|
2245
2245
|
if (a && (n[this.useridForeignKeyColumn] = a), r)
|
|
2246
|
-
for (let
|
|
2247
|
-
if (r[
|
|
2246
|
+
for (let p = 0; p < r.length; ++p) {
|
|
2247
|
+
if (r[p].includes("#")) throw new o(l.InvalidRedirectUri, "Redirect Uri's may not contain page fragments");
|
|
2248
2248
|
try {
|
|
2249
|
-
new URL(r[
|
|
2249
|
+
new URL(r[p]);
|
|
2250
2250
|
} catch {
|
|
2251
|
-
throw new o(l.InvalidRedirectUri, `Redriect uri ${r[
|
|
2251
|
+
throw new o(l.InvalidRedirectUri, `Redriect uri ${r[p]} is not valid`);
|
|
2252
2252
|
}
|
|
2253
2253
|
}
|
|
2254
2254
|
if (i) {
|
|
2255
|
-
for (let
|
|
2256
|
-
if (!b.isValidFlow(i[
|
|
2255
|
+
for (let p = 0; p < i.length; ++p)
|
|
2256
|
+
if (!b.isValidFlow(i[p])) throw new o(l.InvalidOAuthFlow, "Invalid flow " + i[p]);
|
|
2257
2257
|
}
|
|
2258
|
-
let c = [],
|
|
2258
|
+
let c = [], d = [], w = [], y = this.dbPool.parameters();
|
|
2259
2259
|
try {
|
|
2260
|
-
for (let
|
|
2261
|
-
c.push(
|
|
2260
|
+
for (let p in n)
|
|
2261
|
+
c.push(p), d.push(y.nextParameter()), w.push(n[p]);
|
|
2262
2262
|
if (c.length > 0) {
|
|
2263
|
-
let
|
|
2264
|
-
const k = `insert into ${this.clientTable} (${
|
|
2263
|
+
let p = c.join(", "), T = d.join(", ");
|
|
2264
|
+
const k = `insert into ${this.clientTable} (${p}) values (${T})`;
|
|
2265
2265
|
await e.execute(k, w);
|
|
2266
2266
|
}
|
|
2267
|
-
} catch (
|
|
2268
|
-
throw typeof
|
|
2267
|
+
} catch (p) {
|
|
2268
|
+
throw typeof p == "object" && p != null && "code" in p && typeof p.code == "string" && (p.code.startsWith("22") || p.code.startsWith("23")) ? (u.logger.debug(f({ err: p })), new o(l.InvalidClientId, "Attempt to create an OAuth client with a client_id that already exists. Maximum attempts failed")) : (u.logger.debug(f({ err: p })), new o(l.Connection, "Error saving OAuth client"));
|
|
2269
2269
|
}
|
|
2270
|
-
let
|
|
2271
|
-
if (
|
|
2270
|
+
let C = await this.getClientWithTransaction(e, "client_id", t.client_id, t.userid);
|
|
2271
|
+
if (C.length == 0)
|
|
2272
2272
|
throw u.logger.error(f({ msg: "Attempt to create key that already exists. Stack trace follows" })), new o(l.KeyExists);
|
|
2273
|
-
let
|
|
2273
|
+
let v = C[0];
|
|
2274
2274
|
if (r)
|
|
2275
|
-
for (let
|
|
2275
|
+
for (let p = 0; p < r.length; ++p) {
|
|
2276
2276
|
w = [], y = this.dbPool.parameters();
|
|
2277
2277
|
let T = `insert into ${this.redirectUriTable} (client_id, uri) values (` + y.nextParameter() + ", " + y.nextParameter() + ")";
|
|
2278
|
-
w.push(
|
|
2278
|
+
w.push(v.client_id), w.push(r[p]), await e.execute(T, w);
|
|
2279
2279
|
}
|
|
2280
2280
|
if (i)
|
|
2281
|
-
for (let
|
|
2281
|
+
for (let p = 0; p < i.length; ++p) {
|
|
2282
2282
|
w = [], y = this.dbPool.parameters();
|
|
2283
2283
|
let T = `insert into ${this.validFlowTable} (client_id, flow) values (` + y.nextParameter() + ", " + y.nextParameter() + ")";
|
|
2284
|
-
w.push(
|
|
2284
|
+
w.push(v.client_id), w.push(i[p]), await e.execute(T, w);
|
|
2285
2285
|
}
|
|
2286
|
-
return { ...
|
|
2286
|
+
return { ...v, redirect_uri: r, valid_flow: i };
|
|
2287
2287
|
}
|
|
2288
2288
|
/**
|
|
2289
2289
|
*
|
|
@@ -2341,29 +2341,29 @@ class We extends me {
|
|
|
2341
2341
|
if (!b.isValidFlow(i[T])) throw new o(l.InvalidOAuthFlow, "Redirect Uri's may not contain page fragments");
|
|
2342
2342
|
}
|
|
2343
2343
|
if (!t.client_id) throw new o(l.InvalidClientId, "No client ig given");
|
|
2344
|
-
let { client_id: a, redirect_uri: n, valid_flow: c, ...
|
|
2344
|
+
let { client_id: a, redirect_uri: n, valid_flow: c, ...d } = t;
|
|
2345
2345
|
n || (n = []), c || (c = []);
|
|
2346
2346
|
let w = this.dbPool.parameters(), y = `delete from ${this.redirectUriTable} where client_id = ` + w.nextParameter();
|
|
2347
2347
|
await e.execute(y, [t.client_id]), w = this.dbPool.parameters(), y = `delete from ${this.validFlowTable} where client_id = ` + w.nextParameter(), await e.execute(y, [t.client_id]);
|
|
2348
|
-
let
|
|
2348
|
+
let C = [], v = [], p = [];
|
|
2349
2349
|
w = this.dbPool.parameters(), y = `delete from ${this.validFlowTable} where client_id = ` + w.nextParameter();
|
|
2350
|
-
for (let T in
|
|
2351
|
-
|
|
2352
|
-
if (
|
|
2353
|
-
let T =
|
|
2354
|
-
y = `update ${this.clientTable} set (${T}) values (${k})`, await e.execute(y,
|
|
2350
|
+
for (let T in d)
|
|
2351
|
+
C.push(T), v.push(w.nextParameter()), p.push(d[T]);
|
|
2352
|
+
if (C.length > 0) {
|
|
2353
|
+
let T = C.join(", "), k = v.join(", ");
|
|
2354
|
+
y = `update ${this.clientTable} set (${T}) values (${k})`, await e.execute(y, p);
|
|
2355
2355
|
}
|
|
2356
2356
|
if (n)
|
|
2357
2357
|
for (let T = 0; T < n.length; ++T) {
|
|
2358
|
-
|
|
2358
|
+
p = [], w = this.dbPool.parameters();
|
|
2359
2359
|
let k = `insert into ${this.redirectUriTable} (client_id, uri) values (` + w.nextParameter() + ", " + w.nextParameter() + ")";
|
|
2360
|
-
|
|
2360
|
+
p.push(t.client_id), p.push(n[T]), await e.execute(k, p);
|
|
2361
2361
|
}
|
|
2362
2362
|
if (c)
|
|
2363
2363
|
for (let T = 0; T < c.length; ++T) {
|
|
2364
|
-
|
|
2364
|
+
p = [], w = this.dbPool.parameters();
|
|
2365
2365
|
let k = `insert into ${this.validFlowTable} (client_id, flow) values (` + w.nextParameter() + ", " + w.nextParameter() + ")";
|
|
2366
|
-
|
|
2366
|
+
p.push(t.client_id), p.push(c[T]), await e.execute(k, p);
|
|
2367
2367
|
}
|
|
2368
2368
|
}
|
|
2369
2369
|
async getClients(e, t, r) {
|
|
@@ -2387,9 +2387,9 @@ class Je extends we {
|
|
|
2387
2387
|
*/
|
|
2388
2388
|
constructor(e, t = {}) {
|
|
2389
2389
|
super();
|
|
2390
|
-
|
|
2391
|
-
|
|
2392
|
-
|
|
2390
|
+
h(this, "authorizationTable", "oauthauthorization");
|
|
2391
|
+
h(this, "useridForeignKeyColumn", "userid");
|
|
2392
|
+
h(this, "dbPool");
|
|
2393
2393
|
m("authorizationTable", g.String, this, t, "OAUTH_CLIENT_TABLE"), m("useridForeignKeyColumn", g.String, this, t, "USER_ID_FOREIGN_KEY_COLUMN"), this.dbPool = e;
|
|
2394
2394
|
}
|
|
2395
2395
|
async getAuthorizations(e, t) {
|
|
@@ -2410,8 +2410,8 @@ class Je extends we {
|
|
|
2410
2410
|
await i.startTransaction();
|
|
2411
2411
|
let a = this.dbPool.parameters(), n = [], c = `delete from ${this.authorizationTable} where client_id = ` + a.nextParameter();
|
|
2412
2412
|
n.push(e), t ? (c += ` and ${this.useridForeignKeyColumn} = ` + a.nextParameter(), n.push(t)) : c += ` and ${this.useridForeignKeyColumn} is null`, await i.execute(c, n);
|
|
2413
|
-
for (let
|
|
2414
|
-
a = this.dbPool.parameters(), n = [], c = `insert into ${this.authorizationTable} (client_id, userid, scope) values (` + a.nextParameter() + ", " + a.nextParameter() + ", " + a.nextParameter() + ")", n.push(e), n.push(t), n.push(
|
|
2413
|
+
for (let d of r)
|
|
2414
|
+
a = this.dbPool.parameters(), n = [], c = `insert into ${this.authorizationTable} (client_id, userid, scope) values (` + a.nextParameter() + ", " + a.nextParameter() + ", " + a.nextParameter() + ")", n.push(e), n.push(t), n.push(d), await i.execute(c, n);
|
|
2415
2415
|
await i.commit();
|
|
2416
2416
|
} catch (a) {
|
|
2417
2417
|
throw await i.rollback(), a;
|
|
@@ -2433,7 +2433,7 @@ class Ze {
|
|
|
2433
2433
|
class de extends Ye {
|
|
2434
2434
|
constructor(e) {
|
|
2435
2435
|
super();
|
|
2436
|
-
|
|
2436
|
+
h(this, "pgPool");
|
|
2437
2437
|
this.pgPool = e;
|
|
2438
2438
|
}
|
|
2439
2439
|
async connect() {
|
|
@@ -2447,7 +2447,7 @@ class de extends Ye {
|
|
|
2447
2447
|
class Xe extends Ze {
|
|
2448
2448
|
constructor(e) {
|
|
2449
2449
|
super();
|
|
2450
|
-
|
|
2450
|
+
h(this, "pgClient");
|
|
2451
2451
|
this.pgClient = e;
|
|
2452
2452
|
}
|
|
2453
2453
|
crossauthErrorFromPostgresError(e) {
|
|
@@ -2482,7 +2482,7 @@ class Xe extends Ze {
|
|
|
2482
2482
|
class Qe extends Ge {
|
|
2483
2483
|
constructor() {
|
|
2484
2484
|
super();
|
|
2485
|
-
|
|
2485
|
+
h(this, "nextParam", 1);
|
|
2486
2486
|
}
|
|
2487
2487
|
nextParameter() {
|
|
2488
2488
|
return "$" + this.nextParam++;
|
|
@@ -2535,8 +2535,8 @@ class re {
|
|
|
2535
2535
|
* @param options see {@link AuthenticationOptions}
|
|
2536
2536
|
*/
|
|
2537
2537
|
constructor(s) {
|
|
2538
|
-
|
|
2539
|
-
|
|
2538
|
+
h(this, "friendlyName");
|
|
2539
|
+
h(this, "factorName", "");
|
|
2540
2540
|
if (!(s != null && s.friendlyName)) throw new o(l.Configuration, "Authenticator must have a friendly name");
|
|
2541
2541
|
this.friendlyName = s == null ? void 0 : s.friendlyName;
|
|
2542
2542
|
}
|
|
@@ -2547,6 +2547,13 @@ class re {
|
|
|
2547
2547
|
canUpdateSecrets: this.canUpdateSecrets()
|
|
2548
2548
|
};
|
|
2549
2549
|
}
|
|
2550
|
+
/**
|
|
2551
|
+
* If your authenticator doesn't need a user to be in the table (because
|
|
2552
|
+
* it can create one), override this and return false. Default is true
|
|
2553
|
+
*/
|
|
2554
|
+
requireUserEntry() {
|
|
2555
|
+
return !0;
|
|
2556
|
+
}
|
|
2550
2557
|
}
|
|
2551
2558
|
class be extends re {
|
|
2552
2559
|
/** @returns `password` */
|
|
@@ -2784,10 +2791,10 @@ const Ce = process.env.PBKDF2_DIGEST || "sha256", Se = Number(process.env.PBKDF2
|
|
|
2784
2791
|
const i = r[0], a = r[1], n = JSON.parse(Buffer.from(i, "base64url").toString());
|
|
2785
2792
|
if (t && n.t + t * 1e3 > (/* @__PURE__ */ new Date()).getTime())
|
|
2786
2793
|
throw new o(l.Expired);
|
|
2787
|
-
const
|
|
2788
|
-
if (
|
|
2794
|
+
const d = ie(ae, e).update(i).digest("base64url");
|
|
2795
|
+
if (d.length != a.length)
|
|
2789
2796
|
throw new o(l.InvalidKey, "Signature does not match payload");
|
|
2790
|
-
if (!he(Buffer.from(
|
|
2797
|
+
if (!he(Buffer.from(d), Buffer.from(a)))
|
|
2791
2798
|
throw new o(l.InvalidKey, "Signature does not match payload");
|
|
2792
2799
|
return n;
|
|
2793
2800
|
}
|
|
@@ -2852,8 +2859,8 @@ const Ce = process.env.PBKDF2_DIGEST || "sha256", Se = Number(process.env.PBKDF2
|
|
|
2852
2859
|
return c = Buffer.concat([c, n.final()]), c.toString();
|
|
2853
2860
|
}
|
|
2854
2861
|
};
|
|
2855
|
-
|
|
2856
|
-
let
|
|
2862
|
+
h(q, "Base32", "ABCDEFGHJKLMNPQRSTUVWXYZ23456789".split(""));
|
|
2863
|
+
let _ = q;
|
|
2857
2864
|
function tt(S) {
|
|
2858
2865
|
let s = [];
|
|
2859
2866
|
if (!S.password) s.push("Password not provided");
|
|
@@ -2874,19 +2881,19 @@ const le = class le extends be {
|
|
|
2874
2881
|
*/
|
|
2875
2882
|
constructor(e, t = {}) {
|
|
2876
2883
|
super({ friendlyName: "Local password", ...t });
|
|
2877
|
-
|
|
2884
|
+
h(this, "secret");
|
|
2878
2885
|
/** If true, the secret key will be added to the salt when hashing. Default false */
|
|
2879
|
-
|
|
2886
|
+
h(this, "enableSecretForPasswords", !1);
|
|
2880
2887
|
/** See {@link LocalPasswordAuthenticatorOptions.pbkdf2Digest} */
|
|
2881
|
-
|
|
2888
|
+
h(this, "pbkdf2Digest", "sha256");
|
|
2882
2889
|
/** See {@link LocalPasswordAuthenticatorOptions.pbkdf2Iterations} */
|
|
2883
|
-
|
|
2890
|
+
h(this, "pbkdf2Iterations", 6e5);
|
|
2884
2891
|
/** See {@link LocalPasswordAuthenticatorOptions.pbkdf2SaltLength} */
|
|
2885
|
-
|
|
2892
|
+
h(this, "pbkdf2SaltLength", 16);
|
|
2886
2893
|
/** See {@link LocalPasswordAuthenticatorOptions.pbkdf2KeyLength} */
|
|
2887
|
-
|
|
2894
|
+
h(this, "pbkdf2KeyLength", 32);
|
|
2888
2895
|
/** See {@link LocalPasswordAuthenticatorOptions.validatePasswordFn} */
|
|
2889
|
-
|
|
2896
|
+
h(this, "validatePasswordFn", tt);
|
|
2890
2897
|
m("secret", g.String, this, t, "HASHER_SECRET"), m("enableSecretForPasswordHash", g.Boolean, this, t, "ENABLE_SECRET_FOR_PASSWORDS"), m("pbkdf2Digest", g.String, this, t, "PASSWORD_PBKDF2_DIGEST"), m("pbkdf2Iterations", g.String, this, t, "PASSWORD_PBKDF2_ITERATIONS"), m("pbkdf2SaltLength", g.String, this, t, "PASSWORD_PBKDF2_SALTLENGTH"), m("pbkdf2KeyLength", g.String, this, t, "PASSWORD_PBKDF2_KEYLENGTH"), t.validatePasswordFn && (this.validatePasswordFn = t.validatePasswordFn);
|
|
2891
2898
|
}
|
|
2892
2899
|
/**
|
|
@@ -2907,7 +2914,7 @@ const le = class le extends be {
|
|
|
2907
2914
|
async authenticateUser(e, t, r) {
|
|
2908
2915
|
if (!r.password) throw new o(l.PasswordInvalid, "Password not provided");
|
|
2909
2916
|
if (!t.password) throw new o(l.PasswordInvalid);
|
|
2910
|
-
if (!await
|
|
2917
|
+
if (!await _.passwordsEqual(r.password, t.password, this.secret))
|
|
2911
2918
|
throw u.logger.debug(f({ msg: "Invalid password hash", user: e.username })), new o(l.PasswordInvalid);
|
|
2912
2919
|
if (e.state == "awaitingtwofactorsetup") throw new o(l.TwoFactorIncomplete);
|
|
2913
2920
|
if (e.state == "awaitingemailverification") throw new o(l.EmailNotVerified);
|
|
@@ -2937,7 +2944,7 @@ const le = class le extends be {
|
|
|
2937
2944
|
* @returns the encoded hash string.
|
|
2938
2945
|
*/
|
|
2939
2946
|
async createPasswordHash(e, t) {
|
|
2940
|
-
return await
|
|
2947
|
+
return await _.passwordHash(e, {
|
|
2941
2948
|
salt: t,
|
|
2942
2949
|
encode: !0,
|
|
2943
2950
|
secret: this.enableSecretForPasswords ? this.secret : void 0,
|
|
@@ -2962,7 +2969,7 @@ const le = class le extends be {
|
|
|
2962
2969
|
* @returns true if match, false otherwise
|
|
2963
2970
|
*/
|
|
2964
2971
|
async passwordMatchesHash(e, t, r) {
|
|
2965
|
-
return t == le.NoPassword ? !1 : await
|
|
2972
|
+
return t == le.NoPassword ? !1 : await _.passwordsEqual(e, t, r);
|
|
2966
2973
|
}
|
|
2967
2974
|
/**
|
|
2968
2975
|
* This will return p hash of the passed password.
|
|
@@ -3019,7 +3026,7 @@ const le = class le extends be {
|
|
|
3019
3026
|
async reprepareConfiguration(e, t) {
|
|
3020
3027
|
}
|
|
3021
3028
|
};
|
|
3022
|
-
|
|
3029
|
+
h(le, "NoPassword", "********");
|
|
3023
3030
|
let ve = le;
|
|
3024
3031
|
class Z extends re {
|
|
3025
3032
|
/**
|
|
@@ -3029,18 +3036,18 @@ class Z extends re {
|
|
|
3029
3036
|
*/
|
|
3030
3037
|
constructor(e = {}) {
|
|
3031
3038
|
super({ friendlyName: "Email otp", ...e });
|
|
3032
|
-
|
|
3033
|
-
|
|
3034
|
-
|
|
3035
|
-
|
|
3036
|
-
|
|
3037
|
-
|
|
3038
|
-
|
|
3039
|
-
|
|
3040
|
-
|
|
3041
|
-
|
|
3042
|
-
|
|
3043
|
-
|
|
3039
|
+
h(this, "views", "views");
|
|
3040
|
+
h(this, "emailAuthenticatorTextBody", "emailauthenticationtextbody.njk");
|
|
3041
|
+
h(this, "emailAuthenticatorHtmlBody");
|
|
3042
|
+
h(this, "emailAuthenticatorSubject", "Login code");
|
|
3043
|
+
h(this, "emailFrom", "");
|
|
3044
|
+
h(this, "smtpHost", "");
|
|
3045
|
+
h(this, "smtpPort", 587);
|
|
3046
|
+
h(this, "smtpUseTls", !0);
|
|
3047
|
+
h(this, "smtpUsername");
|
|
3048
|
+
h(this, "smtpPassword");
|
|
3049
|
+
h(this, "emailAuthenticatorTokenExpires", 60 * 5);
|
|
3050
|
+
h(this, "render");
|
|
3044
3051
|
m("views", g.String, this, e, "VIEWS"), m("emailAuthenticatorTextBody", g.String, this, e, "EMAIL_AUTHENTICATOR_TEXT_BODY"), m("emailAuthenticatorHtmlBody", g.String, this, e, "EMAIL_AUTHENTICATOR_HTML_BODY"), m("emailAuthenticatorSubject", g.String, this, e, "EMAIL_AUTHENTICATOR_SUBJECT"), m("emailFrom", g.String, this, e, "EMAIL_FROM", !0), m("smtpHost", g.String, this, e, "SMTP_HOST", !0), m("smtpPort", g.Number, this, e, "SMTP_PORT"), m("smtpUsername", g.String, this, e, "SMTP_USERNAME"), m("smtpPassword", g.String, this, e, "SMTP_PASSWORD"), m("smtpUseTls", g.Boolean, this, e, "SMTP_USE_TLS"), m("emailAuthenticatorTokenExpires", g.Number, this, e, "EMAIL_AUTHENTICATOR_TOKEN_EXPIRES"), e.render ? this.render = e.render : W.configure(this.views, { autoescape: !0 });
|
|
3045
3052
|
}
|
|
3046
3053
|
/**
|
|
@@ -3098,10 +3105,10 @@ class Z extends re {
|
|
|
3098
3105
|
factor2: this.factorName,
|
|
3099
3106
|
expiry: a,
|
|
3100
3107
|
otp: t
|
|
3101
|
-
},
|
|
3108
|
+
}, d = this.sendToken(r, t);
|
|
3102
3109
|
return u.logger.info(f({
|
|
3103
3110
|
msg: "Sent factor otp email",
|
|
3104
|
-
emailMessageId:
|
|
3111
|
+
emailMessageId: d,
|
|
3105
3112
|
email: r
|
|
3106
3113
|
})), { userData: n, sessionData: c };
|
|
3107
3114
|
}
|
|
@@ -3244,11 +3251,11 @@ class Q extends re {
|
|
|
3244
3251
|
*/
|
|
3245
3252
|
constructor(e = {}) {
|
|
3246
3253
|
super({ friendlyName: "SMS otp", ...e });
|
|
3247
|
-
|
|
3248
|
-
|
|
3249
|
-
|
|
3250
|
-
|
|
3251
|
-
|
|
3254
|
+
h(this, "views", "views");
|
|
3255
|
+
h(this, "smsAuthenticatorBody", "smsauthenticationbody.njk");
|
|
3256
|
+
h(this, "smsAuthenticatorFrom", "");
|
|
3257
|
+
h(this, "smsAuthenticatorTokenExpires", 60 * 5);
|
|
3258
|
+
h(this, "render");
|
|
3252
3259
|
m("views", g.String, this, e, "VIEWS"), m("smsAuthenticatorBody", g.String, this, e, "SMS_AUTHENTICATOR_BODY"), m("smsAuthenticatorFrom", g.String, this, e, "SMS_AUTHENTICATOR_FROM", !0), m("smsAuthenticatorTokenExpires", g.Number, this, e, "SMS_AUTHENTICATOR_TOKEN_EXPIRES"), e.render ? this.render = e.render : W.configure(this.views, { autoescape: !0 });
|
|
3253
3260
|
}
|
|
3254
3261
|
/**
|
|
@@ -3288,8 +3295,8 @@ class Q extends re {
|
|
|
3288
3295
|
expiry: a,
|
|
3289
3296
|
otp: t
|
|
3290
3297
|
};
|
|
3291
|
-
let
|
|
3292
|
-
const w = this.render ? this.render(this.smsAuthenticatorBody,
|
|
3298
|
+
let d = { otp: t };
|
|
3299
|
+
const w = this.render ? this.render(this.smsAuthenticatorBody, d) : W.render(this.smsAuthenticatorBody, d), y = this.sendSms(r, w);
|
|
3293
3300
|
return u.logger.info(f({
|
|
3294
3301
|
msg: "Sent factor otp sms",
|
|
3295
3302
|
smsMessageId: y,
|
|
@@ -3442,8 +3449,8 @@ class Ue extends Q {
|
|
|
3442
3449
|
*/
|
|
3443
3450
|
constructor(e = {}) {
|
|
3444
3451
|
super(e);
|
|
3445
|
-
|
|
3446
|
-
|
|
3452
|
+
h(this, "accountSid");
|
|
3453
|
+
h(this, "authToken");
|
|
3447
3454
|
if (!process.env.TWILIO_ACCOUNT_SID || !process.env.TWILIO_AUTH_TOKEN)
|
|
3448
3455
|
throw new o(
|
|
3449
3456
|
l.Configuration,
|
|
@@ -3475,7 +3482,7 @@ class Rt extends re {
|
|
|
3475
3482
|
*/
|
|
3476
3483
|
constructor(e, t = {}) {
|
|
3477
3484
|
super({ friendlyName: "Dummy factor2", ...t });
|
|
3478
|
-
|
|
3485
|
+
h(this, "code");
|
|
3479
3486
|
this.code = e;
|
|
3480
3487
|
}
|
|
3481
3488
|
/**
|
|
@@ -3637,9 +3644,9 @@ class Dt extends be {
|
|
|
3637
3644
|
*/
|
|
3638
3645
|
constructor(e, t = {}) {
|
|
3639
3646
|
super({ friendlyName: "LDAP", ...t });
|
|
3640
|
-
|
|
3641
|
-
|
|
3642
|
-
|
|
3647
|
+
h(this, "ldapAutoCreateAccount", !1);
|
|
3648
|
+
h(this, "ldapStorage");
|
|
3649
|
+
h(this, "ldapAutoCreateFactor1", "ldap");
|
|
3643
3650
|
m("ldapAutoCreateAccount", g.Boolean, this, t, "LDAP_AUTO_CREATE_ACCOUNT"), m("ldapAutoCreateFactor1", g.Boolean, this, t, "LDAP_AUTO_CREATE_FACTOR1"), this.ldapStorage = e;
|
|
3644
3651
|
}
|
|
3645
3652
|
/**
|
|
@@ -3655,17 +3662,21 @@ class Dt extends be {
|
|
|
3655
3662
|
if (!r.password) throw new o(l.PasswordInvalid, "Password not provided");
|
|
3656
3663
|
await this.ldapStorage.getLdapUser(e.username, r.password);
|
|
3657
3664
|
let i;
|
|
3658
|
-
|
|
3659
|
-
|
|
3660
|
-
|
|
3661
|
-
|
|
3662
|
-
|
|
3663
|
-
|
|
3664
|
-
|
|
3665
|
-
|
|
3666
|
-
|
|
3667
|
-
|
|
3668
|
-
|
|
3665
|
+
try {
|
|
3666
|
+
if (this.ldapAutoCreateAccount)
|
|
3667
|
+
try {
|
|
3668
|
+
i = (await this.ldapStorage.getUserByUsername(e.username)).user, i.factor1 = this.ldapAutoCreateFactor1;
|
|
3669
|
+
} catch {
|
|
3670
|
+
i = await this.ldapStorage.createUser({ factor1: this.ldapAutoCreateFactor1, ...e }, r);
|
|
3671
|
+
}
|
|
3672
|
+
else
|
|
3673
|
+
i = (await this.ldapStorage.getUserByUsername(e.username)).user;
|
|
3674
|
+
if (i.state == "awaitingtwofactorsetup") throw new o(l.TwoFactorIncomplete);
|
|
3675
|
+
if (i.state == "awaitingemailverification") throw new o(l.EmailNotVerified);
|
|
3676
|
+
if (i.state == "deactivated") throw new o(l.UserNotActive);
|
|
3677
|
+
} catch (a) {
|
|
3678
|
+
throw console.log(a), u.logger.debug(f({ err: a })), a;
|
|
3679
|
+
}
|
|
3669
3680
|
}
|
|
3670
3681
|
/**
|
|
3671
3682
|
* Does nothing as LDAP is responsible for password format (this class doesn't create password entries)
|
|
@@ -3673,6 +3684,9 @@ class Dt extends be {
|
|
|
3673
3684
|
validateSecrets(e) {
|
|
3674
3685
|
return [];
|
|
3675
3686
|
}
|
|
3687
|
+
requireUserEntry() {
|
|
3688
|
+
return !1;
|
|
3689
|
+
}
|
|
3676
3690
|
/**
|
|
3677
3691
|
* Does nothing in this class.
|
|
3678
3692
|
*/
|
|
@@ -3731,7 +3745,7 @@ class xt extends re {
|
|
|
3731
3745
|
*/
|
|
3732
3746
|
constructor(e, t) {
|
|
3733
3747
|
super({ friendlyName: "Google Authenticator", ...t });
|
|
3734
|
-
|
|
3748
|
+
h(this, "appName");
|
|
3735
3749
|
this.appName = e;
|
|
3736
3750
|
}
|
|
3737
3751
|
/**
|
|
@@ -3914,26 +3928,26 @@ class R {
|
|
|
3914
3928
|
* @param options see {@link TokenEmailerOptions}
|
|
3915
3929
|
*/
|
|
3916
3930
|
constructor(s, e, t = {}) {
|
|
3917
|
-
|
|
3918
|
-
|
|
3919
|
-
|
|
3920
|
-
|
|
3921
|
-
|
|
3922
|
-
|
|
3923
|
-
|
|
3924
|
-
|
|
3925
|
-
|
|
3926
|
-
|
|
3927
|
-
|
|
3928
|
-
|
|
3929
|
-
|
|
3930
|
-
|
|
3931
|
-
|
|
3932
|
-
|
|
3933
|
-
|
|
3934
|
-
|
|
3935
|
-
|
|
3936
|
-
|
|
3931
|
+
h(this, "userStorage");
|
|
3932
|
+
h(this, "keyStorage");
|
|
3933
|
+
h(this, "views", "views");
|
|
3934
|
+
h(this, "siteUrl");
|
|
3935
|
+
h(this, "prefix", "/");
|
|
3936
|
+
h(this, "emailVerificationTextBody", "emailverificationtextbody.njk");
|
|
3937
|
+
h(this, "emailVerificationHtmlBody");
|
|
3938
|
+
h(this, "emailVerificationSubject", "Please verify your email");
|
|
3939
|
+
h(this, "passwordResetTextBody", "passwordresettextbody.njk");
|
|
3940
|
+
h(this, "passwordResetHtmlBody");
|
|
3941
|
+
h(this, "passwordResetSubject", "Password reset");
|
|
3942
|
+
h(this, "emailFrom", "");
|
|
3943
|
+
h(this, "smtpHost", "");
|
|
3944
|
+
h(this, "smtpPort", 587);
|
|
3945
|
+
h(this, "smtpUseTls", !0);
|
|
3946
|
+
h(this, "smtpUsername");
|
|
3947
|
+
h(this, "smtpPassword");
|
|
3948
|
+
h(this, "verifyEmailExpires", 60 * 60 * 24);
|
|
3949
|
+
h(this, "passwordResetExpires", 60 * 60 * 24);
|
|
3950
|
+
h(this, "render");
|
|
3937
3951
|
this.userStorage = s, this.keyStorage = e, m("siteUrl", g.String, this, t, "SITE_URL", !0), m("prefix", g.String, this, t, "PREFIX"), m("views", g.String, this, t, "VIEWS"), m("emailVerificationTextBody", g.String, this, t, "EMAIL_VERIFICATION_TEXT_BODY"), m("emailVerificationHtmlBody", g.String, this, t, "EMAIL_VERIFICATION_HTML_BODY"), m("emailVerificationSubject", g.String, this, t, "EMAIL_VERIFICATION_SUBJECT"), m("passwordResetTextBody", g.String, this, t, "PASSWORD_RESET_TEXT_BODY"), m("passwordResetHtmlBody", g.String, this, t, "PASSWORD_RESET_HTML_BODY"), m("passwordResetSubject", g.String, this, t, "PASSWORD_RESET_SUBJECT"), m("emailFrom", g.String, this, t, "EMAIL_FROM", !0), m("smtpHost", g.String, this, t, "SMTP_HOST", !0), m("smtpPort", g.Number, this, t, "SMTP_PORT"), m("smtpUsername", g.String, this, t, "SMTP_USERNAME"), m("smtpPassword", g.String, this, t, "SMTP_PASSWORD"), m("smtpUseTls", g.Boolean, this, t, "SMTP_USE_TLS"), m("verifyEmailExpires", g.Boolean, this, t, "VERIFY_EMAIL_EXPIRES"), m("passwordResetExpires", g.String, this, t, "PASSWORD_RESET_EXPIRES"), t.render ? this.render = t.render : W.configure(this.views, { autoescape: !0 });
|
|
3938
3952
|
}
|
|
3939
3953
|
createEmailer() {
|
|
@@ -3950,24 +3964,24 @@ class R {
|
|
|
3950
3964
|
* correct prefix for inserting into storage.
|
|
3951
3965
|
*/
|
|
3952
3966
|
static hashEmailVerificationToken(s) {
|
|
3953
|
-
return U.emailVerificationToken +
|
|
3967
|
+
return U.emailVerificationToken + _.hash(s);
|
|
3954
3968
|
}
|
|
3955
3969
|
/**
|
|
3956
3970
|
* Produces a hash of the given password reset token with the
|
|
3957
3971
|
* correct prefix for inserting into storage.
|
|
3958
3972
|
*/
|
|
3959
3973
|
static hashPasswordResetToken(s) {
|
|
3960
|
-
return U.passwordResetToken +
|
|
3974
|
+
return U.passwordResetToken + _.hash(s);
|
|
3961
3975
|
}
|
|
3962
3976
|
async createAndSaveEmailVerificationToken(s, e = "") {
|
|
3963
3977
|
let r = 0;
|
|
3964
3978
|
const i = /* @__PURE__ */ new Date(), a = new Date(i.getTime() + 1e3 * this.verifyEmailExpires);
|
|
3965
3979
|
for (; r < 10; ) {
|
|
3966
|
-
let n =
|
|
3980
|
+
let n = _.randomValue(ne), c = R.hashEmailVerificationToken(n);
|
|
3967
3981
|
try {
|
|
3968
3982
|
return await this.keyStorage.saveKey(s, c, i, a, e), n;
|
|
3969
3983
|
} catch {
|
|
3970
|
-
n =
|
|
3984
|
+
n = _.randomValue(ne), c = R.hashEmailVerificationToken(n), r++;
|
|
3971
3985
|
}
|
|
3972
3986
|
}
|
|
3973
3987
|
throw new o(l.Connection, "failed creating a unique key");
|
|
@@ -4052,11 +4066,11 @@ class R {
|
|
|
4052
4066
|
let t = 0;
|
|
4053
4067
|
const r = /* @__PURE__ */ new Date(), i = new Date(r.getTime() + 1e3 * this.passwordResetExpires);
|
|
4054
4068
|
for (; t < 10; ) {
|
|
4055
|
-
let a =
|
|
4069
|
+
let a = _.randomValue(ne), n = R.hashPasswordResetToken(a);
|
|
4056
4070
|
try {
|
|
4057
4071
|
return await this.keyStorage.saveKey(s, n, r, i), a;
|
|
4058
4072
|
} catch {
|
|
4059
|
-
a =
|
|
4073
|
+
a = _.randomValue(ne), n = R.hashPasswordResetToken(a), t++;
|
|
4060
4074
|
}
|
|
4061
4075
|
}
|
|
4062
4076
|
throw new o(l.Connection, "failed creating a unique key");
|
|
@@ -4167,17 +4181,17 @@ class rt {
|
|
|
4167
4181
|
constructor(s = {}) {
|
|
4168
4182
|
// header settings
|
|
4169
4183
|
/** name of the CRSF HTTP header */
|
|
4170
|
-
|
|
4184
|
+
h(this, "headerName", "X-CROSSAUTH-CSRF");
|
|
4171
4185
|
// cookie settings
|
|
4172
4186
|
/** Name of the CSRF Cookie */
|
|
4173
|
-
|
|
4174
|
-
|
|
4175
|
-
|
|
4176
|
-
|
|
4177
|
-
|
|
4178
|
-
|
|
4187
|
+
h(this, "cookieName", "CSRFTOKEN");
|
|
4188
|
+
h(this, "domain");
|
|
4189
|
+
h(this, "httpOnly", !1);
|
|
4190
|
+
h(this, "path", "/");
|
|
4191
|
+
h(this, "secure", !0);
|
|
4192
|
+
h(this, "sameSite", "lax");
|
|
4179
4193
|
// hasher settings
|
|
4180
|
-
|
|
4194
|
+
h(this, "secret", "");
|
|
4181
4195
|
m("headerName", g.String, this, s, "CSRF_HEADER_NAME"), m("cookieName", g.String, this, s, "CSRF_COOKIE_NAME"), m("domain", g.String, this, s, "CSRF_COOKIE_DOMAIN"), m("httpOnly", g.Boolean, this, s, "CSRF_COOKIE_HTTPONLY"), m("path", g.String, this, s, "CSRF_COOKIE_PATH"), m("secure", g.Boolean, this, s, "CSRF_COOKIE_SECURE"), m("sameSite", g.String, this, s, "CSRF_COOKIE_SAMESITE"), m("secret", g.String, this, s, "SECRET", !0);
|
|
4182
4196
|
}
|
|
4183
4197
|
/**
|
|
@@ -4188,7 +4202,7 @@ class rt {
|
|
|
4188
4202
|
* @returns a random CSRF token.
|
|
4189
4203
|
*/
|
|
4190
4204
|
createCsrfToken() {
|
|
4191
|
-
return
|
|
4205
|
+
return _.randomValue(_e);
|
|
4192
4206
|
}
|
|
4193
4207
|
/**
|
|
4194
4208
|
* Returns a {@link Cookie } object with the given session key.
|
|
@@ -4197,7 +4211,7 @@ class rt {
|
|
|
4197
4211
|
* @returns a {@link Cookie } object,
|
|
4198
4212
|
*/
|
|
4199
4213
|
makeCsrfCookie(s) {
|
|
4200
|
-
const e =
|
|
4214
|
+
const e = _.signSecureToken(s, this.secret);
|
|
4201
4215
|
let t = {};
|
|
4202
4216
|
return this.domain && (t.domain = this.domain), this.path && (t.path = this.path), t.sameSite = this.sameSite, this.httpOnly && (t.httpOnly = this.httpOnly), this.secure && (t.secure = this.secure), {
|
|
4203
4217
|
name: this.cookieName,
|
|
@@ -4209,7 +4223,7 @@ class rt {
|
|
|
4209
4223
|
return this.maskCsrfToken(s);
|
|
4210
4224
|
}
|
|
4211
4225
|
unsignCookie(s) {
|
|
4212
|
-
return
|
|
4226
|
+
return _.unsignSecureToken(s, this.secret);
|
|
4213
4227
|
}
|
|
4214
4228
|
/**
|
|
4215
4229
|
* Takes a session ID and creates a string representation of the cookie (value of the HTTP `Cookie` header).
|
|
@@ -4222,14 +4236,14 @@ class rt {
|
|
|
4222
4236
|
return this.domain && (e += "; " + this.domain), this.path && (e += "; " + this.path), this.httpOnly && (e += "; httpOnly"), this.secure && (e += "; secure"), e;
|
|
4223
4237
|
}
|
|
4224
4238
|
maskCsrfToken(s) {
|
|
4225
|
-
const e =
|
|
4239
|
+
const e = _.randomValue(_e), t = _.xor(s, e);
|
|
4226
4240
|
return e + "." + t;
|
|
4227
4241
|
}
|
|
4228
4242
|
unmaskCsrfToken(s) {
|
|
4229
4243
|
const e = s.split(".");
|
|
4230
4244
|
if (e.length != 2) throw new o(l.InvalidCsrf, "CSRF token in header or form not in correct format");
|
|
4231
4245
|
const t = e[0], r = e[1];
|
|
4232
|
-
return
|
|
4246
|
+
return _.xor(r, t);
|
|
4233
4247
|
}
|
|
4234
4248
|
/**
|
|
4235
4249
|
* Validates the passed CSRF token.
|
|
@@ -4246,12 +4260,12 @@ class rt {
|
|
|
4246
4260
|
const t = this.unmaskCsrfToken(e);
|
|
4247
4261
|
let r;
|
|
4248
4262
|
try {
|
|
4249
|
-
r =
|
|
4263
|
+
r = _.unsignSecureToken(s, this.secret);
|
|
4250
4264
|
} catch (i) {
|
|
4251
4265
|
throw u.logger.error(f({ err: i })), new o(l.InvalidCsrf, "Invalid CSRF cookie");
|
|
4252
4266
|
}
|
|
4253
4267
|
if (r != t)
|
|
4254
|
-
throw u.logger.warn(f({ msg: "Invalid CSRF token received - form/header value does not match", csrfCookieHash:
|
|
4268
|
+
throw u.logger.warn(f({ msg: "Invalid CSRF token received - form/header value does not match", csrfCookieHash: _.hash(s) })), new o(l.InvalidCsrf);
|
|
4255
4269
|
}
|
|
4256
4270
|
/**
|
|
4257
4271
|
* Validates the passed CSRF cookie (doesn't check it matches the token, just that the cookie is valid).
|
|
@@ -4265,7 +4279,7 @@ class rt {
|
|
|
4265
4279
|
*/
|
|
4266
4280
|
validateCsrfCookie(s) {
|
|
4267
4281
|
try {
|
|
4268
|
-
return
|
|
4282
|
+
return _.unsignSecureToken(s, this.secret);
|
|
4269
4283
|
} catch (e) {
|
|
4270
4284
|
throw u.logger.error(f({ err: e })), new o(l.InvalidCsrf, "Invalid CSRF cookie");
|
|
4271
4285
|
}
|
|
@@ -4280,26 +4294,26 @@ class D {
|
|
|
4280
4294
|
* expires option is ignored (cookies are session-only).
|
|
4281
4295
|
*/
|
|
4282
4296
|
constructor(s, e = {}) {
|
|
4283
|
-
|
|
4284
|
-
|
|
4297
|
+
h(this, "userStorage");
|
|
4298
|
+
h(this, "keyStorage");
|
|
4285
4299
|
/** This is set from input options. Number of seconds before an
|
|
4286
4300
|
* idle session will time out
|
|
4287
4301
|
*/
|
|
4288
|
-
|
|
4289
|
-
|
|
4290
|
-
|
|
4302
|
+
h(this, "idleTimeout", 0);
|
|
4303
|
+
h(this, "persist", !0);
|
|
4304
|
+
h(this, "filterFunction");
|
|
4291
4305
|
// cookie settings
|
|
4292
4306
|
/** Name of the CSRF Cookie, set from input options */
|
|
4293
|
-
|
|
4294
|
-
|
|
4307
|
+
h(this, "cookieName", "SESSIONID");
|
|
4308
|
+
h(this, "maxAge", 60 * 60 * 24 * 30);
|
|
4295
4309
|
// 30 days
|
|
4296
|
-
|
|
4297
|
-
|
|
4298
|
-
|
|
4299
|
-
|
|
4300
|
-
|
|
4310
|
+
h(this, "domain");
|
|
4311
|
+
h(this, "httpOnly", !1);
|
|
4312
|
+
h(this, "path", "/");
|
|
4313
|
+
h(this, "secure", !0);
|
|
4314
|
+
h(this, "sameSite", "lax");
|
|
4301
4315
|
// hasher settings
|
|
4302
|
-
|
|
4316
|
+
h(this, "secret", "");
|
|
4303
4317
|
e.userStorage && (this.userStorage = e.userStorage), this.keyStorage = s, m("idleTimeout", g.Number, this, e, "SESSION_IDLE_TIMEOUT"), m("persist", g.Boolean, this, e, "PERSIST_SESSION_ID"), this.filterFunction = e.filterFunction, m("cookieName", g.String, this, e, "SESSION_COOKIE_NAME"), m("maxAge", g.String, this, e, "SESSION_COOKIE_MAX_AGE"), m("domain", g.String, this, e, "SESSION_COOKIE_DOMAIN"), m("httpOnly", g.Boolean, this, e, "SESSIONCOOKIE_HTTPONLY"), m("path", g.String, this, e, "SESSION_COOKIE_PATH"), m("secure", g.Boolean, this, e, "SESSION_COOKIE_SECURE"), m("sameSite", g.String, this, e, "SESSION_COOKIE_SAMESITE"), m("secret", g.String, this, e, "SECRET", !0);
|
|
4304
4318
|
}
|
|
4305
4319
|
expiry(s) {
|
|
@@ -4314,7 +4328,7 @@ class D {
|
|
|
4314
4328
|
* @returns a base64-url-encoded string that can go into the storage
|
|
4315
4329
|
*/
|
|
4316
4330
|
static hashSessionId(s) {
|
|
4317
|
-
return U.session +
|
|
4331
|
+
return U.session + _.hash(s);
|
|
4318
4332
|
}
|
|
4319
4333
|
/**
|
|
4320
4334
|
* Creates a session key and saves in storage
|
|
@@ -4333,17 +4347,17 @@ class D {
|
|
|
4333
4347
|
* attempts exceeded trying to create a unique session id
|
|
4334
4348
|
*/
|
|
4335
4349
|
async createSessionKey(s, e = {}) {
|
|
4336
|
-
let r = 0, i =
|
|
4350
|
+
let r = 0, i = _.randomValue(ke);
|
|
4337
4351
|
const a = /* @__PURE__ */ new Date();
|
|
4338
4352
|
let n = this.expiry(a), c = !1;
|
|
4339
4353
|
for (; r < 10 && !c; ) {
|
|
4340
|
-
const
|
|
4354
|
+
const d = D.hashSessionId(i);
|
|
4341
4355
|
try {
|
|
4342
|
-
this.idleTimeout > 0 && s && (e = { ...e, lastActivity: /* @__PURE__ */ new Date() }), await this.keyStorage.saveKey(s,
|
|
4356
|
+
this.idleTimeout > 0 && s && (e = { ...e, lastActivity: /* @__PURE__ */ new Date() }), await this.keyStorage.saveKey(s, d, a, n, void 0, e), c = !0;
|
|
4343
4357
|
} catch (w) {
|
|
4344
4358
|
let y = o.asCrossauthError(w);
|
|
4345
4359
|
if (y.code == l.KeyExists || y.code == l.InvalidKey) {
|
|
4346
|
-
if (r++, i =
|
|
4360
|
+
if (r++, i = _.randomValue(ke), r > 10)
|
|
4347
4361
|
throw u.logger.error(f({ msg: "Max attempts exceeded trying to create session ID" })), new o(l.KeyExists);
|
|
4348
4362
|
} else
|
|
4349
4363
|
throw u.logger.debug(f({ err: w })), w;
|
|
@@ -4366,7 +4380,7 @@ class D {
|
|
|
4366
4380
|
* @returns a {@link Cookie } object,
|
|
4367
4381
|
*/
|
|
4368
4382
|
makeCookie(s, e) {
|
|
4369
|
-
let t =
|
|
4383
|
+
let t = _.signSecureToken(s.value, this.secret), r = {};
|
|
4370
4384
|
return e == null && (e = this.persist), this.domain && (r.domain = this.domain), s.expires && e && (r.expires = s.expires), this.path && (r.path = this.path), r.sameSite = this.sameSite, this.httpOnly && (r.httpOnly = this.httpOnly), this.secure && (r.secure = this.secure), {
|
|
4371
4385
|
name: this.cookieName,
|
|
4372
4386
|
value: t,
|
|
@@ -4403,7 +4417,7 @@ class D {
|
|
|
4403
4417
|
* is invalid.
|
|
4404
4418
|
*/
|
|
4405
4419
|
unsignCookie(s) {
|
|
4406
|
-
return
|
|
4420
|
+
return _.unsignSecureToken(s, this.secret);
|
|
4407
4421
|
}
|
|
4408
4422
|
/**
|
|
4409
4423
|
* Returns the user matching the given session key in session storage, or throws an exception.
|
|
@@ -4443,11 +4457,11 @@ class D {
|
|
|
4443
4457
|
async getSessionKey(s) {
|
|
4444
4458
|
const e = Date.now(), t = D.hashSessionId(s), r = await this.keyStorage.getKey(t);
|
|
4445
4459
|
if (r.value = s, r.expires && e > r.expires.getTime())
|
|
4446
|
-
throw u.logger.warn(f({ msg: "Session id in cookie expired in key storage", hashedSessionCookie:
|
|
4460
|
+
throw u.logger.warn(f({ msg: "Session id in cookie expired in key storage", hashedSessionCookie: _.hash(s) })), new o(l.Expired);
|
|
4447
4461
|
if (r.userid && this.idleTimeout > 0 && r.lastactive && e > r.lastactive.getTime() + this.idleTimeout * 1e3)
|
|
4448
|
-
throw u.logger.warn(f({ msg: "Session cookie with expired idle time received", hashedSessionCookie:
|
|
4462
|
+
throw u.logger.warn(f({ msg: "Session cookie with expired idle time received", hashedSessionCookie: _.hash(s) })), new o(l.Expired);
|
|
4449
4463
|
if (this.filterFunction && !this.filterFunction(r))
|
|
4450
|
-
throw u.logger.warn(f({ msg: "Filter function on session id in cookie failed", hashedSessionCookie:
|
|
4464
|
+
throw u.logger.warn(f({ msg: "Filter function on session id in cookie failed", hashedSessionCookie: _.hash(s) })), new o(l.InvalidKey);
|
|
4451
4465
|
return r;
|
|
4452
4466
|
}
|
|
4453
4467
|
/**
|
|
@@ -4467,17 +4481,17 @@ class Lt {
|
|
|
4467
4481
|
* @param options optional parameters for authentication. See {@link SessionManagerOptions }.
|
|
4468
4482
|
*/
|
|
4469
4483
|
constructor(s, e, t = {}) {
|
|
4470
|
-
|
|
4471
|
-
|
|
4472
|
-
|
|
4473
|
-
|
|
4474
|
-
|
|
4475
|
-
|
|
4484
|
+
h(this, "userStorage");
|
|
4485
|
+
h(this, "keyStorage");
|
|
4486
|
+
h(this, "emailTokenStorage");
|
|
4487
|
+
h(this, "csrfTokens");
|
|
4488
|
+
h(this, "session");
|
|
4489
|
+
h(this, "authenticators");
|
|
4476
4490
|
//readonly authenticator : UsernamePasswordAuthenticator;
|
|
4477
|
-
|
|
4478
|
-
|
|
4479
|
-
|
|
4480
|
-
|
|
4491
|
+
h(this, "enableEmailVerification", !1);
|
|
4492
|
+
h(this, "enablePasswordReset", !1);
|
|
4493
|
+
h(this, "tokenEmailer");
|
|
4494
|
+
h(this, "allowedFactor2", []);
|
|
4481
4495
|
t.userStorage && (this.userStorage = t.userStorage), this.keyStorage = s, this.authenticators = e;
|
|
4482
4496
|
for (let r in this.authenticators)
|
|
4483
4497
|
this.authenticators[r].factorName = r;
|
|
@@ -4539,39 +4553,50 @@ class Lt {
|
|
|
4539
4553
|
*/
|
|
4540
4554
|
async login(s, e, t = {}, r, i, a = !1) {
|
|
4541
4555
|
if (!this.userStorage) throw new o(l.Configuration, "Cannot call login if no user storage provided");
|
|
4542
|
-
let n;
|
|
4556
|
+
let n = { userid: "" }, c = "";
|
|
4543
4557
|
if (i)
|
|
4544
4558
|
n = (await this.userStorage.getUserByUsername(i.username, { skipActiveCheck: !0, skipEmailVerifiedCheck: !0 })).secrets;
|
|
4545
4559
|
else {
|
|
4560
|
+
let v = { username: "", state: "active" };
|
|
4561
|
+
try {
|
|
4562
|
+
console.log("Checking user in table");
|
|
4563
|
+
let T = await this.userStorage.getUserByUsername(s, { skipActiveCheck: !0, skipEmailVerifiedCheck: !0 });
|
|
4564
|
+
n = T.secrets, i = T.user, v = T.user;
|
|
4565
|
+
} catch {
|
|
4566
|
+
console.log("CHecking authenticators");
|
|
4567
|
+
for (let k in this.authenticators)
|
|
4568
|
+
console.log("Checking authenticator", k, this.authenticators[k].requireUserEntry()), this.authenticators[k].requireUserEntry() || (v = { username: e.username, state: "active" }, c = k);
|
|
4569
|
+
}
|
|
4570
|
+
if (console.log("Using authenticator", (i == null ? void 0 : i.factor1) ?? c), v.username == "") throw new o(l.UserNotExist);
|
|
4571
|
+
await this.authenticators[(i == null ? void 0 : i.factor1) ?? c].authenticateUser(v, n, e);
|
|
4546
4572
|
let p = await this.userStorage.getUserByUsername(s, { skipActiveCheck: !0, skipEmailVerifiedCheck: !0 });
|
|
4547
|
-
|
|
4548
|
-
await this.authenticators[i.factor1].authenticateUser(i, n, e);
|
|
4573
|
+
n = p.secrets, i = p.user;
|
|
4549
4574
|
}
|
|
4550
|
-
let
|
|
4575
|
+
let d;
|
|
4551
4576
|
if (i.state == E.passwordChangeNeeded)
|
|
4552
|
-
|
|
4577
|
+
d = (await this.createAnonymousSession({ data: JSON.stringify({ passwordchange: { username: i.username } }) })).sessionCookie;
|
|
4553
4578
|
else if (i.state == E.factor2ResetNeeded)
|
|
4554
|
-
|
|
4579
|
+
d = (await this.createAnonymousSession({ data: JSON.stringify({ factor2change: { username: i.username } }) })).sessionCookie;
|
|
4555
4580
|
else if (!a && i.factor2 && i.factor2 != "") {
|
|
4556
|
-
const { sessionCookie:
|
|
4557
|
-
|
|
4581
|
+
const { sessionCookie: v } = await this.initiateTwoFactorLogin(i);
|
|
4582
|
+
d = v;
|
|
4558
4583
|
} else {
|
|
4559
|
-
const
|
|
4560
|
-
|
|
4584
|
+
const v = await this.session.createSessionKey(i.id, t);
|
|
4585
|
+
d = this.session.makeCookie(v, r);
|
|
4561
4586
|
}
|
|
4562
|
-
const
|
|
4587
|
+
const w = this.csrfTokens.createCsrfToken(), y = this.csrfTokens.makeCsrfCookie(w), C = this.csrfTokens.makeCsrfFormOrHeaderToken(w);
|
|
4563
4588
|
try {
|
|
4564
4589
|
this.emailTokenStorage.deleteAllForUser(
|
|
4565
4590
|
i.id,
|
|
4566
4591
|
U.passwordResetToken
|
|
4567
4592
|
);
|
|
4568
|
-
} catch (
|
|
4569
|
-
u.logger.warn(f({ msg: "Couldn't delete password reset tokens while logging in", user: s })), u.logger.debug(f({ err:
|
|
4593
|
+
} catch (v) {
|
|
4594
|
+
u.logger.warn(f({ msg: "Couldn't delete password reset tokens while logging in", user: s })), u.logger.debug(f({ err: v }));
|
|
4570
4595
|
}
|
|
4571
4596
|
return {
|
|
4572
|
-
sessionCookie:
|
|
4573
|
-
csrfCookie:
|
|
4574
|
-
csrfFormOrHeaderValue:
|
|
4597
|
+
sessionCookie: d,
|
|
4598
|
+
csrfCookie: y,
|
|
4599
|
+
csrfFormOrHeaderValue: C,
|
|
4575
4600
|
user: i,
|
|
4576
4601
|
secrets: n
|
|
4577
4602
|
};
|
|
@@ -4752,7 +4777,7 @@ class Lt {
|
|
|
4752
4777
|
*/
|
|
4753
4778
|
async updateSessionData(s, e, t) {
|
|
4754
4779
|
const r = D.hashSessionId(s);
|
|
4755
|
-
u.logger.debug(f({ msg: `Updating session data value${e}`, hashedSessionCookie:
|
|
4780
|
+
u.logger.debug(f({ msg: `Updating session data value${e}`, hashedSessionCookie: _.hash(s) })), await this.keyStorage.updateData(r, e, t);
|
|
4756
4781
|
}
|
|
4757
4782
|
/**
|
|
4758
4783
|
* Update field sin the session data.
|
|
@@ -4764,7 +4789,7 @@ class Lt {
|
|
|
4764
4789
|
*/
|
|
4765
4790
|
async updateManySessionData(s, e) {
|
|
4766
4791
|
const t = D.hashSessionId(s);
|
|
4767
|
-
u.logger.debug(f({ msg: "Updating session data", hashedSessionCookie:
|
|
4792
|
+
u.logger.debug(f({ msg: "Updating session data", hashedSessionCookie: _.hash(s) })), await this.keyStorage.updateManyData(t, e);
|
|
4768
4793
|
}
|
|
4769
4794
|
/**
|
|
4770
4795
|
* Deletes a field from the session data.
|
|
@@ -4776,7 +4801,7 @@ class Lt {
|
|
|
4776
4801
|
*/
|
|
4777
4802
|
async deleteSessionData(s, e) {
|
|
4778
4803
|
const t = D.hashSessionId(s);
|
|
4779
|
-
u.logger.debug(f({ msg: `Updating session data value${e}`, hashedSessionCookie:
|
|
4804
|
+
u.logger.debug(f({ msg: `Updating session data value${e}`, hashedSessionCookie: _.hash(s) })), await this.keyStorage.deleteData(t, e);
|
|
4780
4805
|
}
|
|
4781
4806
|
/**
|
|
4782
4807
|
* Deletes the given session ID from the key storage (not the cookie)
|
|
@@ -4837,12 +4862,12 @@ class Lt {
|
|
|
4837
4862
|
if (!this.userStorage) throw new o(l.Configuration, "Cannot call initiateTwoFactorSignup if no user storage provided");
|
|
4838
4863
|
if (!this.authenticators[s.factor1]) throw new o(l.Configuration, "Authenticator cannot create users");
|
|
4839
4864
|
if (!this.authenticators[s.factor2]) throw new o(l.Configuration, "Two factor authentication not enabled for user");
|
|
4840
|
-
const a = await this.authenticators[s.factor2].prepareConfiguration(s), n = a == null ? {} : a.userData, c = a == null ? {} : a.sessionData,
|
|
4865
|
+
const a = await this.authenticators[s.factor2].prepareConfiguration(s), n = a == null ? {} : a.userData, c = a == null ? {} : a.sessionData, d = await this.authenticators[s.factor1].createPersistentSecrets(s.username, e, r);
|
|
4841
4866
|
return s.state = "awaitingtwofactorsetup", await this.keyStorage.updateData(
|
|
4842
4867
|
D.hashSessionId(t),
|
|
4843
4868
|
"2fa",
|
|
4844
4869
|
c
|
|
4845
|
-
), { userid: (await this.userStorage.createUser(s,
|
|
4870
|
+
), { userid: (await this.userStorage.createUser(s, d)).id, userData: n };
|
|
4846
4871
|
}
|
|
4847
4872
|
/**
|
|
4848
4873
|
* Begins the process of setting up 2FA for a user which has already been
|
|
@@ -4885,10 +4910,10 @@ class Lt {
|
|
|
4885
4910
|
*/
|
|
4886
4911
|
async repeatTwoFactorSignup(s) {
|
|
4887
4912
|
if (!this.userStorage) throw new o(l.Configuration, "Cannot call repeatTwoFactorSignup if no user storage provided");
|
|
4888
|
-
const e = (await this.dataForSessionId(s))["2fa"], t = e.username, r = e.factor2, i = D.hashSessionId(s), a = await this.keyStorage.getKey(i), c = await this.authenticators[r].reprepareConfiguration(t, a),
|
|
4913
|
+
const e = (await this.dataForSessionId(s))["2fa"], t = e.username, r = e.factor2, i = D.hashSessionId(s), a = await this.keyStorage.getKey(i), c = await this.authenticators[r].reprepareConfiguration(t, a), d = c == null ? {} : c.userData, w = c == null ? {} : c.secrets, y = c == null ? {} : c.newSessionData;
|
|
4889
4914
|
y && await this.keyStorage.updateData(i, "2fa", y);
|
|
4890
|
-
const { user:
|
|
4891
|
-
return { userid:
|
|
4915
|
+
const { user: C } = await this.userStorage.getUserByUsername(t, { skipActiveCheck: !0, skipEmailVerifiedCheck: !0 });
|
|
4916
|
+
return { userid: C.id, userData: d, secrets: w };
|
|
4892
4917
|
}
|
|
4893
4918
|
/**
|
|
4894
4919
|
* Authenticates with the second factor.
|
|
@@ -4901,7 +4926,7 @@ class Lt {
|
|
|
4901
4926
|
* @throws {@link @crossauth/common!CrossauthError} if authentication fails.
|
|
4902
4927
|
*/
|
|
4903
4928
|
async completeTwoFactorSetup(s, e) {
|
|
4904
|
-
var
|
|
4929
|
+
var v;
|
|
4905
4930
|
if (!this.userStorage) throw new o(l.Configuration, "Cannot call completeTwoFactorSetup if no user storage provided");
|
|
4906
4931
|
let t = !1, { user: r, key: i } = await this.session.getUserForSessionId(e, {
|
|
4907
4932
|
skipActiveCheck: !0
|
|
@@ -4914,18 +4939,18 @@ class Lt {
|
|
|
4914
4939
|
let n = a.username;
|
|
4915
4940
|
const c = this.authenticators[a.factor2];
|
|
4916
4941
|
if (!c) throw new o(l.Configuration, "Unrecognised second factor authentication");
|
|
4917
|
-
const
|
|
4918
|
-
for (let
|
|
4919
|
-
w.includes(
|
|
4942
|
+
const d = {}, w = c.secretNames();
|
|
4943
|
+
for (let p in a)
|
|
4944
|
+
w.includes(p) && (d[p] = a[p]);
|
|
4920
4945
|
await c.authenticateUser(void 0, a, s), r || (t = !0, r = (await this.userStorage.getUserByUsername(n, { skipActiveCheck: !0, skipEmailVerifiedCheck: !0 })).user);
|
|
4921
4946
|
const y = c.skipEmailVerificationOnSignup() == !0;
|
|
4922
4947
|
if (!r) throw new o(l.UserNotExist, "Couldn't fetch user");
|
|
4923
|
-
const
|
|
4948
|
+
const C = {
|
|
4924
4949
|
id: r.id,
|
|
4925
4950
|
state: !y && this.enableEmailVerification ? "awaitingemailverification" : "active",
|
|
4926
4951
|
factor2: a.factor2
|
|
4927
4952
|
};
|
|
4928
|
-
return c.secretNames().length > 0 ? await this.userStorage.updateUser(
|
|
4953
|
+
return c.secretNames().length > 0 ? await this.userStorage.updateUser(C, d) : await this.userStorage.updateUser(C), !y && t && this.enableEmailVerification && this.tokenEmailer && await ((v = this.tokenEmailer) == null ? void 0 : v.sendEmailVerificationToken(r.id, void 0)), await this.keyStorage.updateData(D.hashSessionId(i.value), "2fa", void 0), { ...r, ...C };
|
|
4929
4954
|
}
|
|
4930
4955
|
/**
|
|
4931
4956
|
* Initiates the two factor login process.
|
|
@@ -4955,13 +4980,13 @@ class Lt {
|
|
|
4955
4980
|
*/
|
|
4956
4981
|
async initiateTwoFactorPageVisit(s, e, t, r, i) {
|
|
4957
4982
|
const n = await this.authenticators[s.factor2].createOneTimeSecrets(s);
|
|
4958
|
-
let c,
|
|
4983
|
+
let c, d, w;
|
|
4959
4984
|
const y = D.hashSessionId(e);
|
|
4960
4985
|
u.logger.debug("initiateTwoFactorPageVisit " + s.username + " " + e + " " + y);
|
|
4961
|
-
let
|
|
4962
|
-
return i && (
|
|
4986
|
+
let C = { username: s.username, factor2: s.factor2, secrets: n, body: t, url: r };
|
|
4987
|
+
return i && (C["content-type"] = i), await this.keyStorage.updateData(y, "pre2fa", C), {
|
|
4963
4988
|
sessionCookie: c,
|
|
4964
|
-
csrfCookie:
|
|
4989
|
+
csrfCookie: d,
|
|
4965
4990
|
csrfFormOrHeaderValue: w
|
|
4966
4991
|
};
|
|
4967
4992
|
}
|
|
@@ -4983,8 +5008,8 @@ class Lt {
|
|
|
4983
5008
|
const { secrets: i } = await this.userStorage.getUserByUsername(r.pre2fa.username), a = this.authenticators[r.pre2fa.factor2];
|
|
4984
5009
|
if (!a) throw new o(l.Configuration, "Unrecognised second factor authentication");
|
|
4985
5010
|
const n = {}, c = a.secretNames();
|
|
4986
|
-
for (let
|
|
4987
|
-
c.includes(
|
|
5011
|
+
for (let d in i)
|
|
5012
|
+
c.includes(d) && d in i && (n[d] = i[d]);
|
|
4988
5013
|
await a.authenticateUser(void 0, { ...n, ...r.pre2fa.secrets }, s), await this.keyStorage.updateData(D.hashSessionId(t.value), "pre2fa", void 0);
|
|
4989
5014
|
}
|
|
4990
5015
|
/**
|
|
@@ -5025,25 +5050,25 @@ class Lt {
|
|
|
5025
5050
|
let { key: i } = await this.session.getUserForSessionId(e);
|
|
5026
5051
|
if (!i || !i.data || i.data == "") throw new o(l.Unauthorized);
|
|
5027
5052
|
let a = x.decodeData(i.data)["2fa"], n = a.username, c = a.factor2;
|
|
5028
|
-
const { user:
|
|
5053
|
+
const { user: d, secrets: w } = await this.userStorage.getUserByUsername(n), y = this.authenticators[c];
|
|
5029
5054
|
if (!y) throw new o(l.Configuration, "Second factor " + c + " not enabled");
|
|
5030
|
-
await y.authenticateUser(
|
|
5031
|
-
const
|
|
5055
|
+
await y.authenticateUser(d, { ...w, ...a }, s);
|
|
5056
|
+
const C = await this.session.createSessionKey(d.id, t);
|
|
5032
5057
|
await this.keyStorage.deleteKey(D.hashSessionId(i.value));
|
|
5033
|
-
const
|
|
5058
|
+
const v = this.session.makeCookie(C, r), p = this.csrfTokens.createCsrfToken(), T = this.csrfTokens.makeCsrfCookie(p), k = this.csrfTokens.makeCsrfFormOrHeaderToken(p);
|
|
5034
5059
|
try {
|
|
5035
5060
|
this.emailTokenStorage.deleteAllForUser(
|
|
5036
|
-
|
|
5061
|
+
d.id,
|
|
5037
5062
|
U.passwordResetToken
|
|
5038
5063
|
);
|
|
5039
5064
|
} catch (A) {
|
|
5040
5065
|
u.logger.warn(f({ msg: "Couldn't delete password reset tokens while logging in", user: n })), u.logger.debug(f({ err: A }));
|
|
5041
5066
|
}
|
|
5042
5067
|
return {
|
|
5043
|
-
sessionCookie:
|
|
5068
|
+
sessionCookie: v,
|
|
5044
5069
|
csrfCookie: T,
|
|
5045
5070
|
csrfFormOrHeaderValue: k,
|
|
5046
|
-
user:
|
|
5071
|
+
user: d
|
|
5047
5072
|
};
|
|
5048
5073
|
}
|
|
5049
5074
|
/**
|
|
@@ -5097,10 +5122,10 @@ class Lt {
|
|
|
5097
5122
|
let { user: a, secrets: n } = await this.userStorage.getUserByUsername(s);
|
|
5098
5123
|
const c = e == 1 ? a.factor1 : a.factor2;
|
|
5099
5124
|
i != null && await this.authenticators[c].authenticateUser(a, n, i);
|
|
5100
|
-
const
|
|
5125
|
+
const d = await this.authenticators[a.factor1].createPersistentSecrets(a.username, t, r);
|
|
5101
5126
|
await this.userStorage.updateUser(
|
|
5102
5127
|
{ id: a.id },
|
|
5103
|
-
|
|
5128
|
+
d
|
|
5104
5129
|
);
|
|
5105
5130
|
try {
|
|
5106
5131
|
this.emailTokenStorage.deleteAllForUser(
|
|
@@ -5119,15 +5144,15 @@ class Lt {
|
|
|
5119
5144
|
* @returns true if email verification is now needed, false otherwise
|
|
5120
5145
|
*/
|
|
5121
5146
|
async updateUser(s, e, t = !1, r = !1) {
|
|
5122
|
-
var y,
|
|
5147
|
+
var y, C;
|
|
5123
5148
|
let i;
|
|
5124
5149
|
if (!this.userStorage) throw new o(l.Configuration, "Cannot call updateUser if no user storage provided");
|
|
5125
5150
|
if (!("id" in s) || s.id == null)
|
|
5126
5151
|
throw new o(l.UserNotExist, "Please specify a user id");
|
|
5127
5152
|
if (!("username" in s) || s.username == null)
|
|
5128
5153
|
throw new o(l.UserNotExist, "Please specify a userername");
|
|
5129
|
-
let { email: a, username: n, password: c, ...
|
|
5130
|
-
|
|
5154
|
+
let { email: a, username: n, password: c, ...d } = e;
|
|
5155
|
+
d.userid = s.userid;
|
|
5131
5156
|
let w = !1;
|
|
5132
5157
|
if (a)
|
|
5133
5158
|
i = a, R.validateEmail(i), w = !0;
|
|
@@ -5139,7 +5164,7 @@ class Lt {
|
|
|
5139
5164
|
}
|
|
5140
5165
|
w && R.validateEmail(i);
|
|
5141
5166
|
}
|
|
5142
|
-
return !t && this.enableEmailVerification && w ? await ((y = this.tokenEmailer) == null ? void 0 : y.sendEmailVerificationToken(s.id, i)) : (a && (
|
|
5167
|
+
return !t && this.enableEmailVerification && w ? await ((y = this.tokenEmailer) == null ? void 0 : y.sendEmailVerificationToken(s.id, i)) : (a && (d.email = a), n && (d.username = n)), (e.state == E.passwordResetNeeded || e.state == E.passwordAndFactor2ResetNeeded) && await ((C = this.tokenEmailer) == null ? void 0 : C.sendPasswordResetToken(s.id, {}, r)), await this.userStorage.updateUser(d), {
|
|
5143
5168
|
emailVerificationTokenSent: !t && this.enableEmailVerification && w,
|
|
5144
5169
|
passwordResetTokenSent: e.state == E.passwordResetNeeded || e.state == E.passwordAndFactor2ResetNeeded
|
|
5145
5170
|
};
|
|
@@ -5184,15 +5209,15 @@ class ge {
|
|
|
5184
5209
|
* @param options options. See {@link ApiKeyManagerOptions}
|
|
5185
5210
|
*/
|
|
5186
5211
|
constructor(s, e = {}) {
|
|
5187
|
-
|
|
5188
|
-
|
|
5189
|
-
|
|
5212
|
+
h(this, "apiKeyStorage");
|
|
5213
|
+
h(this, "keyLength", 16);
|
|
5214
|
+
h(this, "secret", "");
|
|
5190
5215
|
/** The prefix to add to the hashed key in storage. Defaults to
|
|
5191
5216
|
* {@link @crossauth/common!KeyPrefix}.apiKey
|
|
5192
5217
|
*/
|
|
5193
|
-
|
|
5218
|
+
h(this, "prefix", U.apiKey);
|
|
5194
5219
|
/** The name of the speak in the Authorization header. Defaults to "ApiKey" */
|
|
5195
|
-
|
|
5220
|
+
h(this, "authScheme", "ApiKey");
|
|
5196
5221
|
this.apiKeyStorage = s, m("secret", g.String, this, e, "SECRET", !0), m("keyLength", g.String, this, e, "APIKEY_LENGTH"), m("prefix", g.String, this, e, "APIKEY_PREFIX"), m("authScheme", g.String, this, e, "APIKEY_AUTHSCHEME");
|
|
5197
5222
|
}
|
|
5198
5223
|
/**
|
|
@@ -5214,7 +5239,7 @@ class ge {
|
|
|
5214
5239
|
* Authorization header (with the signature appended.)
|
|
5215
5240
|
*/
|
|
5216
5241
|
async createKey(s, e, t, r, i) {
|
|
5217
|
-
const a =
|
|
5242
|
+
const a = _.randomValue(this.keyLength), n = /* @__PURE__ */ new Date(), c = r ? new Date(n.getTime() + r * 1e3) : void 0, d = ge.hashApiKeyValue(a), w = {
|
|
5218
5243
|
name: s,
|
|
5219
5244
|
value: a,
|
|
5220
5245
|
userid: e,
|
|
@@ -5225,7 +5250,7 @@ class ge {
|
|
|
5225
5250
|
};
|
|
5226
5251
|
await this.apiKeyStorage.saveKey(
|
|
5227
5252
|
e,
|
|
5228
|
-
this.prefix +
|
|
5253
|
+
this.prefix + d,
|
|
5229
5254
|
n,
|
|
5230
5255
|
c,
|
|
5231
5256
|
w.data,
|
|
@@ -5235,7 +5260,7 @@ class ge {
|
|
|
5235
5260
|
return { key: w, token: y };
|
|
5236
5261
|
}
|
|
5237
5262
|
static hashApiKeyValue(s) {
|
|
5238
|
-
return
|
|
5263
|
+
return _.hash(s);
|
|
5239
5264
|
}
|
|
5240
5265
|
/**
|
|
5241
5266
|
* Returns the hash of the bearer value from the Authorization header.
|
|
@@ -5246,13 +5271,13 @@ class ge {
|
|
|
5246
5271
|
* @returns a hash of the value (without the prefix).
|
|
5247
5272
|
*/
|
|
5248
5273
|
static hashSignedApiKeyValue(s) {
|
|
5249
|
-
return
|
|
5274
|
+
return _.hash(s.split(".")[0]);
|
|
5250
5275
|
}
|
|
5251
5276
|
unsignApiKeyValue(s) {
|
|
5252
|
-
return
|
|
5277
|
+
return _.unsign(s, this.secret).v;
|
|
5253
5278
|
}
|
|
5254
5279
|
signApiKeyValue(s) {
|
|
5255
|
-
return
|
|
5280
|
+
return _.sign({ v: s }, this.secret);
|
|
5256
5281
|
}
|
|
5257
5282
|
async getKey(s) {
|
|
5258
5283
|
if (this.authScheme != "" && s.startsWith(this.authScheme + " ")) {
|
|
@@ -5283,10 +5308,10 @@ class J {
|
|
|
5283
5308
|
* @param options See {@link OAuthClientManagerOptions}
|
|
5284
5309
|
*/
|
|
5285
5310
|
constructor(s = {}) {
|
|
5286
|
-
|
|
5287
|
-
|
|
5288
|
-
|
|
5289
|
-
|
|
5311
|
+
h(this, "oauthPbkdf2Digest", "sha256");
|
|
5312
|
+
h(this, "oauthPbkdf2Iterations", 4e4);
|
|
5313
|
+
h(this, "oauthPbkdf2KeyLength", 32);
|
|
5314
|
+
h(this, "clientStorage");
|
|
5290
5315
|
if (!s.clientStorage) throw new o(
|
|
5291
5316
|
l.Configuration,
|
|
5292
5317
|
"Must specify clientStorage when adding a client manager"
|
|
@@ -5308,7 +5333,7 @@ class J {
|
|
|
5308
5333
|
async createClient(s, e, t, r = !0, i) {
|
|
5309
5334
|
const a = J.randomClientId();
|
|
5310
5335
|
let n, c;
|
|
5311
|
-
r && (c = J.randomClientSecret(), n = await
|
|
5336
|
+
r && (c = J.randomClientSecret(), n = await _.passwordHash(c, {
|
|
5312
5337
|
encode: !0,
|
|
5313
5338
|
iterations: this.oauthPbkdf2Iterations,
|
|
5314
5339
|
keyLen: this.oauthPbkdf2KeyLength,
|
|
@@ -5316,7 +5341,7 @@ class J {
|
|
|
5316
5341
|
})), e.forEach((y) => {
|
|
5317
5342
|
J.validateUri(y);
|
|
5318
5343
|
}), t || (t = b.allFlows());
|
|
5319
|
-
const
|
|
5344
|
+
const d = {
|
|
5320
5345
|
client_id: a,
|
|
5321
5346
|
client_secret: n,
|
|
5322
5347
|
client_name: s,
|
|
@@ -5328,13 +5353,13 @@ class J {
|
|
|
5328
5353
|
let w;
|
|
5329
5354
|
for (let y = 0; y < 5; ++y)
|
|
5330
5355
|
try {
|
|
5331
|
-
w = await this.clientStorage.createClient(
|
|
5356
|
+
w = await this.clientStorage.createClient(d);
|
|
5332
5357
|
break;
|
|
5333
|
-
} catch (
|
|
5358
|
+
} catch (C) {
|
|
5334
5359
|
if (y == 4) {
|
|
5335
|
-
if (o.asCrossauthError(
|
|
5360
|
+
if (o.asCrossauthError(C).code != l.ClientExists) throw C;
|
|
5336
5361
|
} else
|
|
5337
|
-
|
|
5362
|
+
d.client_id = J.randomClientId();
|
|
5338
5363
|
}
|
|
5339
5364
|
if (!w) throw new o(l.ClientExists);
|
|
5340
5365
|
return w.client_secret && c && (w.client_secret = c), w;
|
|
@@ -5351,7 +5376,7 @@ class J {
|
|
|
5351
5376
|
async updateClient(s, e, t = !1) {
|
|
5352
5377
|
const r = await this.clientStorage.getClientById(s);
|
|
5353
5378
|
let i = !1, a;
|
|
5354
|
-
e.confidential === !0 && !r.confidential || e.confidential === !0 && t ? (a = J.randomClientSecret(), e.client_secret = await
|
|
5379
|
+
e.confidential === !0 && !r.confidential || e.confidential === !0 && t ? (a = J.randomClientSecret(), e.client_secret = await _.passwordHash(a, {
|
|
5355
5380
|
encode: !0,
|
|
5356
5381
|
iterations: this.oauthPbkdf2Iterations,
|
|
5357
5382
|
keyLen: this.oauthPbkdf2KeyLength,
|
|
@@ -5366,13 +5391,13 @@ class J {
|
|
|
5366
5391
|
* Create a random OAuth client id
|
|
5367
5392
|
*/
|
|
5368
5393
|
static randomClientId() {
|
|
5369
|
-
return
|
|
5394
|
+
return _.randomValue(it);
|
|
5370
5395
|
}
|
|
5371
5396
|
/**
|
|
5372
5397
|
* Create a random OAuth client secret
|
|
5373
5398
|
*/
|
|
5374
5399
|
static randomClientSecret() {
|
|
5375
|
-
return
|
|
5400
|
+
return _.randomValue(st);
|
|
5376
5401
|
}
|
|
5377
5402
|
/** If the passed redirect URI is not in the set of valid ones,
|
|
5378
5403
|
* throw {@link @crossauth/common!CrossauthError} with
|
|
@@ -5434,57 +5459,57 @@ class zt {
|
|
|
5434
5459
|
* @param options See {@link OAuthAuthorizationServerOptions }
|
|
5435
5460
|
*/
|
|
5436
5461
|
constructor(s, e, t, r = {}) {
|
|
5437
|
-
|
|
5438
|
-
|
|
5439
|
-
|
|
5440
|
-
|
|
5441
|
-
|
|
5462
|
+
h(this, "clientStorage");
|
|
5463
|
+
h(this, "keyStorage");
|
|
5464
|
+
h(this, "userStorage");
|
|
5465
|
+
h(this, "authenticators", {});
|
|
5466
|
+
h(this, "authStorage");
|
|
5442
5467
|
/** For validating redirect URIs. */
|
|
5443
|
-
|
|
5444
|
-
|
|
5445
|
-
|
|
5446
|
-
|
|
5447
|
-
|
|
5448
|
-
|
|
5449
|
-
|
|
5450
|
-
|
|
5451
|
-
|
|
5452
|
-
|
|
5453
|
-
|
|
5454
|
-
|
|
5455
|
-
|
|
5456
|
-
|
|
5457
|
-
|
|
5458
|
-
|
|
5459
|
-
|
|
5460
|
-
|
|
5461
|
-
|
|
5462
|
-
|
|
5463
|
-
|
|
5464
|
-
|
|
5465
|
-
|
|
5466
|
-
|
|
5467
|
-
|
|
5468
|
-
|
|
5469
|
-
|
|
5470
|
-
|
|
5471
|
-
|
|
5472
|
-
|
|
5473
|
-
|
|
5474
|
-
|
|
5468
|
+
h(this, "clientManager");
|
|
5469
|
+
h(this, "oauthIssuer", "");
|
|
5470
|
+
h(this, "audience", null);
|
|
5471
|
+
h(this, "requireRedirectUriRegistration", !0);
|
|
5472
|
+
h(this, "requireClientSecretOrChallenge", !0);
|
|
5473
|
+
h(this, "jwtAlgorithm", "RS256");
|
|
5474
|
+
h(this, "jwtAlgorithmChecked", "RS256");
|
|
5475
|
+
h(this, "codeLength", 32);
|
|
5476
|
+
h(this, "jwtKeyType", "");
|
|
5477
|
+
h(this, "jwtSecretKey", "");
|
|
5478
|
+
h(this, "jwtPublicKey", "");
|
|
5479
|
+
h(this, "jwtPrivateKey", "");
|
|
5480
|
+
h(this, "jwtSecretKeyFile", "");
|
|
5481
|
+
h(this, "jwtPublicKeyFile", "");
|
|
5482
|
+
h(this, "jwtPrivateKeyFile", "");
|
|
5483
|
+
h(this, "jwtKid", "1");
|
|
5484
|
+
h(this, "secretOrPrivateKey", "");
|
|
5485
|
+
h(this, "secretOrPublicKey", "");
|
|
5486
|
+
h(this, "persistAccessToken", !1);
|
|
5487
|
+
h(this, "issueRefreshToken", !1);
|
|
5488
|
+
h(this, "opaqueAccessToken", !1);
|
|
5489
|
+
h(this, "accessTokenExpiry", 60 * 60);
|
|
5490
|
+
h(this, "refreshTokenExpiry", 60 * 60);
|
|
5491
|
+
h(this, "rollingRefreshToken", !0);
|
|
5492
|
+
h(this, "authorizationCodeExpiry", 60 * 5);
|
|
5493
|
+
h(this, "mfaTokenExpiry", 60 * 5);
|
|
5494
|
+
h(this, "clockTolerance", 10);
|
|
5495
|
+
h(this, "emptyScopeIsValid", !0);
|
|
5496
|
+
h(this, "validateScopes", !1);
|
|
5497
|
+
h(this, "validScopes", []);
|
|
5498
|
+
h(this, "idTokenClaims", {});
|
|
5499
|
+
h(this, "accessTokenClaims", {});
|
|
5475
5500
|
// device code
|
|
5476
|
-
|
|
5477
|
-
|
|
5478
|
-
|
|
5479
|
-
|
|
5480
|
-
|
|
5481
|
-
|
|
5482
|
-
|
|
5483
|
-
|
|
5501
|
+
h(this, "userCodeExpiry", 60 * 5);
|
|
5502
|
+
h(this, "userCodeThrottle", 1500);
|
|
5503
|
+
h(this, "deviceCodePollInterval", 5);
|
|
5504
|
+
h(this, "userCodeLength", 8);
|
|
5505
|
+
h(this, "deviceCodeLength", 16);
|
|
5506
|
+
h(this, "userCodeDashEvery", 4);
|
|
5507
|
+
h(this, "deviceCodeVerificationUri", "");
|
|
5508
|
+
h(this, "authServerBaseUrl", "");
|
|
5484
5509
|
/** Set from options. See {@link OAuthAuthorizationServerOptions.validFlows} */
|
|
5485
|
-
|
|
5510
|
+
h(this, "validFlows", ["all"]);
|
|
5486
5511
|
/** Set from options. See {@link OAuthAuthorizationServerOptions.allowedFactor2} */
|
|
5487
|
-
|
|
5512
|
+
h(this, "allowedFactor2", []);
|
|
5488
5513
|
this.clientStorage = s, this.keyStorage = e, this.userStorage = r.userStorage, this.authStorage = r.authStorage, t && (this.authenticators = t), this.clientManager = new J({ clientStorage: s, ...r }), m("authServerBaseUrl", g.String, this, r, "AUTH_SERVER_BASE_URL", !0), m("oauthIssuer", g.String, this, r, "OAUTH_ISSUER"), this.oauthIssuer || (this.oauthIssuer = this.authServerBaseUrl), m("audience", g.String, this, r, "OAUTH_AUDIENCE"), m("oauthPbkdf2Iterations", g.String, this, r, "OAUTH_PBKDF2_ITERATIONS"), m("requireClientSecretOrChallenge", g.Boolean, this, r, "OAUTH_REQUIRE_CLIENT_SECRET_OR_CHALLENGE"), m("jwtAlgorithm", g.String, this, r, "JWT_ALGORITHM"), m("codeLength", g.Number, this, r, "OAUTH_CODE_LENGTH"), m("jwtKeyType", g.String, this, r, "JWT_KEY_TYPE"), m("jwtSecretKeyFile", g.String, this, r, "JWT_SECRET_KEY_FILE"), m("jwtPublicKeyFile", g.String, this, r, "JWT_PUBLIC_KEY_FILE"), m("jwtPrivateKeyFile", g.String, this, r, "JWT_PRIVATE_KEY_FILE"), m("jwtSecretKey", g.String, this, r, "JWT_SECRET_KEY"), m("jwtPublicKey", g.String, this, r, "JWT_PUBLIC_KEY"), m("jwtPrivateKey", g.String, this, r, "JWT_PRIVATE_KEY"), m("jwtKid", g.String, this, r, "JWT_KID"), m("persistAccessToken", g.String, this, r, "OAUTH_PERSIST_ACCESS_TOKEN"), m("issueRefreshToken", g.String, this, r, "OAUTH_ISSUE_REFRESH_TOKEN"), m("opaqueAccessToken", g.String, this, r, "OAUTH_OPAQUE_ACCESS_TOKEN"), m("accessTokenExpiry", g.Number, this, r, "OAUTH_ACCESS_TOKEN_EXPIRY"), m("refreshTokenExpiry", g.Number, this, r, "OAUTH_REFRESH_TOKEN_EXPIRY"), m("rollingRefreshToken", g.Boolean, this, r, "OAUTH_ROLLING_REFRESH_TOKEN"), m("authorizationCodeExpiry", g.Number, this, r, "OAUTH_AUTHORIZATION_CODE_EXPIRY"), m("mfaTokenExpiry", g.Number, this, r, "OAUTH_MFA_TOKEN_EXPIRY"), m("clockTolerance", g.Number, this, r, "OAUTH_CLOCK_TOLERANCE"), m("validateScopes", g.Boolean, this, r, "OAUTH_VALIDATE_SCOPES"), m("emptyScopeIsValid", g.Boolean, this, r, "OAUTH_EMPTY_SCOPE_VALID"), m("validScopes", g.JsonArray, this, r, "OAUTH_VALID_SCOPES"), m("validFlows", g.JsonArray, this, r, "OAUTH_validFlows"), m("idTokenClaims", g.Json, this, r, "OAUTH_ID_TOKEN_CLAIMS"), m("accessTokenClaims", g.Json, this, r, "OAUTH_ACCESS_TOKEN_CLAIMS"), m("allowedFactor2", g.JsonArray, this, r, "ALLOWED_FACTOR2"), m("userCodeExpiry", g.Number, this, r, "DEVICECODE_USERCODE_EXPIRY"), m("userCodeThrottle", g.Number, this, r, "DEVICECODE_USERCODE_THROTTLE"), m("deviceCodePollInterval", g.Number, this, r, "DEVICECODE_POLL_INTERVAL"), m("deviceCodeLength", g.Number, this, r, "DEVICECODE_LENGTH"), m("userCodeLength", g.Number, this, r, "DEVICECODE_USERCODE_LENGTH");
|
|
5489
5514
|
let i = {};
|
|
5490
5515
|
if (m("userCodeDashEvery", g.String, i, r, "DEVICECODE_USERCODE_DASH_EVERY"), i.userCodeDashEvery)
|
|
@@ -5586,23 +5611,23 @@ class zt {
|
|
|
5586
5611
|
}
|
|
5587
5612
|
const {
|
|
5588
5613
|
scopes: y,
|
|
5589
|
-
error:
|
|
5590
|
-
error_description:
|
|
5614
|
+
error: C,
|
|
5615
|
+
error_description: v
|
|
5591
5616
|
} = await this.validateAndPersistScope(e, r, c);
|
|
5592
|
-
if (
|
|
5593
|
-
error:
|
|
5594
|
-
error_description:
|
|
5617
|
+
if (C) return {
|
|
5618
|
+
error: C,
|
|
5619
|
+
error_description: v
|
|
5595
5620
|
};
|
|
5596
|
-
const
|
|
5597
|
-
if (!
|
|
5621
|
+
const p = this.inferFlowFromGet(s, y || [], a);
|
|
5622
|
+
if (!p || !this.validFlows.includes(p))
|
|
5598
5623
|
return {
|
|
5599
5624
|
error: "access_denied",
|
|
5600
|
-
error_description: "Unsupported flow type " +
|
|
5625
|
+
error_description: "Unsupported flow type " + p
|
|
5601
5626
|
};
|
|
5602
|
-
if (!w.valid_flow.includes(
|
|
5627
|
+
if (!w.valid_flow.includes(p))
|
|
5603
5628
|
return {
|
|
5604
5629
|
error: "unauthorized_client",
|
|
5605
|
-
error_description: "Client does not support " +
|
|
5630
|
+
error_description: "Client does not support " + p
|
|
5606
5631
|
};
|
|
5607
5632
|
try {
|
|
5608
5633
|
this.validateState(i);
|
|
@@ -5712,7 +5737,7 @@ class zt {
|
|
|
5712
5737
|
} : r && (!t || !e.client_secret) ? {
|
|
5713
5738
|
error: "access_denied",
|
|
5714
5739
|
error_description: "Client is confidential but either secret not passed or is missing in database"
|
|
5715
|
-
} : r && !await
|
|
5740
|
+
} : r && !await _.passwordsEqual(
|
|
5716
5741
|
t ?? "",
|
|
5717
5742
|
e.client_secret ?? ""
|
|
5718
5743
|
) ? {
|
|
@@ -5755,12 +5780,12 @@ class zt {
|
|
|
5755
5780
|
codeVerifier: a,
|
|
5756
5781
|
refreshToken: n,
|
|
5757
5782
|
username: c,
|
|
5758
|
-
password:
|
|
5783
|
+
password: d,
|
|
5759
5784
|
mfaToken: w,
|
|
5760
5785
|
oobCode: y,
|
|
5761
|
-
bindingCode:
|
|
5762
|
-
otp:
|
|
5763
|
-
deviceCode:
|
|
5786
|
+
bindingCode: C,
|
|
5787
|
+
otp: v,
|
|
5788
|
+
deviceCode: p
|
|
5764
5789
|
}) {
|
|
5765
5790
|
var O, V, j;
|
|
5766
5791
|
const T = this.inferFlowFromPost(s, a);
|
|
@@ -5830,7 +5855,7 @@ class zt {
|
|
|
5830
5855
|
};
|
|
5831
5856
|
}
|
|
5832
5857
|
try {
|
|
5833
|
-
const F = U.refreshToken +
|
|
5858
|
+
const F = U.refreshToken + _.hash(n);
|
|
5834
5859
|
await this.keyStorage.deleteKey(F);
|
|
5835
5860
|
} catch (F) {
|
|
5836
5861
|
const I = o.asCrossauthError(F);
|
|
@@ -5861,7 +5886,7 @@ class zt {
|
|
|
5861
5886
|
issueRefreshToken: H
|
|
5862
5887
|
});
|
|
5863
5888
|
} else if (s == "password") {
|
|
5864
|
-
if (!c || !
|
|
5889
|
+
if (!c || !d)
|
|
5865
5890
|
return {
|
|
5866
5891
|
error: "access_denied",
|
|
5867
5892
|
error_description: "Username and/or password not provided for password flow"
|
|
@@ -5881,7 +5906,7 @@ class zt {
|
|
|
5881
5906
|
await B.authenticateUser(
|
|
5882
5907
|
I,
|
|
5883
5908
|
$,
|
|
5884
|
-
{ password:
|
|
5909
|
+
{ password: d }
|
|
5885
5910
|
), K = I;
|
|
5886
5911
|
} catch (I) {
|
|
5887
5912
|
return u.logger.debug(f({ err: I })), {
|
|
@@ -5919,7 +5944,7 @@ class zt {
|
|
|
5919
5944
|
error: P,
|
|
5920
5945
|
error_description: F
|
|
5921
5946
|
};
|
|
5922
|
-
if (!
|
|
5947
|
+
if (!v)
|
|
5923
5948
|
return {
|
|
5924
5949
|
error: "access_denied",
|
|
5925
5950
|
error_description: "OTP not provided"
|
|
@@ -5929,7 +5954,7 @@ class zt {
|
|
|
5929
5954
|
error: "access_denied",
|
|
5930
5955
|
error_description: "MFA token not provided"
|
|
5931
5956
|
};
|
|
5932
|
-
const I = await this.validateMfaToken(w), $ = U.mfaToken +
|
|
5957
|
+
const I = await this.validateMfaToken(w), $ = U.mfaToken + _.hash(w);
|
|
5933
5958
|
if (!I.user || !I.key)
|
|
5934
5959
|
return {
|
|
5935
5960
|
error: "access_denied",
|
|
@@ -5946,7 +5971,7 @@ class zt {
|
|
|
5946
5971
|
await B.authenticateUser(
|
|
5947
5972
|
I.user,
|
|
5948
5973
|
M,
|
|
5949
|
-
{ otp:
|
|
5974
|
+
{ otp: v }
|
|
5950
5975
|
);
|
|
5951
5976
|
} catch (M) {
|
|
5952
5977
|
return u.logger.debug(f({ err: M })), {
|
|
@@ -5982,7 +6007,7 @@ class zt {
|
|
|
5982
6007
|
error: P,
|
|
5983
6008
|
error_description: F
|
|
5984
6009
|
};
|
|
5985
|
-
if (!y || !
|
|
6010
|
+
if (!y || !C)
|
|
5986
6011
|
return {
|
|
5987
6012
|
error: "access_denied",
|
|
5988
6013
|
error_description: "OOB code or binding code not provided"
|
|
@@ -6019,7 +6044,7 @@ class zt {
|
|
|
6019
6044
|
await $.authenticateUser(
|
|
6020
6045
|
I.user,
|
|
6021
6046
|
{ ...B, otp: M.otp, expiry: (V = I.key.expires) == null ? void 0 : V.getTime() },
|
|
6022
|
-
{ otp:
|
|
6047
|
+
{ otp: C }
|
|
6023
6048
|
);
|
|
6024
6049
|
} catch (B) {
|
|
6025
6050
|
return u.logger.debug(f({ err: B })), {
|
|
@@ -6045,14 +6070,14 @@ class zt {
|
|
|
6045
6070
|
user: I.user
|
|
6046
6071
|
});
|
|
6047
6072
|
} else if (s == "urn:ietf:params:oauth:grant-type:device_code") {
|
|
6048
|
-
if (!
|
|
6073
|
+
if (!p)
|
|
6049
6074
|
return {
|
|
6050
6075
|
error: "invalid_request",
|
|
6051
6076
|
error_description: "No device code given"
|
|
6052
6077
|
};
|
|
6053
6078
|
let N;
|
|
6054
6079
|
try {
|
|
6055
|
-
N = await this.keyStorage.getKey(U.deviceCode +
|
|
6080
|
+
N = await this.keyStorage.getKey(U.deviceCode + p);
|
|
6056
6081
|
} catch (P) {
|
|
6057
6082
|
const F = o.asCrossauthError(P);
|
|
6058
6083
|
return u.logger.debug(f({ err: F })), u.logger.error(f({ msg: "Couldn't get device code", cerr: F })), {
|
|
@@ -6063,7 +6088,7 @@ class zt {
|
|
|
6063
6088
|
try {
|
|
6064
6089
|
const P = JSON.parse(N.data ?? "{}"), F = (/* @__PURE__ */ new Date()).getTime();
|
|
6065
6090
|
if (N.expires && F > N.expires.getTime())
|
|
6066
|
-
return await this.deleteDeviceCode(
|
|
6091
|
+
return await this.deleteDeviceCode(p), {
|
|
6067
6092
|
error: "expired_token",
|
|
6068
6093
|
error_description: "Code has expired"
|
|
6069
6094
|
};
|
|
@@ -6074,7 +6099,7 @@ class zt {
|
|
|
6074
6099
|
};
|
|
6075
6100
|
{
|
|
6076
6101
|
let I = P.scope ? P.scope.split(" ") : void 0, $ = P.userid ? await ((j = this.userStorage) == null ? void 0 : j.getUserById(P.userid)) : void 0;
|
|
6077
|
-
return await this.deleteDeviceCode(
|
|
6102
|
+
return await this.deleteDeviceCode(p), await this.makeAccessToken({
|
|
6078
6103
|
client: A,
|
|
6079
6104
|
client_secret: i,
|
|
6080
6105
|
codeVerifier: a,
|
|
@@ -6085,7 +6110,7 @@ class zt {
|
|
|
6085
6110
|
}
|
|
6086
6111
|
} catch (P) {
|
|
6087
6112
|
const F = o.asCrossauthError(P);
|
|
6088
|
-
return u.logger.debug(f({ err: F })), u.logger.error(f({ msg: "Couldn't get device code", cerr: F })), await this.deleteDeviceCode(
|
|
6113
|
+
return u.logger.debug(f({ err: F })), u.logger.error(f({ msg: "Couldn't get device code", cerr: F })), await this.deleteDeviceCode(p), {
|
|
6089
6114
|
error: "accerss_denied",
|
|
6090
6115
|
error_description: "Invalid device code"
|
|
6091
6116
|
};
|
|
@@ -6128,7 +6153,7 @@ class zt {
|
|
|
6128
6153
|
scope: e,
|
|
6129
6154
|
client_secret: t
|
|
6130
6155
|
}) {
|
|
6131
|
-
var
|
|
6156
|
+
var p;
|
|
6132
6157
|
if (this.deviceCodeVerificationUri == "")
|
|
6133
6158
|
return {
|
|
6134
6159
|
error: "invalid_request",
|
|
@@ -6158,53 +6183,53 @@ class zt {
|
|
|
6158
6183
|
error_description: k
|
|
6159
6184
|
};
|
|
6160
6185
|
}
|
|
6161
|
-
let c,
|
|
6162
|
-
const w = /* @__PURE__ */ new Date(), y = this.userCodeExpiry,
|
|
6163
|
-
for (let T = 0; T < 10 && !
|
|
6186
|
+
let c, d = !1;
|
|
6187
|
+
const w = /* @__PURE__ */ new Date(), y = this.userCodeExpiry, C = new Date(w.getTime() + this.userCodeExpiry * 1e3 + this.clockTolerance * 1e3);
|
|
6188
|
+
for (let T = 0; T < 10 && !d; ++T)
|
|
6164
6189
|
try {
|
|
6165
|
-
c =
|
|
6190
|
+
c = _.randomValue(this.deviceCodeLength), await this.keyStorage.saveKey(
|
|
6166
6191
|
void 0,
|
|
6167
6192
|
U.deviceCode + c,
|
|
6168
6193
|
w,
|
|
6169
|
-
|
|
6194
|
+
C,
|
|
6170
6195
|
JSON.stringify({ scope: e, client_id: s })
|
|
6171
|
-
),
|
|
6196
|
+
), d = !0;
|
|
6172
6197
|
} catch {
|
|
6173
6198
|
u.logger.debug(f({ msg: `Attempt number${T} at creating a unique authozation code failed` }));
|
|
6174
6199
|
}
|
|
6175
|
-
if (!
|
|
6200
|
+
if (!d || !c)
|
|
6176
6201
|
return {
|
|
6177
6202
|
error: "server_error",
|
|
6178
6203
|
error_description: "Couldn't create device code"
|
|
6179
6204
|
};
|
|
6180
|
-
let
|
|
6181
|
-
|
|
6182
|
-
for (let T = 0; T < 10 && !
|
|
6205
|
+
let v;
|
|
6206
|
+
d = !1;
|
|
6207
|
+
for (let T = 0; T < 10 && !d; ++T)
|
|
6183
6208
|
try {
|
|
6184
|
-
|
|
6209
|
+
v = _.randomBase32(this.userCodeLength), await this.keyStorage.saveKey(
|
|
6185
6210
|
void 0,
|
|
6186
|
-
U.userCode +
|
|
6211
|
+
U.userCode + v,
|
|
6187
6212
|
w,
|
|
6188
|
-
|
|
6213
|
+
C,
|
|
6189
6214
|
JSON.stringify({ deviceCode: c })
|
|
6190
|
-
),
|
|
6215
|
+
), d = !0;
|
|
6191
6216
|
} catch {
|
|
6192
6217
|
u.logger.debug(f({ msg: `Attempt number${T} at creating a unique authozation code failed` }));
|
|
6193
6218
|
}
|
|
6194
|
-
if (!
|
|
6219
|
+
if (!d || !v)
|
|
6195
6220
|
return await this.deleteDeviceCode(c), {
|
|
6196
6221
|
error: "server_error",
|
|
6197
6222
|
error_description: "Couldn't create device code"
|
|
6198
6223
|
};
|
|
6199
|
-
if (
|
|
6224
|
+
if (v && this.userCodeDashEvery) {
|
|
6200
6225
|
const T = new RegExp(String.raw`(.{1,${this.userCodeDashEvery}})`, "g");
|
|
6201
|
-
|
|
6226
|
+
v = (p = v.match(T)) == null ? void 0 : p.join("-");
|
|
6202
6227
|
}
|
|
6203
6228
|
return {
|
|
6204
6229
|
device_code: c,
|
|
6205
|
-
user_code:
|
|
6230
|
+
user_code: v,
|
|
6206
6231
|
verification_uri: this.deviceCodeVerificationUri,
|
|
6207
|
-
verification_uri_complete: this.deviceCodeVerificationUri + "?user_code=" +
|
|
6232
|
+
verification_uri_complete: this.deviceCodeVerificationUri + "?user_code=" + v,
|
|
6208
6233
|
expires_in: y,
|
|
6209
6234
|
interval: this.deviceCodePollInterval
|
|
6210
6235
|
};
|
|
@@ -6237,7 +6262,7 @@ class zt {
|
|
|
6237
6262
|
};
|
|
6238
6263
|
}
|
|
6239
6264
|
if (!r.deviceCode)
|
|
6240
|
-
return u.logger.error(f({ msg: "No device code for user code", userCodeHash:
|
|
6265
|
+
return u.logger.error(f({ msg: "No device code for user code", userCodeHash: _.hash(s) })), await this.deleteUserCode(s), {
|
|
6241
6266
|
ok: !1,
|
|
6242
6267
|
error: "server_error",
|
|
6243
6268
|
error_description: "No device code for user code"
|
|
@@ -6246,12 +6271,12 @@ class zt {
|
|
|
6246
6271
|
try {
|
|
6247
6272
|
i = await this.keyStorage.getKey(U.deviceCode + r.deviceCode);
|
|
6248
6273
|
} catch (y) {
|
|
6249
|
-
const
|
|
6250
|
-
return u.logger.debug(f({ err:
|
|
6274
|
+
const C = o.asCrossauthError(y);
|
|
6275
|
+
return u.logger.debug(f({ err: C })), u.logger.error(f({
|
|
6251
6276
|
msg: "Invalid device code for user code",
|
|
6252
|
-
userCodeHash:
|
|
6253
|
-
deviceCodeHash:
|
|
6254
|
-
cerr:
|
|
6277
|
+
userCodeHash: _.hash(s),
|
|
6278
|
+
deviceCodeHash: _.hash(r.deviceCode),
|
|
6279
|
+
cerr: C
|
|
6255
6280
|
})), await this.deleteUserCode(s), {
|
|
6256
6281
|
ok: !1,
|
|
6257
6282
|
error: "server_error",
|
|
@@ -6284,24 +6309,24 @@ class zt {
|
|
|
6284
6309
|
error_description: "User code has already been used",
|
|
6285
6310
|
client_id: n
|
|
6286
6311
|
};
|
|
6287
|
-
let
|
|
6312
|
+
let d = !1;
|
|
6288
6313
|
if (u.logger.debug(f({
|
|
6289
6314
|
msg: "Checking scopes have been authorized",
|
|
6290
6315
|
scope: a
|
|
6291
|
-
})), a ?
|
|
6316
|
+
})), a ? d = await this.hasAllScopes(
|
|
6292
6317
|
n,
|
|
6293
6318
|
e,
|
|
6294
6319
|
a.split(" ")
|
|
6295
|
-
) :
|
|
6320
|
+
) : d = await this.hasAllScopes(
|
|
6296
6321
|
n,
|
|
6297
6322
|
e,
|
|
6298
6323
|
[null]
|
|
6299
|
-
), !
|
|
6324
|
+
), !d) {
|
|
6300
6325
|
try {
|
|
6301
6326
|
e != null && e.id && await this.keyStorage.updateData(U.deviceCode + r.deviceCode, "userid", e.id);
|
|
6302
6327
|
} catch (y) {
|
|
6303
|
-
const
|
|
6304
|
-
return u.logger.debug(f({ err:
|
|
6328
|
+
const C = o.asCrossauthError(y);
|
|
6329
|
+
return u.logger.debug(f({ err: C })), u.logger.warn(f({ msg: "Couldn't update user id on user code entry - deleting", cerr: C })), await this.deleteUserCode(s), await this.deleteDeviceCode(r.deviceCode), {
|
|
6305
6330
|
ok: !1,
|
|
6306
6331
|
error: "access_denied",
|
|
6307
6332
|
error_description: "Invalid user code",
|
|
@@ -6318,8 +6343,8 @@ class zt {
|
|
|
6318
6343
|
try {
|
|
6319
6344
|
e != null && e.id && await this.keyStorage.updateData(U.deviceCode + r.deviceCode, "userid", e.id), await this.keyStorage.updateData(U.deviceCode + r.deviceCode, "ok", !0);
|
|
6320
6345
|
} catch (y) {
|
|
6321
|
-
const
|
|
6322
|
-
return u.logger.debug(f({ err:
|
|
6346
|
+
const C = o.asCrossauthError(y);
|
|
6347
|
+
return u.logger.debug(f({ err: C })), u.logger.warn(f({ msg: "Couldn't update status on user code entry - deleting", cerr: C })), await this.deleteUserCode(s), await this.deleteDeviceCode(r.deviceCode), {
|
|
6323
6348
|
ok: !1,
|
|
6324
6349
|
error: "access_denied",
|
|
6325
6350
|
error_description: "Invalid user code",
|
|
@@ -6345,7 +6370,7 @@ class zt {
|
|
|
6345
6370
|
};
|
|
6346
6371
|
}
|
|
6347
6372
|
if (!t.deviceCode)
|
|
6348
|
-
return u.logger.error(f({ msg: "No device code for user code", userCodeHash:
|
|
6373
|
+
return u.logger.error(f({ msg: "No device code for user code", userCodeHash: _.hash(s) })), await this.deleteUserCode(s), {
|
|
6349
6374
|
ok: !1,
|
|
6350
6375
|
error: "server_error",
|
|
6351
6376
|
error_description: "No device code for user code"
|
|
@@ -6357,8 +6382,8 @@ class zt {
|
|
|
6357
6382
|
const c = o.asCrossauthError(n);
|
|
6358
6383
|
return u.logger.debug(f({ err: c })), u.logger.error(f({
|
|
6359
6384
|
msg: "Invalid device code for user code",
|
|
6360
|
-
userCodeHash:
|
|
6361
|
-
deviceCodeHash:
|
|
6385
|
+
userCodeHash: _.hash(s),
|
|
6386
|
+
deviceCodeHash: _.hash(t.deviceCode),
|
|
6362
6387
|
cerr: c
|
|
6363
6388
|
})), await this.deleteUserCode(s), {
|
|
6364
6389
|
ok: !1,
|
|
@@ -6396,7 +6421,7 @@ class zt {
|
|
|
6396
6421
|
};
|
|
6397
6422
|
}
|
|
6398
6423
|
async createMfaRequest(s) {
|
|
6399
|
-
const e =
|
|
6424
|
+
const e = _.randomValue(this.codeLength), t = U.mfaToken + _.hash(e), r = /* @__PURE__ */ new Date();
|
|
6400
6425
|
try {
|
|
6401
6426
|
await this.keyStorage.saveKey(
|
|
6402
6427
|
s.id,
|
|
@@ -6422,7 +6447,7 @@ class zt {
|
|
|
6422
6447
|
var r;
|
|
6423
6448
|
let e, t;
|
|
6424
6449
|
try {
|
|
6425
|
-
const i = U.mfaToken +
|
|
6450
|
+
const i = U.mfaToken + _.hash(s);
|
|
6426
6451
|
if (t = await this.keyStorage.getKey(i), !t.userid)
|
|
6427
6452
|
return {
|
|
6428
6453
|
error: "access_denied",
|
|
@@ -6509,8 +6534,8 @@ class zt {
|
|
|
6509
6534
|
async mfaChallengeEndpoint(s, e, t, r, i) {
|
|
6510
6535
|
const a = b.PasswordMfa, n = await this.getClientById(e);
|
|
6511
6536
|
if (!n.client) return n;
|
|
6512
|
-
const c = n.client,
|
|
6513
|
-
if (
|
|
6537
|
+
const c = n.client, d = await this.authenticateClient(a, c, t);
|
|
6538
|
+
if (d.error) return d;
|
|
6514
6539
|
const w = await this.validateMfaToken(s);
|
|
6515
6540
|
if (!w.user || !w.key) return w;
|
|
6516
6541
|
if (w.user.factor2 != i)
|
|
@@ -6525,23 +6550,23 @@ class zt {
|
|
|
6525
6550
|
};
|
|
6526
6551
|
let y = {};
|
|
6527
6552
|
r == "oob" && (y = {
|
|
6528
|
-
oobCode:
|
|
6553
|
+
oobCode: _.randomValue(this.codeLength)
|
|
6529
6554
|
});
|
|
6530
6555
|
try {
|
|
6531
|
-
const
|
|
6532
|
-
if (!
|
|
6556
|
+
const C = this.authenticators[w.user.factor2];
|
|
6557
|
+
if (!C)
|
|
6533
6558
|
throw new o(
|
|
6534
6559
|
l.Configuration,
|
|
6535
6560
|
"User's authenticator has not been loaded"
|
|
6536
6561
|
);
|
|
6537
|
-
const
|
|
6562
|
+
const v = await C.createOneTimeSecrets(w.user);
|
|
6538
6563
|
await this.keyStorage.updateData(
|
|
6539
6564
|
w.key.value,
|
|
6540
6565
|
"omfa",
|
|
6541
|
-
{ ...y, ...
|
|
6566
|
+
{ ...y, ...v }
|
|
6542
6567
|
);
|
|
6543
|
-
} catch (
|
|
6544
|
-
return u.logger.debug(f({ err:
|
|
6568
|
+
} catch (C) {
|
|
6569
|
+
return u.logger.debug(f({ err: C })), {
|
|
6545
6570
|
error: "server_error",
|
|
6546
6571
|
error_description: "Unable to initiate OOB authentication"
|
|
6547
6572
|
};
|
|
@@ -6603,28 +6628,28 @@ class zt {
|
|
|
6603
6628
|
error: "invalid_request",
|
|
6604
6629
|
error_description: `The redirect uri ${e} is invalid`
|
|
6605
6630
|
};
|
|
6606
|
-
const
|
|
6607
|
-
t && (y.scope = t), i && (y.challengeMethod = a, y.challenge =
|
|
6608
|
-
const
|
|
6609
|
-
let
|
|
6610
|
-
for (let T = 0; T < 10 && !
|
|
6631
|
+
const d = /* @__PURE__ */ new Date(), w = this.authorizationCodeExpiry ? new Date(d.getTime() + this.authorizationCodeExpiry * 1e3 + this.clockTolerance * 1e3) : void 0, y = {};
|
|
6632
|
+
t && (y.scope = t), i && (y.challengeMethod = a, y.challenge = _.hash(i)), n && (y.username = n.username, y.id = n.id);
|
|
6633
|
+
const C = JSON.stringify(y);
|
|
6634
|
+
let v = !1, p = "";
|
|
6635
|
+
for (let T = 0; T < 10 && !v; ++T)
|
|
6611
6636
|
try {
|
|
6612
|
-
|
|
6637
|
+
p = _.randomValue(this.codeLength), await this.keyStorage.saveKey(
|
|
6613
6638
|
void 0,
|
|
6614
|
-
U.authorizationCode +
|
|
6615
|
-
|
|
6639
|
+
U.authorizationCode + _.hash(p),
|
|
6640
|
+
d,
|
|
6616
6641
|
w,
|
|
6617
|
-
|
|
6618
|
-
),
|
|
6642
|
+
C
|
|
6643
|
+
), v = !0;
|
|
6619
6644
|
} catch {
|
|
6620
6645
|
u.logger.debug(f({ msg: `Attempt number${T} at creating a unique authozation code failed` }));
|
|
6621
6646
|
}
|
|
6622
|
-
if (!
|
|
6647
|
+
if (!v)
|
|
6623
6648
|
throw new o(
|
|
6624
6649
|
l.KeyExists,
|
|
6625
6650
|
"Couldn't create a authorization code"
|
|
6626
6651
|
);
|
|
6627
|
-
return { code:
|
|
6652
|
+
return { code: p, state: r };
|
|
6628
6653
|
}
|
|
6629
6654
|
/**
|
|
6630
6655
|
* Create an access token
|
|
@@ -6641,7 +6666,7 @@ class zt {
|
|
|
6641
6666
|
var z, H;
|
|
6642
6667
|
let c = !0;
|
|
6643
6668
|
try {
|
|
6644
|
-
s.client_secret != null && (c = await
|
|
6669
|
+
s.client_secret != null && (c = await _.passwordsEqual(
|
|
6645
6670
|
t ?? "",
|
|
6646
6671
|
s.client_secret ?? ""
|
|
6647
6672
|
));
|
|
@@ -6652,11 +6677,11 @@ class zt {
|
|
|
6652
6677
|
error: "access_denied",
|
|
6653
6678
|
error_description: "Invalid client secret"
|
|
6654
6679
|
};
|
|
6655
|
-
let
|
|
6680
|
+
let d = {};
|
|
6656
6681
|
if (e) {
|
|
6657
6682
|
let K;
|
|
6658
6683
|
try {
|
|
6659
|
-
K = await this.keyStorage.getKey(U.authorizationCode +
|
|
6684
|
+
K = await this.keyStorage.getKey(U.authorizationCode + _.hash(e)), d = x.decodeData(K.data);
|
|
6660
6685
|
} catch (O) {
|
|
6661
6686
|
return u.logger.debug(f({ err: O })), {
|
|
6662
6687
|
error: "access_denied",
|
|
@@ -6672,26 +6697,26 @@ class zt {
|
|
|
6672
6697
|
client_id: s == null ? void 0 : s.client_id
|
|
6673
6698
|
}));
|
|
6674
6699
|
}
|
|
6675
|
-
i =
|
|
6700
|
+
i = d.scope;
|
|
6676
6701
|
}
|
|
6677
|
-
if (n && (
|
|
6702
|
+
if (n && (d.username = n.username), d.challengeMethod && !d.challenge && d.challengeMethod != "plain" && d.challengeMethod != "S256")
|
|
6678
6703
|
return {
|
|
6679
6704
|
error: "access_denied",
|
|
6680
6705
|
error_description: "Invalid code challenge/code challenge method method for authorization code"
|
|
6681
6706
|
};
|
|
6682
|
-
if (
|
|
6683
|
-
const K =
|
|
6684
|
-
if (
|
|
6707
|
+
if (d.challenge) {
|
|
6708
|
+
const K = d.challengeMethod == "plain" ? r ?? "" : _.sha256(r ?? "");
|
|
6709
|
+
if (_.hash(K) != d.challenge)
|
|
6685
6710
|
return {
|
|
6686
6711
|
error: "access_denied",
|
|
6687
6712
|
error_description: "Code verifier is incorrect"
|
|
6688
6713
|
};
|
|
6689
6714
|
}
|
|
6690
6715
|
const w = /* @__PURE__ */ new Date(), y = Math.ceil(w.getTime() / 1e3);
|
|
6691
|
-
let
|
|
6692
|
-
if ((i && i.includes("openid") || Object.keys(this.accessTokenClaims).length > 0) && this.userStorage &&
|
|
6716
|
+
let C;
|
|
6717
|
+
if ((i && i.includes("openid") || Object.keys(this.accessTokenClaims).length > 0) && this.userStorage && d.username)
|
|
6693
6718
|
try {
|
|
6694
|
-
const { user: K } = await this.userStorage.getUserByUsername(
|
|
6719
|
+
const { user: K } = await this.userStorage.getUserByUsername(d.username);
|
|
6695
6720
|
n = K;
|
|
6696
6721
|
} catch (K) {
|
|
6697
6722
|
return u.logger.error(f({ err: K })), {
|
|
@@ -6699,18 +6724,18 @@ class zt {
|
|
|
6699
6724
|
error_description: "Couldn't load user data"
|
|
6700
6725
|
};
|
|
6701
6726
|
}
|
|
6702
|
-
const
|
|
6703
|
-
let
|
|
6704
|
-
jti:
|
|
6727
|
+
const v = _.uuid();
|
|
6728
|
+
let p = {
|
|
6729
|
+
jti: v,
|
|
6705
6730
|
iat: y,
|
|
6706
6731
|
iss: this.oauthIssuer,
|
|
6707
|
-
sub:
|
|
6732
|
+
sub: d.username,
|
|
6708
6733
|
type: "access"
|
|
6709
6734
|
};
|
|
6710
|
-
|
|
6735
|
+
p = this.addClaims(p, this.accessTokenClaims, i, n), i && (p.scope = i), this.accessTokenExpiry != null && (p.exp = y + this.accessTokenExpiry, C = new Date(w.getTime() + this.accessTokenExpiry * 1e3 + this.clockTolerance * 1e3)), this.audience && (p.aud = this.audience);
|
|
6711
6736
|
const T = await new Promise((K, O) => {
|
|
6712
6737
|
se.sign(
|
|
6713
|
-
|
|
6738
|
+
p,
|
|
6714
6739
|
this.secretOrPrivateKey,
|
|
6715
6740
|
{ algorithm: this.jwtAlgorithmChecked, keyid: "1" },
|
|
6716
6741
|
(V, j) => {
|
|
@@ -6724,19 +6749,19 @@ class zt {
|
|
|
6724
6749
|
this.persistAccessToken && this.keyStorage && await ((z = this.keyStorage) == null ? void 0 : z.saveKey(
|
|
6725
6750
|
void 0,
|
|
6726
6751
|
// to avoid user storage dependency, we don't set this
|
|
6727
|
-
U.accessToken +
|
|
6752
|
+
U.accessToken + _.hash(v),
|
|
6728
6753
|
w,
|
|
6729
|
-
|
|
6754
|
+
C
|
|
6730
6755
|
));
|
|
6731
6756
|
let k;
|
|
6732
6757
|
if (i && i.includes("openid")) {
|
|
6733
|
-
const K =
|
|
6758
|
+
const K = _.uuid();
|
|
6734
6759
|
let O = {
|
|
6735
6760
|
aud: s.client_id,
|
|
6736
6761
|
jti: K,
|
|
6737
6762
|
iat: y,
|
|
6738
6763
|
iss: this.oauthIssuer,
|
|
6739
|
-
sub:
|
|
6764
|
+
sub: d.username,
|
|
6740
6765
|
type: "id"
|
|
6741
6766
|
};
|
|
6742
6767
|
if (i.includes("email") && (n != null && n.email) && (O.email = n.email), i.includes("address") && n && "address" in n && (O.address = n.address), i.includes("phone") && n && "phone" in n && (O.phone = n.phone), i.includes("profile") && n)
|
|
@@ -6777,16 +6802,16 @@ class zt {
|
|
|
6777
6802
|
let A;
|
|
6778
6803
|
if (a) {
|
|
6779
6804
|
const K = {
|
|
6780
|
-
username:
|
|
6805
|
+
username: d.username,
|
|
6781
6806
|
client_id: s.client_id
|
|
6782
6807
|
};
|
|
6783
6808
|
i && (K.scope = i);
|
|
6784
6809
|
let O;
|
|
6785
6810
|
const j = {
|
|
6786
|
-
jti:
|
|
6811
|
+
jti: _.uuid(),
|
|
6787
6812
|
iat: y,
|
|
6788
6813
|
iss: this.oauthIssuer,
|
|
6789
|
-
sub:
|
|
6814
|
+
sub: d.username,
|
|
6790
6815
|
type: "refresh"
|
|
6791
6816
|
};
|
|
6792
6817
|
this.refreshTokenExpiry != null && (j.exp = y + this.refreshTokenExpiry, O = this.refreshTokenExpiry ? new Date(y + this.refreshTokenExpiry * 1e3 + this.clockTolerance * 1e3) : void 0), this.oauthIssuer && (j.aud = this.oauthIssuer), A = await new Promise((N, P) => {
|
|
@@ -6804,7 +6829,7 @@ class zt {
|
|
|
6804
6829
|
}), A && await ((H = this.keyStorage) == null ? void 0 : H.saveKey(
|
|
6805
6830
|
void 0,
|
|
6806
6831
|
// to avoid user storage dependency
|
|
6807
|
-
U.refreshToken +
|
|
6832
|
+
U.refreshToken + _.hash(A),
|
|
6808
6833
|
w,
|
|
6809
6834
|
O,
|
|
6810
6835
|
JSON.stringify(K)
|
|
@@ -6860,7 +6885,7 @@ class zt {
|
|
|
6860
6885
|
*/
|
|
6861
6886
|
async validAuthorizationCode(s) {
|
|
6862
6887
|
try {
|
|
6863
|
-
const e = U.authorizationCode +
|
|
6888
|
+
const e = U.authorizationCode + _.hash(s);
|
|
6864
6889
|
return await this.keyStorage.getKey(e), !0;
|
|
6865
6890
|
} catch (e) {
|
|
6866
6891
|
return u.logger.debug(f({ err: e })), !1;
|
|
@@ -6874,7 +6899,7 @@ class zt {
|
|
|
6874
6899
|
*/
|
|
6875
6900
|
async validRefreshToken(s) {
|
|
6876
6901
|
try {
|
|
6877
|
-
const e = U.refreshToken +
|
|
6902
|
+
const e = U.refreshToken + _.hash(s);
|
|
6878
6903
|
return await this.keyStorage.getKey(e), !0;
|
|
6879
6904
|
} catch (e) {
|
|
6880
6905
|
return u.logger.debug(f({ err: e })), !1;
|
|
@@ -6889,7 +6914,7 @@ class zt {
|
|
|
6889
6914
|
async getRefreshTokenData(s) {
|
|
6890
6915
|
if (s)
|
|
6891
6916
|
try {
|
|
6892
|
-
const e = U.refreshToken +
|
|
6917
|
+
const e = U.refreshToken + _.hash(s), t = await this.keyStorage.getKey(e);
|
|
6893
6918
|
return JSON.parse(t.data || "{}");
|
|
6894
6919
|
} catch (e) {
|
|
6895
6920
|
u.logger.debug(f({ err: e }));
|
|
@@ -6923,7 +6948,7 @@ class zt {
|
|
|
6923
6948
|
try {
|
|
6924
6949
|
const e = await this.validateJwt(s, "access");
|
|
6925
6950
|
if (this.persistAccessToken) {
|
|
6926
|
-
const t = U.accessToken +
|
|
6951
|
+
const t = U.accessToken + _.hash(e.payload.jti);
|
|
6927
6952
|
await this.keyStorage.getKey(t);
|
|
6928
6953
|
}
|
|
6929
6954
|
return e;
|
|
@@ -7129,15 +7154,15 @@ class nt extends Pe {
|
|
|
7129
7154
|
/**
|
|
7130
7155
|
* Value passed to the constructor. The `aud` claim must match it
|
|
7131
7156
|
*/
|
|
7132
|
-
|
|
7157
|
+
h(this, "audience");
|
|
7133
7158
|
/**
|
|
7134
7159
|
* Value passed to the constructor. If true, access tokens are saved
|
|
7135
7160
|
* in storage,
|
|
7136
7161
|
*/
|
|
7137
|
-
|
|
7138
|
-
|
|
7139
|
-
|
|
7140
|
-
|
|
7162
|
+
h(this, "persistAccessToken", !1);
|
|
7163
|
+
h(this, "keyStorage");
|
|
7164
|
+
h(this, "jwtSecretKeyFile", "");
|
|
7165
|
+
h(this, "jwtPublicKeyFile", "");
|
|
7141
7166
|
if (this.audience = e, m("authServerBaseUrl", g.String, this, t, "AUTH_SERVER_BASE_URL", !0), m("jwtSecretKeyFile", g.String, this, t, "JWT_SECRET_KEY_FILE"), m("jwtPublicKeyFile", g.String, this, t, "JWT_PUBLIC_KEY_FILE"), m("jwtSecretKey", g.String, this, t, "JWT_SECRET_KEY"), m("jwtPublicKey", g.String, this, t, "JWT_PUBLIC_KEY"), m("clockTolerance", g.Number, this, t, "OAUTH_CLOCK_TOLERANCE"), m("persistAccessToken", g.Boolean, this, t, "OAUTH_PERSIST_ACCESS_TOKEN"), this.keyStorage = t.keyStorage, this.jwtSecretKey || this.jwtSecretKeyFile) {
|
|
7142
7167
|
if (this.jwtPublicKey || this.jwtPublicKeyFile)
|
|
7143
7168
|
throw new o(
|
|
@@ -7166,7 +7191,7 @@ class nt extends Pe {
|
|
|
7166
7191
|
* @returns Base64-url-encoded hash
|
|
7167
7192
|
*/
|
|
7168
7193
|
async hash(e) {
|
|
7169
|
-
return
|
|
7194
|
+
return _.hash(e);
|
|
7170
7195
|
}
|
|
7171
7196
|
/**
|
|
7172
7197
|
* If the given token is valid, the paylaod is returned. Otherwise
|
|
@@ -7187,7 +7212,7 @@ class nt extends Pe {
|
|
|
7187
7212
|
const r = await super.tokenAuthorized(e, t);
|
|
7188
7213
|
if (r && t == "access" && this.persistAccessToken && this.keyStorage)
|
|
7189
7214
|
try {
|
|
7190
|
-
const a = U.accessToken +
|
|
7215
|
+
const a = U.accessToken + _.hash(r.jti ? r.jti : r.sid ? r.sid : ""), n = await this.keyStorage.getKey(a), c = /* @__PURE__ */ new Date();
|
|
7191
7216
|
if (n.expires && ((i = n.expires) == null ? void 0 : i.getTime()) < c.getTime()) {
|
|
7192
7217
|
u.logger.error(f({ msg: "Access token expired in storage but not in JWT" }));
|
|
7193
7218
|
return;
|
|
@@ -7195,7 +7220,7 @@ class nt extends Pe {
|
|
|
7195
7220
|
} catch (a) {
|
|
7196
7221
|
u.logger.warn(f({
|
|
7197
7222
|
msg: "Couldn't get token from database - is it valid?",
|
|
7198
|
-
hashedAccessToken:
|
|
7223
|
+
hashedAccessToken: _.hash(r.jti ? r.jti : r.sid ? r.sid : "")
|
|
7199
7224
|
})), u.logger.debug(f({ err: a }));
|
|
7200
7225
|
return;
|
|
7201
7226
|
}
|
|
@@ -7227,12 +7252,12 @@ class Ht extends Ke {
|
|
|
7227
7252
|
),
|
|
7228
7253
|
...t
|
|
7229
7254
|
});
|
|
7230
|
-
|
|
7231
|
-
|
|
7232
|
-
|
|
7233
|
-
|
|
7234
|
-
|
|
7235
|
-
|
|
7255
|
+
h(this, "deviceAuthorizationUrl", "device_authorization");
|
|
7256
|
+
h(this, "userCreationType", "idToken");
|
|
7257
|
+
h(this, "userMatchField", "username");
|
|
7258
|
+
h(this, "idTokenMatchField", "sub");
|
|
7259
|
+
h(this, "userCreationFn");
|
|
7260
|
+
h(this, "userStorage");
|
|
7236
7261
|
this.client_id = r.client_id;
|
|
7237
7262
|
let i = {};
|
|
7238
7263
|
if (m("stateLength", g.String, this, t, "OAUTH_STATE_LENGTH"), m("verifierLength", g.String, this, t, "OAUTH_VERIFIER_LENGTH"), m("client_secret", g.String, i, t, "OAUTH_CLIENT_SECRET"), m("codeChallengeMethod", g.String, this, t, "OAUTH_CODE_CHALLENGE_METHOD"), m("deviceAuthorizationUrl", g.String, this, t, "OAUTH_DEVICE_AUTHORIZATION_URL"), m("oauthLogFetch", g.Boolean, this, t, "OAUTH_LOG_FETCH"), this.deviceAuthorizationUrl.startsWith("/") && (this.deviceAuthorizationUrl = this.deviceAuthorizationUrl.substring(1)), i.client_secret && (this.client_secret = i.client_secret), m("userCreationType", g.String, this, t, "OAUTH_USER_CREATION_TYPE"), m("userMatchField", g.String, this, t, "OAUTH_USER_MATCH_FIELD"), m("idTokenMatchField", g.String, this, t, "OAUTH_IDTOKEN_MaTCH_FIELD"), this.userCreationType == "merge" ? this.userCreationFn = ot : this.userCreationType == "embed" ? this.userCreationFn = lt : t.userCreationFn && this.userCreationType == "custom" ? this.userCreationFn = t.userCreationFn : this.userCreationFn = ct, t.userStorage && (this.userStorage = t.userStorage), m("oauthPostType", g.String, this, t, "OAUTH_POST_TYPE"), m("oauthUseUserInfoEndpoint", g.Boolean, this, t, "OAUTH_USE_USER_INFO_ENDPOINT"), m("oauthAuthorizeRedirect", g.String, this, t, "OAUTH_AUTHORIZE_REDIRECT"), this.oauthPostType != "json" && this.oauthPostType != "form")
|
|
@@ -7245,7 +7270,7 @@ class Ht extends Ke {
|
|
|
7245
7270
|
* @returns the Base64-URL-encoded random string
|
|
7246
7271
|
*/
|
|
7247
7272
|
randomValue(e) {
|
|
7248
|
-
return
|
|
7273
|
+
return _.randomValue(e);
|
|
7249
7274
|
}
|
|
7250
7275
|
/**
|
|
7251
7276
|
* Uses {@link @crossauth/backend!Crypto.sha256} to create hash a string using SHA256
|
|
@@ -7253,7 +7278,7 @@ class Ht extends Ke {
|
|
|
7253
7278
|
* @returns the Base64-URL-encoded hash
|
|
7254
7279
|
*/
|
|
7255
7280
|
async sha256(e) {
|
|
7256
|
-
return
|
|
7281
|
+
return _.sha256(e);
|
|
7257
7282
|
}
|
|
7258
7283
|
}
|
|
7259
7284
|
async function ot(S, s, e, t) {
|
|
@@ -7300,7 +7325,7 @@ class jt {
|
|
|
7300
7325
|
* Keyed on auth server base URL then audience. The latter may be ""
|
|
7301
7326
|
* for none
|
|
7302
7327
|
*/
|
|
7303
|
-
|
|
7328
|
+
h(this, "tokenConsumers");
|
|
7304
7329
|
this.tokenConsumers = [...s];
|
|
7305
7330
|
}
|
|
7306
7331
|
/**
|
|
@@ -7332,7 +7357,7 @@ class jt {
|
|
|
7332
7357
|
export {
|
|
7333
7358
|
ge as ApiKeyManager,
|
|
7334
7359
|
re as Authenticator,
|
|
7335
|
-
|
|
7360
|
+
_ as Crypto,
|
|
7336
7361
|
rt as DoubleSubmitCsrfToken,
|
|
7337
7362
|
Rt as DummyFactor2Authenticator,
|
|
7338
7363
|
Z as EmailAuthenticator,
|