diff --git a/Makefile b/Makefile index d135796..9f08eca 100644 --- a/Makefile +++ b/Makefile @@ -38,6 +38,7 @@ JSSRC= \ window/Edit.js \ window/PasswordEdit.js \ window/TaskViewer.js \ + node/APT.js \ node/NetworkEdit.js \ node/NetworkView.js \ node/DNSEdit.js \ diff --git a/Utils.js b/Utils.js index a0f0b69..fd23eb1 100644 --- a/Utils.js +++ b/Utils.js @@ -60,6 +60,11 @@ Ext.define('Proxmox.Utils', { utilities: { stateText: gettext('State'), groupText: gettext('Group'), + getNoSubKeyHtml: function(url) { + // url http://www.proxmox.com/products/proxmox-ve/subscription-service-plans + return Ext.String.format('You do not have a valid subscription for this server. Please visit www.proxmox.com to get a list of available options.', url || 'http://www.proxmox.com'); + }, + format_boolean_with_default: function(value) { if (Ext.isDefined(value) && value !== '__default__') { return value ? Proxmox.Utils.yesText : Proxmox.Utils.noText; @@ -288,6 +293,37 @@ Ext.define('Proxmox.Utils', { utilities: { Ext.Ajax.request(newopts); }, + checked_command: function(orig_cmd) { + Proxmox.Utils.API2Request({ + url: '/nodes/localhost/subscription', + method: 'GET', + //waitMsgTarget: me, + failure: function(response, opts) { + Ext.Msg.alert(gettext('Error'), response.htmlStatus); + }, + success: function(response, opts) { + var data = response.result.data; + + if (data.status !== 'Active') { + Ext.Msg.show({ + title: gettext('No valid subscription'), + icon: Ext.Msg.WARNING, + msg: Proxmox.Utils.getNoSubKeyHtml(data.url), + buttons: Ext.Msg.OK, + callback: function(btn) { + if (btn !== 'ok') { + return; + } + orig_cmd(); + } + }); + } else { + orig_cmd(); + } + } + }); + }, + assemble_field_data: function(values, data) { if (Ext.isObject(data)) { Ext.Object.each(data, function(name, val) { diff --git a/node/APT.js b/node/APT.js new file mode 100644 index 0000000..68075b6 --- /dev/null +++ b/node/APT.js @@ -0,0 +1,207 @@ +Ext.define('apt-pkglist', { + extend: 'Ext.data.Model', + fields: [ 'Package', 'Title', 'Description', 'Section', 'Arch', + 'Priority', 'Version', 'OldVersion', 'ChangeLogUrl', 'Origin' ], + idProperty: 'Package' +}); + +Ext.define('Proxmox.node.APT', { + extend: 'Ext.grid.GridPanel', + + xtype: 'proxmoxNodeAPT', + + upgradeBtn: undefined, + + columns: [ + { + header: gettext('Package'), + width: 200, + sortable: true, + dataIndex: 'Package' + }, + { + text: gettext('Version'), + columns: [ + { + header: gettext('current'), + width: 100, + sortable: false, + dataIndex: 'OldVersion' + }, + { + header: gettext('new'), + width: 100, + sortable: false, + dataIndex: 'Version' + } + ] + }, + { + header: gettext('Description'), + sortable: false, + dataIndex: 'Title', + flex: 1 + } + ], + + initComponent : function() { + var me = this; + + if (!me.nodename) { + throw "no node name specified"; + } + + var store = Ext.create('Ext.data.Store', { + model: 'apt-pkglist', + groupField: 'Origin', + proxy: { + type: 'proxmox', + url: "/api2/json/nodes/" + me.nodename + "/apt/update" + }, + sorters: [ + { + property : 'Package', + direction: 'ASC' + } + ] + }); + + var groupingFeature = Ext.create('Ext.grid.feature.Grouping', { + groupHeaderTpl: '{[ "Origin: " + values.name ]} ({rows.length} Item{[values.rows.length > 1 ? "s" : ""]})', + enableGroupingMenu: false + }); + + var rowBodyFeature = Ext.create('Ext.grid.feature.RowBody', { + getAdditionalData: function (data, rowIndex, record, orig) { + var headerCt = this.view.headerCt; + var colspan = headerCt.getColumnCount(); + // Usually you would style the my-body-class in CSS file + return { + rowBody: '