]> git.proxmox.com Git - pve-manager.git/blob - www/manager6/dc/Cluster.js
drop jslint lines
[pve-manager.git] / www / manager6 / dc / Cluster.js
1 Ext.define('pve-cluster-nodes', {
2 extend: 'Ext.data.Model',
3 fields: [
4 'node', { type: 'integer', name: 'nodeid' }, 'ring0_addr', 'ring1_addr',
5 { type: 'integer', name: 'quorum_votes' }
6 ],
7 proxy: {
8 type: 'proxmox',
9 url: "/api2/json/cluster/config/nodes"
10 },
11 idProperty: 'nodeid'
12 });
13
14 Ext.define('pve-cluster-info', {
15 extend: 'Ext.data.Model',
16 proxy: {
17 type: 'proxmox',
18 url: "/api2/json/cluster/config/join"
19 }
20 });
21
22 Ext.define('PVE.ClusterAdministration', {
23 extend: 'Ext.panel.Panel',
24 xtype: 'pveClusterAdministration',
25
26 title: gettext('Cluster Administration'),
27 onlineHelp: 'chapter_pvecm',
28
29 border: false,
30 defaults: { border: false },
31
32 viewModel: {
33 parent: null,
34 data: {
35 totem: {},
36 nodelist: [],
37 preferred_node: {
38 name: '',
39 fp: '',
40 addr: ''
41 },
42 isInCluster: false,
43 nodecount: 0
44 }
45 },
46
47 items: [
48 {
49 xtype: 'panel',
50 title: gettext('Cluster Information'),
51 controller: {
52 xclass: 'Ext.app.ViewController',
53
54 init: function(view) {
55 view.store = Ext.create('Proxmox.data.UpdateStore', {
56 autoStart: true,
57 interval: 15 * 1000,
58 storeid: 'pve-cluster-info',
59 model: 'pve-cluster-info'
60 });
61 view.store.on('load', this.onLoad, this);
62 view.on('destroy', view.store.stopUpdate);
63 },
64
65 onLoad: function(store, records, success) {
66 var vm = this.getViewModel();
67 if (!success || !records || !records[0].data) {
68 vm.set('totem', {});
69 vm.set('isInCluster', false);
70 vm.set('nodelist', []);
71 vm.set('preferred_node', {
72 name: '',
73 addr: '',
74 fp: ''
75 });
76 return;
77 }
78 var data = records[0].data;
79 vm.set('totem', data.totem);
80 vm.set('isInCluster', !!data.totem.cluster_name);
81 vm.set('nodelist', data.nodelist);
82
83 var nodeinfo = Ext.Array.findBy(data.nodelist, function (el) {
84 return el.name === data.preferred_node;
85 });
86
87 let links = {};
88 let ring_addr = [];
89 PVE.Utils.forEachCorosyncLink(nodeinfo, (num, link) => {
90 links[num] = link;
91 ring_addr.push(link);
92 });
93
94 vm.set('preferred_node', {
95 name: data.preferred_node,
96 addr: nodeinfo.pve_addr,
97 peerLinks: links,
98 ring_addr: ring_addr,
99 fp: nodeinfo.pve_fp
100 });
101 },
102
103 onCreate: function() {
104 var view = this.getView();
105 view.store.stopUpdate();
106 var win = Ext.create('PVE.ClusterCreateWindow', {
107 autoShow: true,
108 listeners: {
109 destroy: function() {
110 view.store.startUpdate();
111 }
112 }
113 });
114 },
115
116 onClusterInfo: function() {
117 var vm = this.getViewModel();
118 var win = Ext.create('PVE.ClusterInfoWindow', {
119 joinInfo: {
120 ipAddress: vm.get('preferred_node.addr'),
121 fingerprint: vm.get('preferred_node.fp'),
122 peerLinks: vm.get('preferred_node.peerLinks'),
123 ring_addr: vm.get('preferred_node.ring_addr'),
124 totem: vm.get('totem')
125 }
126 });
127 win.show();
128 },
129
130 onJoin: function() {
131 var view = this.getView();
132 view.store.stopUpdate();
133 var win = Ext.create('PVE.ClusterJoinNodeWindow', {
134 autoShow: true,
135 listeners: {
136 destroy: function() {
137 view.store.startUpdate();
138 }
139 }
140 });
141 }
142 },
143 tbar: [
144 {
145 text: gettext('Create Cluster'),
146 reference: 'createButton',
147 handler: 'onCreate',
148 bind: {
149 disabled: '{isInCluster}'
150 }
151 },
152 {
153 text: gettext('Join Information'),
154 reference: 'addButton',
155 handler: 'onClusterInfo',
156 bind: {
157 disabled: '{!isInCluster}'
158 }
159 },
160 {
161 text: gettext('Join Cluster'),
162 reference: 'joinButton',
163 handler: 'onJoin',
164 bind: {
165 disabled: '{isInCluster}'
166 }
167 }
168 ],
169 layout: 'hbox',
170 bodyPadding: 5,
171 items: [
172 {
173 xtype: 'displayfield',
174 fieldLabel: gettext('Cluster Name'),
175 bind: {
176 value: '{totem.cluster_name}',
177 hidden: '{!isInCluster}'
178 },
179 flex: 1
180 },
181 {
182 xtype: 'displayfield',
183 fieldLabel: gettext('Config Version'),
184 bind: {
185 value: '{totem.config_version}',
186 hidden: '{!isInCluster}'
187 },
188 flex: 1
189 },
190 {
191 xtype: 'displayfield',
192 fieldLabel: gettext('Number of Nodes'),
193 labelWidth: 120,
194 bind: {
195 value: '{nodecount}',
196 hidden: '{!isInCluster}'
197 },
198 flex: 1
199 },
200 {
201 xtype: 'displayfield',
202 value: gettext('Standalone node - no cluster defined'),
203 bind: {
204 hidden: '{isInCluster}'
205 },
206 flex: 1
207 }
208 ]
209 },
210 {
211 xtype: 'grid',
212 title: gettext('Cluster Nodes'),
213 autoScroll: true,
214 enableColumnHide: false,
215 controller: {
216 xclass: 'Ext.app.ViewController',
217
218 init: function(view) {
219 view.rstore = Ext.create('Proxmox.data.UpdateStore', {
220 autoLoad: true,
221 xtype: 'update',
222 interval: 5 * 1000,
223 autoStart: true,
224 storeid: 'pve-cluster-nodes',
225 model: 'pve-cluster-nodes'
226 });
227 view.setStore(Ext.create('Proxmox.data.DiffStore', {
228 rstore: view.rstore,
229 sorters: {
230 property: 'nodeid',
231 order: 'DESC'
232 }
233 }));
234 Proxmox.Utils.monStoreErrors(view, view.rstore);
235 view.rstore.on('load', this.onLoad, this);
236 view.on('destroy', view.rstore.stopUpdate);
237 },
238
239 onLoad: function(store, records, success) {
240 var view = this.getView();
241 var vm = this.getViewModel();
242
243 if (!success || !records || !records.length) {
244 vm.set('nodecount', 0);
245 return;
246 }
247 vm.set('nodecount', records.length);
248
249 // show/hide columns according to used links
250 var linkIndex = view.columns.length;
251 var columns = Ext.each(view.columns, (col, i) => {
252 if (col.linkNumber !== undefined) {
253 col.setHidden(true);
254
255 // save offset at which link columns start, so we
256 // can address them directly below
257 if (i < linkIndex) {
258 linkIndex = i;
259 }
260 }
261 });
262
263 PVE.Utils.forEachCorosyncLink(records[0].data,
264 (linknum, val) => {
265 if (linknum > 7) {
266 return;
267 }
268 view.columns[linkIndex+linknum].setHidden(false);
269 }
270 );
271 }
272 },
273 columns: {
274 items: [
275 {
276 header: gettext('Nodename'),
277 hidden: false,
278 dataIndex: 'name'
279 },
280 {
281 header: gettext('ID'),
282 minWidth: 100,
283 width: 100,
284 flex: 0,
285 hidden: false,
286 dataIndex: 'nodeid'
287 },
288 {
289 header: gettext('Votes'),
290 minWidth: 100,
291 width: 100,
292 flex: 0,
293 hidden: false,
294 dataIndex: 'quorum_votes'
295 },
296 {
297 header: Ext.String.format(gettext('Link {0}'), 0),
298 dataIndex: 'ring0_addr',
299 linkNumber: 0
300 },
301 {
302 header: Ext.String.format(gettext('Link {0}'), 1),
303 dataIndex: 'ring1_addr',
304 linkNumber: 1
305 },
306 {
307 header: Ext.String.format(gettext('Link {0}'), 2),
308 dataIndex: 'ring2_addr',
309 linkNumber: 2
310 },
311 {
312 header: Ext.String.format(gettext('Link {0}'), 3),
313 dataIndex: 'ring3_addr',
314 linkNumber: 3
315 },
316 {
317 header: Ext.String.format(gettext('Link {0}'), 4),
318 dataIndex: 'ring4_addr',
319 linkNumber: 4
320 },
321 {
322 header: Ext.String.format(gettext('Link {0}'), 5),
323 dataIndex: 'ring5_addr',
324 linkNumber: 5
325 },
326 {
327 header: Ext.String.format(gettext('Link {0}'), 6),
328 dataIndex: 'ring6_addr',
329 linkNumber: 6
330 },
331 {
332 header: Ext.String.format(gettext('Link {0}'), 7),
333 dataIndex: 'ring7_addr',
334 linkNumber: 7
335 }
336 ],
337 defaults: {
338 flex: 1,
339 hidden: true,
340 minWidth: 150
341 }
342 }
343 }
344 ]
345 });