kui-shell
Version:
This is the monorepo for Kui, the hybrid command-line/GUI electron-based Kubernetes tool
411 lines • 21.3 kB
JavaScript
;
var __awaiter = (this && this.__awaiter) || function (thisArg, _arguments, P, generator) {
function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
return new (P || (P = Promise))(function (resolve, reject) {
function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
step((generator = generator.apply(thisArg, _arguments || [])).next());
});
};
Object.defineProperty(exports, "__esModule", { value: true });
const debug_1 = require("debug");
const dom_1 = require("./util/dom");
const table_1 = require("./models/table");
const table_2 = require("./views/table");
const sidecar_1 = require("./views/sidecar");
const sidecar_selector_1 = require("./views/sidecar-selector");
const modes_1 = require("./views/registrar/modes");
const exec_1 = require("../repl/exec");
const types_1 = require("../util/types");
const entity_1 = require("../models/entity");
const types_2 = require("../models/mmr/types");
const content_types_1 = require("../models/mmr/content-types");
const debug = debug_1.default('webapp/picture-in-picture');
function isDirectViewEntity(direct) {
return sidecar_1.isCustomSpec(direct);
}
function isToggle(result) {
return result && Array.isArray(result.toggle);
}
const callDirect = (tab, makeView, entity, execOptions) => __awaiter(void 0, void 0, void 0, function* () {
if (typeof makeView === 'string') {
debug('makeView as string');
if (execOptions && execOptions.exec === 'pexec') {
return exec_1.pexec(makeView, execOptions);
}
else if (execOptions && execOptions.exec === 'rexec') {
return exec_1.rexec(makeView, execOptions);
}
else {
return exec_1.qexec(makeView, undefined, undefined, Object.assign({}, execOptions, { rethrowErrors: true }));
}
}
else if (typeof makeView === 'function') {
debug('makeView as function');
return Promise.resolve(makeView(tab, entity));
}
else if (isDirectViewEntity(makeView)) {
const combined = Object.assign({}, entity, makeView);
return combined;
}
else {
const provider = yield Promise.resolve().then(() => require('@kui-shell/plugin-' + makeView.plugin));
try {
return provider[makeView.operation](tab, makeView.parameters, entity);
}
catch (err) {
console.error('could not render mode', makeView.operation, err);
}
}
});
function isHighLevelMode(mode) {
return types_2.isButton(mode) || content_types_1.hasContent(mode);
}
function isSidecarMode(entity) {
const mode = entity;
return mode.mode !== undefined && (isHighLevelMode(mode) || mode.direct !== undefined || mode.command !== undefined);
}
exports.isSidecarMode = isSidecarMode;
exports.rawCSS = {
buttons: '.sidecar-top-stripe .sidecar-bottom-stripe-left-bits'
};
exports.css = {
buttons: (tab) => sidecar_selector_1.default(tab, exports.rawCSS.buttons),
backContainer: (tab) => sidecar_selector_1.default(tab, '.sidecar-bottom-stripe .sidecar-bottom-stripe-left-bits .sidecar-bottom-stripe-back-bits'),
backButton: (tab) => sidecar_selector_1.default(tab, '.sidecar-bottom-stripe .sidecar-bottom-stripe-left-bits .sidecar-bottom-stripe-back-button'),
button: 'sidecar-bottom-stripe-button',
tab: ['bx--tabs__nav-item', 'sidecar-bottom-stripe-button'],
buttonAction: 'bx--tabs__nav-link',
buttonActingAsButton: 'sidecar-bottom-stripe-button-as-button',
buttonActingAsRadioButton: 'sidecar-bottom-stripe-button-as-radio-button',
modeContainer: (tab) => sidecar_selector_1.default(tab, '.sidecar-top-stripe .sidecar-bottom-stripe-left-bits .sidecar-bottom-stripe-mode-bits .bx--tabs__nav'),
bottomContainer: (tab) => sidecar_selector_1.default(tab, '.sidecar-bottom-stripe-toolbar .sidecar-bottom-stripe-mode-bits'),
active: 'bx--tabs__nav-item--selected',
selected: 'selected',
hidden: 'hidden'
};
const _addModeButton = (tab, modeStripe, bottomStripe, opts, entity, show) => {
const { mode, label, defaultMode } = opts;
const isTab = (content_types_1.hasContent(opts) && !types_2.isButton(opts)) ||
(!isHighLevelMode(opts) && !(opts.flush === 'right' || opts.flush === 'weak'));
const button = document.createElement(isTab ? 'li' : 'a');
const buttonAction = document.createElement(isTab ? 'a' : 'span');
button.appendChild(buttonAction);
button.setAttribute('role', 'presentation');
buttonAction.setAttribute('role', 'tab');
if (isTab) {
buttonAction.setAttribute('href', '#');
buttonAction.classList.add('kui--tab-navigatable', 'kui--notab-when-sidecar-hidden');
}
else {
button.setAttribute('href', '#');
button.classList.add('kui--tab-navigatable', 'kui--notab-when-sidecar-hidden');
}
if (!isHighLevelMode(opts)) {
if (opts.visibleWhen && opts.visibleWhen !== show) {
return;
}
else if (opts.visibleWhen) {
button.setAttribute('data-visible-when', opts.visibleWhen);
}
if (opts.actAsButton) {
button.classList.add(exports.css.buttonActingAsButton);
if (opts.radioButton) {
button.classList.add(exports.css.buttonActingAsRadioButton);
}
if (opts.selected) {
button.classList.add(exports.css.selected);
}
if (opts.selectionController) {
opts.selectionController.on('change', (selected) => {
const op = selected ? 'add' : 'remove';
button.classList[op](exports.css.selected);
});
}
}
if (opts.data) {
for (const attr in opts.data) {
button.setAttribute(attr, opts.data[attr]);
}
}
}
if ((((!show || show === 'default') && defaultMode) || show === mode) &&
(isHighLevelMode(opts) || !opts.actAsButton)) {
button.classList.add(exports.css.active);
}
button.setAttribute('data-mode', mode);
const fontawesome = !isHighLevelMode(opts) && opts.fontawesome;
if (fontawesome) {
const iconContainer = document.createElement('span');
const icon = document.createElement('i');
if (/trash/.test(fontawesome)) {
icon.innerHTML =
'<svg focusable="false" preserveAspectRatio="xMidYMid meet" style="will-change: transform;" xmlns="http://www.w3.org/2000/svg" width="16" height="16" viewBox="0 0 16 16" aria-hidden="true"><path d="M6 6h1v6H6zm3 0h1v6H9z"></path><path d="M2 3v1h1v10c0 .6.4 1 1 1h8c.6 0 1-.4 1-1V4h1V3H2zm2 11V4h8v10H4zM6 1h4v1H6z"></path></svg>';
}
else if (/fa-unlock/.test(fontawesome)) {
icon.innerHTML =
'<svg focusable="false" preserveAspectRatio="xMidYMid meet" style="will-change: transform;" xmlns="http://www.w3.org/2000/svg" width="16" height="16" viewBox="0 0 16 16" aria-hidden="true"><path d="M12 7H6V4c0-1.1.9-2 2-2s2 .9 2 2h1c0-1.7-1.3-3-3-3S5 2.3 5 4v3H4c-.6 0-1 .4-1 1v6c0 .6.4 1 1 1h8c.6 0 1-.4 1-1V8c0-.6-.4-1-1-1zm0 7H4V8h8v6z"></path></svg>';
}
else if (/fa-exclamation/.test(fontawesome)) {
icon.innerHTML =
'<svg focusable="false" preserveAspectRatio="xMidYMid meet" style="will-change: transform;" xmlns="http://www.w3.org/2000/svg" width="20" height="20" viewBox="0 0 20 20" aria-hidden="true"><path d="M10 1c-5 0-9 4-9 9s4 9 9 9 9-4 9-9-4-9-9-9zm-.8 4h1.5v7H9.2V5zm.8 11c-.6 0-1-.4-1-1s.4-1 1-1 1 .4 1 1-.4 1-1 1z"></path><path d="M9.2 5h1.5v7H9.2V5zm.8 11c-.6 0-1-.4-1-1s.4-1 1-1 1 .4 1 1-.4 1-1 1z" data-icon-path="inner-path" opacity="0"></path></svg>';
}
else if (/search-plus/.test(fontawesome)) {
icon.innerHTML =
'<svg focusable="false" preserveAspectRatio="xMidYMid meet" style="will-change: transform;" xmlns="http://www.w3.org/2000/svg" width="20" height="20" viewBox="0 0 32 32" aria-hidden="true"><path d="M19 13h-4V9h-2v4H9v2h4v4h2v-4h4v-2z"></path><path d="M22.45 21A10.87 10.87 0 0 0 25 14a11 11 0 1 0-11 11 10.87 10.87 0 0 0 7-2.55L28.59 30 30 28.59zM14 23a9 9 0 1 1 9-9 9 9 0 0 1-9 9z"></path></svg>';
}
else if (/search-minus/.test(fontawesome)) {
icon.innerHTML =
'<svg focusable="false" preserveAspectRatio="xMidYMid meet" style="will-change: transform;" xmlns="http://www.w3.org/2000/svg" width="20" height="20" viewBox="0 0 32 32" aria-hidden="true"><path d="M9 13h10v2H9z"></path><path d="M22.45 21A10.87 10.87 0 0 0 25 14a11 11 0 1 0-11 11 10.87 10.87 0 0 0 7-2.55L28.59 30 30 28.59zM14 23a9 9 0 1 1 9-9 9 9 0 0 1-9 9z"></path></svg>';
}
else if (/chart-bar/.test(fontawesome)) {
icon.innerHTML =
'<svg focusable="false" preserveAspectRatio="xMidYMid meet" style="will-change: transform;" xmlns="http://www.w3.org/2000/svg" width="20" height="20" viewBox="0 0 32 32" aria-hidden="true"><path d="M27 28V6h-8v22h-4V14H7v14H4V2H2v26a2 2 0 0 0 2 2h26v-2zm-14 0H9V16h4zm12 0h-4V8h4z"></path></svg>';
}
else if (/^fas fa-th$/.test(fontawesome)) {
icon.innerHTML =
'<svg focusable="false" preserveAspectRatio="xMidYMid meet" style="will-change: transform;" xmlns="http://www.w3.org/2000/svg" width="20" height="20" viewBox="0 0 32 32" aria-hidden="true"><path d="M12 4H6a2 2 0 0 0-2 2v6a2 2 0 0 0 2 2h6a2 2 0 0 0 2-2V6a2 2 0 0 0-2-2zm0 8H6V6h6zm14-8h-6a2 2 0 0 0-2 2v6a2 2 0 0 0 2 2h6a2 2 0 0 0 2-2V6a2 2 0 0 0-2-2zm0 8h-6V6h6zm-14 6H6a2 2 0 0 0-2 2v6a2 2 0 0 0 2 2h6a2 2 0 0 0 2-2v-6a2 2 0 0 0-2-2zm0 8H6v-6h6zm14-8h-6a2 2 0 0 0-2 2v6a2 2 0 0 0 2 2h6a2 2 0 0 0 2-2v-6a2 2 0 0 0-2-2zm0 8h-6v-6h6z"></path></svg>';
}
else {
icon.className = fontawesome;
}
button.classList.add('graphical-icon');
button.appendChild(iconContainer);
iconContainer.appendChild(icon);
iconContainer.classList.add('icon-container');
if (!isHighLevelMode(opts) && opts.labelBelow) {
const labelContainer = document.createElement('div');
labelContainer.classList.add('deemphasize');
labelContainer.innerText = label;
iconContainer.appendChild(labelContainer);
}
}
else {
buttonAction.innerText = label || mode;
}
let container = modeStripe;
if (!isTab) {
let fillContainer = bottomStripe.querySelector('.fill-container.flush-right[role="tablist"]');
if (!fillContainer) {
fillContainer = document.createElement('div');
fillContainer.className = 'fill-container flush-right';
fillContainer.setAttribute('role', 'tablist');
}
button.classList.add(exports.css.button);
bottomStripe.appendChild(fillContainer);
container = fillContainer;
}
else {
if (Array.isArray(exports.css.tab)) {
exports.css.tab.forEach(_ => button.classList.add(_));
}
else {
button.classList.add(exports.css.tab);
}
buttonAction.classList.add(exports.css.buttonAction);
}
container.appendChild(button);
if (!isHighLevelMode(opts) && opts.balloon) {
button.setAttribute('data-balloon', opts.balloon);
button.setAttribute('data-balloon-pos', !isTab ? 'down-right' : 'down');
if (opts.balloonLength) {
button.setAttribute('data-balloon-length', opts.balloonLength);
}
else {
button.setAttribute('data-balloon-length', 'medium');
}
}
if (entity.type !== 'custom') {
sidecar_1.getSidecar(tab).entity = entity;
}
const url = !isHighLevelMode(opts) && opts.url;
if (url) {
button.onclick = () => window.open(url);
}
else if (isHighLevelMode(opts) || opts.command || opts.direct) {
button.onclick = () => __awaiter(void 0, void 0, void 0, function* () {
const leaveBottomStripeAlone = isHighLevelMode(opts) || opts.leaveBottomStripeAlone;
const actAsButton = !isHighLevelMode(opts) && opts.actAsButton;
const changeActiveButton = () => {
const radioButton = !isHighLevelMode(opts) && opts.radioButton;
const selected = !isHighLevelMode(opts) && opts.selected;
if (!actAsButton) {
const currentActive = modeStripe.querySelector(`.${exports.css.active}`);
if (currentActive) {
currentActive.classList.remove(exports.css.active);
}
button.classList.add(exports.css.active);
const visibleWhens = bottomStripe.querySelectorAll('.sidecar-bottom-stripe-button[data-visible-when]');
for (let idx = 0; idx < visibleWhens.length; idx++) {
const otherButton = visibleWhens[idx];
const when = otherButton.getAttribute('data-visible-when');
if (when === mode) {
otherButton.classList.remove('not-displayed');
}
else {
otherButton.classList.add('not-displayed');
}
}
}
else if (actAsButton && selected !== undefined) {
if (radioButton) {
button.classList.toggle(exports.css.selected);
}
else {
const currentSelected = bottomStripe.querySelector(`.${exports.css.selected}`);
if (currentSelected) {
currentSelected.classList.remove(exports.css.selected);
}
button.classList.add(exports.css.selected);
}
}
};
const present = (view) => {
if (typeof view === 'string') {
const dom = document.createElement('div');
dom.classList.add('padding-content', 'scrollable', 'scrollable-auto');
dom.innerText = view;
sidecar_1.insertCustomContent(tab, dom);
}
else if (content_types_1.isStringWithOptionalContentType(view) && entity_1.isMetadataBearing(entity)) {
sidecar_1.showCustom(tab, {
type: 'custom',
resource: entity,
content: view.content,
contentType: view.contentType
}, { leaveBottomStripeAlone: true });
}
else if (types_1.isHTML(view)) {
const dom = document.createElement('div');
dom.classList.add('padding-content', 'scrollable', 'scrollable-auto');
dom.appendChild(view);
sidecar_1.insertCustomContent(tab, dom);
}
else if (sidecar_1.isCustomSpec(view)) {
sidecar_1.showCustom(tab, view, { leaveBottomStripeAlone: leaveBottomStripeAlone });
}
else if (table_1.isTable(view) || table_1.isMultiTable(view)) {
const dom1 = document.createElement('div');
const dom2 = document.createElement('div');
dom1.classList.add('scrollable', 'scrollable-auto');
dom2.classList.add('result-as-table', 'repl-result');
dom1.appendChild(dom2);
table_2.formatTable(tab, view, dom2, { usePip: true });
sidecar_1.insertCustomContent(tab, dom1);
}
};
if (!isHighLevelMode(opts) && opts.direct) {
try {
if (isDirectViewEntity(opts.direct) || leaveBottomStripeAlone) {
changeActiveButton();
}
const view = yield callDirect(tab, opts.direct, entity, opts.execOptions);
if (actAsButton && isToggle(view)) {
view.toggle.forEach(({ mode, disabled }) => {
const button = modeStripe.querySelector(`.sidecar-bottom-stripe-button[data-mode="${mode}"]`);
if (button) {
if (disabled) {
button.classList.add('disabled');
}
else {
button.classList.remove('disabled');
}
}
});
changeActiveButton();
}
else if (view && !actAsButton && !isToggle(view)) {
if (table_1.isTable(view) || content_types_1.isStringWithOptionalContentType(view)) {
changeActiveButton();
}
present(view);
}
else if (!isToggle(view) && sidecar_1.isCustomSpec(view)) {
sidecar_1.showCustom(tab, view, { leaveBottomStripeAlone: leaveBottomStripeAlone });
}
else if (!leaveBottomStripeAlone) {
changeActiveButton();
}
}
catch (err) {
console.error(err);
}
}
else if (!isHighLevelMode(opts) && opts.command) {
try {
const { echo, noHistory, replSilence } = opts;
yield exec_1.pexec(opts.command(entity), { echo, noHistory, replSilence });
if (leaveBottomStripeAlone) {
changeActiveButton();
}
}
catch (err) {
console.error(err);
}
}
else if (content_types_1.hasContent(opts)) {
const { format } = yield Promise.resolve().then(() => require('../models/mmr/show'));
const view = yield format(tab, entity, opts);
changeActiveButton();
present(view);
}
});
}
return button;
};
exports.addModeButton = (tab, mode, entity) => {
const modeStripe = exports.css.modeContainer(tab);
const bottomStripe = exports.css.bottomContainer(tab);
return _addModeButton(tab, modeStripe, bottomStripe, mode, entity, undefined);
};
exports.addModeButtons = (tab, modesUnsorted = [], entity, options) => {
const command = '';
if (entity_1.isMetadataBearing(entity)) {
modes_1.apply(tab, modesUnsorted, command, { resource: entity });
}
else if (entity_1.isMetadataBearingByReference(entity)) {
modes_1.apply(tab, modesUnsorted, command, entity);
}
const modes = modesUnsorted.sort((a, b) => {
const aFlush = isHighLevelMode(a) ? undefined : a.flush;
const bFlush = isHighLevelMode(b) ? undefined : b.flush;
if (aFlush === bFlush || (aFlush === 'weak' && bFlush === 'right') || (aFlush === 'right' && bFlush === 'weak')) {
return (a.order || 0) - (b.order || 0);
}
else {
if (aFlush === 'right' || aFlush === 'weak') {
return 1;
}
else {
return -1;
}
}
});
const addModeButtons = (tab, modes, entity, show) => {
const modeStripe = exports.css.modeContainer(tab);
const bottomStripe = exports.css.bottomContainer(tab);
dom_1.removeAllDomChildren(modeStripe);
dom_1.removeAllDomChildren(bottomStripe);
if (modes) {
modes.forEach(mode => {
_addModeButton(tab, modeStripe, bottomStripe, mode, entity, show);
});
}
bottomStripe.capture = () => {
const currentSelection = modeStripe.querySelector(`.${exports.css.active}`);
const currentShow = currentSelection && currentSelection.getAttribute('data-mode');
const show = currentShow || (options && options.show);
dom_1.removeAllDomChildren(bottomStripe);
return () => addModeButtons(tab, modes, entity, show);
};
};
const defaultMode = modes && (modes.find(({ defaultMode }) => defaultMode) || modes.find(_ => isHighLevelMode(_) || !_.flush));
const show = (options && options.show) || (defaultMode && (defaultMode.mode || defaultMode.label));
addModeButtons(tab, modes, entity, show);
if (!options || !options.preserveBackButton) {
const backContainer = exports.css.backContainer(tab);
backContainer.classList.remove('has-back-button');
}
};
//# sourceMappingURL=bottom-stripe.js.map