@lcsf/acl
Version:
权限控制模块
221 lines • 23.7 kB
JavaScript
import { Injectable } from '@angular/core';
import { BehaviorSubject } from 'rxjs';
/**
*
* 务必在根目录注册 `LcAclModule.forRoot()` 才能使用服务
*/
export class LcAClService {
constructor() {
this.roles = [];
this.types = [];
this.permissionGroups = [];
this.authPaths = new Map();
this.full = false;
this.aclChange = new BehaviorSubject(null);
}
/** ACL变更通知 */
get change() {
return this.aclChange.asObservable();
}
/** 获取所有数据 */
get data() {
return {
full: this.full,
roles: this.roles,
permissionGroups: this.permissionGroups,
authPaths: this.authPaths,
};
}
parseLcACLType(val) {
let t;
if (typeof val === 'string') {
if (val.indexOf('::') > -1) {
// permissionGroup
t = { permissions: [val] };
}
else {
// role
t = { role: [val] };
}
}
else if (typeof val === 'object' && !Array.isArray(val)) {
t = Object.assign({}, val);
}
else if (Array.isArray(val)) {
if (val[0].toString().indexOf('::') > -1) {
t = { permissions: val };
}
else {
t = { role: val };
}
}
else {
t = { role: val == null ? [] : [val] };
}
return Object.assign({ except: false }, t);
}
/**
* 设置当前用户角色或权限能力(会先清除所有)
*/
set(value) {
this.full = false;
this.roles = [];
this.types = [];
this.permissionGroups = [];
this.authPaths = new Map();
this.add(value);
this.aclChange.next(value);
}
/**
* 标识当前用户为全量,即不受限
*/
setFull(val) {
this.full = val;
this.aclChange.next(val);
}
/**
* 设置当前用户角色(会先清除所有)
*/
setRole(roles) {
this.set({ role: roles });
}
/**
* 为当前用户增加角色或权限能力
*/
add(value) {
if (value.role && value.role.length > 0) {
this.roles.push(...value.role);
}
if (value.type && value.type.length > 0) {
this.types.push(...value.type);
}
if (value.permissionGroups && value.permissionGroups.length > 0) {
this.permissionGroups.push(...value.permissionGroups);
}
if (value.menus && value.menus.length > 0) {
this.authPaths = this.getAuthPaths(value.menus);
}
}
/**
* 为当前用户附加角色
*/
attachRole(roles) {
for (const val of roles) {
if (!this.roles.includes(val)) {
this.roles.push(val);
}
}
this.aclChange.next(this.data);
}
/**
* 为当前用户移除角色
*/
removeRole(roles) {
for (const val of roles) {
const idx = this.roles.indexOf(val);
if (idx !== -1) {
this.roles.splice(idx, 1);
}
}
this.aclChange.next(this.data);
}
/**
* 当前用户是否有对应角色,其实 `number` 表示Ability
*
* - 当 `full: true` 或参数 `null` 时返回 `true`
* - 若使用 `LcACLType` 参数,可以指定 `mode` 校验模式
*/
can(roleOrAbility) {
// debugger
const t = this.parseLcACLType(roleOrAbility);
let result = false;
if (this.full === true || !roleOrAbility) {
result = true;
}
else {
if (t.role && t.role.length > 0) {
if (typeof t.role === 'string') {
t.role = [t.role];
}
if (t.mode === 'allOf') {
result = t.role.every(v => {
if (v.toString().indexOf('-') > -1) {
let arr = v.split('-');
return this.roles.includes(arr[0]) && this.types.includes(arr[1]);
}
return this.roles.includes(v);
});
}
else {
result = t.role.some(v => {
if (v.toString().indexOf('-') > -1) {
let arr = v.split('-');
return this.roles.includes(arr[0]) && this.types.includes(arr[1]);
}
return this.roles.includes(v);
});
}
}
if (t.permissions && t.permissions.length > 0) {
if (typeof t.permissions === 'string') {
t.permissions = [t.permissions];
}
if (t.mode === 'allOf') {
result = t.permissions.every(v => this.permissionGroups.includes(v));
}
else {
result = t.permissions.some(v => this.permissionGroups.includes(v));
}
}
// 用户自定义额外字段
if (typeof t.extraAll !== 'undefined') {
result = result && t.extraAll;
}
if (typeof t.extraOne !== 'undefined') {
result = result || t.extraOne;
}
}
return t.except === true ? !result : result;
}
/**
* 路由权限拦截
* @param url
* @returns
*/
canAuthUrl(url) {
return this.authPaths.has(url);
}
/**
* 获取当前url对应是哪一个model_id
* @param url
* @returns
*/
getUrlModeId(url) {
return this.authPaths.get(url);
}
getAuthPaths(value) {
let reuslt = new Map();
value.forEach(authModel => {
let model_id = authModel.model_id;
reuslt.set(authModel.url, model_id);
let stack = [...authModel.menu_list];
while (stack.length !== 0) {
const item = stack.pop();
if (item) {
reuslt.set(item.url, model_id);
if (item.children) {
for (let i = item.children.length - 1; i >= 0; i--) {
stack.push(Object.assign({}, item.children[i]));
}
}
}
}
});
return reuslt;
}
}
LcAClService.decorators = [
{ type: Injectable }
];
LcAClService.ctorParameters = () => [];
//# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoibGMtYWNsLnNlcnZpY2UuanMiLCJzb3VyY2VSb290IjoiIiwic291cmNlcyI6WyIuLi8uLi8uLi8uLi9hY2wvc3JjL2xjLWFjbC5zZXJ2aWNlLnRzIl0sIm5hbWVzIjpbXSwibWFwcGluZ3MiOiJBQUFBLE9BQU8sRUFBRSxVQUFVLEVBQUUsTUFBTSxlQUFlLENBQUM7QUFDM0MsT0FBTyxFQUFFLGVBQWUsRUFBYyxNQUFNLE1BQU0sQ0FBQztBQUduRDs7O0dBR0c7QUFFSCxNQUFNLE9BQU8sWUFBWTtJQTZCdkI7UUEzQlEsVUFBSyxHQUFhLEVBQUUsQ0FBQztRQUNyQixVQUFLLEdBQWEsRUFBRSxDQUFDO1FBQ3JCLHFCQUFnQixHQUFhLEVBQUUsQ0FBQztRQUNoQyxjQUFTLEdBQXdCLElBQUksR0FBRyxFQUFFLENBQUM7UUFDM0MsU0FBSSxHQUFHLEtBQUssQ0FBQztRQUNiLGNBQVMsR0FBRyxJQUFJLGVBQWUsQ0FBNkIsSUFBSSxDQUFDLENBQUM7SUFzQjNELENBQUM7SUFwQmhCLGNBQWM7SUFDZCxJQUFJLE1BQU07UUFDUixPQUFPLElBQUksQ0FBQyxTQUFTLENBQUMsWUFBWSxFQUFFLENBQUM7SUFDdkMsQ0FBQztJQUVELGFBQWE7SUFDYixJQUFJLElBQUk7UUFNTixPQUFPO1lBQ0wsSUFBSSxFQUFFLElBQUksQ0FBQyxJQUFJO1lBQ2YsS0FBSyxFQUFFLElBQUksQ0FBQyxLQUFLO1lBQ2pCLGdCQUFnQixFQUFFLElBQUksQ0FBQyxnQkFBZ0I7WUFDdkMsU0FBUyxFQUFFLElBQUksQ0FBQyxTQUFTO1NBQzFCLENBQUM7SUFDSixDQUFDO0lBSU8sY0FBYyxDQUFDLEdBQXdCO1FBQzdDLElBQUksQ0FBWSxDQUFDO1FBQ2pCLElBQUksT0FBTyxHQUFHLEtBQUssUUFBUSxFQUFFO1lBQzNCLElBQUksR0FBRyxDQUFDLE9BQU8sQ0FBQyxJQUFJLENBQUMsR0FBRyxDQUFDLENBQUMsRUFBRTtnQkFDMUIsa0JBQWtCO2dCQUNsQixDQUFDLEdBQUcsRUFBRSxXQUFXLEVB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QUM7OztZQS9ORixVQUFVIiwic291cmNlc0NvbnRlbnQiOlsiaW1wb3J0IHsgSW5qZWN0YWJsZSB9IGZyb20gJ0Bhbmd1bGFyL2NvcmUnO1xuaW1wb3J0IHsgQmVoYXZpb3JTdWJqZWN0LCBPYnNlcnZhYmxlIH0gZnJvbSAncnhqcyc7XG5pbXBvcnQgeyBMY0FDTFR5cGUsIExjQUNMQ2FuVHlwZSwgTGNBQ0xDb25maWcsIEF1dGhQYXRoSXRlbSwgQXV0aE1vZGVsTGlzdCB9IGZyb20gJy4vbGMtYWNsLnR5cGUnO1xuXG4vKipcbiAqXG4gKiDliqHlv4XlnKjmoLnnm67lvZXms6jlhowgYExjQWNsTW9kdWxlLmZvclJvb3QoKWAg5omN6IO95L2/55So5pyN5YqhXG4gKi9cbkBJbmplY3RhYmxlKClcbmV4cG9ydCBjbGFzcyBMY0FDbFNlcnZpY2Uge1xuICBwcml2YXRlIG9wdGlvbnM6IExjQUNMQ29uZmlnO1xuICBwcml2YXRlIHJvbGVzOiBzdHJpbmdbXSA9IFtdO1xuICBwcml2YXRlIHR5cGVzOiBzdHJpbmdbXSA9IFtdO1xuICBwcml2YXRlIHBlcm1pc3Npb25Hcm91cHM6IHN0cmluZ1tdID0gW107XG4gIHByaXZhdGUgYXV0aFBhdGhzOiBNYXA8c3RyaW5nLCBzdHJpbmc+ID0gbmV3IE1hcCgpO1xuICBwcml2YXRlIGZ1bGwgPSBmYWxzZTtcbiAgcHJpdmF0ZSBhY2xDaGFuZ2UgPSBuZXcgQmVoYXZpb3JTdWJqZWN0PExjQUNMVHlwZSB8IGJvb2xlYW4gfCBudWxsPihudWxsKTtcblxuICAvKiogQUNM5Y+Y5pu06YCa55+lICovXG4gIGdldCBjaGFuZ2UoKTogT2JzZXJ2YWJsZTxMY0FDTFR5cGUgfCBib29sZWFuIHwgbnVsbD4ge1xuICAgIHJldHVybiB0aGlzLmFjbENoYW5nZS5hc09ic2VydmFibGUoKTtcbiAgfVxuXG4gIC8qKiDojrflj5bmiYDmnInmlbDmja4gKi9cbiAgZ2V0IGRhdGEoKToge1xuICAgIGZ1bGw6IGJvb2xlYW47XG4gICAgcm9sZXM6IHN0cmluZ1tdO1xuICAgIHBlcm1pc3Npb25Hcm91cHM6IHN0cmluZ1tdO1xuICAgIGF1dGhQYXRoczogTWFwPHN0cmluZywgc3RyaW5nPjtcbiAgfSB7XG4gICAgcmV0dXJuIHtcbiAgICAgIGZ1bGw6IHRoaXMuZnVsbCxcbiAgICAgIHJvbGVzOiB0aGlzLnJvbGVzLFxuICAgICAgcGVybWlzc2lvbkdyb3VwczogdGhpcy5wZXJtaXNzaW9uR3JvdXBzLFxuICAgICAgYXV0aFBhdGhzOiB0aGlzLmF1dGhQYXRocyxcbiAgICB9O1xuICB9XG5cbiAgY29uc3RydWN0b3IoKSB7fVxuXG4gIHByaXZhdGUgcGFyc2VMY0FDTFR5cGUodmFsOiBMY0FDTENhblR5cGUgfCBudWxsKTogTGNBQ0xUeXBlIHtcbiAgICBsZXQgdDogTGNBQ0xUeXBlO1xuICAgIGlmICh0eXBlb2YgdmFsID09PSAnc3RyaW5nJykge1xuICAgICAgaWYgKHZhbC5pbmRleE9mKCc6OicpID4gLTEpIHtcbiAgICAgICAgLy8gcGVybWlzc2lvbkdyb3VwXG4gICAgICAgIHQgPSB7IHBlcm1pc3Npb25zOiBbdmFsXSB9O1xuICAgICAgfSBlbHNlIHtcbiAgICAgICAgLy8gcm9sZVxuICAgICAgICB0ID0geyByb2xlOiBbdmFsXSB9O1xuICAgICAgfVxuICAgIH0gZWxzZSBpZiAodHlwZW9mIHZhbCA9PT0gJ29iamVjdCcgJiYgIUFycmF5LmlzQXJyYXkodmFsKSkge1xuICAgICAgdCA9IHsgLi4udmFsIH07XG4gICAgfSBlbHNlIGlmIChBcnJheS5pc0FycmF5KHZhbCkpIHtcbiAgICAgIGlmICh2YWxbMF0udG9TdHJpbmcoKS5pbmRleE9mKCc6OicpID4gLTEpIHtcbiAgICAgICAgdCA9IHsgcGVybWlzc2lvbnM6IHZhbCB9O1xuICAgICAgfSBlbHNlIHtcbiAgICAgICAgdCA9IHsgcm9sZTogdmFsIH07XG4gICAgICB9XG4gICAgfSBlbHNlIHtcbiAgICAgIHQgPSB7IHJvbGU6IHZhbCA9PSBudWxsID8gW10gOiBbdmFsXSB9O1xuICAgIH1cblxuICAgIHJldHVybiB7IGV4Y2VwdDogZmFsc2UsIC4uLnQgfTtcbiAgfVxuXG4gIC8qKlxuICAgKiDorr7nva7lvZPliY3nlKjmiLfop5LoibLmiJbmnYPpmZDog73lipvvvIjkvJrlhYjmuIXpmaTmiYDmnInvvIlcbiAgICovXG4gIHNldCh2YWx1ZTogTGNBQ0xUeXBlKTogdm9pZCB7XG4gICAgdGhpcy5mdWxsID0gZmFsc2U7XG4gICAgdGhpcy5yb2xlcyA9IFtdO1xuICAgIHRoaXMudHlwZXMgPSBbXTtcbiAgICB0aGlzLnBlcm1pc3Npb25Hcm91cHMgPSBbXTtcbiAgICB0aGlzLmF1dGhQYXRocyA9IG5ldyBNYXAoKTtcbiAgICB0aGlzLmFkZCh2YWx1ZSk7XG4gICAgdGhpcy5hY2xDaGFuZ2UubmV4dCh2YWx1ZSk7XG4gIH1cblxuICAvKipcbiAgICog5qCH6K+G5b2T5YmN55So5oi35Li65YWo6YeP77yM5Y2z5LiN5Y+X6ZmQXG4gICAqL1xuICBzZXRGdWxsKHZhbDogYm9vbGVhbik6IHZvaWQge1xuICAgIHRoaXMuZnVsbCA9IHZhbDtcbiAgICB0aGlzLmFjbENoYW5nZS5uZXh0KHZhbCk7XG4gIH1cblxuICAvKipcbiAgICog6K6+572u5b2T5YmN55So5oi36KeS6Imy77yI5Lya5YWI5riF6Zmk5omA5pyJ77yJXG4gICAqL1xuICBzZXRSb2xlKHJvbGVzOiBzdHJpbmdbXSk6IHZvaWQge1xuICAgIHRoaXMuc2V0KHsgcm9sZTogcm9sZXMgfSBhcyBMY0FDTFR5cGUpO1xuICB9XG5cbiAgLyoqXG4gICAqIOS4uuW9k+WJjeeUqOaIt+WinuWKoOinkuiJsuaIluadg+mZkOiDveWKm1xuICAgKi9cbiAgYWRkKHZhbHVlOiBMY0FDTFR5cGUpOiB2b2lkIHtcbiAgICBpZiAodmFsdWUucm9sZSAmJiB2YWx1ZS5yb2xlLmxlbmd0aCA+IDApIHtcbiAgICAgIHRoaXMucm9sZXMucHVzaCguLi52YWx1ZS5yb2xlKTtcbiAgICB9XG4gICAgaWYgKHZhbHVlLnR5cGUgJiYgdmFsdWUudHlwZS5sZW5ndGggPiAwKSB7XG4gICAgICB0aGlzLnR5cGVzLnB1c2goLi4udmFsdWUudHlwZSk7XG4gICAgfVxuICAgIGlmICh2YWx1ZS5wZXJtaXNzaW9uR3JvdXBzICYmIHZhbHVlLnBlcm1pc3Npb25Hcm91cHMubGVuZ3RoID4gMCkge1xuICAgICAgdGhpcy5wZXJtaXNzaW9uR3JvdXBzLnB1c2goLi4udmFsdWUucGVybWlzc2lvbkdyb3Vwcyk7XG4gICAgfVxuICAgIGlmICh2YWx1ZS5tZW51cyAmJiB2YWx1ZS5tZW51cy5sZW5ndGggPiAwKSB7XG4gICAgICB0aGlzLmF1dGhQYXRocyA9IHRoaXMuZ2V0QXV0aFBhdGhzKHZhbHVlLm1lbnVzKTtcbiAgICB9XG4gIH1cblxuICAvKipcbiAgICog5Li65b2T5YmN55So5oi36ZmE5Yqg6KeS6ImyXG4gICAqL1xuICBhdHRhY2hSb2xlKHJvbGVzOiBzdHJpbmdbXSk6IHZvaWQge1xuICAgIGZvciAoY29uc3QgdmFsIG9mIHJvbGVzKSB7XG4gICAgICBpZiAoIXRoaXMucm9sZXMuaW5jbHVkZXModmFsKSkge1xuICAgICAgICB0aGlzLnJvbGVzLnB1c2godmFsKTtcbiAgICAgIH1cbiAgICB9XG4gICAgdGhpcy5hY2xDaGFuZ2UubmV4dCh0aGlzLmRhdGEpO1xuICB9XG5cbiAgLyoqXG4gICAqIOS4uuW9k+WJjeeUqOaIt+enu+mZpOinkuiJslxuICAgKi9cbiAgcmVtb3ZlUm9sZShyb2xlczogc3RyaW5nW10pOiB2b2lkIHtcbiAgICBmb3IgKGNvbnN0IHZhbCBvZiByb2xlcykge1xuICAgICAgY29uc3QgaWR4ID0gdGhpcy5yb2xlcy5pbmRleE9mKHZhbCk7XG4gICAgICBpZiAoaWR4ICE9PSAtMSkge1xuICAgICAgICB0aGlzLnJvbGVzLnNwbGljZShpZHgsIDEpO1xuICAgICAgfVxuICAgIH1cbiAgICB0aGlzLmFjbENoYW5nZS5uZXh0KHRoaXMuZGF0YSk7XG4gIH1cblxuICAvKipcbiAgICog5b2T5YmN55So5oi35piv5ZCm5pyJ5a+55bqU6KeS6Imy77yM5YW25a6eIGBudW1iZXJgIOihqOekukFiaWxpdHlcbiAgICpcbiAgICogLSDlvZMgYGZ1bGw6IHRydWVgIOaIluWPguaVsCBgbnVsbGAg5pe26L+U5ZueIGB0cnVlYFxuICAgKiAtIOiLpeS9v+eUqCBgTGNBQ0xUeXBlYCDlj4LmlbDvvIzlj6/ku6XmjIflrpogYG1vZGVgIOagoemqjOaooeW8j1xuICAgKi9cbiAgY2FuKHJvbGVPckFiaWxpdHk6IExjQUNMQ2FuVHlwZSB8IG51bGwpOiBib29sZWFuIHtcbiAgICAvLyBkZWJ1Z2dlclxuICAgIGNvbnN0IHQgPSB0aGlzLnBhcnNlTGNBQ0xUeXBlKHJvbGVPckFiaWxpdHkpO1xuICAgIGxldCByZXN1bHQgPSBmYWxzZTtcbiAgICBpZiAodGhpcy5mdWxsID09PSB0cnVlIHx8ICFyb2xlT3JBYmlsaXR5KSB7XG4gICAgICByZXN1bHQgPSB0cnVlO1xuICAgIH0gZWxzZSB7XG4gICAgICBpZiAodC5yb2xlICYmIHQucm9sZS5sZW5ndGggPiAwKSB7XG4gICAgICAgIGlmICh0eXBlb2YgdC5yb2xlID09PSAnc3RyaW5nJykge1xuICAgICAgICAgIHQucm9sZSA9IFt0LnJvbGVdO1xuICAgICAgICB9XG4gICAgICAgIGlmICh0Lm1vZGUgPT09ICdhbGxPZicpIHtcbiAgICAgICAgICByZXN1bHQgPSB0LnJvbGUuZXZlcnkodiA9PiB7XG4gICAgICAgICAgICBpZiAodi50b1N0cmluZygpLmluZGV4T2YoJy0nKSA+IC0xKSB7XG4gICAgICAgICAgICAgIGxldCBhcnIgPSB2LnNwbGl0KCctJyk7XG4gICAgICAgICAgICAgIHJldHVybiB0aGlzLnJvbGVzLmluY2x1ZGVzKGFyclswXSkgJiYgdGhpcy50eXBlcy5pbmNsdWRlcyhhcnJbMV0pO1xuICAgICAgICAgICAgfVxuICAgICAgICAgICAgcmV0dXJuIHRoaXMucm9sZXMuaW5jbHVkZXModik7XG4gICAgICAgICAgfSk7XG4gICAgICAgIH0gZWxzZSB7XG4gICAgICAgICAgcmVzdWx0ID0gdC5yb2xlLnNvbWUodiA9PiB7XG4gICAgICAgICAgICBpZiAodi50b1N0cmluZygpLmluZGV4T2YoJy0nKSA+IC0xKSB7XG4gICAgICAgICAgICAgIGxldCBhcnIgPSB2LnNwbGl0KCctJyk7XG4gICAgICAgICAgICAgIHJldHVybiB0aGlzLnJvbGVzLmluY2x1ZGVzKGFyclswXSkgJiYgdGhpcy50eXBlcy5pbmNsdWRlcyhhcnJbMV0pO1xuICAgICAgICAgICAgfVxuICAgICAgICAgICAgcmV0dXJuIHRoaXMucm9sZXMuaW5jbHVkZXModik7XG4gICAgICAgICAgfSk7XG4gICAgICAgIH1cbiAgICAgIH1cbiAgICAgIGlmICh0LnBlcm1pc3Npb25zICYmIHQucGVybWlzc2lvbnMubGVuZ3RoID4gMCkge1xuICAgICAgICBpZiAodHlwZW9mIHQucGVybWlzc2lvbnMgPT09ICdzdHJpbmcnKSB7XG4gICAgICAgICAgdC5wZXJtaXNzaW9ucyA9IFt0LnBlcm1pc3Npb25zXTtcbiAgICAgICAgfVxuICAgICAgICBpZiAodC5tb2RlID09PSAnYWxsT2YnKSB7XG4gICAgICAgICAgcmVzdWx0ID0gdC5wZXJtaXNzaW9ucy5ldmVyeSh2ID0+IHRoaXMucGVybWlzc2lvbkdyb3Vwcy5pbmNsdWRlcyh2KSk7XG4gICAgICAgIH0gZWxzZSB7XG4gICAgICAgICAgcmVzdWx0ID0gdC5wZXJtaXNzaW9ucy5zb21lKHYgPT4gdGhpcy5wZXJtaXNzaW9uR3JvdXBzLmluY2x1ZGVzKHYpKTtcbiAgICAgICAgfVxuICAgICAgfVxuICAgICAgLy8g55So5oi36Ieq5a6a5LmJ6aKd5aSW5a2X5q61XG4gICAgICBpZiAodHlwZW9mIHQuZXh0cmFBbGwgIT09ICd1bmRlZmluZWQnKSB7XG4gICAgICAgIHJlc3VsdCA9IHJlc3VsdCAmJiB0LmV4dHJhQWxsO1xuICAgICAgfVxuICAgICAgaWYgKHR5cGVvZiB0LmV4dHJhT25lICE9PSAndW5kZWZpbmVkJykge1xuICAgICAgICByZXN1bHQgPSByZXN1bHQgfHwgdC5leHRyYU9uZTtcbiAgICAgIH1cbiAgICB9XG4gICAgcmV0dXJuIHQuZXhjZXB0ID09PSB0cnVlID8gIXJlc3VsdCA6IHJlc3VsdDtcbiAgfVxuICAvKipcbiAgICog6Lev55Sx5p2D6ZmQ5oum5oiqXG4gICAqIEBwYXJhbSB1cmxcbiAgICogQHJldHVybnNcbiAgICovXG4gIGNhbkF1dGhVcmwodXJsOiBzdHJpbmcpIHtcbiAgICByZXR1cm4gdGhpcy5hdXRoUGF0aHMuaGFzKHVybCk7XG4gIH1cbiAgLyoqXG4gICAqIOiOt+WPluW9k+WJjXVybOWvueW6lOaYr+WTquS4gOS4qm1vZGVsX2lkXG4gICAqIEBwYXJhbSB1cmxcbiAgICogQHJldHVybnNcbiAgICovXG4gIGdldFVybE1vZGVJZCh1cmw6IHN0cmluZykge1xuICAgIHJldHVybiB0aGlzLmF1dGhQYXRocy5nZXQodXJsKTtcbiAgfVxuXG4gIGdldEF1dGhQYXRocyh2YWx1ZTogQXV0aE1vZGVsTGlzdFtdKTogTWFwPHN0cmluZywgc3RyaW5nPiB7XG4gICAgbGV0IHJldXNsdCA9IG5ldyBNYXAoKTtcblxuICAgIHZhbHVlLmZvckVhY2goYXV0aE1vZGVsID0+IHtcbiAgICAgIGxldCBtb2RlbF9pZCA9IGF1dGhNb2RlbC5tb2RlbF9pZDtcbiAgICAgIHJldXNsdC5zZXQoYXV0aE1vZGVsLnVybCwgbW9kZWxfaWQpO1xuXG4gICAgICBsZXQgc3RhY2s6IEF1dGhQYXRoSXRlbVtdID0gWy4uLmF1dGhNb2RlbC5tZW51X2xpc3RdO1xuICAgICAgd2hpbGUgKHN0YWNrLmxlbmd0aCAhPT0gMCkge1xuICAgICAgICBjb25zdCBpdGVtID0gc3RhY2sucG9wKCk7XG5cbiAgICAgICAgaWYgKGl0ZW0pIHtcbiAgICAgICAgICByZXVzbHQuc2V0KGl0ZW0udXJsLCBtb2RlbF9pZCk7XG5cbiAgICAgICAgICBpZiAoaXRlbS5jaGlsZHJlbikge1xuICAgICAgICAgICAgZm9yIChsZXQgaSA9IGl0ZW0uY2hpbGRyZW4ubGVuZ3RoIC0gMTsgaSA+PSAwOyBpLS0pIHtcbiAgICAgICAgICAgICAgc3RhY2sucHVzaCh7IC4uLml0ZW0uY2hpbGRyZW5baV0gfSk7XG4gICAgICAgICAgICB9XG4gICAgICAgICAgfVxuICAgICAgICB9XG4gICAgICB9XG4gICAgfSk7XG4gICAgcmV0dXJuIHJldXNsdDtcbiAgfVxufVxuIl19