@crossauth/backend 0.0.36 → 0.0.38
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/authenticators/totpauth.d.ts.map +1 -1
- package/dist/index.cjs +1 -1
- package/dist/index.js +617 -596
- package/dist/oauth/authserver.d.ts.map +1 -1
- 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
|
/**
|
|
@@ -3759,8 +3773,8 @@ class xt extends re {
|
|
|
3759
3773
|
}), { qrUrl: r, secret: t };
|
|
3760
3774
|
}
|
|
3761
3775
|
async getSecretFromSession(e, t) {
|
|
3762
|
-
|
|
3763
|
-
if (!("totpsecret" in r))
|
|
3776
|
+
let r = x.decodeData(t.data);
|
|
3777
|
+
if (r && r["2fa"] && (r = r["2fa"]), !("totpsecret" in r))
|
|
3764
3778
|
throw new o(
|
|
3765
3779
|
l.Unauthorized,
|
|
3766
3780
|
"TOTP data not in session"
|
|
@@ -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,48 @@ 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
|
+
let T = await this.userStorage.getUserByUsername(s, { skipActiveCheck: !0, skipEmailVerifiedCheck: !0 });
|
|
4563
|
+
n = T.secrets, i = T.user, v = T.user;
|
|
4564
|
+
} catch {
|
|
4565
|
+
for (let k in this.authenticators)
|
|
4566
|
+
this.authenticators[k].requireUserEntry() || (v = { username: e.username, state: "active" }, c = k);
|
|
4567
|
+
}
|
|
4568
|
+
if (v.username == "") throw new o(l.UserNotExist);
|
|
4569
|
+
await this.authenticators[(i == null ? void 0 : i.factor1) ?? c].authenticateUser(v, n, e);
|
|
4546
4570
|
let p = await this.userStorage.getUserByUsername(s, { skipActiveCheck: !0, skipEmailVerifiedCheck: !0 });
|
|
4547
|
-
|
|
4548
|
-
await this.authenticators[i.factor1].authenticateUser(i, n, e);
|
|
4571
|
+
n = p.secrets, i = p.user;
|
|
4549
4572
|
}
|
|
4550
|
-
let
|
|
4573
|
+
let d;
|
|
4551
4574
|
if (i.state == E.passwordChangeNeeded)
|
|
4552
|
-
|
|
4575
|
+
d = (await this.createAnonymousSession({ data: JSON.stringify({ passwordchange: { username: i.username } }) })).sessionCookie;
|
|
4553
4576
|
else if (i.state == E.factor2ResetNeeded)
|
|
4554
|
-
|
|
4577
|
+
d = (await this.createAnonymousSession({ data: JSON.stringify({ factor2change: { username: i.username } }) })).sessionCookie;
|
|
4555
4578
|
else if (!a && i.factor2 && i.factor2 != "") {
|
|
4556
|
-
const { sessionCookie:
|
|
4557
|
-
|
|
4579
|
+
const { sessionCookie: v } = await this.initiateTwoFactorLogin(i);
|
|
4580
|
+
d = v;
|
|
4558
4581
|
} else {
|
|
4559
|
-
const
|
|
4560
|
-
|
|
4582
|
+
const v = await this.session.createSessionKey(i.id, t);
|
|
4583
|
+
d = this.session.makeCookie(v, r);
|
|
4561
4584
|
}
|
|
4562
|
-
const
|
|
4585
|
+
const w = this.csrfTokens.createCsrfToken(), y = this.csrfTokens.makeCsrfCookie(w), C = this.csrfTokens.makeCsrfFormOrHeaderToken(w);
|
|
4563
4586
|
try {
|
|
4564
4587
|
this.emailTokenStorage.deleteAllForUser(
|
|
4565
4588
|
i.id,
|
|
4566
4589
|
U.passwordResetToken
|
|
4567
4590
|
);
|
|
4568
|
-
} catch (
|
|
4569
|
-
u.logger.warn(f({ msg: "Couldn't delete password reset tokens while logging in", user: s })), u.logger.debug(f({ err:
|
|
4591
|
+
} catch (v) {
|
|
4592
|
+
u.logger.warn(f({ msg: "Couldn't delete password reset tokens while logging in", user: s })), u.logger.debug(f({ err: v }));
|
|
4570
4593
|
}
|
|
4571
4594
|
return {
|
|
4572
|
-
sessionCookie:
|
|
4573
|
-
csrfCookie:
|
|
4574
|
-
csrfFormOrHeaderValue:
|
|
4595
|
+
sessionCookie: d,
|
|
4596
|
+
csrfCookie: y,
|
|
4597
|
+
csrfFormOrHeaderValue: C,
|
|
4575
4598
|
user: i,
|
|
4576
4599
|
secrets: n
|
|
4577
4600
|
};
|
|
@@ -4752,7 +4775,7 @@ class Lt {
|
|
|
4752
4775
|
*/
|
|
4753
4776
|
async updateSessionData(s, e, t) {
|
|
4754
4777
|
const r = D.hashSessionId(s);
|
|
4755
|
-
u.logger.debug(f({ msg: `Updating session data value${e}`, hashedSessionCookie:
|
|
4778
|
+
u.logger.debug(f({ msg: `Updating session data value${e}`, hashedSessionCookie: _.hash(s) })), await this.keyStorage.updateData(r, e, t);
|
|
4756
4779
|
}
|
|
4757
4780
|
/**
|
|
4758
4781
|
* Update field sin the session data.
|
|
@@ -4764,7 +4787,7 @@ class Lt {
|
|
|
4764
4787
|
*/
|
|
4765
4788
|
async updateManySessionData(s, e) {
|
|
4766
4789
|
const t = D.hashSessionId(s);
|
|
4767
|
-
u.logger.debug(f({ msg: "Updating session data", hashedSessionCookie:
|
|
4790
|
+
u.logger.debug(f({ msg: "Updating session data", hashedSessionCookie: _.hash(s) })), await this.keyStorage.updateManyData(t, e);
|
|
4768
4791
|
}
|
|
4769
4792
|
/**
|
|
4770
4793
|
* Deletes a field from the session data.
|
|
@@ -4776,7 +4799,7 @@ class Lt {
|
|
|
4776
4799
|
*/
|
|
4777
4800
|
async deleteSessionData(s, e) {
|
|
4778
4801
|
const t = D.hashSessionId(s);
|
|
4779
|
-
u.logger.debug(f({ msg: `Updating session data value${e}`, hashedSessionCookie:
|
|
4802
|
+
u.logger.debug(f({ msg: `Updating session data value${e}`, hashedSessionCookie: _.hash(s) })), await this.keyStorage.deleteData(t, e);
|
|
4780
4803
|
}
|
|
4781
4804
|
/**
|
|
4782
4805
|
* Deletes the given session ID from the key storage (not the cookie)
|
|
@@ -4837,12 +4860,12 @@ class Lt {
|
|
|
4837
4860
|
if (!this.userStorage) throw new o(l.Configuration, "Cannot call initiateTwoFactorSignup if no user storage provided");
|
|
4838
4861
|
if (!this.authenticators[s.factor1]) throw new o(l.Configuration, "Authenticator cannot create users");
|
|
4839
4862
|
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,
|
|
4863
|
+
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
4864
|
return s.state = "awaitingtwofactorsetup", await this.keyStorage.updateData(
|
|
4842
4865
|
D.hashSessionId(t),
|
|
4843
4866
|
"2fa",
|
|
4844
4867
|
c
|
|
4845
|
-
), { userid: (await this.userStorage.createUser(s,
|
|
4868
|
+
), { userid: (await this.userStorage.createUser(s, d)).id, userData: n };
|
|
4846
4869
|
}
|
|
4847
4870
|
/**
|
|
4848
4871
|
* Begins the process of setting up 2FA for a user which has already been
|
|
@@ -4858,7 +4881,7 @@ class Lt {
|
|
|
4858
4881
|
if (e && e != "none") {
|
|
4859
4882
|
if (!this.authenticators[e]) throw new o(l.Configuration, "Two factor authentication not enabled for user");
|
|
4860
4883
|
const i = await this.authenticators[e].prepareConfiguration(s), a = i == null ? {} : i.userData, n = i == null ? {} : i.sessionData;
|
|
4861
|
-
return await this.keyStorage.updateData(
|
|
4884
|
+
return n && (n.userData = a), await this.keyStorage.updateData(
|
|
4862
4885
|
D.hashSessionId(t),
|
|
4863
4886
|
"2fa",
|
|
4864
4887
|
n
|
|
@@ -4885,10 +4908,10 @@ class Lt {
|
|
|
4885
4908
|
*/
|
|
4886
4909
|
async repeatTwoFactorSignup(s) {
|
|
4887
4910
|
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),
|
|
4911
|
+
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
4912
|
y && await this.keyStorage.updateData(i, "2fa", y);
|
|
4890
|
-
const { user:
|
|
4891
|
-
return { userid:
|
|
4913
|
+
const { user: C } = await this.userStorage.getUserByUsername(t, { skipActiveCheck: !0, skipEmailVerifiedCheck: !0 });
|
|
4914
|
+
return { userid: C.id, userData: d, secrets: w };
|
|
4892
4915
|
}
|
|
4893
4916
|
/**
|
|
4894
4917
|
* Authenticates with the second factor.
|
|
@@ -4901,7 +4924,7 @@ class Lt {
|
|
|
4901
4924
|
* @throws {@link @crossauth/common!CrossauthError} if authentication fails.
|
|
4902
4925
|
*/
|
|
4903
4926
|
async completeTwoFactorSetup(s, e) {
|
|
4904
|
-
var
|
|
4927
|
+
var v;
|
|
4905
4928
|
if (!this.userStorage) throw new o(l.Configuration, "Cannot call completeTwoFactorSetup if no user storage provided");
|
|
4906
4929
|
let t = !1, { user: r, key: i } = await this.session.getUserForSessionId(e, {
|
|
4907
4930
|
skipActiveCheck: !0
|
|
@@ -4914,18 +4937,18 @@ class Lt {
|
|
|
4914
4937
|
let n = a.username;
|
|
4915
4938
|
const c = this.authenticators[a.factor2];
|
|
4916
4939
|
if (!c) throw new o(l.Configuration, "Unrecognised second factor authentication");
|
|
4917
|
-
const
|
|
4918
|
-
for (let
|
|
4919
|
-
w.includes(
|
|
4940
|
+
const d = {}, w = c.secretNames();
|
|
4941
|
+
for (let p in a)
|
|
4942
|
+
w.includes(p) && (d[p] = a[p]);
|
|
4920
4943
|
await c.authenticateUser(void 0, a, s), r || (t = !0, r = (await this.userStorage.getUserByUsername(n, { skipActiveCheck: !0, skipEmailVerifiedCheck: !0 })).user);
|
|
4921
4944
|
const y = c.skipEmailVerificationOnSignup() == !0;
|
|
4922
4945
|
if (!r) throw new o(l.UserNotExist, "Couldn't fetch user");
|
|
4923
|
-
const
|
|
4946
|
+
const C = {
|
|
4924
4947
|
id: r.id,
|
|
4925
4948
|
state: !y && this.enableEmailVerification ? "awaitingemailverification" : "active",
|
|
4926
4949
|
factor2: a.factor2
|
|
4927
4950
|
};
|
|
4928
|
-
return c.secretNames().length > 0 ? await this.userStorage.updateUser(
|
|
4951
|
+
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
4952
|
}
|
|
4930
4953
|
/**
|
|
4931
4954
|
* Initiates the two factor login process.
|
|
@@ -4955,13 +4978,13 @@ class Lt {
|
|
|
4955
4978
|
*/
|
|
4956
4979
|
async initiateTwoFactorPageVisit(s, e, t, r, i) {
|
|
4957
4980
|
const n = await this.authenticators[s.factor2].createOneTimeSecrets(s);
|
|
4958
|
-
let c,
|
|
4981
|
+
let c, d, w;
|
|
4959
4982
|
const y = D.hashSessionId(e);
|
|
4960
4983
|
u.logger.debug("initiateTwoFactorPageVisit " + s.username + " " + e + " " + y);
|
|
4961
|
-
let
|
|
4962
|
-
return i && (
|
|
4984
|
+
let C = { username: s.username, factor2: s.factor2, secrets: n, body: t, url: r };
|
|
4985
|
+
return i && (C["content-type"] = i), await this.keyStorage.updateData(y, "pre2fa", C), {
|
|
4963
4986
|
sessionCookie: c,
|
|
4964
|
-
csrfCookie:
|
|
4987
|
+
csrfCookie: d,
|
|
4965
4988
|
csrfFormOrHeaderValue: w
|
|
4966
4989
|
};
|
|
4967
4990
|
}
|
|
@@ -4983,8 +5006,8 @@ class Lt {
|
|
|
4983
5006
|
const { secrets: i } = await this.userStorage.getUserByUsername(r.pre2fa.username), a = this.authenticators[r.pre2fa.factor2];
|
|
4984
5007
|
if (!a) throw new o(l.Configuration, "Unrecognised second factor authentication");
|
|
4985
5008
|
const n = {}, c = a.secretNames();
|
|
4986
|
-
for (let
|
|
4987
|
-
c.includes(
|
|
5009
|
+
for (let d in i)
|
|
5010
|
+
c.includes(d) && d in i && (n[d] = i[d]);
|
|
4988
5011
|
await a.authenticateUser(void 0, { ...n, ...r.pre2fa.secrets }, s), await this.keyStorage.updateData(D.hashSessionId(t.value), "pre2fa", void 0);
|
|
4989
5012
|
}
|
|
4990
5013
|
/**
|
|
@@ -5025,25 +5048,25 @@ class Lt {
|
|
|
5025
5048
|
let { key: i } = await this.session.getUserForSessionId(e);
|
|
5026
5049
|
if (!i || !i.data || i.data == "") throw new o(l.Unauthorized);
|
|
5027
5050
|
let a = x.decodeData(i.data)["2fa"], n = a.username, c = a.factor2;
|
|
5028
|
-
const { user:
|
|
5051
|
+
const { user: d, secrets: w } = await this.userStorage.getUserByUsername(n), y = this.authenticators[c];
|
|
5029
5052
|
if (!y) throw new o(l.Configuration, "Second factor " + c + " not enabled");
|
|
5030
|
-
await y.authenticateUser(
|
|
5031
|
-
const
|
|
5053
|
+
await y.authenticateUser(d, { ...w, ...a }, s);
|
|
5054
|
+
const C = await this.session.createSessionKey(d.id, t);
|
|
5032
5055
|
await this.keyStorage.deleteKey(D.hashSessionId(i.value));
|
|
5033
|
-
const
|
|
5056
|
+
const v = this.session.makeCookie(C, r), p = this.csrfTokens.createCsrfToken(), T = this.csrfTokens.makeCsrfCookie(p), k = this.csrfTokens.makeCsrfFormOrHeaderToken(p);
|
|
5034
5057
|
try {
|
|
5035
5058
|
this.emailTokenStorage.deleteAllForUser(
|
|
5036
|
-
|
|
5059
|
+
d.id,
|
|
5037
5060
|
U.passwordResetToken
|
|
5038
5061
|
);
|
|
5039
5062
|
} catch (A) {
|
|
5040
5063
|
u.logger.warn(f({ msg: "Couldn't delete password reset tokens while logging in", user: n })), u.logger.debug(f({ err: A }));
|
|
5041
5064
|
}
|
|
5042
5065
|
return {
|
|
5043
|
-
sessionCookie:
|
|
5066
|
+
sessionCookie: v,
|
|
5044
5067
|
csrfCookie: T,
|
|
5045
5068
|
csrfFormOrHeaderValue: k,
|
|
5046
|
-
user:
|
|
5069
|
+
user: d
|
|
5047
5070
|
};
|
|
5048
5071
|
}
|
|
5049
5072
|
/**
|
|
@@ -5097,10 +5120,10 @@ class Lt {
|
|
|
5097
5120
|
let { user: a, secrets: n } = await this.userStorage.getUserByUsername(s);
|
|
5098
5121
|
const c = e == 1 ? a.factor1 : a.factor2;
|
|
5099
5122
|
i != null && await this.authenticators[c].authenticateUser(a, n, i);
|
|
5100
|
-
const
|
|
5123
|
+
const d = await this.authenticators[a.factor1].createPersistentSecrets(a.username, t, r);
|
|
5101
5124
|
await this.userStorage.updateUser(
|
|
5102
5125
|
{ id: a.id },
|
|
5103
|
-
|
|
5126
|
+
d
|
|
5104
5127
|
);
|
|
5105
5128
|
try {
|
|
5106
5129
|
this.emailTokenStorage.deleteAllForUser(
|
|
@@ -5119,15 +5142,15 @@ class Lt {
|
|
|
5119
5142
|
* @returns true if email verification is now needed, false otherwise
|
|
5120
5143
|
*/
|
|
5121
5144
|
async updateUser(s, e, t = !1, r = !1) {
|
|
5122
|
-
var y,
|
|
5145
|
+
var y, C;
|
|
5123
5146
|
let i;
|
|
5124
5147
|
if (!this.userStorage) throw new o(l.Configuration, "Cannot call updateUser if no user storage provided");
|
|
5125
5148
|
if (!("id" in s) || s.id == null)
|
|
5126
5149
|
throw new o(l.UserNotExist, "Please specify a user id");
|
|
5127
5150
|
if (!("username" in s) || s.username == null)
|
|
5128
5151
|
throw new o(l.UserNotExist, "Please specify a userername");
|
|
5129
|
-
let { email: a, username: n, password: c, ...
|
|
5130
|
-
|
|
5152
|
+
let { email: a, username: n, password: c, ...d } = e;
|
|
5153
|
+
d.userid = s.userid;
|
|
5131
5154
|
let w = !1;
|
|
5132
5155
|
if (a)
|
|
5133
5156
|
i = a, R.validateEmail(i), w = !0;
|
|
@@ -5139,7 +5162,7 @@ class Lt {
|
|
|
5139
5162
|
}
|
|
5140
5163
|
w && R.validateEmail(i);
|
|
5141
5164
|
}
|
|
5142
|
-
return !t && this.enableEmailVerification && w ? await ((y = this.tokenEmailer) == null ? void 0 : y.sendEmailVerificationToken(s.id, i)) : (a && (
|
|
5165
|
+
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
5166
|
emailVerificationTokenSent: !t && this.enableEmailVerification && w,
|
|
5144
5167
|
passwordResetTokenSent: e.state == E.passwordResetNeeded || e.state == E.passwordAndFactor2ResetNeeded
|
|
5145
5168
|
};
|
|
@@ -5184,15 +5207,15 @@ class ge {
|
|
|
5184
5207
|
* @param options options. See {@link ApiKeyManagerOptions}
|
|
5185
5208
|
*/
|
|
5186
5209
|
constructor(s, e = {}) {
|
|
5187
|
-
|
|
5188
|
-
|
|
5189
|
-
|
|
5210
|
+
h(this, "apiKeyStorage");
|
|
5211
|
+
h(this, "keyLength", 16);
|
|
5212
|
+
h(this, "secret", "");
|
|
5190
5213
|
/** The prefix to add to the hashed key in storage. Defaults to
|
|
5191
5214
|
* {@link @crossauth/common!KeyPrefix}.apiKey
|
|
5192
5215
|
*/
|
|
5193
|
-
|
|
5216
|
+
h(this, "prefix", U.apiKey);
|
|
5194
5217
|
/** The name of the speak in the Authorization header. Defaults to "ApiKey" */
|
|
5195
|
-
|
|
5218
|
+
h(this, "authScheme", "ApiKey");
|
|
5196
5219
|
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
5220
|
}
|
|
5198
5221
|
/**
|
|
@@ -5214,7 +5237,7 @@ class ge {
|
|
|
5214
5237
|
* Authorization header (with the signature appended.)
|
|
5215
5238
|
*/
|
|
5216
5239
|
async createKey(s, e, t, r, i) {
|
|
5217
|
-
const a =
|
|
5240
|
+
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
5241
|
name: s,
|
|
5219
5242
|
value: a,
|
|
5220
5243
|
userid: e,
|
|
@@ -5225,7 +5248,7 @@ class ge {
|
|
|
5225
5248
|
};
|
|
5226
5249
|
await this.apiKeyStorage.saveKey(
|
|
5227
5250
|
e,
|
|
5228
|
-
this.prefix +
|
|
5251
|
+
this.prefix + d,
|
|
5229
5252
|
n,
|
|
5230
5253
|
c,
|
|
5231
5254
|
w.data,
|
|
@@ -5235,7 +5258,7 @@ class ge {
|
|
|
5235
5258
|
return { key: w, token: y };
|
|
5236
5259
|
}
|
|
5237
5260
|
static hashApiKeyValue(s) {
|
|
5238
|
-
return
|
|
5261
|
+
return _.hash(s);
|
|
5239
5262
|
}
|
|
5240
5263
|
/**
|
|
5241
5264
|
* Returns the hash of the bearer value from the Authorization header.
|
|
@@ -5246,13 +5269,13 @@ class ge {
|
|
|
5246
5269
|
* @returns a hash of the value (without the prefix).
|
|
5247
5270
|
*/
|
|
5248
5271
|
static hashSignedApiKeyValue(s) {
|
|
5249
|
-
return
|
|
5272
|
+
return _.hash(s.split(".")[0]);
|
|
5250
5273
|
}
|
|
5251
5274
|
unsignApiKeyValue(s) {
|
|
5252
|
-
return
|
|
5275
|
+
return _.unsign(s, this.secret).v;
|
|
5253
5276
|
}
|
|
5254
5277
|
signApiKeyValue(s) {
|
|
5255
|
-
return
|
|
5278
|
+
return _.sign({ v: s }, this.secret);
|
|
5256
5279
|
}
|
|
5257
5280
|
async getKey(s) {
|
|
5258
5281
|
if (this.authScheme != "" && s.startsWith(this.authScheme + " ")) {
|
|
@@ -5283,10 +5306,10 @@ class J {
|
|
|
5283
5306
|
* @param options See {@link OAuthClientManagerOptions}
|
|
5284
5307
|
*/
|
|
5285
5308
|
constructor(s = {}) {
|
|
5286
|
-
|
|
5287
|
-
|
|
5288
|
-
|
|
5289
|
-
|
|
5309
|
+
h(this, "oauthPbkdf2Digest", "sha256");
|
|
5310
|
+
h(this, "oauthPbkdf2Iterations", 4e4);
|
|
5311
|
+
h(this, "oauthPbkdf2KeyLength", 32);
|
|
5312
|
+
h(this, "clientStorage");
|
|
5290
5313
|
if (!s.clientStorage) throw new o(
|
|
5291
5314
|
l.Configuration,
|
|
5292
5315
|
"Must specify clientStorage when adding a client manager"
|
|
@@ -5308,7 +5331,7 @@ class J {
|
|
|
5308
5331
|
async createClient(s, e, t, r = !0, i) {
|
|
5309
5332
|
const a = J.randomClientId();
|
|
5310
5333
|
let n, c;
|
|
5311
|
-
r && (c = J.randomClientSecret(), n = await
|
|
5334
|
+
r && (c = J.randomClientSecret(), n = await _.passwordHash(c, {
|
|
5312
5335
|
encode: !0,
|
|
5313
5336
|
iterations: this.oauthPbkdf2Iterations,
|
|
5314
5337
|
keyLen: this.oauthPbkdf2KeyLength,
|
|
@@ -5316,7 +5339,7 @@ class J {
|
|
|
5316
5339
|
})), e.forEach((y) => {
|
|
5317
5340
|
J.validateUri(y);
|
|
5318
5341
|
}), t || (t = b.allFlows());
|
|
5319
|
-
const
|
|
5342
|
+
const d = {
|
|
5320
5343
|
client_id: a,
|
|
5321
5344
|
client_secret: n,
|
|
5322
5345
|
client_name: s,
|
|
@@ -5328,13 +5351,13 @@ class J {
|
|
|
5328
5351
|
let w;
|
|
5329
5352
|
for (let y = 0; y < 5; ++y)
|
|
5330
5353
|
try {
|
|
5331
|
-
w = await this.clientStorage.createClient(
|
|
5354
|
+
w = await this.clientStorage.createClient(d);
|
|
5332
5355
|
break;
|
|
5333
|
-
} catch (
|
|
5356
|
+
} catch (C) {
|
|
5334
5357
|
if (y == 4) {
|
|
5335
|
-
if (o.asCrossauthError(
|
|
5358
|
+
if (o.asCrossauthError(C).code != l.ClientExists) throw C;
|
|
5336
5359
|
} else
|
|
5337
|
-
|
|
5360
|
+
d.client_id = J.randomClientId();
|
|
5338
5361
|
}
|
|
5339
5362
|
if (!w) throw new o(l.ClientExists);
|
|
5340
5363
|
return w.client_secret && c && (w.client_secret = c), w;
|
|
@@ -5351,7 +5374,7 @@ class J {
|
|
|
5351
5374
|
async updateClient(s, e, t = !1) {
|
|
5352
5375
|
const r = await this.clientStorage.getClientById(s);
|
|
5353
5376
|
let i = !1, a;
|
|
5354
|
-
e.confidential === !0 && !r.confidential || e.confidential === !0 && t ? (a = J.randomClientSecret(), e.client_secret = await
|
|
5377
|
+
e.confidential === !0 && !r.confidential || e.confidential === !0 && t ? (a = J.randomClientSecret(), e.client_secret = await _.passwordHash(a, {
|
|
5355
5378
|
encode: !0,
|
|
5356
5379
|
iterations: this.oauthPbkdf2Iterations,
|
|
5357
5380
|
keyLen: this.oauthPbkdf2KeyLength,
|
|
@@ -5366,13 +5389,13 @@ class J {
|
|
|
5366
5389
|
* Create a random OAuth client id
|
|
5367
5390
|
*/
|
|
5368
5391
|
static randomClientId() {
|
|
5369
|
-
return
|
|
5392
|
+
return _.randomValue(it);
|
|
5370
5393
|
}
|
|
5371
5394
|
/**
|
|
5372
5395
|
* Create a random OAuth client secret
|
|
5373
5396
|
*/
|
|
5374
5397
|
static randomClientSecret() {
|
|
5375
|
-
return
|
|
5398
|
+
return _.randomValue(st);
|
|
5376
5399
|
}
|
|
5377
5400
|
/** If the passed redirect URI is not in the set of valid ones,
|
|
5378
5401
|
* throw {@link @crossauth/common!CrossauthError} with
|
|
@@ -5434,57 +5457,57 @@ class zt {
|
|
|
5434
5457
|
* @param options See {@link OAuthAuthorizationServerOptions }
|
|
5435
5458
|
*/
|
|
5436
5459
|
constructor(s, e, t, r = {}) {
|
|
5437
|
-
|
|
5438
|
-
|
|
5439
|
-
|
|
5440
|
-
|
|
5441
|
-
|
|
5460
|
+
h(this, "clientStorage");
|
|
5461
|
+
h(this, "keyStorage");
|
|
5462
|
+
h(this, "userStorage");
|
|
5463
|
+
h(this, "authenticators", {});
|
|
5464
|
+
h(this, "authStorage");
|
|
5442
5465
|
/** 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
|
-
|
|
5466
|
+
h(this, "clientManager");
|
|
5467
|
+
h(this, "oauthIssuer", "");
|
|
5468
|
+
h(this, "audience", null);
|
|
5469
|
+
h(this, "requireRedirectUriRegistration", !0);
|
|
5470
|
+
h(this, "requireClientSecretOrChallenge", !0);
|
|
5471
|
+
h(this, "jwtAlgorithm", "RS256");
|
|
5472
|
+
h(this, "jwtAlgorithmChecked", "RS256");
|
|
5473
|
+
h(this, "codeLength", 32);
|
|
5474
|
+
h(this, "jwtKeyType", "");
|
|
5475
|
+
h(this, "jwtSecretKey", "");
|
|
5476
|
+
h(this, "jwtPublicKey", "");
|
|
5477
|
+
h(this, "jwtPrivateKey", "");
|
|
5478
|
+
h(this, "jwtSecretKeyFile", "");
|
|
5479
|
+
h(this, "jwtPublicKeyFile", "");
|
|
5480
|
+
h(this, "jwtPrivateKeyFile", "");
|
|
5481
|
+
h(this, "jwtKid", "1");
|
|
5482
|
+
h(this, "secretOrPrivateKey", "");
|
|
5483
|
+
h(this, "secretOrPublicKey", "");
|
|
5484
|
+
h(this, "persistAccessToken", !1);
|
|
5485
|
+
h(this, "issueRefreshToken", !1);
|
|
5486
|
+
h(this, "opaqueAccessToken", !1);
|
|
5487
|
+
h(this, "accessTokenExpiry", 60 * 60);
|
|
5488
|
+
h(this, "refreshTokenExpiry", 60 * 60);
|
|
5489
|
+
h(this, "rollingRefreshToken", !0);
|
|
5490
|
+
h(this, "authorizationCodeExpiry", 60 * 5);
|
|
5491
|
+
h(this, "mfaTokenExpiry", 60 * 5);
|
|
5492
|
+
h(this, "clockTolerance", 10);
|
|
5493
|
+
h(this, "emptyScopeIsValid", !0);
|
|
5494
|
+
h(this, "validateScopes", !1);
|
|
5495
|
+
h(this, "validScopes", []);
|
|
5496
|
+
h(this, "idTokenClaims", {});
|
|
5497
|
+
h(this, "accessTokenClaims", {});
|
|
5475
5498
|
// device code
|
|
5476
|
-
|
|
5477
|
-
|
|
5478
|
-
|
|
5479
|
-
|
|
5480
|
-
|
|
5481
|
-
|
|
5482
|
-
|
|
5483
|
-
|
|
5499
|
+
h(this, "userCodeExpiry", 60 * 5);
|
|
5500
|
+
h(this, "userCodeThrottle", 1500);
|
|
5501
|
+
h(this, "deviceCodePollInterval", 5);
|
|
5502
|
+
h(this, "userCodeLength", 8);
|
|
5503
|
+
h(this, "deviceCodeLength", 16);
|
|
5504
|
+
h(this, "userCodeDashEvery", 4);
|
|
5505
|
+
h(this, "deviceCodeVerificationUri", "");
|
|
5506
|
+
h(this, "authServerBaseUrl", "");
|
|
5484
5507
|
/** Set from options. See {@link OAuthAuthorizationServerOptions.validFlows} */
|
|
5485
|
-
|
|
5508
|
+
h(this, "validFlows", ["all"]);
|
|
5486
5509
|
/** Set from options. See {@link OAuthAuthorizationServerOptions.allowedFactor2} */
|
|
5487
|
-
|
|
5510
|
+
h(this, "allowedFactor2", []);
|
|
5488
5511
|
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
5512
|
let i = {};
|
|
5490
5513
|
if (m("userCodeDashEvery", g.String, i, r, "DEVICECODE_USERCODE_DASH_EVERY"), i.userCodeDashEvery)
|
|
@@ -5586,23 +5609,23 @@ class zt {
|
|
|
5586
5609
|
}
|
|
5587
5610
|
const {
|
|
5588
5611
|
scopes: y,
|
|
5589
|
-
error:
|
|
5590
|
-
error_description:
|
|
5612
|
+
error: C,
|
|
5613
|
+
error_description: v
|
|
5591
5614
|
} = await this.validateAndPersistScope(e, r, c);
|
|
5592
|
-
if (
|
|
5593
|
-
error:
|
|
5594
|
-
error_description:
|
|
5615
|
+
if (C) return {
|
|
5616
|
+
error: C,
|
|
5617
|
+
error_description: v
|
|
5595
5618
|
};
|
|
5596
|
-
const
|
|
5597
|
-
if (!
|
|
5619
|
+
const p = this.inferFlowFromGet(s, y || [], a);
|
|
5620
|
+
if (!p || !this.validFlows.includes(p))
|
|
5598
5621
|
return {
|
|
5599
5622
|
error: "access_denied",
|
|
5600
|
-
error_description: "Unsupported flow type " +
|
|
5623
|
+
error_description: "Unsupported flow type " + p
|
|
5601
5624
|
};
|
|
5602
|
-
if (!w.valid_flow.includes(
|
|
5625
|
+
if (!w.valid_flow.includes(p))
|
|
5603
5626
|
return {
|
|
5604
5627
|
error: "unauthorized_client",
|
|
5605
|
-
error_description: "Client does not support " +
|
|
5628
|
+
error_description: "Client does not support " + p
|
|
5606
5629
|
};
|
|
5607
5630
|
try {
|
|
5608
5631
|
this.validateState(i);
|
|
@@ -5712,7 +5735,7 @@ class zt {
|
|
|
5712
5735
|
} : r && (!t || !e.client_secret) ? {
|
|
5713
5736
|
error: "access_denied",
|
|
5714
5737
|
error_description: "Client is confidential but either secret not passed or is missing in database"
|
|
5715
|
-
} : r && !await
|
|
5738
|
+
} : r && !await _.passwordsEqual(
|
|
5716
5739
|
t ?? "",
|
|
5717
5740
|
e.client_secret ?? ""
|
|
5718
5741
|
) ? {
|
|
@@ -5755,12 +5778,12 @@ class zt {
|
|
|
5755
5778
|
codeVerifier: a,
|
|
5756
5779
|
refreshToken: n,
|
|
5757
5780
|
username: c,
|
|
5758
|
-
password:
|
|
5781
|
+
password: d,
|
|
5759
5782
|
mfaToken: w,
|
|
5760
5783
|
oobCode: y,
|
|
5761
|
-
bindingCode:
|
|
5762
|
-
otp:
|
|
5763
|
-
deviceCode:
|
|
5784
|
+
bindingCode: C,
|
|
5785
|
+
otp: v,
|
|
5786
|
+
deviceCode: p
|
|
5764
5787
|
}) {
|
|
5765
5788
|
var O, V, j;
|
|
5766
5789
|
const T = this.inferFlowFromPost(s, a);
|
|
@@ -5830,7 +5853,7 @@ class zt {
|
|
|
5830
5853
|
};
|
|
5831
5854
|
}
|
|
5832
5855
|
try {
|
|
5833
|
-
const F = U.refreshToken +
|
|
5856
|
+
const F = U.refreshToken + _.hash(n);
|
|
5834
5857
|
await this.keyStorage.deleteKey(F);
|
|
5835
5858
|
} catch (F) {
|
|
5836
5859
|
const I = o.asCrossauthError(F);
|
|
@@ -5861,7 +5884,7 @@ class zt {
|
|
|
5861
5884
|
issueRefreshToken: H
|
|
5862
5885
|
});
|
|
5863
5886
|
} else if (s == "password") {
|
|
5864
|
-
if (!c || !
|
|
5887
|
+
if (!c || !d)
|
|
5865
5888
|
return {
|
|
5866
5889
|
error: "access_denied",
|
|
5867
5890
|
error_description: "Username and/or password not provided for password flow"
|
|
@@ -5881,7 +5904,7 @@ class zt {
|
|
|
5881
5904
|
await B.authenticateUser(
|
|
5882
5905
|
I,
|
|
5883
5906
|
$,
|
|
5884
|
-
{ password:
|
|
5907
|
+
{ password: d }
|
|
5885
5908
|
), K = I;
|
|
5886
5909
|
} catch (I) {
|
|
5887
5910
|
return u.logger.debug(f({ err: I })), {
|
|
@@ -5919,7 +5942,7 @@ class zt {
|
|
|
5919
5942
|
error: P,
|
|
5920
5943
|
error_description: F
|
|
5921
5944
|
};
|
|
5922
|
-
if (!
|
|
5945
|
+
if (!v)
|
|
5923
5946
|
return {
|
|
5924
5947
|
error: "access_denied",
|
|
5925
5948
|
error_description: "OTP not provided"
|
|
@@ -5929,7 +5952,7 @@ class zt {
|
|
|
5929
5952
|
error: "access_denied",
|
|
5930
5953
|
error_description: "MFA token not provided"
|
|
5931
5954
|
};
|
|
5932
|
-
const I = await this.validateMfaToken(w), $ = U.mfaToken +
|
|
5955
|
+
const I = await this.validateMfaToken(w), $ = U.mfaToken + _.hash(w);
|
|
5933
5956
|
if (!I.user || !I.key)
|
|
5934
5957
|
return {
|
|
5935
5958
|
error: "access_denied",
|
|
@@ -5946,7 +5969,7 @@ class zt {
|
|
|
5946
5969
|
await B.authenticateUser(
|
|
5947
5970
|
I.user,
|
|
5948
5971
|
M,
|
|
5949
|
-
{ otp:
|
|
5972
|
+
{ otp: v }
|
|
5950
5973
|
);
|
|
5951
5974
|
} catch (M) {
|
|
5952
5975
|
return u.logger.debug(f({ err: M })), {
|
|
@@ -5982,7 +6005,7 @@ class zt {
|
|
|
5982
6005
|
error: P,
|
|
5983
6006
|
error_description: F
|
|
5984
6007
|
};
|
|
5985
|
-
if (!y || !
|
|
6008
|
+
if (!y || !C)
|
|
5986
6009
|
return {
|
|
5987
6010
|
error: "access_denied",
|
|
5988
6011
|
error_description: "OOB code or binding code not provided"
|
|
@@ -6019,7 +6042,7 @@ class zt {
|
|
|
6019
6042
|
await $.authenticateUser(
|
|
6020
6043
|
I.user,
|
|
6021
6044
|
{ ...B, otp: M.otp, expiry: (V = I.key.expires) == null ? void 0 : V.getTime() },
|
|
6022
|
-
{ otp:
|
|
6045
|
+
{ otp: C }
|
|
6023
6046
|
);
|
|
6024
6047
|
} catch (B) {
|
|
6025
6048
|
return u.logger.debug(f({ err: B })), {
|
|
@@ -6045,14 +6068,14 @@ class zt {
|
|
|
6045
6068
|
user: I.user
|
|
6046
6069
|
});
|
|
6047
6070
|
} else if (s == "urn:ietf:params:oauth:grant-type:device_code") {
|
|
6048
|
-
if (!
|
|
6071
|
+
if (!p)
|
|
6049
6072
|
return {
|
|
6050
6073
|
error: "invalid_request",
|
|
6051
6074
|
error_description: "No device code given"
|
|
6052
6075
|
};
|
|
6053
6076
|
let N;
|
|
6054
6077
|
try {
|
|
6055
|
-
N = await this.keyStorage.getKey(U.deviceCode +
|
|
6078
|
+
N = await this.keyStorage.getKey(U.deviceCode + p);
|
|
6056
6079
|
} catch (P) {
|
|
6057
6080
|
const F = o.asCrossauthError(P);
|
|
6058
6081
|
return u.logger.debug(f({ err: F })), u.logger.error(f({ msg: "Couldn't get device code", cerr: F })), {
|
|
@@ -6063,7 +6086,7 @@ class zt {
|
|
|
6063
6086
|
try {
|
|
6064
6087
|
const P = JSON.parse(N.data ?? "{}"), F = (/* @__PURE__ */ new Date()).getTime();
|
|
6065
6088
|
if (N.expires && F > N.expires.getTime())
|
|
6066
|
-
return await this.deleteDeviceCode(
|
|
6089
|
+
return await this.deleteDeviceCode(p), {
|
|
6067
6090
|
error: "expired_token",
|
|
6068
6091
|
error_description: "Code has expired"
|
|
6069
6092
|
};
|
|
@@ -6074,7 +6097,7 @@ class zt {
|
|
|
6074
6097
|
};
|
|
6075
6098
|
{
|
|
6076
6099
|
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(
|
|
6100
|
+
return await this.deleteDeviceCode(p), await this.makeAccessToken({
|
|
6078
6101
|
client: A,
|
|
6079
6102
|
client_secret: i,
|
|
6080
6103
|
codeVerifier: a,
|
|
@@ -6085,7 +6108,7 @@ class zt {
|
|
|
6085
6108
|
}
|
|
6086
6109
|
} catch (P) {
|
|
6087
6110
|
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(
|
|
6111
|
+
return u.logger.debug(f({ err: F })), u.logger.error(f({ msg: "Couldn't get device code", cerr: F })), await this.deleteDeviceCode(p), {
|
|
6089
6112
|
error: "accerss_denied",
|
|
6090
6113
|
error_description: "Invalid device code"
|
|
6091
6114
|
};
|
|
@@ -6128,7 +6151,7 @@ class zt {
|
|
|
6128
6151
|
scope: e,
|
|
6129
6152
|
client_secret: t
|
|
6130
6153
|
}) {
|
|
6131
|
-
var
|
|
6154
|
+
var p;
|
|
6132
6155
|
if (this.deviceCodeVerificationUri == "")
|
|
6133
6156
|
return {
|
|
6134
6157
|
error: "invalid_request",
|
|
@@ -6158,53 +6181,53 @@ class zt {
|
|
|
6158
6181
|
error_description: k
|
|
6159
6182
|
};
|
|
6160
6183
|
}
|
|
6161
|
-
let c,
|
|
6162
|
-
const w = /* @__PURE__ */ new Date(), y = this.userCodeExpiry,
|
|
6163
|
-
for (let T = 0; T < 10 && !
|
|
6184
|
+
let c, d = !1;
|
|
6185
|
+
const w = /* @__PURE__ */ new Date(), y = this.userCodeExpiry, C = new Date(w.getTime() + this.userCodeExpiry * 1e3 + this.clockTolerance * 1e3);
|
|
6186
|
+
for (let T = 0; T < 10 && !d; ++T)
|
|
6164
6187
|
try {
|
|
6165
|
-
c =
|
|
6188
|
+
c = _.randomValue(this.deviceCodeLength), await this.keyStorage.saveKey(
|
|
6166
6189
|
void 0,
|
|
6167
6190
|
U.deviceCode + c,
|
|
6168
6191
|
w,
|
|
6169
|
-
|
|
6192
|
+
C,
|
|
6170
6193
|
JSON.stringify({ scope: e, client_id: s })
|
|
6171
|
-
),
|
|
6194
|
+
), d = !0;
|
|
6172
6195
|
} catch {
|
|
6173
6196
|
u.logger.debug(f({ msg: `Attempt number${T} at creating a unique authozation code failed` }));
|
|
6174
6197
|
}
|
|
6175
|
-
if (!
|
|
6198
|
+
if (!d || !c)
|
|
6176
6199
|
return {
|
|
6177
6200
|
error: "server_error",
|
|
6178
6201
|
error_description: "Couldn't create device code"
|
|
6179
6202
|
};
|
|
6180
|
-
let
|
|
6181
|
-
|
|
6182
|
-
for (let T = 0; T < 10 && !
|
|
6203
|
+
let v;
|
|
6204
|
+
d = !1;
|
|
6205
|
+
for (let T = 0; T < 10 && !d; ++T)
|
|
6183
6206
|
try {
|
|
6184
|
-
|
|
6207
|
+
v = _.randomBase32(this.userCodeLength), await this.keyStorage.saveKey(
|
|
6185
6208
|
void 0,
|
|
6186
|
-
U.userCode +
|
|
6209
|
+
U.userCode + v,
|
|
6187
6210
|
w,
|
|
6188
|
-
|
|
6211
|
+
C,
|
|
6189
6212
|
JSON.stringify({ deviceCode: c })
|
|
6190
|
-
),
|
|
6213
|
+
), d = !0;
|
|
6191
6214
|
} catch {
|
|
6192
6215
|
u.logger.debug(f({ msg: `Attempt number${T} at creating a unique authozation code failed` }));
|
|
6193
6216
|
}
|
|
6194
|
-
if (!
|
|
6217
|
+
if (!d || !v)
|
|
6195
6218
|
return await this.deleteDeviceCode(c), {
|
|
6196
6219
|
error: "server_error",
|
|
6197
6220
|
error_description: "Couldn't create device code"
|
|
6198
6221
|
};
|
|
6199
|
-
if (
|
|
6222
|
+
if (v && this.userCodeDashEvery) {
|
|
6200
6223
|
const T = new RegExp(String.raw`(.{1,${this.userCodeDashEvery}})`, "g");
|
|
6201
|
-
|
|
6224
|
+
v = (p = v.match(T)) == null ? void 0 : p.join("-");
|
|
6202
6225
|
}
|
|
6203
6226
|
return {
|
|
6204
6227
|
device_code: c,
|
|
6205
|
-
user_code:
|
|
6228
|
+
user_code: v,
|
|
6206
6229
|
verification_uri: this.deviceCodeVerificationUri,
|
|
6207
|
-
verification_uri_complete: this.deviceCodeVerificationUri + "?user_code=" +
|
|
6230
|
+
verification_uri_complete: this.deviceCodeVerificationUri + "?user_code=" + v,
|
|
6208
6231
|
expires_in: y,
|
|
6209
6232
|
interval: this.deviceCodePollInterval
|
|
6210
6233
|
};
|
|
@@ -6237,7 +6260,7 @@ class zt {
|
|
|
6237
6260
|
};
|
|
6238
6261
|
}
|
|
6239
6262
|
if (!r.deviceCode)
|
|
6240
|
-
return u.logger.error(f({ msg: "No device code for user code", userCodeHash:
|
|
6263
|
+
return u.logger.error(f({ msg: "No device code for user code", userCodeHash: _.hash(s) })), await this.deleteUserCode(s), {
|
|
6241
6264
|
ok: !1,
|
|
6242
6265
|
error: "server_error",
|
|
6243
6266
|
error_description: "No device code for user code"
|
|
@@ -6246,12 +6269,12 @@ class zt {
|
|
|
6246
6269
|
try {
|
|
6247
6270
|
i = await this.keyStorage.getKey(U.deviceCode + r.deviceCode);
|
|
6248
6271
|
} catch (y) {
|
|
6249
|
-
const
|
|
6250
|
-
return u.logger.debug(f({ err:
|
|
6272
|
+
const C = o.asCrossauthError(y);
|
|
6273
|
+
return u.logger.debug(f({ err: C })), u.logger.error(f({
|
|
6251
6274
|
msg: "Invalid device code for user code",
|
|
6252
|
-
userCodeHash:
|
|
6253
|
-
deviceCodeHash:
|
|
6254
|
-
cerr:
|
|
6275
|
+
userCodeHash: _.hash(s),
|
|
6276
|
+
deviceCodeHash: _.hash(r.deviceCode),
|
|
6277
|
+
cerr: C
|
|
6255
6278
|
})), await this.deleteUserCode(s), {
|
|
6256
6279
|
ok: !1,
|
|
6257
6280
|
error: "server_error",
|
|
@@ -6284,24 +6307,24 @@ class zt {
|
|
|
6284
6307
|
error_description: "User code has already been used",
|
|
6285
6308
|
client_id: n
|
|
6286
6309
|
};
|
|
6287
|
-
let
|
|
6310
|
+
let d = !1;
|
|
6288
6311
|
if (u.logger.debug(f({
|
|
6289
6312
|
msg: "Checking scopes have been authorized",
|
|
6290
6313
|
scope: a
|
|
6291
|
-
})), a ?
|
|
6314
|
+
})), a ? d = await this.hasAllScopes(
|
|
6292
6315
|
n,
|
|
6293
6316
|
e,
|
|
6294
6317
|
a.split(" ")
|
|
6295
|
-
) :
|
|
6318
|
+
) : d = await this.hasAllScopes(
|
|
6296
6319
|
n,
|
|
6297
6320
|
e,
|
|
6298
6321
|
[null]
|
|
6299
|
-
), !
|
|
6322
|
+
), !d) {
|
|
6300
6323
|
try {
|
|
6301
6324
|
e != null && e.id && await this.keyStorage.updateData(U.deviceCode + r.deviceCode, "userid", e.id);
|
|
6302
6325
|
} catch (y) {
|
|
6303
|
-
const
|
|
6304
|
-
return u.logger.debug(f({ err:
|
|
6326
|
+
const C = o.asCrossauthError(y);
|
|
6327
|
+
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
6328
|
ok: !1,
|
|
6306
6329
|
error: "access_denied",
|
|
6307
6330
|
error_description: "Invalid user code",
|
|
@@ -6318,8 +6341,8 @@ class zt {
|
|
|
6318
6341
|
try {
|
|
6319
6342
|
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
6343
|
} catch (y) {
|
|
6321
|
-
const
|
|
6322
|
-
return u.logger.debug(f({ err:
|
|
6344
|
+
const C = o.asCrossauthError(y);
|
|
6345
|
+
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
6346
|
ok: !1,
|
|
6324
6347
|
error: "access_denied",
|
|
6325
6348
|
error_description: "Invalid user code",
|
|
@@ -6345,7 +6368,7 @@ class zt {
|
|
|
6345
6368
|
};
|
|
6346
6369
|
}
|
|
6347
6370
|
if (!t.deviceCode)
|
|
6348
|
-
return u.logger.error(f({ msg: "No device code for user code", userCodeHash:
|
|
6371
|
+
return u.logger.error(f({ msg: "No device code for user code", userCodeHash: _.hash(s) })), await this.deleteUserCode(s), {
|
|
6349
6372
|
ok: !1,
|
|
6350
6373
|
error: "server_error",
|
|
6351
6374
|
error_description: "No device code for user code"
|
|
@@ -6357,8 +6380,8 @@ class zt {
|
|
|
6357
6380
|
const c = o.asCrossauthError(n);
|
|
6358
6381
|
return u.logger.debug(f({ err: c })), u.logger.error(f({
|
|
6359
6382
|
msg: "Invalid device code for user code",
|
|
6360
|
-
userCodeHash:
|
|
6361
|
-
deviceCodeHash:
|
|
6383
|
+
userCodeHash: _.hash(s),
|
|
6384
|
+
deviceCodeHash: _.hash(t.deviceCode),
|
|
6362
6385
|
cerr: c
|
|
6363
6386
|
})), await this.deleteUserCode(s), {
|
|
6364
6387
|
ok: !1,
|
|
@@ -6396,7 +6419,7 @@ class zt {
|
|
|
6396
6419
|
};
|
|
6397
6420
|
}
|
|
6398
6421
|
async createMfaRequest(s) {
|
|
6399
|
-
const e =
|
|
6422
|
+
const e = _.randomValue(this.codeLength), t = U.mfaToken + _.hash(e), r = /* @__PURE__ */ new Date();
|
|
6400
6423
|
try {
|
|
6401
6424
|
await this.keyStorage.saveKey(
|
|
6402
6425
|
s.id,
|
|
@@ -6422,7 +6445,7 @@ class zt {
|
|
|
6422
6445
|
var r;
|
|
6423
6446
|
let e, t;
|
|
6424
6447
|
try {
|
|
6425
|
-
const i = U.mfaToken +
|
|
6448
|
+
const i = U.mfaToken + _.hash(s);
|
|
6426
6449
|
if (t = await this.keyStorage.getKey(i), !t.userid)
|
|
6427
6450
|
return {
|
|
6428
6451
|
error: "access_denied",
|
|
@@ -6509,8 +6532,8 @@ class zt {
|
|
|
6509
6532
|
async mfaChallengeEndpoint(s, e, t, r, i) {
|
|
6510
6533
|
const a = b.PasswordMfa, n = await this.getClientById(e);
|
|
6511
6534
|
if (!n.client) return n;
|
|
6512
|
-
const c = n.client,
|
|
6513
|
-
if (
|
|
6535
|
+
const c = n.client, d = await this.authenticateClient(a, c, t);
|
|
6536
|
+
if (d.error) return d;
|
|
6514
6537
|
const w = await this.validateMfaToken(s);
|
|
6515
6538
|
if (!w.user || !w.key) return w;
|
|
6516
6539
|
if (w.user.factor2 != i)
|
|
@@ -6525,23 +6548,23 @@ class zt {
|
|
|
6525
6548
|
};
|
|
6526
6549
|
let y = {};
|
|
6527
6550
|
r == "oob" && (y = {
|
|
6528
|
-
oobCode:
|
|
6551
|
+
oobCode: _.randomValue(this.codeLength)
|
|
6529
6552
|
});
|
|
6530
6553
|
try {
|
|
6531
|
-
const
|
|
6532
|
-
if (!
|
|
6554
|
+
const C = this.authenticators[w.user.factor2];
|
|
6555
|
+
if (!C)
|
|
6533
6556
|
throw new o(
|
|
6534
6557
|
l.Configuration,
|
|
6535
6558
|
"User's authenticator has not been loaded"
|
|
6536
6559
|
);
|
|
6537
|
-
const
|
|
6560
|
+
const v = await C.createOneTimeSecrets(w.user);
|
|
6538
6561
|
await this.keyStorage.updateData(
|
|
6539
6562
|
w.key.value,
|
|
6540
6563
|
"omfa",
|
|
6541
|
-
{ ...y, ...
|
|
6564
|
+
{ ...y, ...v }
|
|
6542
6565
|
);
|
|
6543
|
-
} catch (
|
|
6544
|
-
return u.logger.debug(f({ err:
|
|
6566
|
+
} catch (C) {
|
|
6567
|
+
return u.logger.debug(f({ err: C })), {
|
|
6545
6568
|
error: "server_error",
|
|
6546
6569
|
error_description: "Unable to initiate OOB authentication"
|
|
6547
6570
|
};
|
|
@@ -6603,28 +6626,28 @@ class zt {
|
|
|
6603
6626
|
error: "invalid_request",
|
|
6604
6627
|
error_description: `The redirect uri ${e} is invalid`
|
|
6605
6628
|
};
|
|
6606
|
-
const
|
|
6607
|
-
t && (y.scope = t), i && (y.challengeMethod = a, y.challenge =
|
|
6608
|
-
const
|
|
6609
|
-
let
|
|
6610
|
-
for (let T = 0; T < 10 && !
|
|
6629
|
+
const d = /* @__PURE__ */ new Date(), w = this.authorizationCodeExpiry ? new Date(d.getTime() + this.authorizationCodeExpiry * 1e3 + this.clockTolerance * 1e3) : void 0, y = {};
|
|
6630
|
+
t && (y.scope = t), i && (y.challengeMethod = a, y.challenge = _.hash(i)), n && (y.username = n.username, y.id = n.id);
|
|
6631
|
+
const C = JSON.stringify(y);
|
|
6632
|
+
let v = !1, p = "";
|
|
6633
|
+
for (let T = 0; T < 10 && !v; ++T)
|
|
6611
6634
|
try {
|
|
6612
|
-
|
|
6635
|
+
p = _.randomValue(this.codeLength), await this.keyStorage.saveKey(
|
|
6613
6636
|
void 0,
|
|
6614
|
-
U.authorizationCode +
|
|
6615
|
-
|
|
6637
|
+
U.authorizationCode + _.hash(p),
|
|
6638
|
+
d,
|
|
6616
6639
|
w,
|
|
6617
|
-
|
|
6618
|
-
),
|
|
6640
|
+
C
|
|
6641
|
+
), v = !0;
|
|
6619
6642
|
} catch {
|
|
6620
6643
|
u.logger.debug(f({ msg: `Attempt number${T} at creating a unique authozation code failed` }));
|
|
6621
6644
|
}
|
|
6622
|
-
if (!
|
|
6645
|
+
if (!v)
|
|
6623
6646
|
throw new o(
|
|
6624
6647
|
l.KeyExists,
|
|
6625
6648
|
"Couldn't create a authorization code"
|
|
6626
6649
|
);
|
|
6627
|
-
return { code:
|
|
6650
|
+
return { code: p, state: r };
|
|
6628
6651
|
}
|
|
6629
6652
|
/**
|
|
6630
6653
|
* Create an access token
|
|
@@ -6641,7 +6664,7 @@ class zt {
|
|
|
6641
6664
|
var z, H;
|
|
6642
6665
|
let c = !0;
|
|
6643
6666
|
try {
|
|
6644
|
-
s.client_secret != null && (c = await
|
|
6667
|
+
s.client_secret != null && (c = await _.passwordsEqual(
|
|
6645
6668
|
t ?? "",
|
|
6646
6669
|
s.client_secret ?? ""
|
|
6647
6670
|
));
|
|
@@ -6652,11 +6675,11 @@ class zt {
|
|
|
6652
6675
|
error: "access_denied",
|
|
6653
6676
|
error_description: "Invalid client secret"
|
|
6654
6677
|
};
|
|
6655
|
-
let
|
|
6678
|
+
let d = {};
|
|
6656
6679
|
if (e) {
|
|
6657
6680
|
let K;
|
|
6658
6681
|
try {
|
|
6659
|
-
K = await this.keyStorage.getKey(U.authorizationCode +
|
|
6682
|
+
K = await this.keyStorage.getKey(U.authorizationCode + _.hash(e)), d = x.decodeData(K.data);
|
|
6660
6683
|
} catch (O) {
|
|
6661
6684
|
return u.logger.debug(f({ err: O })), {
|
|
6662
6685
|
error: "access_denied",
|
|
@@ -6672,26 +6695,26 @@ class zt {
|
|
|
6672
6695
|
client_id: s == null ? void 0 : s.client_id
|
|
6673
6696
|
}));
|
|
6674
6697
|
}
|
|
6675
|
-
i =
|
|
6698
|
+
i = d.scope;
|
|
6676
6699
|
}
|
|
6677
|
-
if (n && (
|
|
6700
|
+
if (n && (d.username = n.username), d.challengeMethod && !d.challenge && d.challengeMethod != "plain" && d.challengeMethod != "S256")
|
|
6678
6701
|
return {
|
|
6679
6702
|
error: "access_denied",
|
|
6680
6703
|
error_description: "Invalid code challenge/code challenge method method for authorization code"
|
|
6681
6704
|
};
|
|
6682
|
-
if (
|
|
6683
|
-
const K =
|
|
6684
|
-
if (
|
|
6705
|
+
if (d.challenge) {
|
|
6706
|
+
const K = d.challengeMethod == "plain" ? r ?? "" : _.sha256(r ?? "");
|
|
6707
|
+
if (_.hash(K) != d.challenge)
|
|
6685
6708
|
return {
|
|
6686
6709
|
error: "access_denied",
|
|
6687
6710
|
error_description: "Code verifier is incorrect"
|
|
6688
6711
|
};
|
|
6689
6712
|
}
|
|
6690
6713
|
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 &&
|
|
6714
|
+
let C;
|
|
6715
|
+
if ((i && i.includes("openid") || Object.keys(this.accessTokenClaims).length > 0) && this.userStorage && d.username)
|
|
6693
6716
|
try {
|
|
6694
|
-
const { user: K } = await this.userStorage.getUserByUsername(
|
|
6717
|
+
const { user: K } = await this.userStorage.getUserByUsername(d.username);
|
|
6695
6718
|
n = K;
|
|
6696
6719
|
} catch (K) {
|
|
6697
6720
|
return u.logger.error(f({ err: K })), {
|
|
@@ -6699,18 +6722,18 @@ class zt {
|
|
|
6699
6722
|
error_description: "Couldn't load user data"
|
|
6700
6723
|
};
|
|
6701
6724
|
}
|
|
6702
|
-
const
|
|
6703
|
-
let
|
|
6704
|
-
jti:
|
|
6725
|
+
const v = _.uuid();
|
|
6726
|
+
let p = {
|
|
6727
|
+
jti: v,
|
|
6705
6728
|
iat: y,
|
|
6706
6729
|
iss: this.oauthIssuer,
|
|
6707
|
-
sub:
|
|
6730
|
+
sub: d.username,
|
|
6708
6731
|
type: "access"
|
|
6709
6732
|
};
|
|
6710
|
-
|
|
6733
|
+
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
6734
|
const T = await new Promise((K, O) => {
|
|
6712
6735
|
se.sign(
|
|
6713
|
-
|
|
6736
|
+
p,
|
|
6714
6737
|
this.secretOrPrivateKey,
|
|
6715
6738
|
{ algorithm: this.jwtAlgorithmChecked, keyid: "1" },
|
|
6716
6739
|
(V, j) => {
|
|
@@ -6724,19 +6747,19 @@ class zt {
|
|
|
6724
6747
|
this.persistAccessToken && this.keyStorage && await ((z = this.keyStorage) == null ? void 0 : z.saveKey(
|
|
6725
6748
|
void 0,
|
|
6726
6749
|
// to avoid user storage dependency, we don't set this
|
|
6727
|
-
U.accessToken +
|
|
6750
|
+
U.accessToken + _.hash(v),
|
|
6728
6751
|
w,
|
|
6729
|
-
|
|
6752
|
+
C
|
|
6730
6753
|
));
|
|
6731
6754
|
let k;
|
|
6732
6755
|
if (i && i.includes("openid")) {
|
|
6733
|
-
const K =
|
|
6756
|
+
const K = _.uuid();
|
|
6734
6757
|
let O = {
|
|
6735
6758
|
aud: s.client_id,
|
|
6736
6759
|
jti: K,
|
|
6737
6760
|
iat: y,
|
|
6738
6761
|
iss: this.oauthIssuer,
|
|
6739
|
-
sub:
|
|
6762
|
+
sub: d.username,
|
|
6740
6763
|
type: "id"
|
|
6741
6764
|
};
|
|
6742
6765
|
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 +6800,16 @@ class zt {
|
|
|
6777
6800
|
let A;
|
|
6778
6801
|
if (a) {
|
|
6779
6802
|
const K = {
|
|
6780
|
-
username:
|
|
6803
|
+
username: d.username,
|
|
6781
6804
|
client_id: s.client_id
|
|
6782
6805
|
};
|
|
6783
6806
|
i && (K.scope = i);
|
|
6784
6807
|
let O;
|
|
6785
6808
|
const j = {
|
|
6786
|
-
jti:
|
|
6809
|
+
jti: _.uuid(),
|
|
6787
6810
|
iat: y,
|
|
6788
6811
|
iss: this.oauthIssuer,
|
|
6789
|
-
sub:
|
|
6812
|
+
sub: d.username,
|
|
6790
6813
|
type: "refresh"
|
|
6791
6814
|
};
|
|
6792
6815
|
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 +6827,7 @@ class zt {
|
|
|
6804
6827
|
}), A && await ((H = this.keyStorage) == null ? void 0 : H.saveKey(
|
|
6805
6828
|
void 0,
|
|
6806
6829
|
// to avoid user storage dependency
|
|
6807
|
-
U.refreshToken +
|
|
6830
|
+
U.refreshToken + _.hash(A),
|
|
6808
6831
|
w,
|
|
6809
6832
|
O,
|
|
6810
6833
|
JSON.stringify(K)
|
|
@@ -6843,11 +6866,9 @@ class zt {
|
|
|
6843
6866
|
...s,
|
|
6844
6867
|
...r
|
|
6845
6868
|
};
|
|
6846
|
-
else
|
|
6847
|
-
console.log(i);
|
|
6869
|
+
else
|
|
6848
6870
|
for (let a in i)
|
|
6849
6871
|
s[a] = r[i[a]];
|
|
6850
|
-
}
|
|
6851
6872
|
}
|
|
6852
6873
|
}
|
|
6853
6874
|
return s;
|
|
@@ -6860,7 +6881,7 @@ class zt {
|
|
|
6860
6881
|
*/
|
|
6861
6882
|
async validAuthorizationCode(s) {
|
|
6862
6883
|
try {
|
|
6863
|
-
const e = U.authorizationCode +
|
|
6884
|
+
const e = U.authorizationCode + _.hash(s);
|
|
6864
6885
|
return await this.keyStorage.getKey(e), !0;
|
|
6865
6886
|
} catch (e) {
|
|
6866
6887
|
return u.logger.debug(f({ err: e })), !1;
|
|
@@ -6874,7 +6895,7 @@ class zt {
|
|
|
6874
6895
|
*/
|
|
6875
6896
|
async validRefreshToken(s) {
|
|
6876
6897
|
try {
|
|
6877
|
-
const e = U.refreshToken +
|
|
6898
|
+
const e = U.refreshToken + _.hash(s);
|
|
6878
6899
|
return await this.keyStorage.getKey(e), !0;
|
|
6879
6900
|
} catch (e) {
|
|
6880
6901
|
return u.logger.debug(f({ err: e })), !1;
|
|
@@ -6889,7 +6910,7 @@ class zt {
|
|
|
6889
6910
|
async getRefreshTokenData(s) {
|
|
6890
6911
|
if (s)
|
|
6891
6912
|
try {
|
|
6892
|
-
const e = U.refreshToken +
|
|
6913
|
+
const e = U.refreshToken + _.hash(s), t = await this.keyStorage.getKey(e);
|
|
6893
6914
|
return JSON.parse(t.data || "{}");
|
|
6894
6915
|
} catch (e) {
|
|
6895
6916
|
u.logger.debug(f({ err: e }));
|
|
@@ -6923,7 +6944,7 @@ class zt {
|
|
|
6923
6944
|
try {
|
|
6924
6945
|
const e = await this.validateJwt(s, "access");
|
|
6925
6946
|
if (this.persistAccessToken) {
|
|
6926
|
-
const t = U.accessToken +
|
|
6947
|
+
const t = U.accessToken + _.hash(e.payload.jti);
|
|
6927
6948
|
await this.keyStorage.getKey(t);
|
|
6928
6949
|
}
|
|
6929
6950
|
return e;
|
|
@@ -7129,15 +7150,15 @@ class nt extends Pe {
|
|
|
7129
7150
|
/**
|
|
7130
7151
|
* Value passed to the constructor. The `aud` claim must match it
|
|
7131
7152
|
*/
|
|
7132
|
-
|
|
7153
|
+
h(this, "audience");
|
|
7133
7154
|
/**
|
|
7134
7155
|
* Value passed to the constructor. If true, access tokens are saved
|
|
7135
7156
|
* in storage,
|
|
7136
7157
|
*/
|
|
7137
|
-
|
|
7138
|
-
|
|
7139
|
-
|
|
7140
|
-
|
|
7158
|
+
h(this, "persistAccessToken", !1);
|
|
7159
|
+
h(this, "keyStorage");
|
|
7160
|
+
h(this, "jwtSecretKeyFile", "");
|
|
7161
|
+
h(this, "jwtPublicKeyFile", "");
|
|
7141
7162
|
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
7163
|
if (this.jwtPublicKey || this.jwtPublicKeyFile)
|
|
7143
7164
|
throw new o(
|
|
@@ -7166,7 +7187,7 @@ class nt extends Pe {
|
|
|
7166
7187
|
* @returns Base64-url-encoded hash
|
|
7167
7188
|
*/
|
|
7168
7189
|
async hash(e) {
|
|
7169
|
-
return
|
|
7190
|
+
return _.hash(e);
|
|
7170
7191
|
}
|
|
7171
7192
|
/**
|
|
7172
7193
|
* If the given token is valid, the paylaod is returned. Otherwise
|
|
@@ -7187,7 +7208,7 @@ class nt extends Pe {
|
|
|
7187
7208
|
const r = await super.tokenAuthorized(e, t);
|
|
7188
7209
|
if (r && t == "access" && this.persistAccessToken && this.keyStorage)
|
|
7189
7210
|
try {
|
|
7190
|
-
const a = U.accessToken +
|
|
7211
|
+
const a = U.accessToken + _.hash(r.jti ? r.jti : r.sid ? r.sid : ""), n = await this.keyStorage.getKey(a), c = /* @__PURE__ */ new Date();
|
|
7191
7212
|
if (n.expires && ((i = n.expires) == null ? void 0 : i.getTime()) < c.getTime()) {
|
|
7192
7213
|
u.logger.error(f({ msg: "Access token expired in storage but not in JWT" }));
|
|
7193
7214
|
return;
|
|
@@ -7195,7 +7216,7 @@ class nt extends Pe {
|
|
|
7195
7216
|
} catch (a) {
|
|
7196
7217
|
u.logger.warn(f({
|
|
7197
7218
|
msg: "Couldn't get token from database - is it valid?",
|
|
7198
|
-
hashedAccessToken:
|
|
7219
|
+
hashedAccessToken: _.hash(r.jti ? r.jti : r.sid ? r.sid : "")
|
|
7199
7220
|
})), u.logger.debug(f({ err: a }));
|
|
7200
7221
|
return;
|
|
7201
7222
|
}
|
|
@@ -7227,12 +7248,12 @@ class Ht extends Ke {
|
|
|
7227
7248
|
),
|
|
7228
7249
|
...t
|
|
7229
7250
|
});
|
|
7230
|
-
|
|
7231
|
-
|
|
7232
|
-
|
|
7233
|
-
|
|
7234
|
-
|
|
7235
|
-
|
|
7251
|
+
h(this, "deviceAuthorizationUrl", "device_authorization");
|
|
7252
|
+
h(this, "userCreationType", "idToken");
|
|
7253
|
+
h(this, "userMatchField", "username");
|
|
7254
|
+
h(this, "idTokenMatchField", "sub");
|
|
7255
|
+
h(this, "userCreationFn");
|
|
7256
|
+
h(this, "userStorage");
|
|
7236
7257
|
this.client_id = r.client_id;
|
|
7237
7258
|
let i = {};
|
|
7238
7259
|
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 +7266,7 @@ class Ht extends Ke {
|
|
|
7245
7266
|
* @returns the Base64-URL-encoded random string
|
|
7246
7267
|
*/
|
|
7247
7268
|
randomValue(e) {
|
|
7248
|
-
return
|
|
7269
|
+
return _.randomValue(e);
|
|
7249
7270
|
}
|
|
7250
7271
|
/**
|
|
7251
7272
|
* Uses {@link @crossauth/backend!Crypto.sha256} to create hash a string using SHA256
|
|
@@ -7253,7 +7274,7 @@ class Ht extends Ke {
|
|
|
7253
7274
|
* @returns the Base64-URL-encoded hash
|
|
7254
7275
|
*/
|
|
7255
7276
|
async sha256(e) {
|
|
7256
|
-
return
|
|
7277
|
+
return _.sha256(e);
|
|
7257
7278
|
}
|
|
7258
7279
|
}
|
|
7259
7280
|
async function ot(S, s, e, t) {
|
|
@@ -7300,7 +7321,7 @@ class jt {
|
|
|
7300
7321
|
* Keyed on auth server base URL then audience. The latter may be ""
|
|
7301
7322
|
* for none
|
|
7302
7323
|
*/
|
|
7303
|
-
|
|
7324
|
+
h(this, "tokenConsumers");
|
|
7304
7325
|
this.tokenConsumers = [...s];
|
|
7305
7326
|
}
|
|
7306
7327
|
/**
|
|
@@ -7332,7 +7353,7 @@ class jt {
|
|
|
7332
7353
|
export {
|
|
7333
7354
|
ge as ApiKeyManager,
|
|
7334
7355
|
re as Authenticator,
|
|
7335
|
-
|
|
7356
|
+
_ as Crypto,
|
|
7336
7357
|
rt as DoubleSubmitCsrfToken,
|
|
7337
7358
|
Rt as DummyFactor2Authenticator,
|
|
7338
7359
|
Z as EmailAuthenticator,
|