2016-01-28 10:58:12 -08:00
|
|
|
// A Config object provides information about how a specific app is
|
|
|
|
|
// configured.
|
|
|
|
|
// mount is the URL for the root of the API; includes http, domain, etc.
|
2016-02-05 14:38:09 -05:00
|
|
|
|
2016-05-18 12:12:30 +12:00
|
|
|
import AppCache from './cache';
|
2016-07-23 06:23:59 +02:00
|
|
|
import SchemaCache from './Controllers/SchemaCache';
|
|
|
|
|
import DatabaseController from './Controllers/DatabaseController';
|
2017-07-23 18:26:30 +02:00
|
|
|
import net from 'net';
|
2020-07-15 20:10:33 +02:00
|
|
|
import { IdempotencyOptions } from './Options/Definitions';
|
2016-02-24 15:55:11 -05:00
|
|
|
|
2016-03-30 19:50:08 -04:00
|
|
|
function removeTrailingSlash(str) {
|
|
|
|
|
if (!str) {
|
|
|
|
|
return str;
|
|
|
|
|
}
|
2018-09-01 13:58:06 -04:00
|
|
|
if (str.endsWith('/')) {
|
2017-01-11 12:31:40 -08:00
|
|
|
str = str.substr(0, str.length - 1);
|
2016-03-30 19:50:08 -04:00
|
|
|
}
|
|
|
|
|
return str;
|
|
|
|
|
}
|
|
|
|
|
|
2016-02-20 12:25:43 -05:00
|
|
|
export class Config {
|
2017-10-23 08:43:05 -04:00
|
|
|
static get(applicationId: string, mount: string) {
|
2016-12-07 15:17:05 -08:00
|
|
|
const cacheInfo = AppCache.get(applicationId);
|
2016-02-26 20:55:17 -08:00
|
|
|
if (!cacheInfo) {
|
2016-02-20 12:25:43 -05:00
|
|
|
return;
|
|
|
|
|
}
|
2017-10-23 08:43:05 -04:00
|
|
|
const config = new Config();
|
|
|
|
|
config.applicationId = applicationId;
|
2018-09-01 13:58:06 -04:00
|
|
|
Object.keys(cacheInfo).forEach(key => {
|
2017-10-23 08:43:05 -04:00
|
|
|
if (key == 'databaseController') {
|
2018-09-01 13:58:06 -04:00
|
|
|
const schemaCache = new SchemaCache(
|
|
|
|
|
cacheInfo.cacheController,
|
2017-10-23 08:43:05 -04:00
|
|
|
cacheInfo.schemaCacheTTL,
|
2018-09-01 13:58:06 -04:00
|
|
|
cacheInfo.enableSingleSchemaCache
|
|
|
|
|
);
|
2020-10-25 15:06:58 -05:00
|
|
|
config.database = new DatabaseController(cacheInfo.databaseController.adapter, schemaCache);
|
2017-10-23 08:43:05 -04:00
|
|
|
} else {
|
|
|
|
|
config[key] = cacheInfo[key];
|
|
|
|
|
}
|
|
|
|
|
});
|
|
|
|
|
config.mount = removeTrailingSlash(mount);
|
2020-10-25 15:06:58 -05:00
|
|
|
config.generateSessionExpiresAt = config.generateSessionExpiresAt.bind(config);
|
2018-09-01 13:58:06 -04:00
|
|
|
config.generateEmailVerifyTokenExpiresAt = config.generateEmailVerifyTokenExpiresAt.bind(
|
|
|
|
|
config
|
|
|
|
|
);
|
2017-10-23 08:43:05 -04:00
|
|
|
return config;
|
|
|
|
|
}
|
2016-02-09 19:31:23 -08:00
|
|
|
|
2017-10-23 08:43:05 -04:00
|
|
|
static put(serverConfiguration) {
|
|
|
|
|
Config.validate(serverConfiguration);
|
|
|
|
|
AppCache.put(serverConfiguration.appId, serverConfiguration);
|
|
|
|
|
Config.setupPasswordValidator(serverConfiguration.passwordPolicy);
|
|
|
|
|
return serverConfiguration;
|
2016-02-20 12:25:43 -05:00
|
|
|
}
|
2016-03-10 14:27:00 -08:00
|
|
|
|
2016-06-10 20:27:21 -07:00
|
|
|
static validate({
|
|
|
|
|
verifyUserEmails,
|
2016-06-28 19:25:44 -07:00
|
|
|
userController,
|
2016-06-10 20:27:21 -07:00
|
|
|
appName,
|
|
|
|
|
publicServerURL,
|
|
|
|
|
revokeSessionOnPasswordReset,
|
|
|
|
|
expireInactiveSessions,
|
|
|
|
|
sessionLength,
|
2017-10-02 06:23:09 -07:00
|
|
|
maxLimit,
|
2016-09-02 17:00:47 -07:00
|
|
|
emailVerifyTokenValidityDuration,
|
2016-11-17 22:07:51 +05:30
|
|
|
accountLockout,
|
2017-07-23 18:26:30 +02:00
|
|
|
passwordPolicy,
|
2017-10-26 15:35:07 -04:00
|
|
|
masterKeyIps,
|
|
|
|
|
masterKey,
|
|
|
|
|
readOnlyMasterKey,
|
2019-09-12 22:03:57 +01:00
|
|
|
allowHeaders,
|
2020-07-15 20:10:33 +02:00
|
|
|
idempotencyOptions,
|
2020-11-26 04:30:52 +11:00
|
|
|
emailVerifyTokenReuseIfValid,
|
2016-06-10 20:27:21 -07:00
|
|
|
}) {
|
2017-10-26 15:35:07 -04:00
|
|
|
if (masterKey === readOnlyMasterKey) {
|
|
|
|
|
throw new Error('masterKey and readOnlyMasterKey should be different');
|
|
|
|
|
}
|
|
|
|
|
|
2016-06-28 19:25:44 -07:00
|
|
|
const emailAdapter = userController.adapter;
|
|
|
|
|
if (verifyUserEmails) {
|
2018-09-01 13:58:06 -04:00
|
|
|
this.validateEmailConfiguration({
|
|
|
|
|
emailAdapter,
|
|
|
|
|
appName,
|
|
|
|
|
publicServerURL,
|
|
|
|
|
emailVerifyTokenValidityDuration,
|
2020-11-26 04:30:52 +11:00
|
|
|
emailVerifyTokenReuseIfValid,
|
2018-09-01 13:58:06 -04:00
|
|
|
});
|
2016-06-28 19:25:44 -07:00
|
|
|
}
|
2016-04-22 15:21:50 -07:00
|
|
|
|
2016-09-02 17:00:47 -07:00
|
|
|
this.validateAccountLockoutPolicy(accountLockout);
|
|
|
|
|
|
2016-11-17 22:07:51 +05:30
|
|
|
this.validatePasswordPolicy(passwordPolicy);
|
|
|
|
|
|
2016-06-10 20:27:21 -07:00
|
|
|
if (typeof revokeSessionOnPasswordReset !== 'boolean') {
|
2016-04-22 15:21:50 -07:00
|
|
|
throw 'revokeSessionOnPasswordReset must be a boolean value';
|
|
|
|
|
}
|
|
|
|
|
|
2016-06-10 20:27:21 -07:00
|
|
|
if (publicServerURL) {
|
2020-10-25 15:06:58 -05:00
|
|
|
if (!publicServerURL.startsWith('http://') && !publicServerURL.startsWith('https://')) {
|
2018-09-01 13:58:06 -04:00
|
|
|
throw 'publicServerURL should be a valid HTTPS URL starting with https://';
|
2016-03-30 19:50:08 -04:00
|
|
|
}
|
|
|
|
|
}
|
2016-06-10 20:27:21 -07:00
|
|
|
this.validateSessionConfiguration(sessionLength, expireInactiveSessions);
|
2017-07-23 18:26:30 +02:00
|
|
|
this.validateMasterKeyIps(masterKeyIps);
|
2017-10-02 06:23:09 -07:00
|
|
|
this.validateMaxLimit(maxLimit);
|
2019-09-12 22:03:57 +01:00
|
|
|
this.validateAllowHeaders(allowHeaders);
|
2020-07-15 20:10:33 +02:00
|
|
|
this.validateIdempotencyOptions(idempotencyOptions);
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
static validateIdempotencyOptions(idempotencyOptions) {
|
2020-10-02 00:19:26 +02:00
|
|
|
if (!idempotencyOptions) {
|
|
|
|
|
return;
|
|
|
|
|
}
|
2020-07-15 20:10:33 +02:00
|
|
|
if (idempotencyOptions.ttl === undefined) {
|
|
|
|
|
idempotencyOptions.ttl = IdempotencyOptions.ttl.default;
|
|
|
|
|
} else if (!isNaN(idempotencyOptions.ttl) && idempotencyOptions.ttl <= 0) {
|
|
|
|
|
throw 'idempotency TTL value must be greater than 0 seconds';
|
|
|
|
|
} else if (isNaN(idempotencyOptions.ttl)) {
|
|
|
|
|
throw 'idempotency TTL value must be a number';
|
|
|
|
|
}
|
|
|
|
|
if (!idempotencyOptions.paths) {
|
|
|
|
|
idempotencyOptions.paths = IdempotencyOptions.paths.default;
|
|
|
|
|
} else if (!(idempotencyOptions.paths instanceof Array)) {
|
|
|
|
|
throw 'idempotency paths must be of an array of strings';
|
|
|
|
|
}
|
2016-02-28 00:15:59 -05:00
|
|
|
}
|
2016-03-10 14:27:00 -08:00
|
|
|
|
2016-09-02 17:00:47 -07:00
|
|
|
static validateAccountLockoutPolicy(accountLockout) {
|
|
|
|
|
if (accountLockout) {
|
2018-09-01 13:58:06 -04:00
|
|
|
if (
|
|
|
|
|
typeof accountLockout.duration !== 'number' ||
|
|
|
|
|
accountLockout.duration <= 0 ||
|
|
|
|
|
accountLockout.duration > 99999
|
|
|
|
|
) {
|
2016-09-02 17:00:47 -07:00
|
|
|
throw 'Account lockout duration should be greater than 0 and less than 100000';
|
|
|
|
|
}
|
|
|
|
|
|
2018-09-01 13:58:06 -04:00
|
|
|
if (
|
|
|
|
|
!Number.isInteger(accountLockout.threshold) ||
|
|
|
|
|
accountLockout.threshold < 1 ||
|
|
|
|
|
accountLockout.threshold > 999
|
|
|
|
|
) {
|
2016-09-02 17:00:47 -07:00
|
|
|
throw 'Account lockout threshold should be an integer greater than 0 and less than 1000';
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
|
2016-11-17 22:07:51 +05:30
|
|
|
static validatePasswordPolicy(passwordPolicy) {
|
|
|
|
|
if (passwordPolicy) {
|
2018-09-01 13:58:06 -04:00
|
|
|
if (
|
|
|
|
|
passwordPolicy.maxPasswordAge !== undefined &&
|
2020-10-25 15:06:58 -05:00
|
|
|
(typeof passwordPolicy.maxPasswordAge !== 'number' || passwordPolicy.maxPasswordAge < 0)
|
2018-09-01 13:58:06 -04:00
|
|
|
) {
|
2016-11-21 21:16:38 +05:30
|
|
|
throw 'passwordPolicy.maxPasswordAge must be a positive number';
|
|
|
|
|
}
|
|
|
|
|
|
2018-09-01 13:58:06 -04:00
|
|
|
if (
|
|
|
|
|
passwordPolicy.resetTokenValidityDuration !== undefined &&
|
|
|
|
|
(typeof passwordPolicy.resetTokenValidityDuration !== 'number' ||
|
|
|
|
|
passwordPolicy.resetTokenValidityDuration <= 0)
|
|
|
|
|
) {
|
2016-11-17 22:07:51 +05:30
|
|
|
throw 'passwordPolicy.resetTokenValidityDuration must be a positive number';
|
|
|
|
|
}
|
|
|
|
|
|
2018-09-01 13:58:06 -04:00
|
|
|
if (passwordPolicy.validatorPattern) {
|
|
|
|
|
if (typeof passwordPolicy.validatorPattern === 'string') {
|
2020-10-25 15:06:58 -05:00
|
|
|
passwordPolicy.validatorPattern = new RegExp(passwordPolicy.validatorPattern);
|
2018-09-01 13:58:06 -04:00
|
|
|
} else if (!(passwordPolicy.validatorPattern instanceof RegExp)) {
|
2017-01-08 20:42:44 +05:30
|
|
|
throw 'passwordPolicy.validatorPattern must be a regex string or RegExp object.';
|
|
|
|
|
}
|
2016-11-17 22:07:51 +05:30
|
|
|
}
|
|
|
|
|
|
2018-09-01 13:58:06 -04:00
|
|
|
if (
|
|
|
|
|
passwordPolicy.validatorCallback &&
|
|
|
|
|
typeof passwordPolicy.validatorCallback !== 'function'
|
|
|
|
|
) {
|
2016-11-17 22:07:51 +05:30
|
|
|
throw 'passwordPolicy.validatorCallback must be a function.';
|
|
|
|
|
}
|
|
|
|
|
|
2018-09-01 13:58:06 -04:00
|
|
|
if (
|
|
|
|
|
passwordPolicy.doNotAllowUsername &&
|
|
|
|
|
typeof passwordPolicy.doNotAllowUsername !== 'boolean'
|
|
|
|
|
) {
|
2016-11-17 22:07:51 +05:30
|
|
|
throw 'passwordPolicy.doNotAllowUsername must be a boolean value.';
|
|
|
|
|
}
|
2016-11-29 22:31:52 +05:30
|
|
|
|
2018-09-01 13:58:06 -04:00
|
|
|
if (
|
|
|
|
|
passwordPolicy.maxPasswordHistory &&
|
|
|
|
|
(!Number.isInteger(passwordPolicy.maxPasswordHistory) ||
|
|
|
|
|
passwordPolicy.maxPasswordHistory <= 0 ||
|
|
|
|
|
passwordPolicy.maxPasswordHistory > 20)
|
|
|
|
|
) {
|
2016-11-29 22:31:52 +05:30
|
|
|
throw 'passwordPolicy.maxPasswordHistory must be an integer ranging 0 - 20';
|
|
|
|
|
}
|
2020-11-26 04:30:52 +11:00
|
|
|
|
|
|
|
|
if (
|
|
|
|
|
passwordPolicy.resetTokenReuseIfValid &&
|
|
|
|
|
typeof passwordPolicy.resetTokenReuseIfValid !== 'boolean'
|
|
|
|
|
) {
|
|
|
|
|
throw 'resetTokenReuseIfValid must be a boolean value';
|
|
|
|
|
}
|
|
|
|
|
if (passwordPolicy.resetTokenReuseIfValid && !passwordPolicy.resetTokenValidityDuration) {
|
|
|
|
|
throw 'You cannot use resetTokenReuseIfValid without resetTokenValidityDuration';
|
|
|
|
|
}
|
2016-11-17 22:07:51 +05:30
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
// if the passwordPolicy.validatorPattern is configured then setup a callback to process the pattern
|
|
|
|
|
static setupPasswordValidator(passwordPolicy) {
|
|
|
|
|
if (passwordPolicy && passwordPolicy.validatorPattern) {
|
2018-09-01 13:58:06 -04:00
|
|
|
passwordPolicy.patternValidator = value => {
|
2016-11-17 22:07:51 +05:30
|
|
|
return passwordPolicy.validatorPattern.test(value);
|
2018-09-01 13:58:06 -04:00
|
|
|
};
|
2016-11-17 22:07:51 +05:30
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
|
2018-09-01 13:58:06 -04:00
|
|
|
static validateEmailConfiguration({
|
|
|
|
|
emailAdapter,
|
|
|
|
|
appName,
|
|
|
|
|
publicServerURL,
|
|
|
|
|
emailVerifyTokenValidityDuration,
|
2020-11-26 04:30:52 +11:00
|
|
|
emailVerifyTokenReuseIfValid,
|
2018-09-01 13:58:06 -04:00
|
|
|
}) {
|
2016-07-05 12:08:46 -07:00
|
|
|
if (!emailAdapter) {
|
|
|
|
|
throw 'An emailAdapter is required for e-mail verification and password resets.';
|
|
|
|
|
}
|
|
|
|
|
if (typeof appName !== 'string') {
|
|
|
|
|
throw 'An app name is required for e-mail verification and password resets.';
|
|
|
|
|
}
|
|
|
|
|
if (typeof publicServerURL !== 'string') {
|
|
|
|
|
throw 'A public server url is required for e-mail verification and password resets.';
|
2016-02-28 00:15:59 -05:00
|
|
|
}
|
2016-07-19 01:10:36 -05:00
|
|
|
if (emailVerifyTokenValidityDuration) {
|
|
|
|
|
if (isNaN(emailVerifyTokenValidityDuration)) {
|
|
|
|
|
throw 'Email verify token validity duration must be a valid number.';
|
|
|
|
|
} else if (emailVerifyTokenValidityDuration <= 0) {
|
2018-09-01 13:58:06 -04:00
|
|
|
throw 'Email verify token validity duration must be a value greater than 0.';
|
2016-07-19 01:10:36 -05:00
|
|
|
}
|
|
|
|
|
}
|
2020-11-26 04:30:52 +11:00
|
|
|
if (emailVerifyTokenReuseIfValid && typeof emailVerifyTokenReuseIfValid !== 'boolean') {
|
|
|
|
|
throw 'emailVerifyTokenReuseIfValid must be a boolean value';
|
|
|
|
|
}
|
|
|
|
|
if (emailVerifyTokenReuseIfValid && !emailVerifyTokenValidityDuration) {
|
|
|
|
|
throw 'You cannot use emailVerifyTokenReuseIfValid without emailVerifyTokenValidityDuration';
|
|
|
|
|
}
|
2016-02-28 00:15:59 -05:00
|
|
|
}
|
2016-02-29 20:51:13 -05:00
|
|
|
|
2017-07-23 18:26:30 +02:00
|
|
|
static validateMasterKeyIps(masterKeyIps) {
|
|
|
|
|
for (const ip of masterKeyIps) {
|
2018-09-01 13:58:06 -04:00
|
|
|
if (!net.isIP(ip)) {
|
2017-07-23 18:26:30 +02:00
|
|
|
throw `Invalid ip in masterKeyIps: ${ip}`;
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
|
2016-03-30 19:50:08 -04:00
|
|
|
get mount() {
|
|
|
|
|
var mount = this._mount;
|
|
|
|
|
if (this.publicServerURL) {
|
|
|
|
|
mount = this.publicServerURL;
|
|
|
|
|
}
|
|
|
|
|
return mount;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
set mount(newValue) {
|
|
|
|
|
this._mount = newValue;
|
|
|
|
|
}
|
|
|
|
|
|
2016-05-06 20:50:45 +01:00
|
|
|
static validateSessionConfiguration(sessionLength, expireInactiveSessions) {
|
|
|
|
|
if (expireInactiveSessions) {
|
|
|
|
|
if (isNaN(sessionLength)) {
|
|
|
|
|
throw 'Session length must be a valid number.';
|
2018-09-01 13:58:06 -04:00
|
|
|
} else if (sessionLength <= 0) {
|
|
|
|
|
throw 'Session length must be a value greater than 0.';
|
2016-05-06 20:50:45 +01:00
|
|
|
}
|
2016-04-02 11:36:47 -04:00
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
|
2017-10-02 06:23:09 -07:00
|
|
|
static validateMaxLimit(maxLimit) {
|
|
|
|
|
if (maxLimit <= 0) {
|
2018-09-01 13:58:06 -04:00
|
|
|
throw 'Max limit must be a value greater than 0.';
|
2017-10-02 06:23:09 -07:00
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
|
2019-09-12 22:03:57 +01:00
|
|
|
static validateAllowHeaders(allowHeaders) {
|
|
|
|
|
if (![null, undefined].includes(allowHeaders)) {
|
|
|
|
|
if (Array.isArray(allowHeaders)) {
|
|
|
|
|
allowHeaders.forEach(header => {
|
|
|
|
|
if (typeof header !== 'string') {
|
|
|
|
|
throw 'Allow headers must only contain strings';
|
|
|
|
|
} else if (!header.trim().length) {
|
|
|
|
|
throw 'Allow headers must not contain empty strings';
|
|
|
|
|
}
|
|
|
|
|
});
|
|
|
|
|
} else {
|
|
|
|
|
throw 'Allow headers must be an array';
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
|
2016-07-19 01:10:36 -05:00
|
|
|
generateEmailVerifyTokenExpiresAt() {
|
|
|
|
|
if (!this.verifyUserEmails || !this.emailVerifyTokenValidityDuration) {
|
|
|
|
|
return undefined;
|
|
|
|
|
}
|
|
|
|
|
var now = new Date();
|
2020-10-25 15:06:58 -05:00
|
|
|
return new Date(now.getTime() + this.emailVerifyTokenValidityDuration * 1000);
|
2016-07-19 01:10:36 -05:00
|
|
|
}
|
|
|
|
|
|
2016-11-17 22:07:51 +05:30
|
|
|
generatePasswordResetTokenExpiresAt() {
|
2020-10-25 15:06:58 -05:00
|
|
|
if (!this.passwordPolicy || !this.passwordPolicy.resetTokenValidityDuration) {
|
2016-11-17 22:07:51 +05:30
|
|
|
return undefined;
|
|
|
|
|
}
|
|
|
|
|
const now = new Date();
|
2020-10-25 15:06:58 -05:00
|
|
|
return new Date(now.getTime() + this.passwordPolicy.resetTokenValidityDuration * 1000);
|
2016-11-17 22:07:51 +05:30
|
|
|
}
|
|
|
|
|
|
2016-04-02 11:36:47 -04:00
|
|
|
generateSessionExpiresAt() {
|
2016-05-06 20:50:45 +01:00
|
|
|
if (!this.expireInactiveSessions) {
|
|
|
|
|
return undefined;
|
|
|
|
|
}
|
2016-04-02 11:36:47 -04:00
|
|
|
var now = new Date();
|
2018-09-01 13:58:06 -04:00
|
|
|
return new Date(now.getTime() + this.sessionLength * 1000);
|
2016-04-02 11:36:47 -04:00
|
|
|
}
|
|
|
|
|
|
2016-02-25 19:04:27 -05:00
|
|
|
get invalidLinkURL() {
|
2020-10-25 15:06:58 -05:00
|
|
|
return this.customPages.invalidLink || `${this.publicServerURL}/apps/invalid_link.html`;
|
2016-02-25 19:04:27 -05:00
|
|
|
}
|
2016-03-10 14:27:00 -08:00
|
|
|
|
2017-05-10 14:02:16 +01:00
|
|
|
get invalidVerificationLinkURL() {
|
2018-09-01 13:58:06 -04:00
|
|
|
return (
|
|
|
|
|
this.customPages.invalidVerificationLink ||
|
|
|
|
|
`${this.publicServerURL}/apps/invalid_verification_link.html`
|
|
|
|
|
);
|
2017-05-10 14:02:16 +01:00
|
|
|
}
|
|
|
|
|
|
|
|
|
|
get linkSendSuccessURL() {
|
2018-09-01 13:58:06 -04:00
|
|
|
return (
|
2020-10-25 15:06:58 -05:00
|
|
|
this.customPages.linkSendSuccess || `${this.publicServerURL}/apps/link_send_success.html`
|
2018-09-01 13:58:06 -04:00
|
|
|
);
|
2017-05-10 14:02:16 +01:00
|
|
|
}
|
|
|
|
|
|
|
|
|
|
get linkSendFailURL() {
|
2020-10-25 15:06:58 -05:00
|
|
|
return this.customPages.linkSendFail || `${this.publicServerURL}/apps/link_send_fail.html`;
|
2017-05-10 14:02:16 +01:00
|
|
|
}
|
|
|
|
|
|
2016-02-25 19:04:27 -05:00
|
|
|
get verifyEmailSuccessURL() {
|
2018-09-01 13:58:06 -04:00
|
|
|
return (
|
|
|
|
|
this.customPages.verifyEmailSuccess ||
|
|
|
|
|
`${this.publicServerURL}/apps/verify_email_success.html`
|
|
|
|
|
);
|
2016-02-25 19:04:27 -05:00
|
|
|
}
|
2016-03-10 14:27:00 -08:00
|
|
|
|
2016-02-25 19:04:27 -05:00
|
|
|
get choosePasswordURL() {
|
2020-10-25 15:06:58 -05:00
|
|
|
return this.customPages.choosePassword || `${this.publicServerURL}/apps/choose_password`;
|
2016-02-27 10:51:12 -05:00
|
|
|
}
|
2016-03-10 14:27:00 -08:00
|
|
|
|
2016-02-27 10:51:12 -05:00
|
|
|
get requestResetPasswordURL() {
|
2019-09-12 22:03:57 +01:00
|
|
|
return `${this.publicServerURL}/apps/${this.applicationId}/request_password_reset`;
|
2016-02-25 19:04:27 -05:00
|
|
|
}
|
2016-03-10 14:27:00 -08:00
|
|
|
|
2016-02-25 19:04:27 -05:00
|
|
|
get passwordResetSuccessURL() {
|
2018-09-01 13:58:06 -04:00
|
|
|
return (
|
|
|
|
|
this.customPages.passwordResetSuccess ||
|
|
|
|
|
`${this.publicServerURL}/apps/password_reset_success.html`
|
|
|
|
|
);
|
2016-02-25 19:04:27 -05:00
|
|
|
}
|
2016-03-10 14:27:00 -08:00
|
|
|
|
2017-01-08 19:56:57 +01:00
|
|
|
get parseFrameURL() {
|
|
|
|
|
return this.customPages.parseFrameURL;
|
|
|
|
|
}
|
|
|
|
|
|
2016-02-25 19:04:27 -05:00
|
|
|
get verifyEmailURL() {
|
2016-02-29 20:51:13 -05:00
|
|
|
return `${this.publicServerURL}/apps/${this.applicationId}/verify_email`;
|
2016-02-25 19:04:27 -05:00
|
|
|
}
|
2016-05-06 20:50:45 +01:00
|
|
|
}
|
2016-01-28 10:58:12 -08:00
|
|
|
|
2016-02-20 12:25:43 -05:00
|
|
|
export default Config;
|
2016-01-28 10:58:12 -08:00
|
|
|
module.exports = Config;
|