mirror of
https://github.com/retspen/webvirtcloud
synced 2024-12-24 15:15:22 +00:00
commit
7efec407c2
4 changed files with 116 additions and 20 deletions
45
instances/templates/add_instance_network_block.html
Normal file
45
instances/templates/add_instance_network_block.html
Normal file
|
@ -0,0 +1,45 @@
|
||||||
|
{% load i18n %}
|
||||||
|
{% if request.user.is_superuser and status == 5 %}
|
||||||
|
<a href="#addInstanceNetwork" type="button" class="btn btn-success pull-right" data-toggle="modal">
|
||||||
|
<span class="glyphicon glyphicon-plus" aria-hidden="true"></span>
|
||||||
|
</a>
|
||||||
|
|
||||||
|
<!-- Modal pool -->
|
||||||
|
<div class="modal fade" id="addInstanceNetwork" tabindex="-1" role="dialog" aria-labelledby="addInstanceNetworkLabel" aria-hidden="true">
|
||||||
|
<div class="modal-dialog">
|
||||||
|
<div class="modal-content">
|
||||||
|
<div class="modal-header">
|
||||||
|
<button type="button" class="close" data-dismiss="modal" aria-hidden="true">×</button>
|
||||||
|
<h4 class="modal-title">{% trans "Add Instance Network" %}</h4>
|
||||||
|
</div>
|
||||||
|
<div class="modal-body">
|
||||||
|
<form class="form-horizontal" method="post" action="" role="form">{% csrf_token %}
|
||||||
|
<div class="form-group">
|
||||||
|
<label class="col-sm-4 control-label">{% trans "Mac" %}</label>
|
||||||
|
<div class="col-sm-6">
|
||||||
|
<input type="text" class="form-control" name="add-net-mac">
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
<div class="form-group">
|
||||||
|
<label class="col-sm-4 control-label">{% trans "Network" %}</label>
|
||||||
|
<div class="col-sm-6">
|
||||||
|
<select class="form-control" name="add-net-network">
|
||||||
|
{% for c_net in compute_networks %}
|
||||||
|
<option value="net:{{ c_net }}">Network {{ c_net }}</option>
|
||||||
|
{% endfor %}
|
||||||
|
{% for c_iface in compute_interfaces %}
|
||||||
|
<option value="iface:{{ c_iface }}">Interface {{ c_iface }}</option>
|
||||||
|
{% endfor %}
|
||||||
|
</select>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
<div class="modal-footer">
|
||||||
|
<button type="button" class="btn btn-default" data-dismiss="modal">{% trans "Close" %}</button>
|
||||||
|
<button type="submit" class="btn btn-primary" name="add_network">{% trans "Add" %}</button>
|
||||||
|
</div>
|
||||||
|
</form>
|
||||||
|
</div> <!-- /.modal-content -->
|
||||||
|
</div> <!-- /.modal-dialog -->
|
||||||
|
</div> <!-- /.modal -->
|
||||||
|
{% endif %}
|
|
@ -827,7 +827,10 @@
|
||||||
{% endif %}
|
{% endif %}
|
||||||
{% if request.user.is_superuser %}
|
{% if request.user.is_superuser %}
|
||||||
<div role="tabpanel" class="tab-pane tab-pane-bordered" id="network">
|
<div role="tabpanel" class="tab-pane tab-pane-bordered" id="network">
|
||||||
<p>{% trans "Assign network device to bridge" %}</p>
|
<p>
|
||||||
|
{% trans "Assign network device to bridge" %}
|
||||||
|
{% include 'add_instance_network_block.html' %}
|
||||||
|
</p>
|
||||||
<form class="form-horizontal" action="" method="post" role="form">{% csrf_token %}
|
<form class="form-horizontal" action="" method="post" role="form">{% csrf_token %}
|
||||||
<p style="font-weight:bold;">{% trans "Network devices" %}</p>
|
<p style="font-weight:bold;">{% trans "Network devices" %}</p>
|
||||||
{% for network in networks %}
|
{% for network in networks %}
|
||||||
|
@ -842,19 +845,19 @@
|
||||||
<div class="col-sm-3">
|
<div class="col-sm-3">
|
||||||
<select name="net-source-{{ forloop.counter0 }}" class="form-control" id="network_select" onchange="network_select_enable()">
|
<select name="net-source-{{ forloop.counter0 }}" class="form-control" id="network_select" onchange="network_select_enable()">
|
||||||
{% for c_nets in compute_networks %}
|
{% for c_nets in compute_networks %}
|
||||||
{% if forloop.counter0 == 0 %}
|
<option value="net:{{ c_nets }}" {% if c_nets == network.nic %}selected{% endif %}>Network {{ c_nets }}</option>
|
||||||
<option value="{{ network.nic }}" selected hidden>{% trans "to Change" %}</option>
|
{% endfor %}
|
||||||
{% endif %}
|
{% for c_iface in compute_interfaces %}
|
||||||
<option value="{{ c_nets }}">{{ c_nets }}</option>
|
<option value="iface:{{ c_iface }}" {% if c_iface == network.nic %}selected{% endif %}>Interface {{ c_iface }}</option>
|
||||||
{% endfor %}
|
{% endfor %}
|
||||||
</select>
|
</select>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
{% endfor %}
|
{% endfor %}
|
||||||
{% ifequal status 5 %}
|
{% ifequal status 5 %}
|
||||||
<button type="submit" class="btn btn-lg btn-success pull-right" id="ali" name="change_network" disabled>{% trans "Change" %}</button>
|
<button type="submit" class="btn btn-lg btn-success pull-right" id="btn_change_network" name="change_network" disabled>{% trans "Change" %}</button>
|
||||||
{% else %}
|
{% else %}
|
||||||
<button type="submit"class="btn btn-lg btn-success pull-right" id="ali" name="change_network" disabled>{% trans "Change" %}</button>
|
<button type="submit" class="btn btn-lg btn-success pull-right" id="btn_change_network" name="change_network" disabled>{% trans "Change" %}</button>
|
||||||
{% endifequal %}
|
{% endifequal %}
|
||||||
</form>
|
</form>
|
||||||
<div class="clearfix"></div>
|
<div class="clearfix"></div>
|
||||||
|
@ -898,7 +901,7 @@
|
||||||
</div>
|
</div>
|
||||||
<div class="col-sm-4">
|
<div class="col-sm-4">
|
||||||
<button type="button" class="btn btn-sm btn-success pull-left" name="random-mac-{{ forloop.counter0 }}"
|
<button type="button" class="btn btn-sm btn-success pull-left" name="random-mac-{{ forloop.counter0 }}"
|
||||||
onclick="random_mac({{ forloop.counter0 }})" style="margin-top: 2px;">{% trans "Random" %}</button>
|
onclick="random_mac('clone-net-mac-{{ forloop.counter0 }}')" style="margin-top: 2px;">{% trans "Random" %}</button>
|
||||||
<button type="button" class="btn btn-sm btn-success pull-left" name="guess-mac-{{ forloop.counter0 }}"
|
<button type="button" class="btn btn-sm btn-success pull-left" name="guess-mac-{{ forloop.counter0 }}"
|
||||||
onclick="guess_mac_address('#clone_name', {{ forloop.counter0 }})" style="margin-top: 2px;">{% trans "Guess" %}</button>
|
onclick="guess_mac_address('#clone_name', {{ forloop.counter0 }})" style="margin-top: 2px;">{% trans "Guess" %}</button>
|
||||||
</div>
|
</div>
|
||||||
|
@ -1230,7 +1233,7 @@
|
||||||
<script>
|
<script>
|
||||||
function random_mac(net) {
|
function random_mac(net) {
|
||||||
$.getJSON('/instance/random_mac_address/', function(data) {
|
$.getJSON('/instance/random_mac_address/', function(data) {
|
||||||
$('input[name="clone-net-mac-'+net+'"]').val(data['mac']);
|
$('input[name="'+net+'"]').val(data['mac']);
|
||||||
});
|
});
|
||||||
};
|
};
|
||||||
</script>
|
</script>
|
||||||
|
@ -1339,7 +1342,8 @@
|
||||||
});
|
});
|
||||||
{% if request.user.is_superuser %}
|
{% if request.user.is_superuser %}
|
||||||
$(document).ready(function () {
|
$(document).ready(function () {
|
||||||
random_mac(0);
|
random_mac('clone-net-mac-0');
|
||||||
|
random_mac('add-net-mac');
|
||||||
});
|
});
|
||||||
{% else %}
|
{% else %}
|
||||||
$('#select_clone_name').on('change', function () {
|
$('#select_clone_name').on('change', function () {
|
||||||
|
@ -1364,11 +1368,7 @@
|
||||||
<script>
|
<script>
|
||||||
function network_select_enable(){
|
function network_select_enable(){
|
||||||
// set network button enabled
|
// set network button enabled
|
||||||
var selected = $('network_select').val();
|
$('button[name="change_network"]').removeAttr('disabled');
|
||||||
if (selected != "to Change") {
|
|
||||||
$('button[name="change_network"]').removeAttr('disabled');
|
|
||||||
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
</script>
|
</script>
|
||||||
<script src="{% static "js/Chart.min.js" %}"></script>
|
<script src="{% static "js/Chart.min.js" %}"></script>
|
||||||
|
|
|
@ -321,6 +321,13 @@ def instance(request, compute_id, vname):
|
||||||
if dev not in existing_devs:
|
if dev not in existing_devs:
|
||||||
return dev
|
return dev
|
||||||
raise Exception(_('None available device name'))
|
raise Exception(_('None available device name'))
|
||||||
|
|
||||||
|
def get_network_tuple(network_source_str):
|
||||||
|
network_source_pack = network_source_str.split(":", 1)
|
||||||
|
if len(network_source_pack) > 1:
|
||||||
|
return (network_source_pack[1], network_source_pack[0])
|
||||||
|
else:
|
||||||
|
return (network_source_pack[0], 'net')
|
||||||
|
|
||||||
try:
|
try:
|
||||||
conn = wvmInstance(compute.hostname,
|
conn = wvmInstance(compute.hostname,
|
||||||
|
@ -329,6 +336,7 @@ def instance(request, compute_id, vname):
|
||||||
compute.type,
|
compute.type,
|
||||||
vname)
|
vname)
|
||||||
compute_networks = sorted(conn.get_networks())
|
compute_networks = sorted(conn.get_networks())
|
||||||
|
compute_interfaces = sorted(conn.get_ifaces())
|
||||||
status = conn.get_status()
|
status = conn.get_status()
|
||||||
autostart = conn.get_autostart()
|
autostart = conn.get_autostart()
|
||||||
vcpu = conn.get_vcpu()
|
vcpu = conn.get_vcpu()
|
||||||
|
@ -686,7 +694,11 @@ def instance(request, compute_id, vname):
|
||||||
network_data = {}
|
network_data = {}
|
||||||
|
|
||||||
for post in request.POST:
|
for post in request.POST:
|
||||||
if post.startswith('net-'):
|
if post.startswith('net-source-'):
|
||||||
|
(source, source_type) = get_network_tuple(request.POST.get(post))
|
||||||
|
network_data[post] = source
|
||||||
|
network_data[post + '-type'] = source_type
|
||||||
|
elif post.startswith('net-'):
|
||||||
network_data[post] = request.POST.get(post, '')
|
network_data[post] = request.POST.get(post, '')
|
||||||
|
|
||||||
conn.change_network(network_data)
|
conn.change_network(network_data)
|
||||||
|
@ -696,6 +708,17 @@ def instance(request, compute_id, vname):
|
||||||
messages.success(request, msg)
|
messages.success(request, msg)
|
||||||
return HttpResponseRedirect(request.get_full_path() + '#network')
|
return HttpResponseRedirect(request.get_full_path() + '#network')
|
||||||
|
|
||||||
|
if 'add_network' in request.POST:
|
||||||
|
mac = request.POST.get('add-net-mac')
|
||||||
|
(source, source_type) = get_network_tuple(request.POST.get('add-net-network'))
|
||||||
|
|
||||||
|
conn.add_network(mac, source, source_type)
|
||||||
|
msg = _("Edit network")
|
||||||
|
addlogmsg(request.user.username, instance.name, msg)
|
||||||
|
msg = _("Network Devices are changed. Please reboot instance to activate.")
|
||||||
|
messages.success(request, msg)
|
||||||
|
return HttpResponseRedirect(request.get_full_path() + '#network')
|
||||||
|
|
||||||
if 'add_owner' in request.POST:
|
if 'add_owner' in request.POST:
|
||||||
user_id = int(request.POST.get('user_id', ''))
|
user_id = int(request.POST.get('user_id', ''))
|
||||||
|
|
||||||
|
|
|
@ -742,18 +742,46 @@ class wvmInstance(wvmConnect):
|
||||||
|
|
||||||
return self.get_instance(clone_data['name']).UUIDString()
|
return self.get_instance(clone_data['name']).UUIDString()
|
||||||
|
|
||||||
|
def get_bridge_name(self, source, source_type='net'):
|
||||||
|
if source_type == 'iface':
|
||||||
|
iface = self.get_iface(source)
|
||||||
|
bridge_name = iface.name()
|
||||||
|
else:
|
||||||
|
net = self.get_network(source)
|
||||||
|
bridge_name = net.bridgeName()
|
||||||
|
return bridge_name
|
||||||
|
|
||||||
|
def add_network(self, mac_address, source, source_type='net', interface_type='bridge', model='virtio'):
|
||||||
|
tree = ElementTree.fromstring(self._XMLDesc(0))
|
||||||
|
bridge_name = self.get_bridge_name(source, source_type)
|
||||||
|
xml_interface = """
|
||||||
|
<interface type='%s'>
|
||||||
|
<mac address='%s'/>
|
||||||
|
<source bridge='%s'/>
|
||||||
|
<model type='%s'/>
|
||||||
|
</interface>
|
||||||
|
""" % (interface_type, mac_address, bridge_name, model)
|
||||||
|
if self.get_status() == 5:
|
||||||
|
devices = tree.find('devices')
|
||||||
|
elm_interface = ElementTree.fromstring(xml_interface)
|
||||||
|
devices.append(elm_interface)
|
||||||
|
xmldom = ElementTree.tostring(tree)
|
||||||
|
self._defineXML(xmldom)
|
||||||
|
|
||||||
def change_network(self, network_data):
|
def change_network(self, network_data):
|
||||||
xml = self._XMLDesc(VIR_DOMAIN_XML_SECURE)
|
xml = self._XMLDesc(VIR_DOMAIN_XML_SECURE)
|
||||||
tree = ElementTree.fromstring(xml)
|
tree = ElementTree.fromstring(xml)
|
||||||
|
|
||||||
for num, interface in enumerate(tree.findall('devices/interface')):
|
for num, interface in enumerate(tree.findall('devices/interface')):
|
||||||
net = self.get_network(network_data['net-source-' + str(num)])
|
net_source = network_data['net-source-' + str(num)]
|
||||||
|
net_source_type = network_data['net-source-' + str(num) + '-type']
|
||||||
|
net_mac = network_data['net-mac-' + str(num)]
|
||||||
|
bridge_name = self.get_bridge_name(net_source, net_source_type)
|
||||||
if interface.get('type') == 'bridge':
|
if interface.get('type') == 'bridge':
|
||||||
source = interface.find('mac')
|
source = interface.find('mac')
|
||||||
source.set('address', network_data['net-mac-' + str(num)])
|
source.set('address', net_mac)
|
||||||
source = interface.find('source')
|
source = interface.find('source')
|
||||||
source.set('bridge', net.bridgeName())
|
source.set('bridge', bridge_name)
|
||||||
source.set('network', net.name())
|
|
||||||
new_xml = ElementTree.tostring(tree)
|
new_xml = ElementTree.tostring(tree)
|
||||||
self._defineXML(new_xml)
|
self._defineXML(new_xml)
|
||||||
|
|
||||||
|
|
Loading…
Reference in a new issue