Statistics
| Branch: | Tag: | Revision:

root / ui / templates / networks.html @ 9422d033

History | View | Annotate | Download (41.1 kB)

1
<!--
2
Copyright 2011 GRNET S.A. All rights reserved.
3

4
Redistribution and use in source and binary forms, with or
5
without modification, are permitted provided that the following
6
conditions are met:
7

8
  1. Redistributions of source code must retain the above
9
     copyright notice, this list of conditions and the following
10
     disclaimer.
11

12
  2. Redistributions in binary form must reproduce the above
13
     copyright notice, this list of conditions and the following
14
     disclaimer in the documentation and/or other materials
15
     provided with the distribution.
16

17
THIS SOFTWARE IS PROVIDED BY GRNET S.A. ``AS IS'' AND ANY EXPRESS
18
OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
19
WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
20
PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL GRNET S.A OR
21
CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
22
SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
23
LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF
24
USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED
25
AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
26
LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN
27
ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
28
POSSIBILITY OF SUCH DAMAGE.
29

30
The views and conclusions contained in the software and
31
documentation are those of the authors and should not be
32
interpreted as representing official policies, either expressed
33
or implied, of GRNET S.A.
34
-->
35

    
36
{% load i18n %}
37

    
38
<!-- the create button -->
39
<div id="networks-createcontainer">
40
    <div id="beforecreate"></div>
41
    <a id="networkscreate" rel="#networks-wizard" href="#">{% trans "Create New +" %}</a>
42
</div>
43

    
44
<!-- add new network overlay -->
45
<div>
46
    <div class="modal" id="networks-wizard">
47
        <div class="header">
48
        </div>
49
        <h2>{% trans "Name your network" %}</h2>
50
        <hr class="topruler" />
51
        <div class="container">
52
            <div class="name-input">
53
                <label>{% trans "Name" %}:</label>
54
                <input type="text" class="text" name="machine_name"></input>
55
                <span class="help">{% trans "(* Required field)" %}</span>
56
            </div>
57
        </div>
58
        <hr class="bottomruler" />
59
        <button type="button" id="add-network-cancel" class="cancel">{% trans "Cancel" %}</button>
60
        <button type="button" id="add-network-create" class="create">{% trans "Create Network" %}</button>
61
        <hr class="separator-end"></hr>
62
    </div>
63
</div>
64

    
65
<!-- networks list -->
66
<div id="networks-container">
67
    <!-- spinner while loading list -->
68
    <div class = "large-spinner"></div>
69

    
70
    <!-- public network template -->
71
    <div class="network" id="public-template">
72
        <img class="network-logos" src="static/internet.png" />
73
        <div href="#" class="name-div">
74
            <h5 class="namecontainer">
75
                <span class="name">{% trans "Internet" %}</span>
76
            </h5>
77
        </div>
78
        <h5 class="network-machines">
79
            {% trans "Show:" %} <span class="show-machines">{% trans "machines" %}</span>
80
            (<span class="machines-count">0</span>)
81
        </h5>
82
        <div class="network-contents">
83
            <div class="network-placeholder">
84
                <div class="network-contents-start-separator"></div>
85
                <div class="machines-list">
86
                <!-- append machines here -->
87
                </div>
88
                <div class="empty-network-slot" id="machine-template">
89
                    <div class='network-add-machine'>
90
                        {# Replace the following with the comment below for full public network functionality #}
91
                        {# <span class="add-icon">+</span> #}
92
                        <span>&nbsp;</span>
93
                    </div>
94
                </div>
95
            </div>
96
            <div class="network-contents-end-separator"></div>
97
        </div>
98
        <div class="state">
99
            <div class="status">{% trans "Public Network" %}</div>
100
            <div class="indicators network-indicator">
101
                <div class="indicator1"></div>
102
                <div class="indicator2"></div>
103
                <div class="indicator3"></div>
104
                <div class="indicator4"></div>
105
            </div>
106
        </div>
107
        <div class="actions">
108
            {# Commented out the following until there is full public network support #}
109
            {# <a href="#" class="action-add">{% trans "Add Machine" %}</a> #}
110
        </div>
111
        <div class="confirm_single">
112
            <button class="yes">{% trans "Confirm" %}</button>
113
            <button class="no">{% trans "Cancel" %}</button>
114
        </div>
115
        <div class="action_error" align="center">
116
            {% trans "<span>Error</span> on" %} <span class="action">{% trans "error action" %}</span>
117
            <span class="code"></span>
118
            <span class="message"></span>
119
            <button class="details">{% trans "Details" %}</button>
120
        </div>
121
    </div>
122

    
123
    <!-- template for machines in public network -->
124
    <div class="network-machine" id="public-machine-template">
125
        <div class="machine-actions">
126
            <a href="#" class="action-details">{% trans "Details" %}</a>
127
        </div>
128
        <div class="confirm_single">
129
            <button class="yes">{% trans "Confirm" %}</button>
130
            <button class="no">{% trans "Cancel" %}</button>
131
        </div>
132
        <div class="action_error" align="center">
133
            {% trans "<span>Error</span> on" %} <span class="action">{% trans "error action" %}</span>
134
            <span class="code"></span>
135
            <span class="message"></span>
136
            <button class="details">{% trans "Details" %}</button>
137
        </div>
138
        <div class="ips">
139
            <div class="ip4-container status">
140
                <span class="discreet">{% trans "IPv4" %}: </span>
141
                <span class="ip4">192.94.73.15</span>
142
            </div>
143
            <div class="ip6-container status">
144
                <span class="discreet">{% trans "IPv6" %}: </span>
145
                <span class="ip6">vv</span>
146
            </div>
147
            <img class="spinner" style="display:none" src="static/icons/indicators/medium/progress.gif" />
148
            <img class="wave" style="display:none" src="static/icons/indicators/medium/wave.gif" />
149
        </div>
150
        <img class="logo" src="static/icons/machines/medium/debian-on.png" />
151
        <div class='network-remove-machine'>
152
            {# Replace the following with the comment below for full public network functionality #}
153
            {# <span class="remove-icon">X</span> #}
154
            <span>&nbsp;</span>
155
        </div>
156
        <div href="#" class="machine-name-div">
157
            <h5 class="namecontainer">
158
                <span class="name">my desktop1</span>
159
            </h5>
160
        </div>
161
        <h5 class="machine-settings">
162
            <span class="ip">{% trans "IPs" %}</span> |
163
            <span class="show-firewall">{% trans "Firewall" %}</span>
164
            (<span class="firewall-off">{% trans "Off" %}</span>)
165
        </h5>
166
        <div class="firewall-content">
167
            <div class="firewall-contents-start-separator"></div>
168
            <input type="radio" class="checkboxes" name="image-id1" />
169
            <span class="checkbox-legends">{% trans "Unprotected mode (Firewall off)" %}</span>
170
            <br />
171
            <input type="radio" class="checkboxes" name="image-id1" />
172
            <span class="checkbox-legends">{% trans "Fully protected mode (Firewall on)" %}</span>
173
            <br />
174
            <input type="radio" class="checkboxes" name="image-id1" />
175
            <span class="checkbox-legends">{% trans "Basically protected mode (Firewall on)" %}</span>
176
            <br />
177
            <input type="radio" class="checkboxes" name="image-id1" />
178
            <span class="checkbox-legends">{% trans "Custom protection" %} <a href="#" class="firewall-settings">{% trans "settings" %}</a> {% trans "(Advanced users only)" %}</span>
179
            <button type="submit" class="firewall-apply">{% trans "Apply" %}</button>
180
            <div class="firewall-contents-end-separator"></div>
181
        </div>
182
        <div class="network-separator machines"></div>
183
    </div>
184

    
185
    <!-- private network template -->
186
    <div class="network" id="private-template">
187
        <div class="actions">
188
            <a href="#" class="action-add">{% trans "Add Machine" %}</a>
189
            <a href="#" class="action-network-destroy">{% trans "Destroy" %}</a>
190
        </div>
191
        <div class="action_error" align="center">
192
            {% trans "<span>Error</span> on" %} <span class="action">{% trans "error action" %}</span>
193
            <span class="code"></span>
194
            <span class="message"></span>
195
            <button class="details">{% trans "Details" %}</button>
196
        </div>
197
        <div class="confirm_single">
198
            <button class="yes">{% trans "Confirm" %}</button>
199
            <button class="no">X</button>
200
        </div>
201
        <div class="action_error" align="center">
202
            {% trans "<span>Error</span> on" %} <span class="action">{% trans "error action" %}</span>
203
            <span class="code"></span>
204
            <span class="message"></span>
205
            <button class="details">{% trans "Details" %}</button>
206
        </div>
207
        <div class="state">
208
            <div class="status">{% trans "Private Network" %}</div>
209
            <div class="indicators network-indicator">
210
                <div class="indicator1"></div>
211
                <div class="indicator2"></div>
212
                <div class="indicator3"></div>
213
                <div class="indicator4"></div>
214
            </div>
215
            <img class="spinner" style="display:none" src="static/icons/indicators/medium/progress.gif" />
216
            <img class="wave" style="display:none" src="static/icons/indicators/medium/wave.gif" />
217
        </div>
218
        <img class="network-logos" src="static/network.png" />
219
        <div href="#" class="name-div">
220
            <h5 class="namecontainer editable">
221
                <span class="name">{% trans "My Network 1" %}</span>
222
                <span class="rename-network"></span>
223
                <div class="editbuttons" style="display:none">
224
                    <span class="save"></span>
225
                    <span class="cancel"></span>
226
                </div>
227
            </h5>
228
        </div>
229
        <h5 class="network-machines">
230
            {% trans "Show:" %} <span class="show-machines">{% trans "machines" %}</span>
231
            (<span class="machines-count">0</span>)
232
        </h5>
233
        <div class="network-contents">
234
            <div class="network-placeholder">
235
                <div class="network-contents-start-separator"></div>
236
                <div class="machines-list">
237
                <!-- append machines here -->
238
                </div>
239
                <div class="empty-network-slot" id="machine-template">
240
                    <div class='network-add-machine'><span class="add-icon">+</span></div>
241
                </div>
242
            </div>
243
            <div class="network-contents-end-separator"></div>
244
        </div>
245
        <div class="separator"></div>
246
    </div>
247

    
248
    <!-- template for machines in private network -->
249
    <div class="network-machine" id="private-machine-template">
250
        <div class="machine-actions">
251
            <a href="#" class="action-disconnect">{% trans "Disconnect" %}</a>
252
            <a href="#" class="action-details">{% trans "Details" %}</a>
253
        </div>
254
        <div class="confirm_single">
255
            <button class="yes">{% trans "Confirm" %}</button>
256
            <button class="no">X</button>
257
        </div>
258
        <div class="action_error" align="center">
259
            {% trans "<span>Error</span> on" %} <span class="action">{% trans "error action" %}</span>
260
            <span class="code"></span>
261
            <span class="message"></span>
262
            <button class="details">{% trans "Details" %}</button>
263
        </div>
264
        <div class="state">
265
            <img class="spinner" style="display:none" src="static/icons/indicators/medium/progress.gif" />
266
            <img class="wave" style="display:none" src="static/icons/indicators/medium/wave.gif" />
267
        </div>
268
        <img class="logo" src="static/icons/machines/medium/debian-on.png" />
269
        <div class='network-remove-machine'><span class="remove-icon">X</span></div>
270
        <div href="#" class="machine-name-div">
271
            <h5 class="namecontainer editable">
272
                <span class="name">my desktop1</span>
273
            </h5>
274
        </div>
275
        <h5 class='machine-connect'>
276
            <span>{% trans "Connect" %}</span> {% trans "to manage private IPs" %}
277
        </h5>
278
        <div class="network-separator machines"></div>
279
    </div>
280

    
281
    <!-- the actual structure to be populated -->
282
    <div class="public-networks"></div>
283
    <div class="private-networks" style="display:none;"></div>
284
</div>
285

    
286
<!-- add servers to network overlay -->
287
<div>
288
    <div id="add-machines-wizard" class="modal">
289
        <h3 class="popup-header">{% trans "Add machine" %}</h3>
290
        <p style='display:none;'>hidden network id</p>
291
        <div class="popup-body">
292
            <div class="popup-body-inner">
293
                <div class="popup-title">{% trans "Select machines to add to:" %}</div>
294
                <div class="network-name"></div>
295
                <div class="popup-separator"></div>
296
                <div class="machines-container">
297
                    <div class="large-spinner"></div>
298
                    <div id='machine-entry-template' style="display:none;">
299
                        <input type="checkbox" />
300
                        <img class=list-logo src="static/icons/machines/small/debian-on.png" title="debian"></img>
301
                        <span class="machine-name">kati</span>
302
                    </div>
303
                </div>
304
            </div>
305
        </div>
306
        <div class="buttons">
307
            <button type="button" class="cancel" id="add-server-cancel">{% trans "Cancel" %}</button>
308
            <button type="button" class="add" id="add-server-add">{% trans "Add" %}</button>
309
        </div>
310
    </div>
311
</div>
312

    
313
<a id="add-machines-overlay" href="#" rel="#add-machines-wizard"></a>
314

    
315
<!-- multiple confirmation dialog -->
316
<div class="confirm_multiple">
317
    <p>{% trans "Your actions will affect" %} <span class="actionLen">XX</span> {% trans "networks" %}</p>
318
    <button class="yes">{% trans "Confirm All" %}</button>
319
    <button class="no">{% trans "Cancel All" %}</button>
320
</div>
321

    
322
<script>
323
// add network wizard initialization
324
$(function() {
325
    // create wizard overlay
326
    $("a#networkscreate").overlay({
327
        mask: '#000',
328
        effect: 'default',
329
        top: '10%',
330
        closeOnClick: false,
331
        oneInstance: false,
332
        closeOnEsc: true,
333
        load: false
334
    });
335
});
336

337
// intercept click to create new private network
338
$("#networkscreate").click(function() {
339
    // reset and load wizard
340
    $('#networks-wizard span.help').removeClass('red');
341
    $('#networks-wizard input').val('');
342
    $('#networks-wizard #add-network-create').text('{% trans 'Create Network' %}');
343
    $("#networks-wizard").show();
344
    $('#networks-wizard input').focus();
345
    $("a#networkscreate").data('overlay').load();
346
    return false;
347
});
348

349
// exit the add machine to network wizard
350
$("#add-network-cancel").live('click', function() {
351
    $("a#networkscreate").overlay().close();
352
});
353

354
// add selected machines to network
355
$("#add-network-create").live('click', function() {
356
    if ($('#networks-wizard input').val() == '') {
357
        $('#networks-wizard input').focus();
358
        $('#networks-wizard span.help').addClass('red');
359
    } else {
360
        $(this).text('');
361
        $(this).html('<img src="static/icons/indicators/medium/horizontal-progress.gif"></img>');
362
        networkName = $('#networks-wizard input').val();
363
        create_network(networkName);
364
    }
365
    return false;
366
});
367

368
// toggle component with class network-contents
369
$("#networks-pane .show-machines").live('click', function() {
370
    if ($('#networks-pane .network-contents .network-machine').length > 0) {
371
        $(this).parent().next("#networks-pane .network-contents").slideToggle(600);
372
    }
373
    return false;
374
});
375

376
// toggle component with class network-contents
377
$("#networks-pane .network-logos").live('click', function() {
378
    $(this).siblings("#networks-pane .network-contents").slideToggle(600);
379
    return false;
380
});
381

382
//initiate network renaming
383
$("#networks-pane .name-div .rename-network, #networks-pane .name-div h5.editable span.name").live('click', function() {
384
    $(this).parent().find('.name').html("<input id=\"txtEdit\" type=\"text\" class=\"nametextbox\" value=\"" +
385
                                        $(this).parent().find('.name').text() +
386
                                        "\" / ><span class=\"oldValue\">" +
387
                                        $(this).parent().find('.name').text() + "</span>");
388
    $(this).parent().find('.rename-network').hide();
389
    $(this).parent().find(".editbuttons").fadeIn();
390
    $(this).parent().find(".nametextbox").focus().select();
391
    $(this).parent().removeClass('editable');
392

393
    //submit wizard by pressing enter on the name textbox
394
    $("#txtEdit").keydown(function (e) {
395
        if ((e.which && e.which == 13) || (e.keyCode && e.keyCode == 13)) {
396
            $(this).parent().parent().find('div.editbuttons span.save').click();
397
            return false;
398
        } else if ((e.which && e.which == 27) || (e.keyCode && e.keyCode == 27)) {
399
            $(this).parent().parent().find('div.editbuttons span.cancel').click();
400
            return true;
401
        }
402
    });
403
    return false;
404
});
405

406
//rename machine
407
$("#networks-pane .name-div .editbuttons .save").live('click', function() {
408
    networkID = $(this).closest('.network').attr("id").split('-').pop();
409
    networkName = $(this).parent().parent().find('.nametextbox').val();
410
    if (networkName.trim() == ''){
411
        return false;
412
    }
413
    $(this).parent().parent().find('.name').html($(this).parent().parent().find('.nametextbox').val());
414
    $(this).parent().parent().find(".editbuttons").fadeOut("fast");
415
    $(this).parent().parent().find(".rename-network").fadeIn("slow");
416
    rename_network(networkID, networkName);
417
    return false;
418
});
419

420
//cancel renaming
421
$("#networks-pane .name-div .editbuttons .cancel").live('click', function() {
422
    $(this).parent().parent().find('.name').html($(this).parent().parent().find('.oldValue').text());
423
    $(this).parent().parent().find(".editbuttons").hide();
424
    $(this).parent().parent().find(".rename-network").fadeIn();
425
    $(this).parent().parent().addClass('editable');
426
    return false;
427
});
428

429
// intercept click to delete network
430
$("#networks-pane .action-network-destroy").live('click', function() {
431
    var networkID = $(this).parent().parent().attr('id').split('-').pop();
432
    var networkName = $(this).parent().parent().find(".name-div span.name").text();
433
    var found = false;
434
    $(this).parent().children('a').removeClass('selected');
435
    $(this).addClass('selected');
436
    $(this).parent().addClass('display')
437
    $(this).parent().parent().find('.action_error').hide();
438
    for (i=0; i < pending_actions.length; i++){ // if there is already a pending action for this network replace it
439
        if (pending_actions[i][0] == delete_network && pending_actions[i][1] == networkID){
440
            pending_actions[i][0] = delete_network;
441
            found = true
442
        }
443
    }
444
    if (!found) {
445
        // no pending action for this network was found, so let's just add it to the list
446
        pending_actions.push([delete_network, networkID, networkName]);
447
    }
448
    update_network_confirmations();
449
    return false;
450
});
451

452
// intercept click to remove machine from network
453
$("#networks-pane .remove-icon").live('click', function() {
454
    $(this).closest('.network-machine').find('.action-disconnect').click();
455
    return false;
456
});
457

458
// intercept click to remove machine from network
459
$("#networks-pane .action-disconnect").live('click', function() {
460
    var serverID = $(this).parent().parent().attr('id').split('-').pop();
461
    var networkID = $(this).closest('.network').attr('id').split('-').pop();
462
    var found = false;
463
    $(this).parent().children('a').removeClass('selected');
464
    $(this).addClass('selected');
465
    $(this).parent().addClass('display')
466
    $(this).parent().parent().find('.action_error').hide();
467
    for (i=0; i < pending_actions.length; i++){
468
        // if there is already a pending action for this network replace it
469
        if (pending_actions[i][0] == remove_server_from_network &&
470
            pending_actions[i][1] == networkID &&
471
            pending_actions[i][2] == serverID) {
472
                pending_actions[i][0] = remove_server_from_network;
473
                found = true
474
        }
475
    }
476
    if (!found) {
477
        // no pending action for this network was found, so let's just add it to the list
478
        pending_actions.push([remove_server_from_network, networkID, serverID]);
479
    }
480
    update_network_confirmations();
481
    return false;
482
});
483

484
$("#networks-pane .action-details").live('click', function() {
485
    var serverID = $(this).parent().parent().attr('id').split('-').pop();
486
    $.cookie('view', '2');
487
    $.cookie('server', serverID);
488
    $('a#machines').click();
489
    return false
490
});
491

492
// add machines wizard initialization
493
$(function() {
494
    // create wizard overlay
495
    $("a#add-machines-overlay").overlay({
496
        mask: '#000',
497
        effect: 'default',
498
        top: '10%',
499
        closeOnClick: false,
500
        oneInstance: false,
501
        closeOnEsc: true,
502
        load: false
503
    });
504
});
505

506
// intercept click to add machine to  network
507
$("#networks-pane .action-add").live('click', function() {
508
    // reset pre-existing values
509
    $('#add-server-add').text('{% trans 'Add' %}');
510
    $("#add-machines-wizard .network-name").text($(this).closest('.network').find('.name-div span.name').text());
511
    $("#add-machines-wizard p").text($(this).closest('.network').attr('id').split('-').pop());
512
    $("#add-machines-wizard .large-spinner").show();
513
    $('[id^="list-entry-server-"]').remove();
514
    // list new values
515
    list_machines();
516
    // load wizard
517
    $("#add-machines-wizard").show();
518
    $("a#add-machines-overlay").data('overlay').load();
519
    return false;
520
});
521

522
//submit wizard by pressing enter on the name textbox
523
$("#networks-wizard div.name-input input.text").keypress(function (e) {
524
    if ((e.which && e.which == 13) || (e.keyCode && e.keyCode == 13)) {
525
        $('#add-network-create').click();
526
        return false;
527
    } else {
528
        return true;
529
    }
530
});
531

532
// intercept click to bring up the add machine to network wizard
533
$("#networks-pane .add-icon").live('click', function() {
534
    $(this).closest('.network').find('.action-add').click();
535
});
536

537
// get machines in public network and list them in add server to network wizard
538
function list_machines() {
539
    var networkID = $("#add-machines-wizard p").text();
540
    // get the list of servers from the UI
541
    var all_machines = $("#networks-pane .public-networks .network-machine");
542

543
    $.each(all_machines, function(i, machine) {
544
        var currentID = machine.id.split('-').pop();
545
        // if machine already exists in private network
546
        if ( $('#net-' + networkID + '-server-' + currentID).length > 0 ) {
547
            // do nothing
548
        } else {
549
            // put it in the list
550
            var entry = $("#add-machines-wizard #machine-entry-template").clone().attr("id", "list-entry-server-" + currentID);
551
            entry.find('input').attr("name", currentID);
552
            entry.find('img').attr('src', 'static/icons/machines/small/' + $(machine).find('img.logo').attr('src').split('/').pop());
553
            entry.find('.machine-name').text($(machine).find('span.name').text());
554
            entry.appendTo("#add-machines-wizard .machines-container");
555
        }
556
    });
557
    $("#add-machines-wizard .large-spinner").hide();
558
    $('[id^="list-entry-server-"]').fadeIn("slow");
559
    return false;
560
}
561

562
// exit the add machine to network wizard
563
$("#add-server-cancel").live('click', function() {
564
    $("a#add-machines-overlay").overlay().close();
565
});
566

567
// add selected machines to network
568
$("#add-server-add").live('click', function() {
569
    var selections = $("#add-machines-wizard :checkbox:checked");
570
    // if there are no selections simply close the wizard
571
    if (selections.length == 0 ) {
572
        $("a#add-machines-overlay").overlay().close();
573
    }
574
    // if there are servers selected make the proper call
575
    else {
576
        var networkID = $("#add-machines-wizard p").text();
577
        var serverIDs = [];
578
        $.each(selections, function(i, selection) {
579
            serverIDs.push(selection.name);
580
        });
581
        $(this).text('');
582
        add_server_to_network(networkID, serverIDs);
583
        $(this).html('<img src="static/icons/indicators/medium/horizontal-progress.gif"></img>');
584
    }
585
    return false;
586
});
587

588
// toggle component with class firewall-contents
589
$("#networks-pane .show-firewall").live('click', function() {
590
    $(this).parent().next(".firewall-content").slideToggle(600);
591
    return false;
592
});
593

594
//hide firewall content on apply click
595
$("#networks-pane .firewall-apply").live('click', function() {
596
    $(this).parent().slideToggle(600);
597
    return false;
598
});
599

600
// confirm single action
601
$("#networks-pane div.confirm_single .yes").live('click', function() {
602
    // this works both for server and network actions
603
    var serverID = [];
604
    if ($(this).closest('.network-machine').attr('id')) {
605
        serverID = $(this).closest('.network-machine').attr('id').split('-').pop();
606
    }
607
    var networkID = $(this).closest('.network').attr("id").split('-').pop();
608
    // execute actions
609
    for (i=0;i<pending_actions.length;i++){
610
        // if there is a pending action for this server execute it
611
        if (pending_actions[i][0] == delete_network &&
612
            pending_actions[i][1] == networkID){
613
                action = pending_actions.splice(i,1)[0];
614
                $(this).parent().parent().find('.status').text(TRANSITIONS['Destroying']);
615
                $(this).parent().parent().find('.spinner').show();
616
                action[0]([action[1]]); // execute action
617
        } else if ( pending_actions[i][0] == remove_server_from_network &&
618
                    pending_actions[i][1] == networkID &&
619
                    pending_actions[i][2] == serverID) {
620
                        action = pending_actions.splice(i,1)[0];
621
                        action[0]([action[1]], [action[2]]); // execute action
622
        }
623
    }
624
    $(this).parent().hide();
625
    $(this).parent().prev().prev().removeClass('selected');
626
    $(this).closest('div.actions').find('a').removeClass('selected');
627
    $(this).closest("div.network").children('div.actions').removeClass('display');
628
    $(this).closest("div.network").children('div.actions').removeClass('selected');
629
    update_network_confirmations();
630
//
631
//    $(this).closest('div.actions').find('a').removeClass('selected');
632
//    $(this).closest("div.machine").children('.state').children('.spinner').show()
633
//    $(this).closest("div.machine").children('div.actions').removeClass('display');
634
    return false;
635
});
636

637
// cancel single action
638
$("#networks-pane div.confirm_single .no").live('click', function(){
639
    // this works both for server and network actions
640
    var serverID = [];
641
    if ($(this).closest('.network-machine').attr('id')) {
642
        serverID = $(this).closest('.network-machine').attr('id').split('-').pop();
643
    }
644
    var networkID = $(this).closest('.network').attr("id").split('-').pop();
645
    // remove the action from the pending list
646
    $(this).parent().parent().children('div.actions').children('a').removeClass('selected');
647
    $(this).parent().parent().children('div.actions').removeClass('display');
648

649
    for (i=0; i < pending_actions.length; i++) { // if there is a pending action for this network remove it
650
        if (pending_actions[i][0] == delete_network && pending_actions[i][1] == networkID) {
651
                pending_actions.splice(i,1);
652
        } else if ( pending_actions[i][0] == remove_server_from_network &&
653
                    pending_actions[i][1] == networkID &&
654
                    pending_actions[i][2] == serverID) {
655
                        pending_actions.splice(i,1);
656
        }
657
    }
658
    $(this).parent().hide();
659
    update_network_confirmations();
660
    return false;
661
});
662

663
// show, single action, error details
664
$("#networks-pane div.action_error .details").live('click', function(){
665
    // remove the action from the pending list
666
    $(this).parent().hide();
667
    ajax_error($(this).parent().children('.code').text(),
668
                 undefined,
669
                 $(this).parent().children('.action').text(),
670
                 $(this).parent().children('.message').text());
671
    return false;
672
});
673

674
// confirm all actions
675
$("#networks-pane div.confirm_multiple .yes").live('click', function(){
676
    while(pending_actions.length > 0){ // if there is a pending action for this network execute it
677
        action = pending_actions.pop(); // extract action
678
        var networkID = action[1];
679
        $('#networks-pane .selected').removeClass('selected');
680
        $('#networks-pane .display').removeClass('display');
681
        $('#networks-pane .confirm_single').hide();
682
        if (action[0] == delete_network) {
683
            $('#networks-pane #net-' + networkID + ' .status').text(TRANSITIONS['Destroying']);
684
            $('#networks-pane #net-' + networkID + ' .spinner').show();
685
            action[0]([networkID]); // execute action
686
        } else if (action[0] == remove_server_from_network) {
687
            action[0]([action[1]], [action[2]]); // execute action
688
        }
689
    }
690
    update_network_confirmations();
691
    return false;
692
});
693

694
// cancel all actions
695
$("#networks-pane div.confirm_multiple .no").live('click', function(){
696
    pending_actions = [];
697
    $('#networks-pane .selected').removeClass('selected');
698
    $('#networks-pane .display').removeClass('display');
699
    $('#networks-pane .confirm_single').hide();
700
    update_network_confirmations();
701
    return false;
702
});
703

704
// update the networks list
705
function update_networks_view(servers_data, networks_data){
706
    /*
707
    Go through the input data. Update existing entries, add
708
    new ones to the list
709
    */
710

711
    // check for changes in networks
712
    if (networks_data){
713
        /*
714
        Here we are interested in private networks only
715
        and not for any server they might contain
716
        */
717

718
        // if we wait for a new network to be created
719
        if ($('#add-network-create').children().length > 0) {
720
            var response_objects = networks_data.networks.values;
721
            // check all objects in the response
722
            for (i=0; i < response_objects.length; i++) {
723
                // if it contains the network we want to create
724
                var networkName = $('#networks-wizard input').val();
725
                if ( response_objects[i]['name'] == networkName) {
726
                    // close the wizard
727
                    $("a#networkscreate").overlay().close();
728
                    // and the network will be inserted in the DOM
729
                    // during the coming update loop
730
                }
731
            }
732
        }
733

734
        if ($('#add-server-add').children().length > 0)
735
            $("a#add-machines-overlay").overlay().close();
736

737
        // update private networks
738
        $.each(networks_data.networks.values, function(i,network) {
739
            // search DOM for this network
740
            existing = $('#networks-pane #net-' + network.id);
741

742
            // if multiple machines exist in the DOM, delete all but one
743
            // defensive coding - that shouldn't happen normally
744
            while (existing.length > 1){
745
                existing.remove();
746
            }
747
            // If network already exists in DOM, update it
748
            if (existing.length){
749
                // network was deleted
750
                if (network.status == 'DELETED') {
751
                    existing.remove();
752
                }
753

754
                // network was renamed
755
                if (existing.find('.name-div span.name').text() != network.name) {
756
                    // set the new name
757
                    existing.find('.name-div span.name').text(network.name);
758
                }
759
            }
760
            // If network does not exist in DOM, create it, do not take into account public network
761
            else if (network.id != 'public'){
762
                var privNet = $("#networks-pane #private-template").clone().attr("id", "net-" + network.id);
763
                privNet.find(".name-div span.name").text(network.name).fadeIn("slow");
764
                privNet.appendTo("#networks-pane .private-networks");
765
            }
766
        });
767
    }
768

769
    // check for changes in servers
770
    if (servers_data) {
771
        /*
772
        Here we are interested in any server contained
773
        either in a public network or a private one
774
        */
775
        $.each(servers_data.servers.values, function(i,server) {
776
            /*
777
            First update the public network
778
            */
779

780
            // search public network's DOM for this server
781
            existing_public = $('#networks-pane #net-pub-server-' + server.id);
782
            // get the server's OS icon
783
            var server_image = os_icon(server.metadata);
784
            if (!(server.metadata == undefined)) {
785
                var server_image = os_icon(server.metadata);
786
            } else {
787
                var server_image = "unknown"
788
            }
789

790
            // if multiple servers exist in public network, delete all but one
791
            // defensive coding - that shouldn't happen normally
792
            while (existing_public.length > 1){
793
                existing_public.remove();
794
            }
795

796
            // server was deleted
797
            if (server.status == 'DELETED') {
798
                existing_public.remove();
799
            }
800

801
            // If server already exists in public network, update it
802
            if (existing_public.length){
803
                // server was renamed
804
                if (server.name != existing_public.find('span.name').text()) {
805
                    existing_public.find('span.name').text(server.name);
806
                }
807
                // server has changed state
808
                if (server.status=='BUILD' || server.status=='ACTIVE' ||server.status=='REBOOT') {
809
                    existing_public.find("img.logo").attr("src","static/icons/machines/medium/" + server_image + '-on.png');
810
                } else {
811
                    existing_public.find("img.logo").attr("src","static/icons/machines/medium/" + server_image + '-off.png');
812
                }
813
                // server has new ips
814
                var old_ip4 = existing_public.find('span.ip4').text();
815
                var old_ip6 = existing_public.find('span.ip6').text();
816
                // the following are valid because the public ips always come in this order from the api
817
                var new_ips = get_public_ips(server);
818
                var new_ip4 = new_ips['ip4'];
819
                var new_ip6 = new_ips['ip6'];
820
                if (old_ip4 != new_ip4) {
821
                    if (new_ips['ip4'] == undefined) {
822
                        existing_public.find(".ip4-container").hide();
823
                    } else {
824
                        existing_public.find('span.ip4').text(new_ip4);
825
                    }
826
                }
827
                if (old_ip6 != new_ip6) {
828
                    if (new_ip6 == undefined) {
829
                        existing_public.find(".ip6-container").hide();
830
                    } else {
831
                        existing_public.find('span.ip6').text(new_ip6);
832
                    }
833
                }
834
                //TODO: server has changed OS
835
            }
836
            // If server does not exist in public network, create it
837
            else {
838
                var machine = $("#networks-pane #public-machine-template").clone().attr("id", "net-pub-server-" + server.id).fadeIn("slow");
839
                machine.find('span.name').text(server.name);
840
                // find and display ips
841
                var ips = get_public_ips(server);
842
                if (ips['ip4'] == undefined) {
843
                    machine.find(".ip4-container").hide();
844
                } else {
845
                    machine.find("span.ip4").text(ips['ip4']);
846
                }
847
                if (ips['ip6'] == undefined) {
848
                    machine.find(".ip6-container").hide();
849
                } else {
850
                    machine.find("span.ip6").text(ips['ip6']);
851
                }
852
                // add the proper icon
853
                if (server.status=='BUILD' || server.status=='ACTIVE' ||server.status=='REBOOT') {
854
                    machine.find("img.logo").attr("src","static/icons/machines/medium/" + server_image + '-on.png');
855
                } else {
856
                    machine.find("img.logo").attr("src","static/icons/machines/medium/" + server_image + '-off.png');
857
                }
858
                machine.appendTo("#networks-pane .public-networks .machines-list");
859
            }
860

861
            /*
862
            Now update all private networks
863
            Since one server may belong to more than one private networks,
864
            we follow a different approach.
865
            We check each server and add, update or leave it as it is accordingly
866
            */
867
            try {
868
                $.each(server.addresses.values, function(i,server_net) {
869
                    // find in which private networks it belongs
870
                    if (server_net.id != "public") {
871
                        var existing_private = $("#networks-pane .private-networks #net-" + server_net.id + "-server-" + server.id);
872
                        // add new server
873
                        if (!existing_private.length) {
874
                            var machine = $("#networks-pane #private-machine-template").clone().attr("id", "net-" + server_net.id + "-server-" + server.id).fadeIn("slow");
875
                            machine.find('span.name').text(server.name);
876
                            if (server.status=='BUILD' || server.status=='ACTIVE' ||server.status=='REBOOT') {
877
                                machine.find("img.logo").attr("src","static/icons/machines/medium/" + server_image + '-on.png');
878
                            } else {
879
                                machine.find("img.logo").attr("src","static/icons/machines/medium/" + server_image + '-off.png');
880
                            }
881
                            machine.appendTo("#networks-pane .private-networks #net-" + server_net.id + " .machines-list");
882
                        }
883
                        // server was deleted
884
                        if (server.status == 'DELETED') {
885
                            existing_private.remove();
886
                        }
887
                        // server was renamed
888
                        if (server.name != existing_private.find('span.name').text()) {
889
                            existing_private.find('span.name').text(server.name);
890
                        }
891
                        // server has changed state
892
                        if (server.status=='BUILD' || server.status=='ACTIVE' ||server.status=='REBOOT') {
893
                            existing_private.find("img.logo").attr("src","static/icons/machines/medium/" + server_image + '-on.png');
894
                        } else {
895
                            existing_private.find("img.logo").attr("src","static/icons/machines/medium/" + server_image + '-off.png');
896
                        }
897
                        //TODO: server has changed OS
898
                    }
899
                });
900
            } catch (err) {
901
                try{console.info('Server ' + server.id + ' has no network addresses')}catch(err){};
902
            }
903
        });
904
    }
905

906
    $("#networks-pane #networks-container > .large-spinner").hide();
907

908
    // show all separators and hide the last one
909
    $("div.private-networks div.network div.separator").show();
910
    $("div.private-networks div.network div.separator:last").hide();
911
    // update the counters of servers in each network
912
    var nets = $('#networks-pane .network');
913
    $.each(nets, function(i,net) {
914
        $(net).find('span.machines-count').text($(net).find('.network-machine').length);
915
    });
916

917
    // the private div shows only when private networks are available
918
    if ($("div.private-networks div.network").length > 0) {
919
        $("div.private-networks").fadeIn("slow");
920
    } else {
921
        $("div.private-networks").fadeOut("slow");
922
    }
923

924
    // tag the last seperator for better styling
925
    $("#pub .network-machine").removeClass('last');
926
    $("#pub .network-machine").last().addClass('last');
927
}
928

929
// indicate that the requested action was not completed
930
function display_failure(status, networkID, action, responseText) {
931
    $('#networks-container #net-'+networkID+ ' .spinner').hide();
932
    $('#networks-container #net-'+networkID+ ' .action_error .action').text(action);
933
    $('#networks-container #net-'+networkID+ ' .action_error .code').text(status);
934
    $('#networks-container #net-'+networkID+ ' .action_error .message').text(responseText);
935
    $('#networks-container #net-'+networkID+ ' .action_error').show();
936
}
937

938

939
// reposition multiple confirmation box on window resize
940
$(window).resize(function(){
941
    if (this.innerHeight - 220 < $('#networks-pane #networks-container').height())
942
        $('#networks-pane .confirm_multiple').addClass('fixed');
943
    else
944
        $('#networks-pane .confirm_multiple').removeClass('fixed');
945
});
946

947
// basic functions executed on page load
948
// hide the all of the networks contents
949
$("#networks-pane .network-contents").hide();
950
// hide the all of the firewall contents
951
$("#networks-pane .firewall-content").hide();
952
changes_since = 0; // to reload full list of servers
953
networks_changes_since= 0; // to reload full list of networks
954
// there is alway one public network to render
955
var pubNet = $("#networks-pane #public-template").clone().attr("id", "pub").fadeIn("slow");
956
pubNet.appendTo("#networks-pane .public-networks");
957
update_networks(UPDATE_INTERVAL);
958

    
959
</script>