mirror of
https://git.proxmox.com/git/pve-manager
synced 2025-06-13 00:39:04 +00:00
158 lines
3.7 KiB
JavaScript
158 lines
3.7 KiB
JavaScript
Ext.define('PVE.qemu.Monitor', {
|
|
extend: 'Ext.panel.Panel',
|
|
|
|
alias: 'widget.pveQemuMonitor',
|
|
|
|
// start to trim saved command output once there are *both*, more than `commandLimit` commands
|
|
// executed and the total of saved in+output is over `lineLimit` lines; repeat by dropping one
|
|
// full command output until either condition is false again
|
|
commandLimit: 10,
|
|
lineLimit: 5000,
|
|
|
|
initComponent: function() {
|
|
var me = this;
|
|
|
|
var nodename = me.pveSelNode.data.node;
|
|
if (!nodename) {
|
|
throw "no node name specified";
|
|
}
|
|
|
|
var vmid = me.pveSelNode.data.vmid;
|
|
if (!vmid) {
|
|
throw "no VM ID specified";
|
|
}
|
|
|
|
var history = [];
|
|
var histNum = -1;
|
|
let commands = [];
|
|
|
|
var textbox = Ext.createWidget('panel', {
|
|
region: 'center',
|
|
xtype: 'panel',
|
|
autoScroll: true,
|
|
border: true,
|
|
margins: '5 5 5 5',
|
|
bodyStyle: 'font-family: monospace;',
|
|
});
|
|
|
|
var scrollToEnd = function() {
|
|
var el = textbox.getTargetEl();
|
|
var dom = Ext.getDom(el);
|
|
|
|
var clientHeight = dom.clientHeight;
|
|
// BrowserBug: clientHeight reports 0 in IE9 StrictMode
|
|
// Instead we are using offsetHeight and hardcoding borders
|
|
if (Ext.isIE9 && Ext.isStrict) {
|
|
clientHeight = dom.offsetHeight + 2;
|
|
}
|
|
dom.scrollTop = dom.scrollHeight - clientHeight;
|
|
};
|
|
|
|
var refresh = function() {
|
|
textbox.update(`<pre>${commands.flat(2).join('\n')}</pre>`);
|
|
scrollToEnd();
|
|
};
|
|
|
|
let recordInput = line => {
|
|
commands.push([line]);
|
|
|
|
// drop oldest commands and their output until we're not over both limits anymore
|
|
while (commands.length > me.commandLimit && commands.flat(2).length > me.lineLimit) {
|
|
commands.shift();
|
|
}
|
|
};
|
|
|
|
let addResponse = lines => commands[commands.length - 1].push(lines);
|
|
|
|
var executeCmd = function(cmd) {
|
|
recordInput("# " + Ext.htmlEncode(cmd), true);
|
|
if (cmd) {
|
|
history.unshift(cmd);
|
|
if (history.length > 20) {
|
|
history.splice(20);
|
|
}
|
|
}
|
|
histNum = -1;
|
|
|
|
refresh();
|
|
Proxmox.Utils.API2Request({
|
|
params: { command: cmd },
|
|
url: '/nodes/' + nodename + '/qemu/' + vmid + "/monitor",
|
|
method: 'POST',
|
|
waitMsgTarget: me,
|
|
success: function(response, opts) {
|
|
var res = response.result.data;
|
|
addResponse(res.split('\n').map(line => Ext.htmlEncode(line)));
|
|
refresh();
|
|
},
|
|
failure: function(response, opts) {
|
|
Ext.Msg.alert('Error', response.htmlStatus);
|
|
},
|
|
});
|
|
};
|
|
|
|
Ext.apply(me, {
|
|
layout: { type: 'border' },
|
|
border: false,
|
|
items: [
|
|
textbox,
|
|
{
|
|
region: 'south',
|
|
margins: '0 5 5 5',
|
|
border: false,
|
|
xtype: 'textfield',
|
|
name: 'cmd',
|
|
value: '',
|
|
fieldStyle: 'font-family: monospace;',
|
|
allowBlank: true,
|
|
listeners: {
|
|
afterrender: function(f) {
|
|
f.focus(false);
|
|
recordInput("Type 'help' for help.");
|
|
refresh();
|
|
},
|
|
specialkey: function(f, e) {
|
|
var key = e.getKey();
|
|
switch (key) {
|
|
case e.ENTER:
|
|
var cmd = f.getValue();
|
|
f.setValue('');
|
|
executeCmd(cmd);
|
|
break;
|
|
case e.PAGE_UP:
|
|
textbox.scrollBy(0, -0.9*textbox.getHeight(), false);
|
|
break;
|
|
case e.PAGE_DOWN:
|
|
textbox.scrollBy(0, 0.9*textbox.getHeight(), false);
|
|
break;
|
|
case e.UP:
|
|
if (histNum + 1 < history.length) {
|
|
f.setValue(history[++histNum]);
|
|
}
|
|
e.preventDefault();
|
|
break;
|
|
case e.DOWN:
|
|
if (histNum > 0) {
|
|
f.setValue(history[--histNum]);
|
|
}
|
|
e.preventDefault();
|
|
break;
|
|
default:
|
|
break;
|
|
}
|
|
},
|
|
},
|
|
},
|
|
],
|
|
listeners: {
|
|
show: function() {
|
|
var field = me.query('textfield[name="cmd"]')[0];
|
|
field.focus(false, true);
|
|
},
|
|
},
|
|
});
|
|
|
|
me.callParent();
|
|
},
|
|
});
|