Skip to content

Commit

Permalink
feat: expand the MFA recipe interface
Browse files Browse the repository at this point in the history
  • Loading branch information
porcellus committed Oct 4, 2023
1 parent 0942361 commit 19e79e6
Show file tree
Hide file tree
Showing 28 changed files with 949 additions and 154 deletions.
3 changes: 3 additions & 0 deletions lib/build/recipe/multifactorauth/api/implementation.d.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,3 @@
// @ts-nocheck
import { APIInterface } from "../";
export default function getAPIInterface(): APIInterface;
6 changes: 6 additions & 0 deletions lib/build/recipe/multifactorauth/api/implementation.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,6 @@
"use strict";
Object.defineProperty(exports, "__esModule", { value: true });
function getAPIInterface() {
return {};
}
exports.default = getAPIInterface;
8 changes: 8 additions & 0 deletions lib/build/recipe/multifactorauth/api/mfaInfo.d.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,8 @@
// @ts-nocheck
import { APIInterface, APIOptions } from "..";
export default function mfaInfo(
apiImplementation: APIInterface,
tenantId: string,
options: APIOptions,
userContext: any
): Promise<boolean>;
52 changes: 52 additions & 0 deletions lib/build/recipe/multifactorauth/api/mfaInfo.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,52 @@
"use strict";
/* Copyright (c) 2021, VRAI Labs and/or its affiliates. All rights reserved.
*
* This software is licensed under the Apache License, Version 2.0 (the
* "License") as published by the Apache Software Foundation.
*
* You may not use this file except in compliance with the License. You may
* obtain a copy of the License at http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
* WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
* License for the specific language governing permissions and limitations
* under the License.
*/
var __importDefault =
(this && this.__importDefault) ||
function (mod) {
return mod && mod.__esModule ? mod : { default: mod };
};
Object.defineProperty(exports, "__esModule", { value: true });
const utils_1 = require("../../../utils");
const session_1 = __importDefault(require("../../session"));
async function mfaInfo(apiImplementation, tenantId, options, userContext) {
let result;
if (apiImplementation.mfaInfoGET === undefined) {
return false;
}
const session = await session_1.default.getSession(
options.req,
options.res,
{ overrideGlobalClaimValidators: () => [], sessionRequired: true },
userContext
);
let response = await apiImplementation.mfaInfoGET({
tenantId,
options,
session,
userContext,
});
if (response.status === "OK") {
// if there is a new session, it will be
// automatically added to the response by the createNewSession function call
// inside the verifyEmailPOST function.
result = { status: "OK" };
} else {
result = response;
}
utils_1.send200Response(options.res, result);
return true;
}
exports.default = mfaInfo;
2 changes: 2 additions & 0 deletions lib/build/recipe/multifactorauth/constants.d.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,2 @@
// @ts-nocheck
export declare const GET_MFA_INFO = "/mfa-info";
18 changes: 18 additions & 0 deletions lib/build/recipe/multifactorauth/constants.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,18 @@
"use strict";
/* Copyright (c) 2021, VRAI Labs and/or its affiliates. All rights reserved.
*
* This software is licensed under the Apache License, Version 2.0 (the
* "License") as published by the Apache Software Foundation.
*
* You may not use this file except in compliance with the License. You may
* obtain a copy of the License at http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
* WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
* License for the specific language governing permissions and limitations
* under the License.
*/
Object.defineProperty(exports, "__esModule", { value: true });
exports.GET_MFA_INFO = void 0;
exports.GET_MFA_INFO = "/mfa-info";
5 changes: 5 additions & 0 deletions lib/build/recipe/multifactorauth/error.d.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,5 @@
// @ts-nocheck
import STError from "../../error";
export default class SessionError extends STError {
constructor(options: { type: "BAD_INPUT_ERROR"; message: string });
}
29 changes: 29 additions & 0 deletions lib/build/recipe/multifactorauth/error.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,29 @@
"use strict";
/* Copyright (c) 2021, VRAI Labs and/or its affiliates. All rights reserved.
*
* This software is licensed under the Apache License, Version 2.0 (the
* "License") as published by the Apache Software Foundation.
*
* You may not use this file except in compliance with the License. You may
* obtain a copy of the License at http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
* WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
* License for the specific language governing permissions and limitations
* under the License.
*/
var __importDefault =
(this && this.__importDefault) ||
function (mod) {
return mod && mod.__esModule ? mod : { default: mod };
};
Object.defineProperty(exports, "__esModule", { value: true });
const error_1 = __importDefault(require("../../error"));
class SessionError extends error_1.default {
constructor(options) {
super(Object.assign({}, options));
this.fromRecipe = "multifactorauth";
}
}
exports.default = SessionError;
36 changes: 36 additions & 0 deletions lib/build/recipe/multifactorauth/index.d.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,36 @@
// @ts-nocheck
import Recipe from "./recipe";
import { RecipeInterface, APIOptions, APIInterface } from "./types";
import { MultiFactorAuthClaim } from "./multiFactorAuthClaim";
import { SessionContainerInterface } from "../session/types";
export default class Wrapper {
static init: typeof Recipe.init;
static MultiFactorAuthClaim: import("./multiFactorAuthClaim").MultiFactorAuthClaimClass;
static enableFactorForUser(
userId: string,
factorId: string,
userContext?: any
): Promise<{
status: "OK";
newEnabledFactors: string[];
}>;
static enableFactorForTenant(
tenantId: string,
factorId: string,
userContext?: any
): Promise<{
status: "OK";
newEnabledFactors: string[];
}>;
static completeFactorInSession(
session: SessionContainerInterface,
factor: string,
userContext?: any
): Promise<void>;
}
export declare let init: typeof Recipe.init;
export declare let enableFactorForTenant: typeof Wrapper.enableFactorForTenant;
export declare let enableFactorForUser: typeof Wrapper.enableFactorForUser;
export declare let completeFactorInSession: typeof Wrapper.completeFactorInSession;
export { MultiFactorAuthClaim };
export type { RecipeInterface, APIOptions, APIInterface };
62 changes: 62 additions & 0 deletions lib/build/recipe/multifactorauth/index.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,62 @@
"use strict";
/* Copyright (c) 2021, VRAI Labs and/or its affiliates. All rights reserved.
*
* This software is licensed under the Apache License, Version 2.0 (the
* "License") as published by the Apache Software Foundation.
*
* You may not use this file except in compliance with the License. You may
* obtain a copy of the License at http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
* WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
* License for the specific language governing permissions and limitations
* under the License.
*/
var __importDefault =
(this && this.__importDefault) ||
function (mod) {
return mod && mod.__esModule ? mod : { default: mod };
};
Object.defineProperty(exports, "__esModule", { value: true });
exports.MultiFactorAuthClaim = exports.completeFactorInSession = exports.enableFactorForUser = exports.enableFactorForTenant = exports.init = void 0;
const recipe_1 = __importDefault(require("./recipe"));
const multiFactorAuthClaim_1 = require("./multiFactorAuthClaim");
Object.defineProperty(exports, "MultiFactorAuthClaim", {
enumerable: true,
get: function () {
return multiFactorAuthClaim_1.MultiFactorAuthClaim;
},
});
class Wrapper {
static async enableFactorForUser(userId, factorId, userContext) {
const recipeInstance = recipe_1.default.getInstanceOrThrowError();
return recipeInstance.recipeInterfaceImpl.enableFactorForUser({
userId,
factorId,
userContext: userContext === undefined ? {} : userContext,
});
}
static async enableFactorForTenant(tenantId, factorId, userContext) {
const recipeInstance = recipe_1.default.getInstanceOrThrowError();
return recipeInstance.recipeInterfaceImpl.enableFactorForTenant({
tenantId,
factorId,
userContext: userContext === undefined ? {} : userContext,
});
}
static async completeFactorInSession(session, factor, userContext) {
return recipe_1.default.getInstanceOrThrowError().completeFactorInSession({
session,
factor,
userContext: userContext !== null && userContext !== void 0 ? userContext : {},
});
}
}
exports.default = Wrapper;
Wrapper.init = recipe_1.default.init;
Wrapper.MultiFactorAuthClaim = multiFactorAuthClaim_1.MultiFactorAuthClaim;
exports.init = Wrapper.init;
exports.enableFactorForTenant = Wrapper.enableFactorForTenant;
exports.enableFactorForUser = Wrapper.enableFactorForUser;
exports.completeFactorInSession = Wrapper.completeFactorInSession;
50 changes: 50 additions & 0 deletions lib/build/recipe/multifactorauth/multiFactorAuthClaim.d.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,50 @@
// @ts-nocheck
import RecipeUserId from "../../recipeUserId";
import { SessionClaim } from "../session/claims";
import { JSONObject } from "../usermetadata";
import { MFAClaimValue, MFARequirementList } from "./types";
/**
* We include "Class" in the class name, because it makes it easier to import the right thing (the instance) instead of this.
* */
export declare class MultiFactorAuthClaimClass extends SessionClaim<MFAClaimValue> {
constructor(key?: string);
buildNextArray(_completedClaims: MFAClaimValue["c"], _requirements: MFARequirementList): never[];
fetchValue: (
_userId: string,
_recipeUserId: RecipeUserId,
_tenantId: string | undefined,
_userContext: any
) => {
c: {};
n: never[];
};
addToPayload_internal: (
payload: JSONObject,
value: MFAClaimValue
) => {
[x: string]:
| string
| number
| boolean
| JSONObject
| import("../../types").JSONArray
| {
c: {
[x: string]: number;
};
n: string[];
}
| null
| undefined;
};
removeFromPayload: (
payload: JSONObject
) => {
[x: string]: import("../../types").JSONValue;
};
removeFromPayloadByMerge_internal: () => {
[x: string]: null;
};
getValueFromPayload: (payload: JSONObject) => MFAClaimValue;
}
export declare const MultiFactorAuthClaim: MultiFactorAuthClaimClass;
49 changes: 49 additions & 0 deletions lib/build/recipe/multifactorauth/multiFactorAuthClaim.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,49 @@
"use strict";
Object.defineProperty(exports, "__esModule", { value: true });
exports.MultiFactorAuthClaim = exports.MultiFactorAuthClaimClass = void 0;
const claims_1 = require("../session/claims");
/**
* We include "Class" in the class name, because it makes it easier to import the right thing (the instance) instead of this.
* */
class MultiFactorAuthClaimClass extends claims_1.SessionClaim {
constructor(key) {
super(key !== null && key !== void 0 ? key : "st-mfa");
this.fetchValue = (_userId, _recipeUserId, _tenantId, _userContext) => {
return {
c: {},
n: [],
};
};
this.addToPayload_internal = (payload, value) => {
const prevValue = payload[this.key];
return Object.assign(Object.assign({}, payload), {
[this.key]: {
c: Object.assign(
Object.assign({}, prevValue === null || prevValue === void 0 ? void 0 : prevValue.c),
value.c
),
n: value.n,
},
});
};
this.removeFromPayload = (payload) => {
const retVal = Object.assign({}, payload);
delete retVal[this.key];
return retVal;
};
this.removeFromPayloadByMerge_internal = () => {
return {
[this.key]: null,
};
};
this.getValueFromPayload = (payload) => {
return payload[this.key];
};
}
buildNextArray(_completedClaims, _requirements) {
// TODO
return [];
}
}
exports.MultiFactorAuthClaimClass = MultiFactorAuthClaimClass;
exports.MultiFactorAuthClaim = new MultiFactorAuthClaimClass();
46 changes: 46 additions & 0 deletions lib/build/recipe/multifactorauth/recipe.d.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,46 @@
// @ts-nocheck
import { BaseRequest, BaseResponse } from "../../framework";
import NormalisedURLPath from "../../normalisedURLPath";
import RecipeModule from "../../recipeModule";
import STError from "../../error";
import { APIHandled, HTTPMethod, NormalisedAppinfo, RecipeListFunction } from "../../types";
import { ProviderInput } from "../thirdparty/types";
import { APIInterface, RecipeInterface, TypeInput, TypeNormalisedInput } from "./types";
import { SessionContainerInterface } from "../session/types";
export default class Recipe extends RecipeModule {
private static instance;
static RECIPE_ID: string;
config: TypeNormalisedInput;
recipeInterfaceImpl: RecipeInterface;
apiImpl: APIInterface;
isInServerlessEnv: boolean;
staticThirdPartyProviders: ProviderInput[];
getAllowedDomainsForTenantId?: (tenantId: string, userContext: any) => Promise<string[] | undefined>;
constructor(recipeId: string, appInfo: NormalisedAppinfo, isInServerlessEnv: boolean, config?: TypeInput);
static getInstanceOrThrowError(): Recipe;
static getInstance(): Recipe | undefined;
static init(config?: TypeInput): RecipeListFunction;
static reset(): void;
getAPIsHandled: () => APIHandled[];
handleAPIRequest: (
id: string,
tenantId: string,
req: BaseRequest,
res: BaseResponse,
_: NormalisedURLPath,
__: HTTPMethod,
userContext: any
) => Promise<boolean>;
handleError: (err: STError, _: BaseRequest, __: BaseResponse) => Promise<void>;
getAllCORSHeaders: () => string[];
isErrorFromThisRecipe: (err: any) => err is STError;
completeFactorInSession({
session,
factor,
userContext,
}: {
session: SessionContainerInterface;
factor: string;
userContext: any;
}): Promise<void>;
}
Loading

0 comments on commit 19e79e6

Please sign in to comment.