@opensesame/orchestrator-dom
Version:
Orchestrator DOM library with common MicroUI utils
156 lines (146 loc) • 6.41 kB
JavaScript
;
class Logger {
provider;
constructor(provider) {
this.provider = provider;
}
getDate() {
return new Date().toLocaleTimeString("en-US", { hour12: false });
}
setMessage(level, message, metadata) {
const hasMetadata = metadata !== undefined ? " " + JSON.stringify(metadata) : "";
return `[${level}][${this.getDate()}] ${message}${hasMetadata}`;
}
info(message, metadata) {
this.provider.log(this.setMessage("INFO", message, metadata));
}
warn(message, metadata) {
this.provider.log(this.setMessage("WARN", message, metadata));
}
error(message, metadata) {
this.provider.error(this.setMessage("ERROR", message, metadata));
}
}
const $logger = new Logger(console);
class Scope {
_state = {};
actions = {
register: this.setModule.bind(this),
};
get _actions() {
return this.actions;
}
set _actions(value) {
console.error("Cannot set the 'actions' property directly.");
}
getModule(module) {
return this._state[module];
}
setModule(module, state) {
// Convert kebab-case module names to camelCase
const parsedModule = module.replace(/-([a-z])/g, (match, letter) => letter.toUpperCase());
// Immutability: create a new object instead of modifying the existing one
const newState = {
...this._state,
[parsedModule]: {
...this._state[parsedModule],
...state,
},
};
this._state = newState;
}
registerModule(module) {
if (this.getModule(module)) {
$logger.error(`Module should be unique in scope. Set multiple or mirroring={true}. See: ${module}.`);
return;
}
this.setModule(module, {});
}
}
class Context {
scope;
constructor() {
this.scope = new Scope();
}
}
class Orchestrator {
context;
apiMap = new Map();
constructor(props) {
this.context = new Context();
$logger.info("[ORCHESTRATOR] Orchestrator successfully started.");
}
}
class Cookies {
static get(key) {
const cookies = document.cookie.split("; ");
for (const cookie of cookies) {
const [name, value] = cookie.split("=");
if (name === key) {
return decodeURIComponent(value);
}
}
return null;
}
}
function e(e){this.message=e;}e.prototype=new Error,e.prototype.name="InvalidCharacterError";var r="undefined"!=typeof window&&window.atob&&window.atob.bind(window)||function(r){var t=String(r).replace(/=+$/,"");if(t.length%4==1)throw new e("'atob' failed: The string to be decoded is not correctly encoded.");for(var n,o,a=0,i=0,c="";o=t.charAt(i++);~o&&(n=a%4?64*n+o:o,a++%4)?c+=String.fromCharCode(255&n>>(-2*a&6)):0)o="ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/=".indexOf(o);return c};function t(e){var t=e.replace(/-/g,"+").replace(/_/g,"/");switch(t.length%4){case 0:break;case 2:t+="==";break;case 3:t+="=";break;default:throw "Illegal base64url string!"}try{return function(e){return decodeURIComponent(r(e).replace(/(.)/g,(function(e,r){var t=r.charCodeAt(0).toString(16).toUpperCase();return t.length<2&&(t="0"+t),"%"+t})))}(t)}catch(e){return r(t)}}function n(e){this.message=e;}function o(e,r){if("string"!=typeof e)throw new n("Invalid token specified");var o=!0===(r=r||{}).header?0:1;try{return JSON.parse(t(e.split(".")[o]))}catch(e){throw new n("Invalid token specified: "+e.message)}}n.prototype=new Error,n.prototype.name="InvalidTokenError";
var WhiteListedIntegrations;
(function (WhiteListedIntegrations) {
WhiteListedIntegrations["GENERAL_CATALOG"] = "opensesamegeneralcatalog";
WhiteListedIntegrations["EFRONTPRO"] = "efrontpro";
})(WhiteListedIntegrations || (WhiteListedIntegrations = {}));
class JwtGuard {
multiAdminGuard() {
const accessToken = Cookies.get('okta_access_token');
if (!accessToken) {
$logger.warn("[JwtGuard] No access token found.");
return false;
}
const decodedAccessToken = this.extractData(accessToken);
const isIntegrationValid = this.isValidIntegrationKey(decodedAccessToken);
const orgsInContext = this.extractOrgUUIDs(decodedAccessToken);
$logger.info("[JwtGuard] MultiAdmin Guard check:", { isIntegrationValid, orgsInContext });
const hasMultiAdminCookie = this.checkForMultiAdminCookie();
return isIntegrationValid && orgsInContext.length >= 1 && hasMultiAdminCookie;
}
checkForMultiAdminCookie() {
const osOmsIdCookie = document.cookie.split('; ').find(row => row.startsWith('os_oms_id='));
return !!osOmsIdCookie;
}
extractData(token) {
const decoded = o(token);
if (!decoded) {
$logger.error("[JwtGuard] Failed to decode the JWT");
throw new Error("Failed to decode the JWT");
}
return decoded;
}
isValidIntegrationKey(decodedToken) {
const integrationKey = decodedToken['integration']?.toLowerCase();
$logger.info("[JwtGuard] Checking integration key validity");
return !integrationKey || integrationKey.includes(WhiteListedIntegrations.GENERAL_CATALOG);
}
extractOrgUUIDs(decodedToken) {
const orgs = decodedToken['orgs'] || [];
const validOrgsUUID = [];
for (const org of orgs) {
let [, , integration, orgUid] = org.split('.');
const hasValidIntegration = this.validateOrgIntegration(integration);
if (!hasValidIntegration)
return [];
validOrgsUUID.push(orgUid);
}
$logger.info("[JwtGuard] Extracted Org UUIDs:", validOrgsUUID);
return validOrgsUUID;
}
validateOrgIntegration(integrationKey) {
const isGeneralCatalog = integrationKey.toLowerCase().includes(WhiteListedIntegrations.GENERAL_CATALOG);
const isEFrontPro = integrationKey.toLowerCase().includes(WhiteListedIntegrations.EFRONTPRO);
$logger.info("[JwtGuard] Validating Org Integration:", { isGeneralCatalog, isEFrontPro });
return isGeneralCatalog || isEFrontPro;
}
}
exports.Cookies = Cookies;
exports.JwtGuard = JwtGuard;
exports.Orchestrator = Orchestrator;
//# sourceMappingURL=index.cjs.js.map