def reinstall(request, cluster_slug, instance): """ Reinstall a VM. """ user = request.user instance = get_object_or_404(VirtualMachine, cluster__slug=cluster_slug, hostname=instance) # Check permissions. # XXX Reinstalling is somewhat similar to deleting in that you destroy data, # so use that for now. if not ( user.is_superuser or user.has_any_perms(instance, ["remove", "admin"]) or user.has_perm("admin", instance.cluster) ): return render_403(request, 'You do not have sufficient privileges') if request.method == 'GET': return render_to_response("virtual_machine/reinstall.html", {'vm': instance, 'oschoices': cluster_os_list(instance.cluster), 'current_os': instance.operating_system, 'submitted': False}, context_instance=RequestContext(request), ) elif request.method == 'POST': # Reinstall instance if "os" in request.POST: os = request.POST["os"] else: os = instance.operating_system # XXX no_startup=True prevents quota circumventions. possible future solution would be a checkbox # asking whether they want to start up, and check quota here if they do (would also involve # checking whether this VM is already running and subtracting that) job_id = instance.rapi.ReinstallInstance(instance.hostname, os=os, no_startup=True) job = Job.objects.create(job_id=job_id, obj=instance, cluster=instance.cluster) VirtualMachine.objects.filter(id=instance.id).update(last_job=job, ignore_cache=True) # log information log_action('VM_REINSTALL', user, instance, job) return HttpResponseRedirect( reverse('instance-detail', args=[instance.cluster.slug, instance.hostname])) return HttpResponseNotAllowed(["GET","POST"])
def cluster_options(request): """ Ajax view for retrieving node and operating system choices for a given cluster. """ cluster_id = request.GET.get('cluster_id', None) cluster = get_object_or_404(Cluster, id__exact=cluster_id) user = request.user if not (user.is_superuser or user.has_perm('create_vm', cluster) or user.has_perm('admin', cluster)): return render_403(request, 'You do not have permissions to view this cluster') oslist = cluster_os_list(cluster) nodes = [str(h) for h in cluster.nodes.values_list('hostname', flat=True)] content = json.dumps({'nodes':nodes, 'os':oslist}) return HttpResponse(content, mimetype='application/json')
def modify(request, cluster_slug, instance): cluster = get_object_or_404(Cluster, slug=cluster_slug) vm = get_object_or_404(VirtualMachine, hostname=instance, cluster=cluster) user = request.user if not (user.is_superuser or user.has_any_perms(vm, ['admin','modify']) or user.has_perm('admin', cluster)): return render_403(request, 'You do not have permissions to edit this virtual machine') if request.method == 'POST': form = ModifyVirtualMachineForm(user, None, request.POST) form.fields['os'].choices = request.session['os_list'] if form.is_valid(): data = form.cleaned_data request.session['edit_form'] = data return HttpResponseRedirect( reverse('instance-modify-confirm', args=[cluster.slug, vm.hostname])) elif request.method == 'GET': if 'edit_form' in request.session: form = ModifyVirtualMachineForm(user, cluster, request.session['edit_form']) del request.session['edit_form'] else: # Need to set initial values from vm.info as these are not saved # per the vm model. if vm.info and 'hvparams' in vm.info: info = vm.info initial = {} hvparams = info['hvparams'] # XXX Convert ram string since it comes out # from ganeti as an int and the DataVolumeField does not like # ints. initial['vcpus'] = info['beparams']['vcpus'] initial['memory'] = str(info['beparams']['memory']) initial['nic_link'] = info['nic.links'][0] initial['nic_mac'] = info['nic.macs'][0] initial['os'] = info['os'] fields = ('acpi', 'disk_cache', 'initrd_path', 'kernel_args', 'kvm_flag', 'mem_path', 'migration_downtime', 'security_domain', 'security_model', 'usb_mouse', 'use_chroot', 'use_localtime', 'vnc_bind_address', 'vnc_tls', 'vnc_x509_path', 'vnc_x509_verify', 'disk_type', 'boot_order', 'nic_type', 'root_path', 'kernel_path', 'serial_console', 'cdrom_image_path', ) for field in fields: initial[field] = hvparams[field] form = ModifyVirtualMachineForm(user, cluster, initial=initial) # Get the list of oses from the cluster os_list = cluster_os_list(cluster) # Set os_list for cluster in session request.session['os_list'] = os_list form.fields['os'].choices = os_list return render_to_response("virtual_machine/edit.html", { 'cluster': cluster, 'instance': vm, 'form': form, }, context_instance=RequestContext(request), )
def __init__(self, user, cluster=None, initial=None, *args, **kwargs): self.user = user super(NewVirtualMachineForm, self).__init__(initial, *args, **kwargs) if initial: if 'cluster' in initial and initial['cluster']: try: cluster = Cluster.objects.get(pk=initial['cluster']) except Cluster.DoesNotExist: # defer to clean function to return errors pass if cluster is not None: # set choices based on selected cluster if given oslist = cluster_os_list(cluster) nodelist = [str(h) for h in cluster.nodes.values_list('hostname', flat=True)] nodes = zip(nodelist, nodelist) nodes.insert(0, self.empty_field) oslist.insert(0, self.empty_field) self.fields['pnode'].choices = nodes self.fields['snode'].choices = nodes self.fields['os'].choices = oslist defaults = cluster_default_info(cluster) if defaults['iallocator'] != '' : self.fields['iallocator'].initial = True self.fields['iallocator_hostname'] = forms.CharField( \ initial=defaults['iallocator'], \ required=False, \ widget = forms.HiddenInput()) self.fields['vcpus'].initial = defaults['vcpus'] self.fields['memory'].initial = defaults['memory'] self.fields['disk_type'].initial = defaults['disk_type'] self.fields['root_path'].initial = defaults['root_path'] self.fields['kernel_path'].initial = defaults['kernel_path'] self.fields['serial_console'].initial = defaults['serial_console'] self.fields['nic_link'].initial = defaults['nic_link'] # set cluster choices based on the given owner if initial and 'owner' in initial and initial['owner']: try: self.owner = ClusterUser.objects.get(pk=initial['owner']).cast() except ClusterUser.DoesNotExist: self.owner = None else: self.owner = None # Set up owner and cluster choices. if user.is_superuser: # Superusers may do whatever they like. self.fields['owner'].queryset = ClusterUser.objects.all() self.fields['cluster'].queryset = Cluster.objects.all() else: # Fill out owner choices. Remember, the list of owners is a list # of tuple(ClusterUser.id, label). If you put ids from other # Models into this, no magical correction will be applied and you # will assign permissions to the wrong owner; see #2007. owners = [(u'', u'---------')] for group in user.groups.all(): owners.append((group.organization.id, group.name)) if user.has_any_perms(Cluster, ['admin','create_vm'], False): profile = user.get_profile() owners.append((profile.id, profile.name)) self.fields['owner'].choices = owners # Set cluster choices. If an owner has been selected then filter # by the owner. Otherwise show everything the user has access to # through themselves or any groups they are a member of if self.owner: q = self.owner.get_objects_any_perms(Cluster, ['admin','create_vm']) else: q = user.get_objects_any_perms(Cluster, ['admin','create_vm']) self.fields['cluster'].queryset = q