From 07a464231d541203c9baef9dd0e13b95f79a60eb Mon Sep 17 00:00:00 2001
From: Arvind Tiwari <tiwariav@gmail.com>
Date: Thu, 14 Sep 2017 02:24:10 +0530
Subject: [PATCH 01/82] animation added to vm termination

---
 hosting/static/hosting/css/landing-page.css   |   3 +
 .../static/hosting/css/virtual-machine.css    |  33 ++++++++
 hosting/static/hosting/img/ajax-loader.gif    | Bin 0 -> 404 bytes
 .../hosting/js/virtual_machine_detail.js      |  38 ++++++++-
 .../hosting/includes/_navbar_user.html        |   5 --
 .../hosting/virtual_machine_detail.html       |  35 ++++----
 hosting/urls.py                               |   2 +
 hosting/views.py                              |  76 +++++++++++-------
 8 files changed, 141 insertions(+), 51 deletions(-)
 create mode 100644 hosting/static/hosting/img/ajax-loader.gif

diff --git a/hosting/static/hosting/css/landing-page.css b/hosting/static/hosting/css/landing-page.css
index 71b7a33d..9d067b3c 100644
--- a/hosting/static/hosting/css/landing-page.css
+++ b/hosting/static/hosting/css/landing-page.css
@@ -853,6 +853,9 @@ a.list-group-item-danger:focus,
 .panel-danger > .panel-heading {
     color: #eb4d5c;
 }
+.alert-danger{
+    background: rgba(235, 204, 209, 0.2);
+}
 .has-error .form-control,
 .has-error .input-group-addon {
     color: #eb4d5c;
diff --git a/hosting/static/hosting/css/virtual-machine.css b/hosting/static/hosting/css/virtual-machine.css
index b4916da0..b6afe4ef 100644
--- a/hosting/static/hosting/css/virtual-machine.css
+++ b/hosting/static/hosting/css/virtual-machine.css
@@ -290,6 +290,11 @@
   text-align: center;
 }
 
+.vm-vmid .alert {
+  margin-top: 15px;
+  margin-bottom: -60px;
+}
+
 .vm-item-lg {
   font-size: 22px;
   margin-top: 5px;
@@ -305,6 +310,10 @@
   color: #e47f2f;
 }
 
+.vm-color-failed {
+  color: #eb4d5c;
+}
+
 .vm-detail-item .value{
   font-weight: 400;
 }
@@ -627,4 +636,28 @@
     left: auto;
     right: 8px;
   }
+}
+
+.processing > .btn {
+  position: relative;
+  border-color: #eee;
+}
+.processing > .btn:hover,
+.processing > .btn:focus,
+.processing > .btn:active {
+  border-color: #eee;
+}
+
+.processing > .btn:after {
+  content: ' ';
+  display: block;
+  position: absolute;
+  background-image: url('/static/hosting/img/ajax-loader.gif');
+  background-repeat: no-repeat;
+  background-position: center;
+  background-color: #eee;
+  width: 100%;
+  top: 0;
+  height: 100%;
+  left: 0;
 }
\ No newline at end of file
diff --git a/hosting/static/hosting/img/ajax-loader.gif b/hosting/static/hosting/img/ajax-loader.gif
new file mode 100644
index 0000000000000000000000000000000000000000..a7c3f2bacbe630950c16f53e3c27dd840f2e8622
GIT binary patch
literal 404
zcmZ?wbhEHb)Mnsj_{hNU?%lhzw6s;LRsl)He^Smxsfi`2DGKG8B^e5dS&0=n`H3ld
znR#jX42nNl7`PZ17!?0=`?-b$J39ur8tEA@GXjNlfS3VfAOn+8OCQJSX*X{)e?H13
zeJ||u>DC8kZ4r?R)6{G4&Dyt|CtcU`diyE8Uq?3owA-;j!N^AxXd>8TMr31bj{uEP
z;7?56IIHFOnwrlu67PNQNtrQY{;7pt&RzvNJJ_?&Ze06Pg>MsMs)$s6#HZT6Q+}5p
z&C*E<I=&ueA`^;<Acq+MO<XxEEBa3UBYrO7?UfHJdzM^TuwobAGVVjKeUi;OpPxMU
z@@LSj8EZ_>81%TGdiiN4(8Lw%U?wsno9F=b>WnG7*rn?>{@R)9v%+M)yIi1FiTcrX
vD}VECG@HG3ZvWp+k0+)$$G&~0?NxTdRajt8g3>tw(O*m=3=Gzwa03GXAUBr*

literal 0
HcmV?d00001

diff --git a/hosting/static/hosting/js/virtual_machine_detail.js b/hosting/static/hosting/js/virtual_machine_detail.js
index 303f95ca..ce97d44e 100644
--- a/hosting/static/hosting/js/virtual_machine_detail.js
+++ b/hosting/static/hosting/js/virtual_machine_detail.js
@@ -2,7 +2,43 @@
 $( document ).ready(function() {
 
 	$('#confirm-cancel').on('click', '.btn-ok', function(e) {
-		$('#virtual_machine_cancel_form').trigger('submit');
+    var url = $('#virtual_machine_cancel_form').attr('action');
+    var $container = $('#terminate-VM');
+    var $btn = $container.find('.btn');
+    var text = $container.find('.vm-item-lg').text();
+    var altText = $container.attr('data-alt');
+    $container.find('.alert-danger').addClass('hide');
+    $container.addClass('processing')
+      .find('.vm-item-lg').attr('class', '')
+      .addClass('vm-item-lg vm-color-failed')
+      .text(altText);
+    $btn.prop('disabled', true);
+    $('#confirm-cancel').modal('hide');
+    $.post(url)
+      .done(function(data) {
+        console.log( "success" , data);
+        if (data.status == true) {
+          $container.addClass('terminate-success')
+            .find('.vm-item-lg').text(data.text);
+          $btn.remove();
+          // window.location = data.redirect;
+        }
+        else {
+          $container.addClass('terminate-fail')
+            .find('.vm-item-lg').text(text);
+          $container.find('.btn').prop('disabled', false);
+          $container.find('.alert-danger').text(data.text).removeClass('hide');
+        }
+      })
+      .fail(function(data) {
+        $container.addClass('terminate-fail')
+          .find('.vm-item-lg').text(text);
+        $container.find('.btn').prop('disabled', false);
+        $container.find('.alert-danger').removeClass('hide');
+      })
+      .always(function(data) {
+        $container.removeClass('processing');
+      });
 	});
 
   var hash = window.location.hash;
diff --git a/hosting/templates/hosting/includes/_navbar_user.html b/hosting/templates/hosting/includes/_navbar_user.html
index d06477ca..37c01109 100644
--- a/hosting/templates/hosting/includes/_navbar_user.html
+++ b/hosting/templates/hosting/includes/_navbar_user.html
@@ -37,11 +37,6 @@
                 </li>
                 <li>
                     {% get_current_language as LANGUAGE_CODE %}
-                    {% if LANGUAGE_CODE == 'en-us'%}
-                        <a href="{% change_lang 'de' %}"><i class="fa fa-fw fa-globe" aria-hidden="true"></i>&nbsp;&nbsp;Deutsch</a>
-                    {% else %}
-                        <a href="{% change_lang 'en-us' %}"><i class="fa fa-fw fa-globe" aria-hidden="true"></i>&nbsp;&nbsp;English</a>
-                    {% endif %}
                 </li>
             </ul>
         </div>
diff --git a/hosting/templates/hosting/virtual_machine_detail.html b/hosting/templates/hosting/virtual_machine_detail.html
index 6243c309..a5c82e90 100644
--- a/hosting/templates/hosting/virtual_machine_detail.html
+++ b/hosting/templates/hosting/virtual_machine_detail.html
@@ -46,26 +46,33 @@
 				<div class="vm-vmid">
 					<div class="vm-item-subtitle">{% trans "Current Pricing" %}</div>
 					<div class="vm-item-lg">{{virtual_machine.price|floatformat}} CHF/{% trans "Month" %}</div>
-					<a class="btn btn-vm-invoice" href="{% url 'hosting:orders' order.pk %}">{% trans "See Invoice" %}</a>
+					<a class="btn btn-vm-invoice" href="{% url 'hosting:orders' 2 %}">{% trans "See Invoice" %}</a>
 				</div>
 			</div>
 			<div class="vm-detail-item">
 				<h2 class="vm-detail-title">{% trans "Status" %} <img src="{% static 'hosting/img/connected.svg' %}" class="un-icon"></h2>
 				<div class="vm-vmid">
 					<div class="vm-item-subtitle">{% trans "Your VM is" %}</div>
-					{% if virtual_machine.state == 'PENDING' %}
-						<div class="vm-item-lg vm-color-pending">{% trans "Pending" %}</div>
-					{% elif  virtual_machine.state == 'ACTIVE' %}
-						<div class="vm-item-lg vm-color-online">{% trans "Online" %}</div>
-					{% elif  virtual_machine.state == 'FAILED'%}
-						<div class="vm-item-lg vm-color-failed">{% trans "Failed" %}</div>
-					{% endif %}
-					{% if not virtual_machine.status == 'canceled' %}
-						<form method="POST" id="virtual_machine_cancel_form" class="cancel-form" action="{% url 'hosting:virtual_machines' virtual_machine.vm_id %}">
-							{% csrf_token %}
-						</form>
-						<button data-href="{% url 'hosting:virtual_machines' virtual_machine.vm_id %}" data-toggle="modal" data-target="#confirm-cancel" class="btn btn-vm-term">{% trans "Terminate VM" %}</button>
-					{% endif %}
+						<div id="terminate-VM" data-alt="{% trans 'Terminating' %}">
+							{% if virtual_machine.state == 'PENDING' %}
+								<div class="vm-item-lg vm-color-pending">{% trans "Pending" %}</div>
+							{% elif  virtual_machine.state == 'ACTIVE' %}
+								<div class="vm-item-lg vm-color-online">{% trans "Online" %}</div>
+							{% elif  virtual_machine.state == 'FAILED'%}
+								<div class="vm-item-lg vm-color-failed">{% trans "Failed" %}</div>
+							{% else %}
+								<div class="vm-item-lg"></div>
+							{% endif %}
+							{% if not virtual_machine.status == 'canceled' %}
+								<form method="POST" id="virtual_machine_cancel_form" class="cancel-form" action="{% url 'hosting:virtual_machines' 2 %}">
+									{% csrf_token %}
+								</form>
+								<button data-toggle="modal" data-target="#confirm-cancel" class="btn btn-vm-term">{% trans "Terminate VM" %}</button>
+								<div class="alert alert-danger hide">
+									{% trans "Sorry, there was an unexpected error. Kindly retry." %}
+								</div>
+							{% endif %}
+						</div>
 				</div>
 			</div>
 		</div>
diff --git a/hosting/urls.py b/hosting/urls.py
index 10e09dd0..c3b982cb 100644
--- a/hosting/urls.py
+++ b/hosting/urls.py
@@ -10,9 +10,11 @@ from .views import (
     HostingBillDetailView, SSHKeyDeleteView, SSHKeyCreateView, SSHKeyListView,
     SSHKeyChoiceView, DashboardView, SettingsView)
 
+from django.views.generic import TemplateView
 
 
 urlpatterns = [
+    url(r'test/?$', TemplateView.as_view(template_name='hosting/virtual_machine_detail.html')),
     url(r'index/?$', IndexView.as_view(), name='index'),
     url(r'django/?$', DjangoHostingView.as_view(), name='djangohosting'),
     url(r'dashboard/?$', DashboardView.as_view(), name='dashboard'),
diff --git a/hosting/views.py b/hosting/views.py
index f7d6e414..df6e6100 100644
--- a/hosting/views.py
+++ b/hosting/views.py
@@ -1,4 +1,6 @@
 import uuid
+import json
+from time import sleep
 
 from django.conf import settings
 from django.contrib import messages
@@ -6,13 +8,12 @@ from django.contrib.auth.mixins import LoginRequiredMixin
 from django.contrib.auth.tokens import default_token_generator
 from django.core.files.base import ContentFile
 from django.core.urlresolvers import reverse_lazy, reverse
-from django.http import Http404
-from django.http import HttpResponseRedirect
-from django.shortcuts import redirect
-from django.shortcuts import render
+from django.http import Http404, HttpResponseRedirect, HttpResponse
+from django.shortcuts import redirect, render
 from django.utils.http import urlsafe_base64_decode
 from django.utils.safestring import mark_safe
 from django.utils.translation import ugettext_lazy as _
+from django.utils.translation import ugettext
 from django.views.generic import View, CreateView, FormView, ListView, \
     DetailView, \
     DeleteView, TemplateView, UpdateView
@@ -711,7 +712,7 @@ class PaymentVMView(LoginRequiredMixin, FormView):
                                                request.get_host()),
                 'page_header': _(
                     'Your New VM %(vm_name)s at Data Center Light') % {
-                                   'vm_name': vm.get('name')}
+                    'vm_name': vm.get('name')}
             }
             email_data = {
                 'subject': context.get('page_header'),
@@ -924,6 +925,7 @@ class VirtualMachineView(LoginRequiredMixin, View):
         return render(request, self.template_name, context)
 
     def post(self, request, *args, **kwargs):
+        response = {}
         owner = self.request.user
         vm = self.get_object()
 
@@ -934,41 +936,53 @@ class VirtualMachineView(LoginRequiredMixin, View):
             password=owner.password
         )
         vm_data = VirtualMachineSerializer(manager.get_vm(vm.id)).data
-        terminated = manager.delete_vm(
-            vm.id
-        )
+
+        terminated = manager.delete_vm(vm.id)
 
         if not terminated:
             messages.error(
                 request,
                 'Error terminating VM %s' % (opennebula_vm_id)
             )
-            return HttpResponseRedirect(self.get_success_url())
-        context = {
-            'vm': vm_data,
-            'base_url': "{0}://{1}".format(self.request.scheme,
-                                           self.request.get_host()),
-            'page_header': _('Virtual Machine Cancellation')
-        }
-        email_data = {
-            'subject': context['page_header'],
-            'to': self.request.user.email,
-            'context': context,
-            'template_name': 'vm_canceled',
-            'template_path': 'hosting/emails/',
-            'from_address': settings.DCL_SUPPORT_FROM_ADDRESS,
-        }
-        email = BaseEmail(**email_data)
-        email.send()
+            response['status'] = False
+        else:
+            context = {
+                'vm': vm_data,
+                'base_url': "{0}://{1}".format(self.request.scheme,
+                                               self.request.get_host()),
+                'page_header': _('Virtual Machine Cancellation')
+            }
+            email_data = {
+                'subject': context['page_header'],
+                'to': self.request.user.email,
+                'context': context,
+                'template_name': 'vm_canceled',
+                'template_path': 'hosting/emails/',
+                'from_address': settings.DCL_SUPPORT_FROM_ADDRESS,
+            }
+            email = BaseEmail(**email_data)
+            email.send()
 
-        messages.error(
-            request,
-            _('VM %(VM_ID)s terminated successfully') % {
-                'VM_ID': opennebula_vm_id}
+            # messages.error(
+            #     request,
+            #     _('VM %(VM_ID)s terminated successfully') % {
+            #         'VM_ID': opennebula_vm_id}
+            # )
+            deleting = True
+            t = 0
+            while deleting:
+                if t < 150 and manager.get_vm(self.kwargs.get('pk')):
+                    sleep(2)
+                else:
+                    deleting = False
+            response['status'] = True
+            response['redirect'] = self.get_success_url()
+            response['text'] = ugettext('Terminated')
+        return HttpResponse(
+            json.dumps(response),
+            content_type="application/json"
         )
 
-        return HttpResponseRedirect(self.get_success_url())
-
 
 class HostingBillListView(PermissionRequiredMixin, LoginRequiredMixin,
                           ListView):

From 8ca1b13f80a70c7ed1bdf29836d60ae3e302b1b9 Mon Sep 17 00:00:00 2001
From: Arvind Tiwari <tiwariav@gmail.com>
Date: Thu, 14 Sep 2017 02:29:51 +0530
Subject: [PATCH 02/82] template fixed

---
 hosting/templates/hosting/virtual_machine_detail.html | 4 ++--
 1 file changed, 2 insertions(+), 2 deletions(-)

diff --git a/hosting/templates/hosting/virtual_machine_detail.html b/hosting/templates/hosting/virtual_machine_detail.html
index a5c82e90..d0bfae47 100644
--- a/hosting/templates/hosting/virtual_machine_detail.html
+++ b/hosting/templates/hosting/virtual_machine_detail.html
@@ -46,7 +46,7 @@
 				<div class="vm-vmid">
 					<div class="vm-item-subtitle">{% trans "Current Pricing" %}</div>
 					<div class="vm-item-lg">{{virtual_machine.price|floatformat}} CHF/{% trans "Month" %}</div>
-					<a class="btn btn-vm-invoice" href="{% url 'hosting:orders' 2 %}">{% trans "See Invoice" %}</a>
+					<a class="btn btn-vm-invoice" href="{% url 'hosting:orders' order.pk %}">{% trans "See Invoice" %}</a>
 				</div>
 			</div>
 			<div class="vm-detail-item">
@@ -64,7 +64,7 @@
 								<div class="vm-item-lg"></div>
 							{% endif %}
 							{% if not virtual_machine.status == 'canceled' %}
-								<form method="POST" id="virtual_machine_cancel_form" class="cancel-form" action="{% url 'hosting:virtual_machines' 2 %}">
+								<form method="POST" id="virtual_machine_cancel_form" class="cancel-form" action="{% url 'hosting:virtual_machines' virtual_machine.vm_id %}">
 									{% csrf_token %}
 								</form>
 								<button data-toggle="modal" data-target="#confirm-cancel" class="btn btn-vm-term">{% trans "Terminate VM" %}</button>

From abc290de61c748a22f0ae85d5ffe8820ff9d455d Mon Sep 17 00:00:00 2001
From: Arvind Tiwari <tiwariav@gmail.com>
Date: Thu, 14 Sep 2017 02:43:01 +0530
Subject: [PATCH 03/82] added error msg

---
 hosting/views.py | 5 +----
 1 file changed, 1 insertion(+), 4 deletions(-)

diff --git a/hosting/views.py b/hosting/views.py
index df6e6100..ca80a8d1 100644
--- a/hosting/views.py
+++ b/hosting/views.py
@@ -940,11 +940,8 @@ class VirtualMachineView(LoginRequiredMixin, View):
         terminated = manager.delete_vm(vm.id)
 
         if not terminated:
-            messages.error(
-                request,
-                'Error terminating VM %s' % (opennebula_vm_id)
-            )
             response['status'] = False
+            response['text'] = 'Error terminating VM %s' % (opennebula_vm_id)
         else:
             context = {
                 'vm': vm_data,

From a808f3bf7e2173fbf44e0521591981f2e38e4d57 Mon Sep 17 00:00:00 2001
From: Arvind Tiwari <tiwariav@gmail.com>
Date: Thu, 14 Sep 2017 02:48:56 +0530
Subject: [PATCH 04/82] error fix on termination

---
 hosting/views.py | 14 +++++++++-----
 1 file changed, 9 insertions(+), 5 deletions(-)

diff --git a/hosting/views.py b/hosting/views.py
index ca80a8d1..685fe0b4 100644
--- a/hosting/views.py
+++ b/hosting/views.py
@@ -965,13 +965,17 @@ class VirtualMachineView(LoginRequiredMixin, View):
             #     _('VM %(VM_ID)s terminated successfully') % {
             #         'VM_ID': opennebula_vm_id}
             # )
-            deleting = True
             t = 0
-            while deleting:
-                if t < 150 and manager.get_vm(self.kwargs.get('pk')):
-                    sleep(2)
+            while True:
+                if t > 150:
+                    break
+                try:
+                    manager.get_vm(self.kwargs.get('pk'))
+                except:
+                    break
                 else:
-                    deleting = False
+                    sleep(2)
+
             response['status'] = True
             response['redirect'] = self.get_success_url()
             response['text'] = ugettext('Terminated')

From e045caebbe6f704b6a95fc7763365de1c2e18a2e Mon Sep 17 00:00:00 2001
From: Arvind Tiwari <tiwariav@gmail.com>
Date: Thu, 14 Sep 2017 02:52:37 +0530
Subject: [PATCH 05/82] redirect on success

---
 hosting/static/hosting/js/virtual_machine_detail.js | 2 +-
 hosting/views.py                                    | 2 +-
 2 files changed, 2 insertions(+), 2 deletions(-)

diff --git a/hosting/static/hosting/js/virtual_machine_detail.js b/hosting/static/hosting/js/virtual_machine_detail.js
index ce97d44e..076ec344 100644
--- a/hosting/static/hosting/js/virtual_machine_detail.js
+++ b/hosting/static/hosting/js/virtual_machine_detail.js
@@ -21,7 +21,7 @@ $( document ).ready(function() {
           $container.addClass('terminate-success')
             .find('.vm-item-lg').text(data.text);
           $btn.remove();
-          // window.location = data.redirect;
+          window.location = data.redirect;
         }
         else {
           $container.addClass('terminate-fail')
diff --git a/hosting/views.py b/hosting/views.py
index 685fe0b4..cf17c9f8 100644
--- a/hosting/views.py
+++ b/hosting/views.py
@@ -971,7 +971,7 @@ class VirtualMachineView(LoginRequiredMixin, View):
                     break
                 try:
                     manager.get_vm(self.kwargs.get('pk'))
-                except:
+                except BaseException:
                     break
                 else:
                     sleep(2)

From 8393afe1418408b8cfac9c7d71c608e10b446293 Mon Sep 17 00:00:00 2001
From: Arvind Tiwari <tiwariav@gmail.com>
Date: Thu, 14 Sep 2017 02:59:08 +0530
Subject: [PATCH 06/82] translations and test methods removed

---
 hosting/locale/de/LC_MESSAGES/django.po | 21 +++++++++++++++++----
 hosting/urls.py                         |  3 ---
 hosting/views.py                        |  3 ++-
 3 files changed, 19 insertions(+), 8 deletions(-)

diff --git a/hosting/locale/de/LC_MESSAGES/django.po b/hosting/locale/de/LC_MESSAGES/django.po
index 780419b1..2f6cee4e 100644
--- a/hosting/locale/de/LC_MESSAGES/django.po
+++ b/hosting/locale/de/LC_MESSAGES/django.po
@@ -8,7 +8,7 @@ msgid ""
 msgstr ""
 "Project-Id-Version: PACKAGE VERSION\n"
 "Report-Msgid-Bugs-To: \n"
-"POT-Creation-Date: 2017-09-09 06:04+0000\n"
+"POT-Creation-Date: 2017-09-14 02:55+0530\n"
 "PO-Revision-Date: YEAR-MO-DA HO:MI+ZONE\n"
 "Last-Translator: FULL NAME <EMAIL@ADDRESS>\n"
 "Language-Team: LANGUAGE <LL@li.org>\n"
@@ -524,6 +524,9 @@ msgstr "Aktueller Preis"
 msgid "Your VM is"
 msgstr "Deine VM ist"
 
+msgid "Terminating"
+msgstr "Beenden"
+
 msgid "Pending"
 msgstr "In Vorbereitung"
 
@@ -536,6 +539,11 @@ msgstr "Fehlgeschlagen"
 msgid "Terminate VM"
 msgstr "VM Beenden"
 
+msgid "Sorry, there was an unexpected error. Kindly retry."
+msgstr ""
+"Bitte entschuldige, es scheint ein unerwarteter Fehler aufgetreten zu sein. "
+"Versuche es doch bitte noch einmal."
+
 msgid "Something doesn't work?"
 msgstr "Etwas funktioniert nicht?"
 
@@ -624,12 +632,17 @@ msgid ""
 "contact Data Center Light Support."
 msgstr "Kontaktiere den Data Center Light Support."
 
+msgid "Error terminating VM"
+msgstr "Fehler beenden VM"
+
 msgid "Virtual Machine Cancellation"
 msgstr "VM Kündigung"
 
-#, python-format
-msgid "VM %(VM_ID)s terminated successfully"
-msgstr "VM %(VM_ID)s erfolgreich beendet"
+msgid "Terminated"
+msgstr "Beendet"
+
+#~ msgid "VM %(VM_ID)s terminated successfully"
+#~ msgstr "VM %(VM_ID)s erfolgreich beendet"
 
 #~ msgid "My Virtual Machines"
 #~ msgstr "Meine virtuellen Maschinen"
diff --git a/hosting/urls.py b/hosting/urls.py
index c3b982cb..455aa97f 100644
--- a/hosting/urls.py
+++ b/hosting/urls.py
@@ -10,11 +10,8 @@ from .views import (
     HostingBillDetailView, SSHKeyDeleteView, SSHKeyCreateView, SSHKeyListView,
     SSHKeyChoiceView, DashboardView, SettingsView)
 
-from django.views.generic import TemplateView
-
 
 urlpatterns = [
-    url(r'test/?$', TemplateView.as_view(template_name='hosting/virtual_machine_detail.html')),
     url(r'index/?$', IndexView.as_view(), name='index'),
     url(r'django/?$', DjangoHostingView.as_view(), name='djangohosting'),
     url(r'dashboard/?$', DashboardView.as_view(), name='dashboard'),
diff --git a/hosting/views.py b/hosting/views.py
index cf17c9f8..4d9aeb18 100644
--- a/hosting/views.py
+++ b/hosting/views.py
@@ -941,7 +941,8 @@ class VirtualMachineView(LoginRequiredMixin, View):
 
         if not terminated:
             response['status'] = False
-            response['text'] = 'Error terminating VM %s' % (opennebula_vm_id)
+            response['text'] = ugettext(
+                'Error terminating VM') + opennebula_vm_id
         else:
             context = {
                 'vm': vm_data,

From a1a90ed5d0a79940fc1528d2e7ec061e4a3323d4 Mon Sep 17 00:00:00 2001
From: Arvind Tiwari <tiwariav@gmail.com>
Date: Fri, 15 Sep 2017 00:14:09 +0530
Subject: [PATCH 07/82] while loop code formating

---
 hosting/views.py | 16 +++++++++-------
 1 file changed, 9 insertions(+), 7 deletions(-)

diff --git a/hosting/views.py b/hosting/views.py
index 4d9aeb18..290d5f0f 100644
--- a/hosting/views.py
+++ b/hosting/views.py
@@ -968,14 +968,16 @@ class VirtualMachineView(LoginRequiredMixin, View):
             # )
             t = 0
             while True:
-                if t > 150:
-                    break
-                try:
-                    manager.get_vm(self.kwargs.get('pk'))
-                except BaseException:
-                    break
+                if t < 150:
+                    t += 1
+                    try:
+                        manager.get_vm(self.kwargs.get('pk'))
+                    except BaseException:
+                        break
+                    else:
+                        sleep(2)
                 else:
-                    sleep(2)
+                    break
 
             response['status'] = True
             response['redirect'] = self.get_success_url()

From c2b5c620147231de927719384b92091a94fb31ab Mon Sep 17 00:00:00 2001
From: Arvind Tiwari <tiwariav@gmail.com>
Date: Fri, 15 Sep 2017 00:49:39 +0530
Subject: [PATCH 08/82] hosting calculator added

---
 .../static/hosting/css/price_calculator.css   | 186 ++++++++++++++++++
 hosting/templates/hosting/base_short.html     |   4 +-
 .../templates/hosting/calculator_form.html    | 123 ++++++++++++
 .../hosting/create_virtual_machine.html       |  87 +++-----
 4 files changed, 334 insertions(+), 66 deletions(-)
 create mode 100644 hosting/static/hosting/css/price_calculator.css
 create mode 100644 hosting/templates/hosting/calculator_form.html

diff --git a/hosting/static/hosting/css/price_calculator.css b/hosting/static/hosting/css/price_calculator.css
new file mode 100644
index 00000000..bf99c66f
--- /dev/null
+++ b/hosting/static/hosting/css/price_calculator.css
@@ -0,0 +1,186 @@
+/*Pricing page*/
+
+.price-calc-section {
+    padding: 80px 40px !important;
+    background: -webkit-linear-gradient(top, #f0f4f7, #fff) no-repeat;
+    background: linear-gradient(to bottom, #f0f4f7, #fff) no-repeat;
+    display: flex;
+    /*font-family: 'Lato', sans-serif;*/
+/*     font-weight: normal; */
+}
+
+.price-calc-section .text {
+    width: 50%;
+}
+
+.price-calc-section .text .section-heading {
+    font-size: 48px;
+    line-height: 48px;
+    padding-bottom: 27px;
+    color: #3a3a3a;
+    letter-spacing: 1px;
+    position: relative;
+    text-align: right;
+}
+
+.price-calc-section .text .description {
+    font-size: 20px;
+    text-align: right;
+}
+
+.price-calc-section .text .section-heading::before {
+    content: "";
+    position: absolute;
+    bottom: 0;
+    background: #29427A;
+    height: 7px;
+    width: 70px;
+    right: 0;
+}
+
+.price-calc-section .card {
+    width: 50%;
+    margin: 0 auto;
+    background: #fff;
+    box-shadow: 0 10px 20px rgba(0, 0, 0, 0.19), 0 6px 6px rgba(0, 0, 0, 0.23);
+    padding-bottom: 40px;
+    border-radius: 7px;
+    text-align: center;
+    /* margin-right: auto; */
+    max-width: 400px;
+    position: relative;
+}
+
+.price-calc-section .landing {
+    width: 100% !important;
+}
+
+.no-padding {
+    padding: 0 !important;
+}
+
+.price-calc-section .card .img-beta {
+    position: absolute;
+    top: 5px;
+    width: 60px;
+    left: 3px;
+}
+
+.price-calc-section .card .title {
+    padding: 15px 40px;
+}
+
+.price-calc-section .card .title h3 {
+    /*font-family: 'Lato', sans-serif;*/
+    font-weight: normal;
+}
+
+.price-calc-section .card .price {
+    background: #5A74AF;
+    padding: 22px;
+    color: #fff;
+    font-size: 32px;
+}
+
+.price-calc-section .card .price .price-text {
+    font-size: 14px;
+}
+
+.price-calc-section .card .description {
+    padding: 12px;
+    position: relative;
+    display: flex;
+    justify-content: space-around !important;
+    align-items: center !important;
+}
+
+.price-calc-section .card .description span {
+    font-size: 16px;
+    margin-left: 4px;
+    margin-left: 0px;
+    /* justify-self: start; */
+    width: 30%;
+    text-align: left;
+}
+
+.price-calc-section .card .description .select-number{
+    font-size: 20px;
+    text-align: center;
+    width: 85px;
+}
+
+.price-calc-section .card .description i {
+    color: #29427A;
+    cursor: pointer;
+    font-size: 24px;
+}
+
+.price-calc-section .card .description .left {
+    margin-right: 7px;
+}
+
+.price-calc-section .card .description .right {
+    margin-left: 7px;
+}
+
+.price-calc-section .card .descriptions {
+    padding: 10px 30px;
+}
+
+.price-calc-section .card .description p {
+    margin: 0;
+}
+
+.price-calc-section .card .btn {
+    margin-top: 20px;
+    font-size: 20px;
+    width: 200px;
+    border: none;
+}
+
+.price-calc-section .card .select-configuration select {
+    outline: none;
+    background: #fff;
+    border-color: #d0d0d0;
+    height: 40px;
+    width: 200px;
+    text-align: center;
+    font-size: 16px;
+    margin-left: 10px;
+}
+
+.price-calc-section .card .check-ip {
+    font-size: 18px;
+}
+
+.price-calc-section .card .justify-center {
+    justify-content: center !important;
+}
+
+.price-calc-section .card .description.input label {
+    font-size: 15px;
+    font-weight: 700;
+    /*font-weight: 800;*/
+    /*font-family: 'Lato';*/
+    margin-bottom: 0;
+    width: 40px;
+}
+
+
+/*Changed class****.price-calc-section .card .description.input input*/
+
+.price-calc-section .card .description input {
+    width: 200px;
+    font-size: 14px;
+    text-align: left;
+    padding: 5px 10px;
+    border-radius: 4px;
+    border: 1px solid #d0d0d0;
+    background: #fff;
+    margin-left: 10px;
+}
+
+.price-calc-section .card .check-ip input[type=checkbox] {
+    font-size: 17px;
+    margin: 0 8px;
+}
\ No newline at end of file
diff --git a/hosting/templates/hosting/base_short.html b/hosting/templates/hosting/base_short.html
index 63a0681d..becb7873 100644
--- a/hosting/templates/hosting/base_short.html
+++ b/hosting/templates/hosting/base_short.html
@@ -25,6 +25,7 @@
     <link href="{% static 'hosting/css/commons.css' %}" rel="stylesheet">
     <link href="{% static 'hosting/css/virtual-machine.css' %}" rel="stylesheet">
     <link href="{% static 'hosting/css/dashboard.css' %}" rel="stylesheet">
+    <link href="{% static 'hosting/css/price_calculator.css' %}" rel="stylesheet">
     {% block css_extra %}
     {% endblock css_extra %}
 
@@ -33,9 +34,6 @@
     <link rel="stylesheet" href="//maxcdn.bootstrapcdn.com/font-awesome/4.3.0/css/font-awesome.min.css">
     <link href="//fonts.googleapis.com/css?family=Lato:300,400,500,700,300italic,400italic,700italic" rel="stylesheet" type="text/css">
     <link rel="shortcut icon" href="img/favicon.ico" type="image/x-icon" />
-    <link rel="stylesheet" href="{% static 'hosting/css/owl.carousel.min.css' %}">
-    <link rel="stylesheet" href="{% static 'hosting/css/owl.theme.default.min.css' %}">
-
 
     <!-- HTML5 Shim and Respond.js IE8 support of HTML5 elements and media queries -->
     <!-- WARNING: Respond.js doesn't work if you view the page via file:// -->
diff --git a/hosting/templates/hosting/calculator_form.html b/hosting/templates/hosting/calculator_form.html
new file mode 100644
index 00000000..cdba4809
--- /dev/null
+++ b/hosting/templates/hosting/calculator_form.html
@@ -0,0 +1,123 @@
+{% load staticfiles i18n%}
+<form id="order_form" method="POST" action="" data-toggle="validator" role="form">
+    {% csrf_token %}
+    <div class="title">
+        <h3>{% trans "VM hosting" %} </h3>
+    </div>
+    <div class="price">
+        <span id="total">15</span>
+        <span>CHF/{% trans "month" %}</span>
+        <div class="price-text">
+            <p>{% trans "VAT included" %}</p>
+        </div>
+    </div>
+    <div class="descriptions">
+        <div class="description form-group">
+            <p>{% trans "Hosted in Switzerland" %}</p>
+        </div>
+        <div class="form-group">
+            <div class="description input">
+                <i class="fa fa-minus-circle left" data-minus="cpu" aria-hidden="true"></i>
+                <input class="input-price select-number" type="number" min="1" max="48" id="coreValue" name="cpu"
+                       data-error="{% trans 'Please enter a value in range 1 - 48.' %}" required>
+                <span> Core</span>
+                <i class="fa fa-plus-circle right" data-plus="cpu" aria-hidden="true"></i>
+            </div>
+            <div class="help-block with-errors">
+                {% for message in messages %}
+                    {% if 'cores' in message.tags %}
+                     <ul class="list-unstyled"><li>
+                        {{ message|safe }}
+                    </li></ul>
+                    {% endif %}
+                {% endfor %}
+            </div>
+        </div>
+        <div class="form-group">
+            <div class="description input">
+                <i class="fa fa-minus-circle left" data-minus="ram" aria-hidden="true"></i>
+                <input id="ramValue" class="input-price select-number" type="number" min="2" max="200" name="ram"
+                       data-error="{% trans 'Please enter a value in range 2 - 200.' %}" required>
+                <span> GB RAM</span>
+                <i class="fa fa-plus-circle right" data-plus="ram" aria-hidden="true"></i>
+            </div>
+            <div class="help-block with-errors">
+                {% for message in messages %}
+                    {% if 'memory' in message.tags %}
+                     <ul class="list-unstyled"><li>
+                        {{ message|safe }}
+                    </li></ul>
+                    {% endif %}
+                {% endfor %}
+            </div>
+        </div>
+        <div class="form-group">
+            <div class="description input">
+                <i class="fa fa-minus-circle left" data-minus="storage" aria-hidden="true"></i>
+                <input id="storageValue" class="input-price select-number" type="number" min="10" max="2000" step="10"
+                       name="storage" data-error="{% trans 'Please enter a value in range 10 - 2000.' %}" required>
+                <span>{% trans "GB Storage (SSD)" %}</span>
+                <i class="fa fa-plus-circle right" data-plus="storage" aria-hidden="true"></i>
+            </div>
+            <div class="help-block with-errors">
+                {% for message in messages %}
+                    {% if 'storage' in message.tags %}
+                     <ul class="list-unstyled"><li>
+                        {{ message|safe }}
+                    </li></ul>
+                    {% endif %}
+                {% endfor %}
+            </div>
+        </div>
+        <div class="description select-configuration input form-group justify-center">
+            <label for="config">OS</label>
+            <select name="config" id="">
+                {% for template in templates %}
+                <option value="{{template.opennebula_vm_template_id}}">{{template.name}}</option>
+                {% endfor %}
+            </select>
+        </div>
+        <input type="hidden" name="total">
+        <!--<div class="description check-ip">
+            <input type="checkbox" name="ipv6"> Ipv6 Only<br>
+        </div>-->
+        <div class="form-group">
+            <div class="description input justify-center">
+                <label for="name" class="control-label">{% trans "Name"%}</label>
+                <input type="text" name="name" class="form-control" placeholder="{% trans 'Your Name'%}"
+                       data-minlength="3" data-error="{% trans 'Please enter your name.' %}" required>
+            </div>
+            <div class="help-block with-errors">
+                {% for message in messages %}
+                {% if 'name' in message.tags %}
+                <ul class="list-unstyled">
+                    <li>
+                        {{ message|safe }}
+                    </li>
+                </ul>
+                {% endif %}
+                {% endfor %}
+            </div>
+        </div>
+        <div class="form-group">
+            <div class="description input justify-center">
+                <label for="email" class="control-label">{% trans "Email"%}</label>
+                <input name="email" type="email" pattern="^[^@\s]+@([^@\s]+\.)+[^@\s]+$" class="form-control"
+                       placeholder="{% trans 'Your Email' %}"
+                       data-error="{% trans 'Please enter a valid email address.' %}" required>
+            </div>
+            <div class="help-block with-errors">
+                {% for message in messages %}
+                {% if 'email' in message.tags %}
+                <ul class="list-unstyled">
+                    <li>
+                        {{ message|safe }}
+                    </li>
+                </ul>
+                {% endif %}
+                {% endfor %}
+            </div>
+        </div>
+    </div>
+    <input type="submit" class="btn btn-primary disabled" value="{% trans 'Continue' %}"></input>
+</form>
diff --git a/hosting/templates/hosting/create_virtual_machine.html b/hosting/templates/hosting/create_virtual_machine.html
index f876ad76..5a5e789e 100644
--- a/hosting/templates/hosting/create_virtual_machine.html
+++ b/hosting/templates/hosting/create_virtual_machine.html
@@ -1,70 +1,31 @@
 {% extends "hosting/base_short.html" %}
 {% load staticfiles bootstrap3 i18n %}
-{% block content %} 
-<div>
-    <div class="dashboard-container" >
-        <div class="row">
 
-                <div class="col-md-12">
-                    <br/>
-                    {% if messages %}
-                        <div class="alert alert-warning">
-                            {% for message in messages %}
-                            <span>{{ message }}</span>
-                            {% endfor %}
-                        </div>
-                    {% endif %}
+{% block content %}
+<div class="dashboard-container">
+    <div class="row">
+        <div class="col-sm-6">
+          <div class="dashboard-container-head">
+              <h3 class="dashboard-title-thin"><img src="{% static 'hosting/img/plusVM.svg' %}" class="un-icon" style="margin-top: -18px;width: 42px;height: 42px;"> {% trans "Create VM" %}</h3>
+              {% if messages %}
+                  <div class="alert alert-warning">
+                      {% for message in messages %}
+                          <span>{{ message }}</span>
+                      {% endfor %}
+                  </div>
+              {% endif %}
+          </div>
+        </div>
+        <div class="col-sm-6">
+            <div class="price-calc-section no-padding">
+                <div class="landing card">
+                    <img class="img-beta" src="{% static 'datacenterlight/img/beta-img.png' %}" alt="">
+                    <div class="caption">
+                        {% include "hosting/calculator_form.html" %}
+                    </div>
                 </div>
-                {% if not error %}
-                <div class="dashboard-title">
-                    <h3>{% trans "New Virtual Machine"%} </h3>
-                    <hr/>
-                </div>
-
-                <form method="POST" action="">
-                    {% csrf_token %}
-            
-                    <div class="step-title">
-                        <h4>{% trans "Step 1. Select VM Template:" %} </h4>
-                    </div>
-                    <div class="parent-container">
-                        <div class="container-os owl-carousel owl-theme" id="containerOs">
-                            
-                            {% for template in templates %}
-                                <div class="os-circle" data-id="{{template.id}}">
-                                    <span class="text" >{{template.name}}</span>
-                                </div>
-                            {% endfor %}
-                        </div>
-                        <input type="hidden" name="vm_template_id">
-                    </div>
-                     <div class="step-title">
-                        <h4>{% trans "Step2. Select VM Configuration" %}</h4>
-                    </div>
-                    <div class="parent-container">
-                        <div class="container-os config owl-carousel owl-theme">
-                           
-                            {% for config in configuration_options %}
-                                <div class="config-box" data-id="{{config.id}}" data-price="{{config.price|floatformat}}">
-                                    <span>CORE: {{config.cpu|floatformat}}</span>
-                                    <span>RAM: {{config.memory|floatformat}} GB</span>
-                                    <span>SSD: {{config.disk_size|floatformat}} GB</span>
-                                </div>
-                            {% endfor %}
-                        </div>
-                         <input type="hidden" name="configuration">
-                    </div>
-                    <div class="container-button">
-                          <div class="price">
-                            <span class="label-price">{% trans "Price " %}<span id="priceValue">0</span>{% trans "CHF/Month" %}</span>
-                          </div>
-                         <button class="btn btn-success" >{% trans "Start VM"%} </button>   
-                    </div>
-                </form>
-                {% endif %}
+            </div>
         </div>
     </div>
-
 </div>
-
-{%endblock%}
+{%endblock%}
\ No newline at end of file

From a935871722f530f0ac08e2b658cf58315db5df0e Mon Sep 17 00:00:00 2001
From: Arvind Tiwari <tiwariav@gmail.com>
Date: Fri, 15 Sep 2017 00:57:59 +0530
Subject: [PATCH 09/82] code reformating

---
 .../hosting/js/virtual_machine_detail.js      | 96 +++++++++----------
 hosting/views.py                              | 28 ++----
 2 files changed, 56 insertions(+), 68 deletions(-)

diff --git a/hosting/static/hosting/js/virtual_machine_detail.js b/hosting/static/hosting/js/virtual_machine_detail.js
index 076ec344..898ecbaa 100644
--- a/hosting/static/hosting/js/virtual_machine_detail.js
+++ b/hosting/static/hosting/js/virtual_machine_detail.js
@@ -1,54 +1,52 @@
+$(document).ready(function() {
 
-$( document ).ready(function() {
+    $('#confirm-cancel').on('click', '.btn-ok', function(e) {
+        var url = $('#virtual_machine_cancel_form').attr('action');
+        var $container = $('#terminate-VM');
+        var $btn = $container.find('.btn');
+        var text = $container.find('.vm-item-lg').text();
+        var altText = $container.attr('data-alt');
+        $container.find('.alert-danger').addClass('hide');
+        $container.addClass('processing')
+            .find('.vm-item-lg').attr('class', '')
+            .addClass('vm-item-lg vm-color-failed')
+            .text(altText);
+        $btn.prop('disabled', true);
+        $('#confirm-cancel').modal('hide');
+        $.post(url)
+            .done(function(data) {
+                console.log("success", data);
+                if (data.status == true) {
+                    $container.addClass('terminate-success')
+                        .find('.vm-item-lg').text(data.text);
+                    $btn.remove();
+                    window.location = data.redirect;
+                } else {
+                    $container.addClass('terminate-fail')
+                        .find('.vm-item-lg').text(text);
+                    $container.find('.btn').prop('disabled', false);
+                    $container.find('.alert-danger').text(data.text).removeClass('hide');
+                }
+            })
+            .fail(function(data) {
+                $container.addClass('terminate-fail')
+                    .find('.vm-item-lg').text(text);
+                $container.find('.btn').prop('disabled', false);
+                $container.find('.alert-danger').removeClass('hide');
+            })
+            .always(function(data) {
+                $container.removeClass('processing');
+            });
+    });
 
-	$('#confirm-cancel').on('click', '.btn-ok', function(e) {
-    var url = $('#virtual_machine_cancel_form').attr('action');
-    var $container = $('#terminate-VM');
-    var $btn = $container.find('.btn');
-    var text = $container.find('.vm-item-lg').text();
-    var altText = $container.attr('data-alt');
-    $container.find('.alert-danger').addClass('hide');
-    $container.addClass('processing')
-      .find('.vm-item-lg').attr('class', '')
-      .addClass('vm-item-lg vm-color-failed')
-      .text(altText);
-    $btn.prop('disabled', true);
-    $('#confirm-cancel').modal('hide');
-    $.post(url)
-      .done(function(data) {
-        console.log( "success" , data);
-        if (data.status == true) {
-          $container.addClass('terminate-success')
-            .find('.vm-item-lg').text(data.text);
-          $btn.remove();
-          window.location = data.redirect;
-        }
-        else {
-          $container.addClass('terminate-fail')
-            .find('.vm-item-lg').text(text);
-          $container.find('.btn').prop('disabled', false);
-          $container.find('.alert-danger').text(data.text).removeClass('hide');
-        }
-      })
-      .fail(function(data) {
-        $container.addClass('terminate-fail')
-          .find('.vm-item-lg').text(text);
-        $container.find('.btn').prop('disabled', false);
-        $container.find('.alert-danger').removeClass('hide');
-      })
-      .always(function(data) {
-        $container.removeClass('processing');
-      });
-	});
+    var hash = window.location.hash;
+    hash && $('ul.nav a[href="' + hash + '"]').tab('show');
 
-  var hash = window.location.hash;
-  hash && $('ul.nav a[href="' + hash + '"]').tab('show');
-
-  $('.nav-tabs a').click(function (e) {
-    $(this).tab('show');
-    var scrollmem = $('body').scrollTop() || $('html').scrollTop();
-    window.location.hash = this.hash;
-    $('html,body').scrollTop(scrollmem);
-  });
+    $('.nav-tabs a').click(function(e) {
+        $(this).tab('show');
+        var scrollmem = $('body').scrollTop() || $('html').scrollTop();
+        window.location.hash = this.hash;
+        $('html,body').scrollTop(scrollmem);
+    });
 
 });
\ No newline at end of file
diff --git a/hosting/views.py b/hosting/views.py
index ed85dbdb..f25d6567 100644
--- a/hosting/views.py
+++ b/hosting/views.py
@@ -957,6 +957,14 @@ class VirtualMachineView(LoginRequiredMixin, View):
             response['text'] = ugettext(
                 'Error terminating VM') + opennebula_vm_id
         else:
+            for t in range(150):
+                try:
+                    manager.get_vm(self.kwargs.get('pk'))
+                except BaseException:
+                    break
+                else:
+                    sleep(2)
+
             context = {
                 'vm': vm_data,
                 'base_url': "{0}://{1}".format(self.request.scheme,
@@ -973,28 +981,10 @@ class VirtualMachineView(LoginRequiredMixin, View):
             }
             email = BaseEmail(**email_data)
             email.send()
-
-            # messages.error(
-            #     request,
-            #     _('VM %(VM_ID)s terminated successfully') % {
-            #         'VM_ID': opennebula_vm_id}
-            # )
-            t = 0
-            while True:
-                if t < 150:
-                    t += 1
-                    try:
-                        manager.get_vm(self.kwargs.get('pk'))
-                    except BaseException:
-                        break
-                    else:
-                        sleep(2)
-                else:
-                    break
-
             response['status'] = True
             response['redirect'] = self.get_success_url()
             response['text'] = ugettext('Terminated')
+
         return HttpResponse(
             json.dumps(response),
             content_type="application/json"

From 75156d2c00389bf2e15a38202f90a68e844a85d1 Mon Sep 17 00:00:00 2001
From: Arvind Tiwari <tiwariav@gmail.com>
Date: Fri, 15 Sep 2017 01:00:07 +0530
Subject: [PATCH 10/82] undo changes in navbar

---
 hosting/templates/hosting/includes/_navbar_user.html | 5 +++++
 1 file changed, 5 insertions(+)

diff --git a/hosting/templates/hosting/includes/_navbar_user.html b/hosting/templates/hosting/includes/_navbar_user.html
index 37c01109..d06477ca 100644
--- a/hosting/templates/hosting/includes/_navbar_user.html
+++ b/hosting/templates/hosting/includes/_navbar_user.html
@@ -37,6 +37,11 @@
                 </li>
                 <li>
                     {% get_current_language as LANGUAGE_CODE %}
+                    {% if LANGUAGE_CODE == 'en-us'%}
+                        <a href="{% change_lang 'de' %}"><i class="fa fa-fw fa-globe" aria-hidden="true"></i>&nbsp;&nbsp;Deutsch</a>
+                    {% else %}
+                        <a href="{% change_lang 'en-us' %}"><i class="fa fa-fw fa-globe" aria-hidden="true"></i>&nbsp;&nbsp;English</a>
+                    {% endif %}
                 </li>
             </ul>
         </div>

From 852c1228bad339bdfbe5939fa4a2cbe39258d4a3 Mon Sep 17 00:00:00 2001
From: Arvind Tiwari <tiwariav@gmail.com>
Date: Fri, 15 Sep 2017 14:48:11 +0530
Subject: [PATCH 11/82] minor fix

---
 hosting/views.py | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/hosting/views.py b/hosting/views.py
index f25d6567..f5780aed 100644
--- a/hosting/views.py
+++ b/hosting/views.py
@@ -957,7 +957,7 @@ class VirtualMachineView(LoginRequiredMixin, View):
             response['text'] = ugettext(
                 'Error terminating VM') + opennebula_vm_id
         else:
-            for t in range(150):
+            for t in range(50):
                 try:
                     manager.get_vm(self.kwargs.get('pk'))
                 except BaseException:

From 6136a48961b0b17146cffdb4298fa788a15ed1fa Mon Sep 17 00:00:00 2001
From: Arvind Tiwari <tiwariav@gmail.com>
Date: Fri, 15 Sep 2017 16:46:56 +0530
Subject: [PATCH 12/82] edge cases handled

---
 .../hosting/js/virtual_machine_detail.js      | 74 +++++++++++++------
 hosting/views.py                              | 19 ++---
 2 files changed, 62 insertions(+), 31 deletions(-)

diff --git a/hosting/static/hosting/js/virtual_machine_detail.js b/hosting/static/hosting/js/virtual_machine_detail.js
index 898ecbaa..0485bc36 100644
--- a/hosting/static/hosting/js/virtual_machine_detail.js
+++ b/hosting/static/hosting/js/virtual_machine_detail.js
@@ -1,42 +1,72 @@
+function VMTerminateStatus($container, url) {
+    $.get(url)
+        .done(function(data) {
+            setTimeout(function(){
+                VMTerminateStatus($container, url);
+            }, 2000);
+        })
+        .fail(function(data) {
+            VMTerminateSuccess($container, data)
+            window.location.reload(true);
+        });
+}
+
+function VMTerminateActive($container, altText) {
+    $container.find('.alert-danger').addClass('hide');
+    $container.addClass('processing')
+        .find('.vm-item-lg').attr('class', '')
+        .addClass('vm-item-lg vm-color-failed')
+        .text(altText);
+    $container.find('.btn').prop('disabled', true);
+    $('#confirm-cancel').modal('hide');
+}
+
+function VMTerminateSuccess($container, data) {
+    $container.addClass('terminate-success')
+        .find('.vm-item-lg').text(data.text);
+    $container.find('.btn').remove();
+}
+
+function VMTerminateFail($container, data, text) {
+    $container.addClass('terminate-fail')
+        .find('.vm-item-lg').text(text);
+    $container.find('.btn').prop('disabled', false);
+    $container.find('.alert-danger').text(data.text).removeClass('hide');
+    $container.removeClass('processing');
+}
+
+
 $(document).ready(function() {
 
     $('#confirm-cancel').on('click', '.btn-ok', function(e) {
         var url = $('#virtual_machine_cancel_form').attr('action');
         var $container = $('#terminate-VM');
-        var $btn = $container.find('.btn');
         var text = $container.find('.vm-item-lg').text();
         var altText = $container.attr('data-alt');
-        $container.find('.alert-danger').addClass('hide');
-        $container.addClass('processing')
-            .find('.vm-item-lg').attr('class', '')
-            .addClass('vm-item-lg vm-color-failed')
-            .text(altText);
-        $btn.prop('disabled', true);
-        $('#confirm-cancel').modal('hide');
+        VMTerminateActive($container, altText);
+
         $.post(url)
             .done(function(data) {
                 console.log("success", data);
                 if (data.status == true) {
-                    $container.addClass('terminate-success')
-                        .find('.vm-item-lg').text(data.text);
-                    $btn.remove();
+                    VMTerminateSuccess($container, data);
                     window.location = data.redirect;
                 } else {
-                    $container.addClass('terminate-fail')
-                        .find('.vm-item-lg').text(text);
-                    $container.find('.btn').prop('disabled', false);
-                    $container.find('.alert-danger').text(data.text).removeClass('hide');
+                    if ('text' in data) {
+                        VMTerminateFail($container, data, text);
+                    } else {
+                        VMTerminateStatus($container, url);
+                    }
                 }
             })
             .fail(function(data) {
-                $container.addClass('terminate-fail')
-                    .find('.vm-item-lg').text(text);
-                $container.find('.btn').prop('disabled', false);
-                $container.find('.alert-danger').removeClass('hide');
+                console.log(data)
+                if (data.status==504) {
+                    VMTerminateStatus($container, url);
+                } else {
+                    VMTerminateFail($container, data, text);
+                }
             })
-            .always(function(data) {
-                $container.removeClass('processing');
-            });
     });
 
     var hash = window.location.hash;
diff --git a/hosting/views.py b/hosting/views.py
index f5780aed..848ac9e8 100644
--- a/hosting/views.py
+++ b/hosting/views.py
@@ -923,7 +923,10 @@ class VirtualMachineView(LoginRequiredMixin, View):
     def get(self, request, *args, **kwargs):
         vm = self.get_object()
         if vm is None:
-            return redirect(reverse('hosting:virtual_machines'))
+            if self.request.is_ajax():
+                raise Http404()
+            else:
+                return redirect(reverse('hosting:virtual_machines'))
         try:
             serializer = VirtualMachineSerializer(vm)
             context = {
@@ -938,7 +941,7 @@ class VirtualMachineView(LoginRequiredMixin, View):
         return render(request, self.template_name, context)
 
     def post(self, request, *args, **kwargs):
-        response = {}
+        response = {'status': False}
         owner = self.request.user
         vm = self.get_object()
 
@@ -948,23 +951,25 @@ class VirtualMachineView(LoginRequiredMixin, View):
             email=owner.email,
             password=owner.password
         )
+
         vm_data = VirtualMachineSerializer(manager.get_vm(vm.id)).data
 
         terminated = manager.delete_vm(vm.id)
 
         if not terminated:
-            response['status'] = False
             response['text'] = ugettext(
                 'Error terminating VM') + opennebula_vm_id
         else:
-            for t in range(50):
+            for t in range(15):
                 try:
                     manager.get_vm(self.kwargs.get('pk'))
                 except BaseException:
+                    response['status'] = True
+                    response['redirect'] = self.get_success_url()
+                    response['text'] = ugettext('Terminated')
                     break
                 else:
                     sleep(2)
-
             context = {
                 'vm': vm_data,
                 'base_url': "{0}://{1}".format(self.request.scheme,
@@ -981,10 +986,6 @@ class VirtualMachineView(LoginRequiredMixin, View):
             }
             email = BaseEmail(**email_data)
             email.send()
-            response['status'] = True
-            response['redirect'] = self.get_success_url()
-            response['text'] = ugettext('Terminated')
-
         return HttpResponse(
             json.dumps(response),
             content_type="application/json"

From fdb5039c029c59ae177fdc9f71d9429e5919256f Mon Sep 17 00:00:00 2001
From: Arvind Tiwari <tiwariav@gmail.com>
Date: Fri, 15 Sep 2017 16:57:17 +0530
Subject: [PATCH 13/82] minor adjustments

---
 hosting/static/hosting/css/virtual-machine.css      | 3 +++
 hosting/static/hosting/js/virtual_machine_detail.js | 2 +-
 hosting/views.py                                    | 2 ++
 3 files changed, 6 insertions(+), 1 deletion(-)

diff --git a/hosting/static/hosting/css/virtual-machine.css b/hosting/static/hosting/css/virtual-machine.css
index b6afe4ef..48932350 100644
--- a/hosting/static/hosting/css/virtual-machine.css
+++ b/hosting/static/hosting/css/virtual-machine.css
@@ -530,6 +530,9 @@
 .vm-status-failed {
   color: #eb4d5c;
 }
+.vm-status-failed {
+  color: #e47f2f;
+}
 
 @media (min-width:768px) {
   .dashboard-subtitle {
diff --git a/hosting/static/hosting/js/virtual_machine_detail.js b/hosting/static/hosting/js/virtual_machine_detail.js
index 0485bc36..df401ebe 100644
--- a/hosting/static/hosting/js/virtual_machine_detail.js
+++ b/hosting/static/hosting/js/virtual_machine_detail.js
@@ -3,7 +3,7 @@ function VMTerminateStatus($container, url) {
         .done(function(data) {
             setTimeout(function(){
                 VMTerminateStatus($container, url);
-            }, 2000);
+            }, 4000);
         })
         .fail(function(data) {
             VMTerminateSuccess($container, data)
diff --git a/hosting/views.py b/hosting/views.py
index 848ac9e8..77c4b8dc 100644
--- a/hosting/views.py
+++ b/hosting/views.py
@@ -924,6 +924,8 @@ class VirtualMachineView(LoginRequiredMixin, View):
         vm = self.get_object()
         if vm is None:
             if self.request.is_ajax():
+                storage = messages.get_messages(request)
+                storage.used = True
                 raise Http404()
             else:
                 return redirect(reverse('hosting:virtual_machines'))

From 0c3f60573568d7a18620f9c125fd767c2af791d9 Mon Sep 17 00:00:00 2001
From: Arvind Tiwari <tiwariav@gmail.com>
Date: Fri, 15 Sep 2017 17:02:02 +0530
Subject: [PATCH 14/82] status pending style in vm-list

---
 hosting/static/hosting/css/virtual-machine.css  | 4 ++--
 hosting/templates/hosting/virtual_machines.html | 2 +-
 2 files changed, 3 insertions(+), 3 deletions(-)

diff --git a/hosting/static/hosting/css/virtual-machine.css b/hosting/static/hosting/css/virtual-machine.css
index 48932350..a14abc31 100644
--- a/hosting/static/hosting/css/virtual-machine.css
+++ b/hosting/static/hosting/css/virtual-machine.css
@@ -521,7 +521,7 @@
   color: #87B6EA;
 }
 
-.vm-status, .vm-status-active, .vm-status-failed {
+.vm-status, .vm-status-active, .vm-status-failed, .vm-status-pending {
   font-weight: 600;
 }
 .vm-status-active {
@@ -530,7 +530,7 @@
 .vm-status-failed {
   color: #eb4d5c;
 }
-.vm-status-failed {
+.vm-status-pending {
   color: #e47f2f;
 }
 
diff --git a/hosting/templates/hosting/virtual_machines.html b/hosting/templates/hosting/virtual_machines.html
index f7461abe..da8c79a5 100644
--- a/hosting/templates/hosting/virtual_machines.html
+++ b/hosting/templates/hosting/virtual_machines.html
@@ -46,7 +46,7 @@
                         {% elif  vm.state == 'FAILED' %}
                             <span class="vm-status-failed"><strong>{{vm.state|title}}</strong></span>
                         {% else %}
-                            <span class="vm-status"><strong>{{vm.state|title}}</strong></span>
+                            <span class="vm-status-pending"><strong>{{vm.state|title}}</strong></span>
                         {% endif %}
                     </td>
                     <td class="text-right last-td">

From 77f2454e3cc1b1c1480e1e46ae2646cd7bc771d6 Mon Sep 17 00:00:00 2001
From: Arvind Tiwari <tiwariav@gmail.com>
Date: Fri, 15 Sep 2017 17:20:42 +0530
Subject: [PATCH 15/82] remove error msg on successful termination

---
 .../hosting/js/virtual_machine_detail.js       | 18 ++++++++++--------
 hosting/views.py                               |  7 ++++++-
 2 files changed, 16 insertions(+), 9 deletions(-)

diff --git a/hosting/static/hosting/js/virtual_machine_detail.js b/hosting/static/hosting/js/virtual_machine_detail.js
index df401ebe..47080cd4 100644
--- a/hosting/static/hosting/js/virtual_machine_detail.js
+++ b/hosting/static/hosting/js/virtual_machine_detail.js
@@ -1,14 +1,16 @@
 function VMTerminateStatus($container, url) {
-    $.get(url)
-        .done(function(data) {
+    $.ajax({
+        url: url,
+        dataType: 'json',
+        success: function(data) {
+            VMTerminateSuccess($container, data);
+        },
+        error: function() {
             setTimeout(function(){
                 VMTerminateStatus($container, url);
             }, 4000);
-        })
-        .fail(function(data) {
-            VMTerminateSuccess($container, data)
-            window.location.reload(true);
-        });
+        }
+    });
 }
 
 function VMTerminateActive($container, altText) {
@@ -25,6 +27,7 @@ function VMTerminateSuccess($container, data) {
     $container.addClass('terminate-success')
         .find('.vm-item-lg').text(data.text);
     $container.find('.btn').remove();
+    window.location = data.redirect;
 }
 
 function VMTerminateFail($container, data, text) {
@@ -50,7 +53,6 @@ $(document).ready(function() {
                 console.log("success", data);
                 if (data.status == true) {
                     VMTerminateSuccess($container, data);
-                    window.location = data.redirect;
                 } else {
                     if ('text' in data) {
                         VMTerminateFail($container, data, text);
diff --git a/hosting/views.py b/hosting/views.py
index 77c4b8dc..072ada8e 100644
--- a/hosting/views.py
+++ b/hosting/views.py
@@ -926,9 +926,14 @@ class VirtualMachineView(LoginRequiredMixin, View):
             if self.request.is_ajax():
                 storage = messages.get_messages(request)
                 storage.used = True
-                raise Http404()
+                return HttpResponse(
+                    json.dumps({'redirect': self.get_success_url()}),
+                    content_type="application/json"
+                )
             else:
                 return redirect(reverse('hosting:virtual_machines'))
+        elif self.request.is_ajax():
+            return HttpResponse()
         try:
             serializer = VirtualMachineSerializer(vm)
             context = {

From bbb1919404085b145a95e00f58a4ee2e4f37f9db Mon Sep 17 00:00:00 2001
From: Arvind Tiwari <tiwariav@gmail.com>
Date: Fri, 15 Sep 2017 17:38:52 +0530
Subject: [PATCH 16/82] error msg fix

---
 hosting/static/hosting/js/virtual_machine_detail.js | 2 --
 hosting/views.py                                    | 2 ++
 2 files changed, 2 insertions(+), 2 deletions(-)

diff --git a/hosting/static/hosting/js/virtual_machine_detail.js b/hosting/static/hosting/js/virtual_machine_detail.js
index 47080cd4..29b08cda 100644
--- a/hosting/static/hosting/js/virtual_machine_detail.js
+++ b/hosting/static/hosting/js/virtual_machine_detail.js
@@ -50,7 +50,6 @@ $(document).ready(function() {
 
         $.post(url)
             .done(function(data) {
-                console.log("success", data);
                 if (data.status == true) {
                     VMTerminateSuccess($container, data);
                 } else {
@@ -62,7 +61,6 @@ $(document).ready(function() {
                 }
             })
             .fail(function(data) {
-                console.log(data)
                 if (data.status==504) {
                     VMTerminateStatus($container, url);
                 } else {
diff --git a/hosting/views.py b/hosting/views.py
index 072ada8e..201f590a 100644
--- a/hosting/views.py
+++ b/hosting/views.py
@@ -925,6 +925,8 @@ class VirtualMachineView(LoginRequiredMixin, View):
         if vm is None:
             if self.request.is_ajax():
                 storage = messages.get_messages(request)
+                for m in storage:
+                    pass
                 storage.used = True
                 return HttpResponse(
                     json.dumps({'redirect': self.get_success_url()}),

From 9c0cefd41968ef03b65dacb6572accc702fdd277 Mon Sep 17 00:00:00 2001
From: Arvind Tiwari <tiwariav@gmail.com>
Date: Fri, 15 Sep 2017 17:44:27 +0530
Subject: [PATCH 17/82] js polling timing to 5s

---
 hosting/static/hosting/js/virtual_machine_detail.js | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/hosting/static/hosting/js/virtual_machine_detail.js b/hosting/static/hosting/js/virtual_machine_detail.js
index 29b08cda..d6387dbc 100644
--- a/hosting/static/hosting/js/virtual_machine_detail.js
+++ b/hosting/static/hosting/js/virtual_machine_detail.js
@@ -8,7 +8,7 @@ function VMTerminateStatus($container, url) {
         error: function() {
             setTimeout(function(){
                 VMTerminateStatus($container, url);
-            }, 4000);
+            }, 5000);
         }
     });
 }

From d49e90bd209868b710f6f4d61a45c146482cc5ff Mon Sep 17 00:00:00 2001
From: Arvind Tiwari <tiwariav@gmail.com>
Date: Fri, 15 Sep 2017 18:15:06 +0530
Subject: [PATCH 18/82] catching WrongIdError

---
 hosting/views.py | 5 ++++-
 1 file changed, 4 insertions(+), 1 deletion(-)

diff --git a/hosting/views.py b/hosting/views.py
index 201f590a..acd7e67b 100644
--- a/hosting/views.py
+++ b/hosting/views.py
@@ -972,10 +972,13 @@ class VirtualMachineView(LoginRequiredMixin, View):
             for t in range(15):
                 try:
                     manager.get_vm(self.kwargs.get('pk'))
-                except BaseException:
+                except WrongIdError:
                     response['status'] = True
                     response['redirect'] = self.get_success_url()
                     response['text'] = ugettext('Terminated')
+                    self.send_mail()
+                    break
+                except BaseException:
                     break
                 else:
                     sleep(2)

From 87327d028a1fac59192783082a9f181b5c2022ad Mon Sep 17 00:00:00 2001
From: Arvind Tiwari <tiwariav@gmail.com>
Date: Fri, 15 Sep 2017 20:03:52 +0530
Subject: [PATCH 19/82] hosting form view modified

---
 .../datacenterlight/calculator_form.html      |   6 +-
 .../static/hosting/css/price_calculator.css   |  99 +++++++++----
 hosting/static/hosting/js/createvm.js         | 137 +++++++++---------
 hosting/static/hosting/js/createvm_old.js     |  73 ++++++++++
 hosting/templates/hosting/base_short.html     |   6 +-
 .../templates/hosting/calculator_form.html    |  86 ++++-------
 .../hosting/create_virtual_machine.html       |  19 ++-
 hosting/views.py                              | 102 ++++++++-----
 8 files changed, 324 insertions(+), 204 deletions(-)
 create mode 100644 hosting/static/hosting/js/createvm_old.js

diff --git a/datacenterlight/templates/datacenterlight/calculator_form.html b/datacenterlight/templates/datacenterlight/calculator_form.html
index cdba4809..b5bac1f9 100644
--- a/datacenterlight/templates/datacenterlight/calculator_form.html
+++ b/datacenterlight/templates/datacenterlight/calculator_form.html
@@ -26,9 +26,9 @@
             <div class="help-block with-errors">
                 {% for message in messages %}
                     {% if 'cores' in message.tags %}
-                     <ul class="list-unstyled"><li>
-                        {{ message|safe }}
-                    </li></ul>
+                        <ul class="list-unstyled">
+                            <li>{{ message|safe }}</li>
+                        </ul>
                     {% endif %}
                 {% endfor %}
             </div>
diff --git a/hosting/static/hosting/css/price_calculator.css b/hosting/static/hosting/css/price_calculator.css
index bf99c66f..5aac2c97 100644
--- a/hosting/static/hosting/css/price_calculator.css
+++ b/hosting/static/hosting/css/price_calculator.css
@@ -1,12 +1,13 @@
-/*Pricing page*/
+/* Create VM calculator */
 
 .price-calc-section {
     padding: 80px 40px !important;
-    background: -webkit-linear-gradient(top, #f0f4f7, #fff) no-repeat;
-    background: linear-gradient(to bottom, #f0f4f7, #fff) no-repeat;
-    display: flex;
-    /*font-family: 'Lato', sans-serif;*/
-/*     font-weight: normal; */
+}
+
+@media (max-width: 768px) {
+    .price-calc-section {
+        margin-top: 40px;
+    }
 }
 
 .price-calc-section .text {
@@ -42,12 +43,12 @@
     width: 50%;
     margin: 0 auto;
     background: #fff;
-    box-shadow: 0 10px 20px rgba(0, 0, 0, 0.19), 0 6px 6px rgba(0, 0, 0, 0.23);
-    padding-bottom: 40px;
-    border-radius: 7px;
+    box-shadow: 1px 3px 6px 2px rgba(0, 0, 0, 0.2);
+    padding-bottom: 30px;
+    /* border-radius: 7px; */
     text-align: center;
     /* margin-right: auto; */
-    max-width: 400px;
+    max-width: 320px;
     position: relative;
 }
 
@@ -87,7 +88,7 @@
 }
 
 .price-calc-section .card .description {
-    padding: 12px;
+    padding: 7px 8px 2px;
     position: relative;
     display: flex;
     justify-content: space-around !important;
@@ -95,24 +96,29 @@
 }
 
 .price-calc-section .card .description span {
-    font-size: 16px;
-    margin-left: 4px;
-    margin-left: 0px;
+    font-size: 14px;
+    margin-left: 5px;
+    /* margin-left: 0px; */
     /* justify-self: start; */
-    width: 30%;
+    width: 29%;
     text-align: left;
+    line-height: 16px;
+    /* font-weight: normal; */
 }
 
 .price-calc-section .card .description .select-number{
-    font-size: 20px;
+    font-size: 16px;
     text-align: center;
     width: 85px;
 }
 
 .price-calc-section .card .description i {
-    color: #29427A;
+    color: #29427a;
     cursor: pointer;
-    font-size: 24px;
+    font-size: 20px;
+    border: 1px solid #eee;
+    padding: 5px 6px 3px;
+    border-radius: 5px;
 }
 
 .price-calc-section .card .description .left {
@@ -124,7 +130,7 @@
 }
 
 .price-calc-section .card .descriptions {
-    padding: 10px 30px;
+    padding: 10px;
 }
 
 .price-calc-section .card .description p {
@@ -132,9 +138,9 @@
 }
 
 .price-calc-section .card .btn {
-    margin-top: 20px;
+    margin-top: 15px;
     font-size: 20px;
-    width: 200px;
+    width: 150px;
     border: none;
 }
 
@@ -142,11 +148,13 @@
     outline: none;
     background: #fff;
     border-color: #d0d0d0;
-    height: 40px;
-    width: 200px;
+    height: 32px;
+    width: 150px;
     text-align: center;
-    font-size: 16px;
+    font-size: 14px;
     margin-left: 10px;
+    padding: 6px;
+    border-radius: 4px;
 }
 
 .price-calc-section .card .check-ip {
@@ -173,7 +181,7 @@
     width: 200px;
     font-size: 14px;
     text-align: left;
-    padding: 5px 10px;
+    padding: 4px 10px;
     border-radius: 4px;
     border: 1px solid #d0d0d0;
     background: #fff;
@@ -183,4 +191,43 @@
 .price-calc-section .card .check-ip input[type=checkbox] {
     font-size: 17px;
     margin: 0 8px;
-}
\ No newline at end of file
+}
+
+.help-block.with-errors {
+    text-align: center;
+    margin: 0 0;
+    padding: 0 0 5px;
+}
+.help-block.with-errors ul {
+    margin-bottom: 0;
+}
+
+.form-group {
+    margin: 0;
+    position: relative;
+}
+
+.form-group:after {
+    content: ' ';
+    display: block;
+    position: absolute;
+    bottom: 0;
+    left: 18%;
+    z-index: 20;
+    height: 1px;
+    width: 65%;
+    background: rgba(128, 128, 128, 0.2);
+}
+
+.btn-primary {
+    background: #29427A;
+    border-color: #29427A;
+    color: #fff;
+    width: auto;
+}
+
+@media(min-width: 768px) {
+    .create-vm-container {
+        padding-top: 120px;
+    }
+}
diff --git a/hosting/static/hosting/js/createvm.js b/hosting/static/hosting/js/createvm.js
index 53646b40..344aedfb 100644
--- a/hosting/static/hosting/js/createvm.js
+++ b/hosting/static/hosting/js/createvm.js
@@ -1,73 +1,76 @@
 (function($){
     "use strict"; // Start of use strict
-    
-    
-    $(window).load(function(){
-    
-  
-    });
-    
-    $(document).ready(function(){
-      _initOs();
-       
-    });
-    
-    $(window).resize(function(){
-        
-        
-    });
-    
 
-
-   	function _initOs(){
-
-   		
-   		$('.os-circle').click(function(event){
-   			$('.os-circle').removeClass('active');
-   			$(this).addClass('active');
-
-        var idTemplate = $(this).data('id');
-        $('input[name=vm_template_id]').val(idTemplate);
-   		});
-   		$('.config-box').click(function(event){
-   			$('.config-box').removeClass('active');
-   			$(this).addClass('active');
-        var idConfig = $(this).data('id');
-        var price = $(this).data('price');
-        $('input[name=configuration]').val(idConfig);
-        $('.container-button').fadeIn();
-        $('#priceValue').text(price);
-   		});
-
-		$('.owl-carousel').owlCarousel({
-        items:4,
-        nav: true,
-        margin:30,
-        responsiveClass:true,
-        navText: ['<i class="fa fa-angle-left"></i>', '<i class="fa fa-angle-right"></i>'],
-        responsive:{
-            0:{
-                items:1,
-                nav:true
-            },
-            600:{
-                items:2,
-                nav:true
-            },
-            768:{
-                items:3,
-                nav:true
-            },
-            990:{
-                items:4,
-                nav:true
-            }
+    var cardPricing = {
+        'cpu': {
+            'id': 'coreValue',
+            'value': 1,
+            'min': 1,
+            'max': 48,
+            'interval': 1
+        },
+        'ram': {
+            'id': 'ramValue',
+            'value': 2,
+            'min': 2,
+            'max': 200,
+            'interval': 1
+        },
+        'storage': {
+            'id': 'storageValue',
+            'value': 10,
+            'min': 10,
+            'max': 2000,
+            'interval': 10
         }
-		});
-	}
-    
-    
-    
-})(jQuery); 
+    };
+
+    function _initPricing() {
+        _fetchPricing();
+
+        $('.fa-minus.left').click(function(event) {
+            var data = $(this).data('minus');
+
+            if (cardPricing[data].value > cardPricing[data].min) {
+                cardPricing[data].value = Number(cardPricing[data].value) - cardPricing[data].interval;
+            }
+            _fetchPricing();
+        });
+        $('.fa-plus.right').click(function(event) {
+            var data = $(this).data('plus');
+            if (cardPricing[data].value < cardPricing[data].max) {
+                cardPricing[data].value = Number(cardPricing[data].value) + cardPricing[data].interval;
+            }
+            _fetchPricing();
+        });
+
+        $('.input-price').change(function() {
+            var data = $(this).attr("name");
+            cardPricing[data].value = $('input[name=' + data + ']').val();
+            _fetchPricing();
+        });
+    }
+
+    function _fetchPricing() {
+        Object.keys(cardPricing).map(function(element) {
+            //$('#'+cardPricing[element].id).val(cardPricing[element].value);
+            $('input[name=' + element + ']').val(cardPricing[element].value);
+        });
+        _calcPricing();
+    }
+
+    function _calcPricing() {
+        var total = (cardPricing['cpu'].value * 5) + (2 * cardPricing['ram'].value) + (0.6 * cardPricing['storage'].value);
+        total = parseFloat(total.toFixed(2));
+
+        $("#total").text(total);
+        $('input[name=total]').val(total);
+    }
+
+    $(document).ready(function() {
+        _initPricing();
+    });
+
+})(jQuery);
 
 
diff --git a/hosting/static/hosting/js/createvm_old.js b/hosting/static/hosting/js/createvm_old.js
new file mode 100644
index 00000000..53646b40
--- /dev/null
+++ b/hosting/static/hosting/js/createvm_old.js
@@ -0,0 +1,73 @@
+(function($){
+    "use strict"; // Start of use strict
+    
+    
+    $(window).load(function(){
+    
+  
+    });
+    
+    $(document).ready(function(){
+      _initOs();
+       
+    });
+    
+    $(window).resize(function(){
+        
+        
+    });
+    
+
+
+   	function _initOs(){
+
+   		
+   		$('.os-circle').click(function(event){
+   			$('.os-circle').removeClass('active');
+   			$(this).addClass('active');
+
+        var idTemplate = $(this).data('id');
+        $('input[name=vm_template_id]').val(idTemplate);
+   		});
+   		$('.config-box').click(function(event){
+   			$('.config-box').removeClass('active');
+   			$(this).addClass('active');
+        var idConfig = $(this).data('id');
+        var price = $(this).data('price');
+        $('input[name=configuration]').val(idConfig);
+        $('.container-button').fadeIn();
+        $('#priceValue').text(price);
+   		});
+
+		$('.owl-carousel').owlCarousel({
+        items:4,
+        nav: true,
+        margin:30,
+        responsiveClass:true,
+        navText: ['<i class="fa fa-angle-left"></i>', '<i class="fa fa-angle-right"></i>'],
+        responsive:{
+            0:{
+                items:1,
+                nav:true
+            },
+            600:{
+                items:2,
+                nav:true
+            },
+            768:{
+                items:3,
+                nav:true
+            },
+            990:{
+                items:4,
+                nav:true
+            }
+        }
+		});
+	}
+    
+    
+    
+})(jQuery); 
+
+
diff --git a/hosting/templates/hosting/base_short.html b/hosting/templates/hosting/base_short.html
index becb7873..382e763f 100644
--- a/hosting/templates/hosting/base_short.html
+++ b/hosting/templates/hosting/base_short.html
@@ -74,8 +74,8 @@
     {% endif %}
     <!-- jQuery -->
     <script src="{% static 'hosting/js/jquery.js' %}"></script>
-    <script type="text/javascript" src="//cdn.jsdelivr.net/jquery.validation/1.13.1/jquery.validate.min.js"></script>
-    <script src="{% static 'hosting/js/vendor/owl.carousel.min.js'%}"></script>
+    <script src="//cdnjs.cloudflare.com/ajax/libs/jquery-validate/1.16.0/jquery.validate.min.js"></script>
+    <script src="//cdnjs.cloudflare.com/ajax/libs/1000hz-bootstrap-validator/0.11.9/validator.min.js"></script>
     <!-- Copy Clipboard -->
     <script src="//cdnjs.cloudflare.com/ajax/libs/clipboard.js/1.5.10/clipboard.min.js"></script>
 
@@ -106,8 +106,6 @@
     <script type="text/javascript" src="//cdnjs.cloudflare.com/ajax/libs/moment.js/2.18.1/moment.min.js"></script>
     <script type="text/javascript" src="//cdnjs.cloudflare.com/ajax/libs/moment.js/2.18.1/moment-with-locales.js"></script>
 
-
-
 </body>
 
 </html>
diff --git a/hosting/templates/hosting/calculator_form.html b/hosting/templates/hosting/calculator_form.html
index cdba4809..5ba2a4c3 100644
--- a/hosting/templates/hosting/calculator_form.html
+++ b/hosting/templates/hosting/calculator_form.html
@@ -1,27 +1,20 @@
 {% load staticfiles i18n%}
 <form id="order_form" method="POST" action="" data-toggle="validator" role="form">
     {% csrf_token %}
-    <div class="title">
-        <h3>{% trans "VM hosting" %} </h3>
-    </div>
     <div class="price">
         <span id="total">15</span>
-        <span>CHF/{% trans "month" %}</span>
+        <span>CHF/30 {% trans "days" %}</span>
         <div class="price-text">
             <p>{% trans "VAT included" %}</p>
         </div>
     </div>
     <div class="descriptions">
-        <div class="description form-group">
-            <p>{% trans "Hosted in Switzerland" %}</p>
-        </div>
         <div class="form-group">
             <div class="description input">
-                <i class="fa fa-minus-circle left" data-minus="cpu" aria-hidden="true"></i>
-                <input class="input-price select-number" type="number" min="1" max="48" id="coreValue" name="cpu"
-                       data-error="{% trans 'Please enter a value in range 1 - 48.' %}" required>
+                <i class="fa fa-minus left" data-minus="cpu" aria-hidden="true"></i>
+                <input class="input-price select-number" type="number" min="1" max="48" id="coreValue" name="cpu" data-error="{% trans 'Please enter a value in range 1 - 48.' %}" required>
                 <span> Core</span>
-                <i class="fa fa-plus-circle right" data-plus="cpu" aria-hidden="true"></i>
+                <i class="fa fa-plus right" data-plus="cpu" aria-hidden="true"></i>
             </div>
             <div class="help-block with-errors">
                 {% for message in messages %}
@@ -35,11 +28,11 @@
         </div>
         <div class="form-group">
             <div class="description input">
-                <i class="fa fa-minus-circle left" data-minus="ram" aria-hidden="true"></i>
+                <i class="fa fa-minus left" data-minus="ram" aria-hidden="true"></i>
                 <input id="ramValue" class="input-price select-number" type="number" min="2" max="200" name="ram"
                        data-error="{% trans 'Please enter a value in range 2 - 200.' %}" required>
                 <span> GB RAM</span>
-                <i class="fa fa-plus-circle right" data-plus="ram" aria-hidden="true"></i>
+                <i class="fa fa-plus right" data-plus="ram" aria-hidden="true"></i>
             </div>
             <div class="help-block with-errors">
                 {% for message in messages %}
@@ -53,11 +46,11 @@
         </div>
         <div class="form-group">
             <div class="description input">
-                <i class="fa fa-minus-circle left" data-minus="storage" aria-hidden="true"></i>
+                <i class="fa fa-minus left" data-minus="storage" aria-hidden="true"></i>
                 <input id="storageValue" class="input-price select-number" type="number" min="10" max="2000" step="10"
                        name="storage" data-error="{% trans 'Please enter a value in range 10 - 2000.' %}" required>
                 <span>{% trans "GB Storage (SSD)" %}</span>
-                <i class="fa fa-plus-circle right" data-plus="storage" aria-hidden="true"></i>
+                <i class="fa fa-plus right" data-plus="storage" aria-hidden="true"></i>
             </div>
             <div class="help-block with-errors">
                 {% for message in messages %}
@@ -69,55 +62,26 @@
                 {% endfor %}
             </div>
         </div>
-        <div class="description select-configuration input form-group justify-center">
-            <label for="config">OS</label>
-            <select name="config" id="">
-                {% for template in templates %}
-                <option value="{{template.opennebula_vm_template_id}}">{{template.name}}</option>
+        <div class="form-group">
+            <div class="description select-configuration input justify-center">
+                <label for="config">OS</label>
+                <select name="config" id="">
+                    {% for template in templates %}
+                    <option value="{{template.opennebula_vm_template_id}}">{{template.name}}</option>
+                    {% endfor %}
+                </select>
+            </div>
+            <div class="help-block with-errors">
+                {% for message in messages %}
+                    {% if 'cores' in message.tags %}
+                     <ul class="list-unstyled"><li>
+                        {{ message|safe }}
+                    </li></ul>
+                    {% endif %}
                 {% endfor %}
-            </select>
+            </div>
         </div>
         <input type="hidden" name="total">
-        <!--<div class="description check-ip">
-            <input type="checkbox" name="ipv6"> Ipv6 Only<br>
-        </div>-->
-        <div class="form-group">
-            <div class="description input justify-center">
-                <label for="name" class="control-label">{% trans "Name"%}</label>
-                <input type="text" name="name" class="form-control" placeholder="{% trans 'Your Name'%}"
-                       data-minlength="3" data-error="{% trans 'Please enter your name.' %}" required>
-            </div>
-            <div class="help-block with-errors">
-                {% for message in messages %}
-                {% if 'name' in message.tags %}
-                <ul class="list-unstyled">
-                    <li>
-                        {{ message|safe }}
-                    </li>
-                </ul>
-                {% endif %}
-                {% endfor %}
-            </div>
-        </div>
-        <div class="form-group">
-            <div class="description input justify-center">
-                <label for="email" class="control-label">{% trans "Email"%}</label>
-                <input name="email" type="email" pattern="^[^@\s]+@([^@\s]+\.)+[^@\s]+$" class="form-control"
-                       placeholder="{% trans 'Your Email' %}"
-                       data-error="{% trans 'Please enter a valid email address.' %}" required>
-            </div>
-            <div class="help-block with-errors">
-                {% for message in messages %}
-                {% if 'email' in message.tags %}
-                <ul class="list-unstyled">
-                    <li>
-                        {{ message|safe }}
-                    </li>
-                </ul>
-                {% endif %}
-                {% endfor %}
-            </div>
-        </div>
     </div>
     <input type="submit" class="btn btn-primary disabled" value="{% trans 'Continue' %}"></input>
 </form>
diff --git a/hosting/templates/hosting/create_virtual_machine.html b/hosting/templates/hosting/create_virtual_machine.html
index 5a5e789e..dff82199 100644
--- a/hosting/templates/hosting/create_virtual_machine.html
+++ b/hosting/templates/hosting/create_virtual_machine.html
@@ -2,24 +2,23 @@
 {% load staticfiles bootstrap3 i18n %}
 
 {% block content %}
-<div class="dashboard-container">
+<div class="dashboard-container create-vm-container">
     <div class="row">
         <div class="col-sm-6">
           <div class="dashboard-container-head">
-              <h3 class="dashboard-title-thin"><img src="{% static 'hosting/img/plusVM.svg' %}" class="un-icon" style="margin-top: -18px;width: 42px;height: 42px;"> {% trans "Create VM" %}</h3>
-              {% if messages %}
-                  <div class="alert alert-warning">
-                      {% for message in messages %}
-                          <span>{{ message }}</span>
-                      {% endfor %}
-                  </div>
-              {% endif %}
+                <h3 class="dashboard-title-thin"><img src="{% static 'hosting/img/plusVM.svg' %}" class="un-icon" style="margin-top: -18px;width: 42px;height: 42px;"> {% trans "Create VM" %}</h3>
+                {% if messages %}
+                    <div class="alert alert-warning">
+                        {% for message in messages %}
+                            <span>{{ message }}</span>
+                        {% endfor %}
+                    </div>
+                {% endif %}
           </div>
         </div>
         <div class="col-sm-6">
             <div class="price-calc-section no-padding">
                 <div class="landing card">
-                    <img class="img-beta" src="{% static 'datacenterlight/img/beta-img.png' %}" alt="">
                     <div class="caption">
                         {% include "hosting/calculator_form.html" %}
                     </div>
diff --git a/hosting/views.py b/hosting/views.py
index f7d6e414..a61f4e41 100644
--- a/hosting/views.py
+++ b/hosting/views.py
@@ -1,9 +1,11 @@
 import uuid
 
+from django import forms
 from django.conf import settings
 from django.contrib import messages
 from django.contrib.auth.mixins import LoginRequiredMixin
 from django.contrib.auth.tokens import default_token_generator
+from django.core.exceptions import ValidationError
 from django.core.files.base import ContentFile
 from django.core.urlresolvers import reverse_lazy, reverse
 from django.http import Http404
@@ -25,7 +27,7 @@ from stored_messages.settings import stored_messages_settings
 from membership.models import CustomUser, StripeCustomer
 from opennebula_api.models import OpenNebulaManager
 from opennebula_api.serializers import VirtualMachineSerializer, \
-    VirtualMachineTemplateSerializer
+    VirtualMachineTemplateSerializer, VMTemplateSerializer
 from utils.forms import BillingAddressForm, PasswordResetRequestForm, \
     UserBillingAddressForm
 from utils.mailer import BaseEmail
@@ -36,6 +38,8 @@ from .forms import HostingUserSignupForm, HostingUserLoginForm, \
     UserHostingKeyForm, generate_ssh_key_name
 from .mixins import ProcessVMSelectionMixin
 from .models import HostingOrder, HostingBill, HostingPlan, UserHostingKey
+from datacenterlight.models import VMTemplate
+
 
 CONNECTION_ERROR = "Your VMs cannot be displayed at the moment due to a backend \
                     connection error. please try again in a few minutes."
@@ -711,7 +715,7 @@ class PaymentVMView(LoginRequiredMixin, FormView):
                                                request.get_host()),
                 'page_header': _(
                     'Your New VM %(vm_name)s at Data Center Light') % {
-                                   'vm_name': vm.get('name')}
+                    'vm_name': vm.get('name')}
             }
             email_data = {
                 'subject': context.get('page_header'),
@@ -827,48 +831,80 @@ class CreateVirtualMachinesView(LoginRequiredMixin, View):
     template_name = "hosting/create_virtual_machine.html"
     login_url = reverse_lazy('hosting:login')
 
-    def get(self, request, *args, **kwargs):
+    def validate_cores(self, value):
+        if (value > 48) or (value < 1):
+            raise ValidationError(_('Invalid number of cores'))
 
+    def validate_memory(self, value):
+        if (value > 200) or (value < 2):
+            raise ValidationError(_('Invalid RAM size'))
+
+    def validate_storage(self, value):
+        if (value > 2000) or (value < 10):
+            raise ValidationError(_('Invalid storage size'))
+
+    def get(self, request, *args, **kwargs):
         if not UserHostingKey.objects.filter(user=self.request.user).exists():
             messages.success(
                 request,
                 _(
-                    'In order to create a VM, you need to create/upload your SSH KEY first.')
+                    'In order to create a VM, you need to'
+                    'create/upload your SSH KEY first.'
+                )
             )
             return HttpResponseRedirect(reverse('hosting:ssh_keys'))
-
-        try:
-            manager = OpenNebulaManager()
-            templates = manager.get_templates()
-            configuration_options = HostingPlan.get_serialized_configs()
-
-            context = {
-                'templates': VirtualMachineTemplateSerializer(templates,
-                                                              many=True).data,
-                'configuration_options': configuration_options,
-            }
-        except:
-            messages.error(
-                request,
-                'We could not load the VM templates due to a backend connection \
-                error. Please try again in a few minutes'
-            )
-            context = {
-                'error': 'connection'
-            }
-
+        context = {'templates': VMTemplate.objects.all()}
         return render(request, self.template_name, context)
 
     def post(self, request):
-        manager = OpenNebulaManager()
-        template_id = request.POST.get('vm_template_id')
-        template = manager.get_template(template_id)
-        configuration_id = int(request.POST.get('configuration'))
-        configuration = HostingPlan.objects.get(id=configuration_id)
-        request.session['template'] = VirtualMachineTemplateSerializer(
-            template).data
+        cores = request.POST.get('cpu')
+        cores_field = forms.IntegerField(validators=[self.validate_cores])
+        memory = request.POST.get('ram')
+        memory_field = forms.IntegerField(validators=[self.validate_memory])
+        storage = request.POST.get('storage')
+        storage_field = forms.IntegerField(validators=[self.validate_storage])
+        price = request.POST.get('total')
+        template_id = int(request.POST.get('config'))
+        template = VMTemplate.objects.filter(
+            opennebula_vm_template_id=template_id).first()
+        template_data = VMTemplateSerializer(template).data
 
-        request.session['specs'] = configuration.serialize()
+        try:
+            cores = cores_field.clean(cores)
+        except ValidationError as err:
+            msg = '{} : {}.'.format(cores, str(err))
+            messages.add_message(self.request, messages.ERROR, msg,
+                                 extra_tags='cores')
+            return HttpResponseRedirect(
+                reverse('datacenterlight:index') + "#order_form")
+
+        try:
+            memory = memory_field.clean(memory)
+        except ValidationError as err:
+            msg = '{} : {}.'.format(memory, str(err))
+            messages.add_message(self.request, messages.ERROR, msg,
+                                 extra_tags='memory')
+            return HttpResponseRedirect(
+                reverse('datacenterlight:index') + "#order_form")
+
+        try:
+            storage = storage_field.clean(storage)
+        except ValidationError as err:
+            msg = '{} : {}.'.format(storage, str(err))
+            messages.add_message(self.request, messages.ERROR, msg,
+                                 extra_tags='storage')
+            return HttpResponseRedirect(
+                reverse('datacenterlight:index') + "#order_form")
+
+        specs = {
+            'cpu': cores,
+            'memory': memory,
+            'disk_size': storage,
+            'price': price
+        }
+
+        request.session['specs'] = specs
+        request.session['template'] = template_data
         return redirect(reverse('hosting:payment'))
 
 

From 556ed75262087ba55478bfcbbcdf91370db47222 Mon Sep 17 00:00:00 2001
From: Arvind Tiwari <tiwariav@gmail.com>
Date: Fri, 15 Sep 2017 20:14:32 +0530
Subject: [PATCH 20/82] translations

---
 .../locale/de/LC_MESSAGES/django.po           | 11 ++-
 hosting/locale/de/LC_MESSAGES/django.po       | 72 +++++++++++++------
 .../static/hosting/css/price_calculator.css   | 10 +--
 hosting/views.py                              |  2 +-
 4 files changed, 67 insertions(+), 28 deletions(-)

diff --git a/datacenterlight/locale/de/LC_MESSAGES/django.po b/datacenterlight/locale/de/LC_MESSAGES/django.po
index 6c9d36ae..4be77f10 100644
--- a/datacenterlight/locale/de/LC_MESSAGES/django.po
+++ b/datacenterlight/locale/de/LC_MESSAGES/django.po
@@ -8,7 +8,7 @@ msgid ""
 msgstr ""
 "Project-Id-Version: PACKAGE VERSION\n"
 "Report-Msgid-Bugs-To: \n"
-"POT-Creation-Date: 2017-09-03 16:44+0000\n"
+"POT-Creation-Date: 2017-09-15 20:11+0530\n"
 "PO-Revision-Date: YEAR-MO-DA HO:MI+ZONE\n"
 "Last-Translator: FULL NAME <EMAIL@ADDRESS>\n"
 "Language-Team: LANGUAGE <LL@li.org>\n"
@@ -183,9 +183,18 @@ msgstr "Kontakt"
 msgid "All Rights Reserved"
 msgstr "Alle Rechte vorbehalten"
 
+msgid "Toggle navigation"
+msgstr "umschalten"
+
 msgid "Why Data Center Light?"
 msgstr "Warum Data Center Light?"
 
+msgid "Login"
+msgstr "Anmelden"
+
+msgid "Dashboard"
+msgstr "Mein Dashboard"
+
 msgid "Finally, an affordable VM hosting in Switzerland!"
 msgstr "Endlich: bezahlbares VM Hosting in der Schweiz"
 
diff --git a/hosting/locale/de/LC_MESSAGES/django.po b/hosting/locale/de/LC_MESSAGES/django.po
index 780419b1..5a72c715 100644
--- a/hosting/locale/de/LC_MESSAGES/django.po
+++ b/hosting/locale/de/LC_MESSAGES/django.po
@@ -8,7 +8,7 @@ msgid ""
 msgstr ""
 "Project-Id-Version: PACKAGE VERSION\n"
 "Report-Msgid-Bugs-To: \n"
-"POT-Creation-Date: 2017-09-09 06:04+0000\n"
+"POT-Creation-Date: 2017-09-15 20:11+0530\n"
 "PO-Revision-Date: YEAR-MO-DA HO:MI+ZONE\n"
 "Last-Translator: FULL NAME <EMAIL@ADDRESS>\n"
 "Language-Team: LANGUAGE <LL@li.org>\n"
@@ -100,6 +100,27 @@ msgstr "vorherige"
 msgid "next"
 msgstr "nächste"
 
+msgid "days"
+msgstr "tage"
+
+msgid "VAT included"
+msgstr "MwSt. inklusive"
+
+msgid "Please enter a value in range 1 - 48."
+msgstr "Bitte gib einen Wert von 1 bis 48 ein."
+
+msgid "Please enter a value in range 2 - 200."
+msgstr "Bitte gib einen Wert von 2 bis 200 ein."
+
+msgid "Please enter a value in range 10 - 2000."
+msgstr "Bitte gib einen Wert von 10 bis 200 ein."
+
+msgid "GB Storage (SSD)"
+msgstr "GB Storage (SSD)"
+
+msgid "Continue"
+msgstr "Weiter"
+
 msgid "SSH Key"
 msgstr "SSH Key"
 
@@ -139,30 +160,12 @@ msgstr "Hast Du bereits ein Benutzerkonto?"
 msgid "Login"
 msgstr "Anmelden"
 
-msgid "New Virtual Machine"
-msgstr "Neue virtuelle Maschine"
-
-msgid "Step 1. Select VM Template:"
-msgstr "Wähle eine Vorlage"
-
-msgid "Step2. Select VM Configuration"
-msgstr "Wähle eine Konfiguration"
-
-msgid "Price "
-msgstr "Preis"
-
-msgid "CHF/Month"
-msgstr "CHF/Monat"
-
-msgid "Start VM"
-msgstr "VM jetzt starten"
+msgid "Create VM"
+msgstr "VM erstellen"
 
 msgid "My Dashboard"
 msgstr "Mein Dashboard"
 
-msgid "Create VM"
-msgstr "VM erstellen"
-
 msgid "My VMs"
 msgstr "Meine VMs"
 
@@ -619,6 +622,15 @@ msgid "In order to create a VM, you need to create/upload your SSH KEY first."
 msgstr ""
 "Um eine VM zu erstellen musst du zuerst einen SSH-Key erstellen / hochladen."
 
+msgid "Invalid number of cores"
+msgstr "Ungültige Anzahle CPU-Kerne"
+
+msgid "Invalid RAM size"
+msgstr "Ungültige RAM-Grösse"
+
+msgid "Invalid storage size"
+msgstr "Ungültige Speicher-Grösse"
+
 msgid ""
 "We could not find the requested VM. Please                            "
 "contact Data Center Light Support."
@@ -631,6 +643,24 @@ msgstr "VM Kündigung"
 msgid "VM %(VM_ID)s terminated successfully"
 msgstr "VM %(VM_ID)s erfolgreich beendet"
 
+#~ msgid "New Virtual Machine"
+#~ msgstr "Neue virtuelle Maschine"
+
+#~ msgid "Step 1. Select VM Template:"
+#~ msgstr "Wähle eine Vorlage"
+
+#~ msgid "Step2. Select VM Configuration"
+#~ msgstr "Wähle eine Konfiguration"
+
+#~ msgid "Price "
+#~ msgstr "Preis"
+
+#~ msgid "CHF/Month"
+#~ msgstr "CHF/Monat"
+
+#~ msgid "Start VM"
+#~ msgstr "VM jetzt starten"
+
 #~ msgid "My Virtual Machines"
 #~ msgstr "Meine virtuellen Maschinen"
 
diff --git a/hosting/static/hosting/css/price_calculator.css b/hosting/static/hosting/css/price_calculator.css
index 5aac2c97..43daa713 100644
--- a/hosting/static/hosting/css/price_calculator.css
+++ b/hosting/static/hosting/css/price_calculator.css
@@ -193,21 +193,21 @@
     margin: 0 8px;
 }
 
-.help-block.with-errors {
+.price-calc-section .help-block.with-errors {
     text-align: center;
     margin: 0 0;
     padding: 0 0 5px;
 }
-.help-block.with-errors ul {
+.price-calc-section .help-block.with-errors ul {
     margin-bottom: 0;
 }
 
-.form-group {
+.price-calc-section .form-group {
     margin: 0;
     position: relative;
 }
 
-.form-group:after {
+.price-calc-section .form-group:after {
     content: ' ';
     display: block;
     position: absolute;
@@ -219,7 +219,7 @@
     background: rgba(128, 128, 128, 0.2);
 }
 
-.btn-primary {
+.price-calc-section .btn-primary {
     background: #29427A;
     border-color: #29427A;
     color: #fff;
diff --git a/hosting/views.py b/hosting/views.py
index a61f4e41..75162536 100644
--- a/hosting/views.py
+++ b/hosting/views.py
@@ -848,7 +848,7 @@ class CreateVirtualMachinesView(LoginRequiredMixin, View):
             messages.success(
                 request,
                 _(
-                    'In order to create a VM, you need to'
+                    'In order to create a VM, you need to '
                     'create/upload your SSH KEY first.'
                 )
             )

From 2de0fc13b9c4506489a33cf75daa026eac4f4f1e Mon Sep 17 00:00:00 2001
From: Arvind Tiwari <tiwariav@gmail.com>
Date: Fri, 15 Sep 2017 20:17:54 +0530
Subject: [PATCH 21/82] translation fix

---
 datacenterlight/locale/de/LC_MESSAGES/django.po | 2 +-
 hosting/locale/de/LC_MESSAGES/django.po         | 2 +-
 2 files changed, 2 insertions(+), 2 deletions(-)

diff --git a/datacenterlight/locale/de/LC_MESSAGES/django.po b/datacenterlight/locale/de/LC_MESSAGES/django.po
index 4be77f10..fe120a25 100644
--- a/datacenterlight/locale/de/LC_MESSAGES/django.po
+++ b/datacenterlight/locale/de/LC_MESSAGES/django.po
@@ -193,7 +193,7 @@ msgid "Login"
 msgstr "Anmelden"
 
 msgid "Dashboard"
-msgstr "Mein Dashboard"
+msgstr "Dashboard"
 
 msgid "Finally, an affordable VM hosting in Switzerland!"
 msgstr "Endlich: bezahlbares VM Hosting in der Schweiz"
diff --git a/hosting/locale/de/LC_MESSAGES/django.po b/hosting/locale/de/LC_MESSAGES/django.po
index 5a72c715..0c031b6a 100644
--- a/hosting/locale/de/LC_MESSAGES/django.po
+++ b/hosting/locale/de/LC_MESSAGES/django.po
@@ -279,7 +279,7 @@ msgstr ""
 "%(base_url)s%(my_virtual_machines_url)s\n"
 
 msgid "Toggle navigation"
-msgstr "Konfiguration"
+msgstr "Umschalten"
 
 msgid "Dashboard"
 msgstr "Mein Dashboard"

From 772469a23e4a6a5362ba5f2f20ef331c1900c0ea Mon Sep 17 00:00:00 2001
From: Arvind Tiwari <tiwariav@gmail.com>
Date: Mon, 18 Sep 2017 19:49:14 +0530
Subject: [PATCH 22/82] design modifications

---
 datacenterlight/locale/de/LC_MESSAGES/django.po      |  2 +-
 hosting/locale/de/LC_MESSAGES/django.po              | 12 ++++++------
 hosting/static/hosting/css/price_calculator.css      |  4 +++-
 hosting/templates/hosting/calculator_form.html       |  2 +-
 .../templates/hosting/create_virtual_machine.html    |  4 ++--
 5 files changed, 13 insertions(+), 11 deletions(-)

diff --git a/datacenterlight/locale/de/LC_MESSAGES/django.po b/datacenterlight/locale/de/LC_MESSAGES/django.po
index fe120a25..234f2a3b 100644
--- a/datacenterlight/locale/de/LC_MESSAGES/django.po
+++ b/datacenterlight/locale/de/LC_MESSAGES/django.po
@@ -8,7 +8,7 @@ msgid ""
 msgstr ""
 "Project-Id-Version: PACKAGE VERSION\n"
 "Report-Msgid-Bugs-To: \n"
-"POT-Creation-Date: 2017-09-15 20:11+0530\n"
+"POT-Creation-Date: 2017-09-17 01:31+0530\n"
 "PO-Revision-Date: YEAR-MO-DA HO:MI+ZONE\n"
 "Last-Translator: FULL NAME <EMAIL@ADDRESS>\n"
 "Language-Team: LANGUAGE <LL@li.org>\n"
diff --git a/hosting/locale/de/LC_MESSAGES/django.po b/hosting/locale/de/LC_MESSAGES/django.po
index 0c031b6a..c7a13e34 100644
--- a/hosting/locale/de/LC_MESSAGES/django.po
+++ b/hosting/locale/de/LC_MESSAGES/django.po
@@ -8,7 +8,7 @@ msgid ""
 msgstr ""
 "Project-Id-Version: PACKAGE VERSION\n"
 "Report-Msgid-Bugs-To: \n"
-"POT-Creation-Date: 2017-09-15 20:11+0530\n"
+"POT-Creation-Date: 2017-09-17 01:31+0530\n"
 "PO-Revision-Date: YEAR-MO-DA HO:MI+ZONE\n"
 "Last-Translator: FULL NAME <EMAIL@ADDRESS>\n"
 "Language-Team: LANGUAGE <LL@li.org>\n"
@@ -100,8 +100,8 @@ msgstr "vorherige"
 msgid "next"
 msgstr "nächste"
 
-msgid "days"
-msgstr "tage"
+msgid "Month"
+msgstr "Monat"
 
 msgid "VAT included"
 msgstr "MwSt. inklusive"
@@ -380,9 +380,6 @@ msgstr "Konfiguration"
 msgid "including VAT"
 msgstr "inkl. Mehrwertsteuer"
 
-msgid "Month"
-msgstr "Monat"
-
 msgid "Billing Address"
 msgstr "Rechnungsadresse"
 
@@ -643,6 +640,9 @@ msgstr "VM Kündigung"
 msgid "VM %(VM_ID)s terminated successfully"
 msgstr "VM %(VM_ID)s erfolgreich beendet"
 
+#~ msgid "days"
+#~ msgstr "tage"
+
 #~ msgid "New Virtual Machine"
 #~ msgstr "Neue virtuelle Maschine"
 
diff --git a/hosting/static/hosting/css/price_calculator.css b/hosting/static/hosting/css/price_calculator.css
index 43daa713..e1ea2a5f 100644
--- a/hosting/static/hosting/css/price_calculator.css
+++ b/hosting/static/hosting/css/price_calculator.css
@@ -116,7 +116,7 @@
     color: #29427a;
     cursor: pointer;
     font-size: 20px;
-    border: 1px solid #eee;
+    border: 1px solid #ccc;
     padding: 5px 6px 3px;
     border-radius: 5px;
 }
@@ -229,5 +229,7 @@
 @media(min-width: 768px) {
     .create-vm-container {
         padding-top: 120px;
+        max-width: 1120px;
+        /* width: 100%; */
     }
 }
diff --git a/hosting/templates/hosting/calculator_form.html b/hosting/templates/hosting/calculator_form.html
index 5ba2a4c3..879f2054 100644
--- a/hosting/templates/hosting/calculator_form.html
+++ b/hosting/templates/hosting/calculator_form.html
@@ -3,7 +3,7 @@
     {% csrf_token %}
     <div class="price">
         <span id="total">15</span>
-        <span>CHF/30 {% trans "days" %}</span>
+        <span>CHF/{% trans "Month" %}</span>
         <div class="price-text">
             <p>{% trans "VAT included" %}</p>
         </div>
diff --git a/hosting/templates/hosting/create_virtual_machine.html b/hosting/templates/hosting/create_virtual_machine.html
index dff82199..5f61eae8 100644
--- a/hosting/templates/hosting/create_virtual_machine.html
+++ b/hosting/templates/hosting/create_virtual_machine.html
@@ -4,7 +4,7 @@
 {% block content %}
 <div class="dashboard-container create-vm-container">
     <div class="row">
-        <div class="col-sm-6">
+        <div class="col-sm-4">
           <div class="dashboard-container-head">
                 <h3 class="dashboard-title-thin"><img src="{% static 'hosting/img/plusVM.svg' %}" class="un-icon" style="margin-top: -18px;width: 42px;height: 42px;"> {% trans "Create VM" %}</h3>
                 {% if messages %}
@@ -16,7 +16,7 @@
                 {% endif %}
           </div>
         </div>
-        <div class="col-sm-6">
+        <div class="col-sm-5">
             <div class="price-calc-section no-padding">
                 <div class="landing card">
                     <div class="caption">

From b276194f31cbacb41aaa6702181a9a617f98b98d Mon Sep 17 00:00:00 2001
From: Arvind Tiwari <tiwariav@gmail.com>
Date: Mon, 18 Sep 2017 20:18:02 +0530
Subject: [PATCH 23/82] width normalized

---
 hosting/static/hosting/css/price_calculator.css       | 2 --
 hosting/templates/hosting/create_virtual_machine.html | 2 +-
 2 files changed, 1 insertion(+), 3 deletions(-)

diff --git a/hosting/static/hosting/css/price_calculator.css b/hosting/static/hosting/css/price_calculator.css
index e1ea2a5f..310a9d05 100644
--- a/hosting/static/hosting/css/price_calculator.css
+++ b/hosting/static/hosting/css/price_calculator.css
@@ -229,7 +229,5 @@
 @media(min-width: 768px) {
     .create-vm-container {
         padding-top: 120px;
-        max-width: 1120px;
-        /* width: 100%; */
     }
 }
diff --git a/hosting/templates/hosting/create_virtual_machine.html b/hosting/templates/hosting/create_virtual_machine.html
index 5f61eae8..aff7862a 100644
--- a/hosting/templates/hosting/create_virtual_machine.html
+++ b/hosting/templates/hosting/create_virtual_machine.html
@@ -16,7 +16,7 @@
                 {% endif %}
           </div>
         </div>
-        <div class="col-sm-5">
+        <div class="col-sm-6">
             <div class="price-calc-section no-padding">
                 <div class="landing card">
                     <div class="caption">

From 226f744bae4307c6b4fd984614340430d1a61d69 Mon Sep 17 00:00:00 2001
From: Arvind Tiwari <tiwariav@gmail.com>
Date: Mon, 18 Sep 2017 21:52:59 +0530
Subject: [PATCH 24/82] success modal added

---
 .../hosting/js/virtual_machine_detail.js      |  2 +-
 .../hosting/virtual_machine_detail.html       | 19 ++++++++++++++++++-
 hosting/views.py                              | 12 ++++++++----
 3 files changed, 27 insertions(+), 6 deletions(-)

diff --git a/hosting/static/hosting/js/virtual_machine_detail.js b/hosting/static/hosting/js/virtual_machine_detail.js
index d6387dbc..711b486b 100644
--- a/hosting/static/hosting/js/virtual_machine_detail.js
+++ b/hosting/static/hosting/js/virtual_machine_detail.js
@@ -27,7 +27,7 @@ function VMTerminateSuccess($container, data) {
     $container.addClass('terminate-success')
         .find('.vm-item-lg').text(data.text);
     $container.find('.btn').remove();
-    window.location = data.redirect;
+    $('#terminate-success').modal('show');
 }
 
 function VMTerminateFail($container, data, text) {
diff --git a/hosting/templates/hosting/virtual_machine_detail.html b/hosting/templates/hosting/virtual_machine_detail.html
index d0bfae47..9d77c31d 100644
--- a/hosting/templates/hosting/virtual_machine_detail.html
+++ b/hosting/templates/hosting/virtual_machine_detail.html
@@ -103,7 +103,7 @@
 				</div>
 	            <div class="modal-body">
 					<div class="modal-icon"><i class="fa fa-ban" aria-hidden="true"></i></div>
-					<h4 class="modal-title" id="ModalLabel">{% trans "Terminate your Virtual Machine"%}</h4>
+					<h4 class="modal-title" id="ModalLabel">{% trans "Terminate your Virtual Machine" %}</h4>
 					<div class="modal-text">
 						<p>{% trans "Do you want to cancel your Virtual Machine" %} ?</p>
 						<p><strong>{{virtual_machine.name}}</strong></p>
@@ -116,4 +116,21 @@
 	    </div>
 	</div>
 	<!-- / Cancel Modal -->
+	<!-- Success Modal -->
+	<div class="modal fade" id="terminate-success" tabindex="-1" role="dialog" aria-hidden="true">
+    <div class="modal-dialog">
+      <div class="modal-content">
+				<div class="modal-header">
+				</div>
+        <div class="modal-body">
+					<div class="modal-icon"><i class="fa fa-ban" aria-hidden="true"></i></div>
+					<h4 class="modal-title" id="ModalLabel">{% trans "Your Virtual Machine" %} {{vm.id}} {% trans "was successfully terminated!" %}</h4>
+          <div class="modal-footer">
+            <a href="{% url 'hosting:virtual_machines' %}"	class="btn btn-danger btn-wide">{% trans "Close" %}</a>
+          </div>
+        </div>
+      </div>
+    </div>
+	</div>
+	<!-- / Cancel Modal -->
 {%endblock%}
diff --git a/hosting/views.py b/hosting/views.py
index acd7e67b..8356d5ad 100644
--- a/hosting/views.py
+++ b/hosting/views.py
@@ -961,7 +961,13 @@ class VirtualMachineView(LoginRequiredMixin, View):
             password=owner.password
         )
 
-        vm_data = VirtualMachineSerializer(manager.get_vm(vm.id)).data
+        try:
+            vm_data = VirtualMachineSerializer(manager.get_vm(vm.id)).data
+        except BaseException:
+            return redirect(
+                reverse('hosting:virtual_machines',
+                        kwargs={'pk': opennebula_vm_id})
+            )
 
         terminated = manager.delete_vm(vm.id)
 
@@ -971,12 +977,10 @@ class VirtualMachineView(LoginRequiredMixin, View):
         else:
             for t in range(15):
                 try:
-                    manager.get_vm(self.kwargs.get('pk'))
+                    manager.get_vm(opennebula_vm_id)
                 except WrongIdError:
                     response['status'] = True
-                    response['redirect'] = self.get_success_url()
                     response['text'] = ugettext('Terminated')
-                    self.send_mail()
                     break
                 except BaseException:
                     break

From 43300c72269faa80983c38aa43a20ccd3f1f4d4f Mon Sep 17 00:00:00 2001
From: Arvind Tiwari <tiwariav@gmail.com>
Date: Mon, 18 Sep 2017 23:21:04 +0530
Subject: [PATCH 25/82] translations added, modal fixed

---
 hosting/locale/de/LC_MESSAGES/django.po       | 20 +++++++++------
 .../hosting/js/virtual_machine_detail.js      |  1 -
 .../hosting/virtual_machine_detail.html       | 25 +++++++++++--------
 3 files changed, 27 insertions(+), 19 deletions(-)

diff --git a/hosting/locale/de/LC_MESSAGES/django.po b/hosting/locale/de/LC_MESSAGES/django.po
index 1c0f3faa..ca78a381 100644
--- a/hosting/locale/de/LC_MESSAGES/django.po
+++ b/hosting/locale/de/LC_MESSAGES/django.po
@@ -8,7 +8,7 @@ msgid ""
 msgstr ""
 "Project-Id-Version: PACKAGE VERSION\n"
 "Report-Msgid-Bugs-To: \n"
-"POT-Creation-Date: 2017-09-14 12:27+0000\n"
+"POT-Creation-Date: 2017-09-18 23:16+0530\n"
 "PO-Revision-Date: YEAR-MO-DA HO:MI+ZONE\n"
 "Last-Translator: FULL NAME <EMAIL@ADDRESS>\n"
 "Language-Team: LANGUAGE <LL@li.org>\n"
@@ -575,6 +575,15 @@ msgstr "Bist Du sicher, dass Du Deine virtuelle Maschine beenden willst"
 msgid "OK"
 msgstr ""
 
+msgid "Your Virtual Machine"
+msgstr "Deine Maschinen Detail"
+
+msgid "was successfully terminated!"
+msgstr "wurde erfolgreich beendet!"
+
+msgid "Close"
+msgstr "Schliessen"
+
 msgid "Virtual Machines"
 msgstr "Virtuelle Maschinen"
 
@@ -645,12 +654,12 @@ msgstr "Kontaktiere den Data Center Light Support."
 msgid "Error terminating VM"
 msgstr "Fehler beenden VM"
 
-msgid "Virtual Machine Cancellation"
-msgstr "VM Kündigung"
-
 msgid "Terminated"
 msgstr "Beendet"
 
+msgid "Virtual Machine Cancellation"
+msgstr "VM Kündigung"
+
 #~ msgid "VM %(VM_ID)s terminated successfully"
 #~ msgstr "VM %(VM_ID)s erfolgreich beendet"
 
@@ -702,9 +711,6 @@ msgstr "Beendet"
 #~ msgid "Ipv6"
 #~ msgstr "IPv6"
 
-#~ msgid "Close"
-#~ msgstr "Schliessen"
-
 #~ msgid "Cancel"
 #~ msgstr "Beenden"
 
diff --git a/hosting/static/hosting/js/virtual_machine_detail.js b/hosting/static/hosting/js/virtual_machine_detail.js
index 711b486b..e611246b 100644
--- a/hosting/static/hosting/js/virtual_machine_detail.js
+++ b/hosting/static/hosting/js/virtual_machine_detail.js
@@ -40,7 +40,6 @@ function VMTerminateFail($container, data, text) {
 
 
 $(document).ready(function() {
-
     $('#confirm-cancel').on('click', '.btn-ok', function(e) {
         var url = $('#virtual_machine_cancel_form').attr('action');
         var $container = $('#terminate-VM');
diff --git a/hosting/templates/hosting/virtual_machine_detail.html b/hosting/templates/hosting/virtual_machine_detail.html
index 9d77c31d..08872c1e 100644
--- a/hosting/templates/hosting/virtual_machine_detail.html
+++ b/hosting/templates/hosting/virtual_machine_detail.html
@@ -96,24 +96,24 @@
 	</div>
 	<!-- Cancel Modal -->
 	<div class="modal fade" id="confirm-cancel" tabindex="-1" role="dialog" aria-labelledby="myModalLabel" aria-hidden="true">
-	    <div class="modal-dialog">
-	        <div class="modal-content">
+    <div class="modal-dialog">
+      <div class="modal-content">
 				<div class="modal-header">
 					<button type="button" class="close" data-dismiss="modal" aria-label="Confirm"><span aria-hidden="true">&times;</span></button>
 				</div>
-	            <div class="modal-body">
+      	<div class="modal-body">
 					<div class="modal-icon"><i class="fa fa-ban" aria-hidden="true"></i></div>
 					<h4 class="modal-title" id="ModalLabel">{% trans "Terminate your Virtual Machine" %}</h4>
 					<div class="modal-text">
 						<p>{% trans "Do you want to cancel your Virtual Machine" %} ?</p>
 						<p><strong>{{virtual_machine.name}}</strong></p>
 					</div>
-		            <div class="modal-footer">
-		                <a class="btn btn-danger btn-ok btn-wide">{% trans "OK" %}</a>
-		            </div>
-	            </div>
-	        </div>
-	    </div>
+          <div class="modal-footer">
+              <a class="btn btn-danger btn-ok btn-wide">{% trans "OK" %}</a>
+          </div>
+        </div>
+      </div>
+    </div>
 	</div>
 	<!-- / Cancel Modal -->
 	<!-- Success Modal -->
@@ -123,10 +123,13 @@
 				<div class="modal-header">
 				</div>
         <div class="modal-body">
-					<div class="modal-icon"><i class="fa fa-ban" aria-hidden="true"></i></div>
+					<div class="modal-icon"><i class="fa fa-check" aria-hidden="true"></i></div>
 					<h4 class="modal-title" id="ModalLabel">{% trans "Your Virtual Machine" %} {{vm.id}} {% trans "was successfully terminated!" %}</h4>
+					<div class="modal-text">
+						<p><strong>{{virtual_machine.name}}</strong></p>
+					</div>
           <div class="modal-footer">
-            <a href="{% url 'hosting:virtual_machines' %}"	class="btn btn-danger btn-wide">{% trans "Close" %}</a>
+            <a href="{% url 'hosting:virtual_machines' %}"	class="btn btn-success btn-wide">{% trans "Close" %}</a>
           </div>
         </div>
       </div>

From 8db7ead9e272e2c9536c31e245d2765915bcf1c3 Mon Sep 17 00:00:00 2001
From: Arvind Tiwari <tiwariav@gmail.com>
Date: Tue, 19 Sep 2017 00:24:06 +0530
Subject: [PATCH 26/82] checking VM termination error

---
 hosting/views.py         | 5 +++--
 opennebula_api/models.py | 7 ++++++-
 2 files changed, 9 insertions(+), 3 deletions(-)

diff --git a/hosting/views.py b/hosting/views.py
index 8356d5ad..5f123dd4 100644
--- a/hosting/views.py
+++ b/hosting/views.py
@@ -969,11 +969,12 @@ class VirtualMachineView(LoginRequiredMixin, View):
                         kwargs={'pk': opennebula_vm_id})
             )
 
-        terminated = manager.delete_vm(vm.id)
+        terminated, err = manager.delete_vm(vm.id)
 
         if not terminated:
             response['text'] = ugettext(
-                'Error terminating VM') + opennebula_vm_id
+                'Error terminating VM') + opennebula_vm_id + '\n' +
+                err
         else:
             for t in range(15):
                 try:
diff --git a/opennebula_api/models.py b/opennebula_api/models.py
index d584bf26..9eb89fdf 100644
--- a/opennebula_api/models.py
+++ b/opennebula_api/models.py
@@ -324,6 +324,7 @@ class OpenNebulaManager():
     def delete_vm(self, vm_id):
         TERMINATE_ACTION = 'terminate'
         vm_terminated = False
+        err = ''
         try:
             self.oneadmin_client.call(
                 oca.VirtualMachine.METHODS['action'],
@@ -333,15 +334,19 @@ class OpenNebulaManager():
             vm_terminated = True
         except socket.timeout as socket_err:
             logger.info("Socket timeout error: {0}".format(socket_err))
+            err = ("Socket timeout error: {0}".format(socket_err))
         except OpenNebulaException as opennebula_err:
             logger.info(
                 "OpenNebulaException error: {0}".format(opennebula_err))
+            err = ("OpenNebulaException error: {0}".format(opennebula_err))
         except OSError as os_err:
             logger.info("OSError : {0}".format(os_err))
+            err = ("OSError : {0}".format(os_err))
         except ValueError as value_err:
             logger.info("ValueError : {0}".format(value_err))
+            err = ("ValueError : {0}".format(value_err))
 
-        return vm_terminated
+        return (vm_terminated, err)
 
     def _get_template_pool(self):
         try:

From 61bf15823861fd45a06b0cafdf399ff73d4189ac Mon Sep 17 00:00:00 2001
From: Arvind Tiwari <tiwariav@gmail.com>
Date: Tue, 19 Sep 2017 00:25:38 +0530
Subject: [PATCH 27/82] fix

---
 hosting/views.py | 3 +--
 1 file changed, 1 insertion(+), 2 deletions(-)

diff --git a/hosting/views.py b/hosting/views.py
index 5f123dd4..8e01bb22 100644
--- a/hosting/views.py
+++ b/hosting/views.py
@@ -973,8 +973,7 @@ class VirtualMachineView(LoginRequiredMixin, View):
 
         if not terminated:
             response['text'] = ugettext(
-                'Error terminating VM') + opennebula_vm_id + '\n' +
-                err
+                'Error terminating VM') + opennebula_vm_id + '\n' + err
         else:
             for t in range(15):
                 try:

From 78423c83e3721da584f917ea6521969e38d68d5d Mon Sep 17 00:00:00 2001
From: Arvind Tiwari <tiwariav@gmail.com>
Date: Tue, 19 Sep 2017 00:59:51 +0530
Subject: [PATCH 28/82] removed error details from error msg

---
 hosting/static/hosting/js/virtual_machine_detail.js | 1 +
 hosting/views.py                                    | 4 ++--
 opennebula_api/models.py                            | 7 +------
 3 files changed, 4 insertions(+), 8 deletions(-)

diff --git a/hosting/static/hosting/js/virtual_machine_detail.js b/hosting/static/hosting/js/virtual_machine_detail.js
index e611246b..76c00a91 100644
--- a/hosting/static/hosting/js/virtual_machine_detail.js
+++ b/hosting/static/hosting/js/virtual_machine_detail.js
@@ -1,6 +1,7 @@
 function VMTerminateStatus($container, url) {
     $.ajax({
         url: url,
+        type: 'GET',
         dataType: 'json',
         success: function(data) {
             VMTerminateSuccess($container, data);
diff --git a/hosting/views.py b/hosting/views.py
index 8e01bb22..8356d5ad 100644
--- a/hosting/views.py
+++ b/hosting/views.py
@@ -969,11 +969,11 @@ class VirtualMachineView(LoginRequiredMixin, View):
                         kwargs={'pk': opennebula_vm_id})
             )
 
-        terminated, err = manager.delete_vm(vm.id)
+        terminated = manager.delete_vm(vm.id)
 
         if not terminated:
             response['text'] = ugettext(
-                'Error terminating VM') + opennebula_vm_id + '\n' + err
+                'Error terminating VM') + opennebula_vm_id
         else:
             for t in range(15):
                 try:
diff --git a/opennebula_api/models.py b/opennebula_api/models.py
index 9eb89fdf..d584bf26 100644
--- a/opennebula_api/models.py
+++ b/opennebula_api/models.py
@@ -324,7 +324,6 @@ class OpenNebulaManager():
     def delete_vm(self, vm_id):
         TERMINATE_ACTION = 'terminate'
         vm_terminated = False
-        err = ''
         try:
             self.oneadmin_client.call(
                 oca.VirtualMachine.METHODS['action'],
@@ -334,19 +333,15 @@ class OpenNebulaManager():
             vm_terminated = True
         except socket.timeout as socket_err:
             logger.info("Socket timeout error: {0}".format(socket_err))
-            err = ("Socket timeout error: {0}".format(socket_err))
         except OpenNebulaException as opennebula_err:
             logger.info(
                 "OpenNebulaException error: {0}".format(opennebula_err))
-            err = ("OpenNebulaException error: {0}".format(opennebula_err))
         except OSError as os_err:
             logger.info("OSError : {0}".format(os_err))
-            err = ("OSError : {0}".format(os_err))
         except ValueError as value_err:
             logger.info("ValueError : {0}".format(value_err))
-            err = ("ValueError : {0}".format(value_err))
 
-        return (vm_terminated, err)
+        return vm_terminated
 
     def _get_template_pool(self):
         try:

From 3ef07758effebf0fdea8c4e1bc6a904a35a02fed Mon Sep 17 00:00:00 2001
From: Arvind Tiwari <tiwariav@gmail.com>
Date: Tue, 19 Sep 2017 01:08:27 +0530
Subject: [PATCH 29/82] translation and text fix

---
 hosting/locale/de/LC_MESSAGES/django.po            | 14 +++++++-------
 .../templates/hosting/virtual_machine_detail.html  |  2 +-
 hosting/views.py                                   |  2 +-
 3 files changed, 9 insertions(+), 9 deletions(-)

diff --git a/hosting/locale/de/LC_MESSAGES/django.po b/hosting/locale/de/LC_MESSAGES/django.po
index ca78a381..cd47faa3 100644
--- a/hosting/locale/de/LC_MESSAGES/django.po
+++ b/hosting/locale/de/LC_MESSAGES/django.po
@@ -8,7 +8,7 @@ msgid ""
 msgstr ""
 "Project-Id-Version: PACKAGE VERSION\n"
 "Report-Msgid-Bugs-To: \n"
-"POT-Creation-Date: 2017-09-18 23:16+0530\n"
+"POT-Creation-Date: 2017-09-19 01:04+0530\n"
 "PO-Revision-Date: YEAR-MO-DA HO:MI+ZONE\n"
 "Last-Translator: FULL NAME <EMAIL@ADDRESS>\n"
 "Language-Team: LANGUAGE <LL@li.org>\n"
@@ -575,10 +575,10 @@ msgstr "Bist Du sicher, dass Du Deine virtuelle Maschine beenden willst"
 msgid "OK"
 msgstr ""
 
-msgid "Your Virtual Machine"
-msgstr "Deine Maschinen Detail"
+msgid "Your virtual machine"
+msgstr "Deine Virtuelle Machine (VM)"
 
-msgid "was successfully terminated!"
+msgid "is successfully terminated!"
 msgstr "wurde erfolgreich beendet!"
 
 msgid "Close"
@@ -651,12 +651,12 @@ msgid ""
 "contact Data Center Light Support."
 msgstr "Kontaktiere den Data Center Light Support."
 
-msgid "Error terminating VM"
-msgstr "Fehler beenden VM"
-
 msgid "Terminated"
 msgstr "Beendet"
 
+msgid "Error terminating VM"
+msgstr "Fehler beenden VM"
+
 msgid "Virtual Machine Cancellation"
 msgstr "VM Kündigung"
 
diff --git a/hosting/templates/hosting/virtual_machine_detail.html b/hosting/templates/hosting/virtual_machine_detail.html
index 08872c1e..d2d23db8 100644
--- a/hosting/templates/hosting/virtual_machine_detail.html
+++ b/hosting/templates/hosting/virtual_machine_detail.html
@@ -124,7 +124,7 @@
 				</div>
         <div class="modal-body">
 					<div class="modal-icon"><i class="fa fa-check" aria-hidden="true"></i></div>
-					<h4 class="modal-title" id="ModalLabel">{% trans "Your Virtual Machine" %} {{vm.id}} {% trans "was successfully terminated!" %}</h4>
+					<h4 class="modal-title" id="ModalLabel">{% trans "Your Virtual Machine" %} {{vm.id}} {% trans "is successfully terminated!" %}</h4>
 					<div class="modal-text">
 						<p><strong>{{virtual_machine.name}}</strong></p>
 					</div>
diff --git a/hosting/views.py b/hosting/views.py
index 8356d5ad..107e0b7b 100644
--- a/hosting/views.py
+++ b/hosting/views.py
@@ -929,7 +929,7 @@ class VirtualMachineView(LoginRequiredMixin, View):
                     pass
                 storage.used = True
                 return HttpResponse(
-                    json.dumps({'redirect': self.get_success_url()}),
+                    json.dumps({'text': ugettext('Terminated')}),
                     content_type="application/json"
                 )
             else:

From e893f1baf170fd12f8caec3349c93b4361123681 Mon Sep 17 00:00:00 2001
From: Arvind Tiwari <tiwariav@gmail.com>
Date: Tue, 19 Sep 2017 01:17:15 +0530
Subject: [PATCH 30/82] padding fix

---
 hosting/static/hosting/css/price_calculator.css       | 8 ++++++--
 hosting/templates/hosting/calculator_form.html        | 2 +-
 hosting/templates/hosting/create_virtual_machine.html | 2 +-
 3 files changed, 8 insertions(+), 4 deletions(-)

diff --git a/hosting/static/hosting/css/price_calculator.css b/hosting/static/hosting/css/price_calculator.css
index 310a9d05..24624f10 100644
--- a/hosting/static/hosting/css/price_calculator.css
+++ b/hosting/static/hosting/css/price_calculator.css
@@ -45,13 +45,17 @@
     background: #fff;
     box-shadow: 1px 3px 6px 2px rgba(0, 0, 0, 0.2);
     padding-bottom: 30px;
-    /* border-radius: 7px; */
     text-align: center;
-    /* margin-right: auto; */
     max-width: 320px;
     position: relative;
 }
 
+@media (min-width: 768px) {
+    .price-calc-section .card {
+        margin-left: 0;
+    }
+}
+
 .price-calc-section .landing {
     width: 100% !important;
 }
diff --git a/hosting/templates/hosting/calculator_form.html b/hosting/templates/hosting/calculator_form.html
index 879f2054..18bdd3cb 100644
--- a/hosting/templates/hosting/calculator_form.html
+++ b/hosting/templates/hosting/calculator_form.html
@@ -5,7 +5,7 @@
         <span id="total">15</span>
         <span>CHF/{% trans "Month" %}</span>
         <div class="price-text">
-            <p>{% trans "VAT included" %}</p>
+            <span>{% trans "VAT included" %}</span>
         </div>
     </div>
     <div class="descriptions">
diff --git a/hosting/templates/hosting/create_virtual_machine.html b/hosting/templates/hosting/create_virtual_machine.html
index aff7862a..4ba5274e 100644
--- a/hosting/templates/hosting/create_virtual_machine.html
+++ b/hosting/templates/hosting/create_virtual_machine.html
@@ -4,7 +4,7 @@
 {% block content %}
 <div class="dashboard-container create-vm-container">
     <div class="row">
-        <div class="col-sm-4">
+        <div class="col-sm-5">
           <div class="dashboard-container-head">
                 <h3 class="dashboard-title-thin"><img src="{% static 'hosting/img/plusVM.svg' %}" class="un-icon" style="margin-top: -18px;width: 42px;height: 42px;"> {% trans "Create VM" %}</h3>
                 {% if messages %}

From c53c9661365576cd39c1805b0cbbeca257fb92e0 Mon Sep 17 00:00:00 2001
From: Arvind Tiwari <tiwariav@gmail.com>
Date: Tue, 19 Sep 2017 14:24:23 +0530
Subject: [PATCH 31/82] success modal modification

---
 hosting/locale/de/LC_MESSAGES/django.po         | 17 ++++++++---------
 .../hosting/virtual_machine_detail.html         |  7 ++-----
 2 files changed, 10 insertions(+), 14 deletions(-)

diff --git a/hosting/locale/de/LC_MESSAGES/django.po b/hosting/locale/de/LC_MESSAGES/django.po
index cd47faa3..3d824deb 100644
--- a/hosting/locale/de/LC_MESSAGES/django.po
+++ b/hosting/locale/de/LC_MESSAGES/django.po
@@ -8,7 +8,7 @@ msgid ""
 msgstr ""
 "Project-Id-Version: PACKAGE VERSION\n"
 "Report-Msgid-Bugs-To: \n"
-"POT-Creation-Date: 2017-09-19 01:04+0530\n"
+"POT-Creation-Date: 2017-09-19 14:20+0530\n"
 "PO-Revision-Date: YEAR-MO-DA HO:MI+ZONE\n"
 "Last-Translator: FULL NAME <EMAIL@ADDRESS>\n"
 "Language-Team: LANGUAGE <LL@li.org>\n"
@@ -575,14 +575,10 @@ msgstr "Bist Du sicher, dass Du Deine virtuelle Maschine beenden willst"
 msgid "OK"
 msgstr ""
 
-msgid "Your virtual machine"
-msgstr "Deine Virtuelle Machine (VM)"
-
-msgid "is successfully terminated!"
-msgstr "wurde erfolgreich beendet!"
-
-msgid "Close"
-msgstr "Schliessen"
+#, python-format
+msgid ""
+"Your Virtual Machine %(virtual_machine.name)s is successfully terminated!"
+msgstr "Deine Virtuelle Machine (VM) %(virtual_machine.name)s wurde erfolgreich beendet!"
 
 msgid "Virtual Machines"
 msgstr "Virtuelle Maschinen"
@@ -660,6 +656,9 @@ msgstr "Fehler beenden VM"
 msgid "Virtual Machine Cancellation"
 msgstr "VM Kündigung"
 
+#~ msgid "Close"
+#~ msgstr "Schliessen"
+
 #~ msgid "VM %(VM_ID)s terminated successfully"
 #~ msgstr "VM %(VM_ID)s erfolgreich beendet"
 
diff --git a/hosting/templates/hosting/virtual_machine_detail.html b/hosting/templates/hosting/virtual_machine_detail.html
index d2d23db8..33c5bf2a 100644
--- a/hosting/templates/hosting/virtual_machine_detail.html
+++ b/hosting/templates/hosting/virtual_machine_detail.html
@@ -124,12 +124,9 @@
 				</div>
         <div class="modal-body">
 					<div class="modal-icon"><i class="fa fa-check" aria-hidden="true"></i></div>
-					<h4 class="modal-title" id="ModalLabel">{% trans "Your Virtual Machine" %} {{vm.id}} {% trans "is successfully terminated!" %}</h4>
-					<div class="modal-text">
-						<p><strong>{{virtual_machine.name}}</strong></p>
-					</div>
+					<h4 class="modal-title" id="ModalLabel">{% blocktrans %}Your Virtual Machine <strong>{{virtual_machine.name}}asdas</strong> is successfully terminated!{% endblocktrans %}</h4>
           <div class="modal-footer">
-            <a href="{% url 'hosting:virtual_machines' %}"	class="btn btn-success btn-wide">{% trans "Close" %}</a>
+            <a href="{% url 'hosting:virtual_machines' %}"	class="btn btn-success btn-wide">{% trans "OK" %}</a>
           </div>
         </div>
       </div>

From 445359e1ed3c9319118004a265403975fe83561e Mon Sep 17 00:00:00 2001
From: Arvind Tiwari <tiwariav@gmail.com>
Date: Tue, 19 Sep 2017 14:29:18 +0530
Subject: [PATCH 32/82] modal restyle

---
 hosting/static/hosting/css/commons.css                | 4 ++++
 hosting/templates/hosting/virtual_machine_detail.html | 2 +-
 2 files changed, 5 insertions(+), 1 deletion(-)

diff --git a/hosting/static/hosting/css/commons.css b/hosting/static/hosting/css/commons.css
index 01ff5090..a922174c 100644
--- a/hosting/static/hosting/css/commons.css
+++ b/hosting/static/hosting/css/commons.css
@@ -139,6 +139,10 @@
 .modal-text p:not(:last-of-type){
 	margin-bottom: 5px;
 }
+
+.modal-title + .modal-footer {
+    margin-top: 5px;
+}
 .modal-footer {
     border-top: 0px solid #e5e5e5;
     width: 100%;
diff --git a/hosting/templates/hosting/virtual_machine_detail.html b/hosting/templates/hosting/virtual_machine_detail.html
index 33c5bf2a..e91fd0eb 100644
--- a/hosting/templates/hosting/virtual_machine_detail.html
+++ b/hosting/templates/hosting/virtual_machine_detail.html
@@ -124,7 +124,7 @@
 				</div>
         <div class="modal-body">
 					<div class="modal-icon"><i class="fa fa-check" aria-hidden="true"></i></div>
-					<h4 class="modal-title" id="ModalLabel">{% blocktrans %}Your Virtual Machine <strong>{{virtual_machine.name}}asdas</strong> is successfully terminated!{% endblocktrans %}</h4>
+					<h4 class="modal-title" id="ModalLabel">{% blocktrans %}Your Virtual Machine <strong>{{virtual_machine.name}}</strong> is successfully terminated!{% endblocktrans %}</h4>
           <div class="modal-footer">
             <a href="{% url 'hosting:virtual_machines' %}"	class="btn btn-success btn-wide">{% trans "OK" %}</a>
           </div>

From 04126c69eeb2769d1cceaffa0b00b4bff181d8f8 Mon Sep 17 00:00:00 2001
From: Arvind Tiwari <tiwariav@gmail.com>
Date: Tue, 19 Sep 2017 14:34:53 +0530
Subject: [PATCH 33/82] vm name added

---
 hosting/templates/hosting/virtual_machine_detail.html | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/hosting/templates/hosting/virtual_machine_detail.html b/hosting/templates/hosting/virtual_machine_detail.html
index e91fd0eb..06d86032 100644
--- a/hosting/templates/hosting/virtual_machine_detail.html
+++ b/hosting/templates/hosting/virtual_machine_detail.html
@@ -124,7 +124,7 @@
 				</div>
         <div class="modal-body">
 					<div class="modal-icon"><i class="fa fa-check" aria-hidden="true"></i></div>
-					<h4 class="modal-title" id="ModalLabel">{% blocktrans %}Your Virtual Machine <strong>{{virtual_machine.name}}</strong> is successfully terminated!{% endblocktrans %}</h4>
+					<h4 class="modal-title" id="ModalLabel">{% blocktrans with machine_name=virtual_machine.name %}Your Virtual Machine <strong>{{machine_name}}</strong> is successfully terminated!{% endblocktrans %}</h4>
           <div class="modal-footer">
             <a href="{% url 'hosting:virtual_machines' %}"	class="btn btn-success btn-wide">{% trans "OK" %}</a>
           </div>

From 98f094e5b850daa09b8575670eee6ce3cfd6812b Mon Sep 17 00:00:00 2001
From: Arvind Tiwari <tiwariav@gmail.com>
Date: Tue, 19 Sep 2017 15:03:06 +0530
Subject: [PATCH 34/82] initial changes

---
 hosting/static/hosting/css/order.css          |   2 +-
 hosting/static/hosting/img/icon-pdf.svg       |  18 ++
 hosting/static/hosting/img/icon-print.svg     |  17 ++
 .../hosting/includes/_navbar_user.html        |   6 +-
 hosting/templates/hosting/order_detail.html   | 287 +++++++++---------
 hosting/urls.py                               |   3 +-
 6 files changed, 180 insertions(+), 153 deletions(-)
 create mode 100644 hosting/static/hosting/img/icon-pdf.svg
 create mode 100644 hosting/static/hosting/img/icon-print.svg

diff --git a/hosting/static/hosting/css/order.css b/hosting/static/hosting/css/order.css
index e8bc0328..f2f7993b 100644
--- a/hosting/static/hosting/css/order.css
+++ b/hosting/static/hosting/css/order.css
@@ -1,4 +1,4 @@
-.order-detail-container {padding-top: 70px; padding-bottom: 70px; margin-bottom: 70px;}
+.order-detail-container {padding-top: 70px;padding-bottom: 70px;/* margin-bottom: 70px; */max-width: 720px;margin: 0 auto;}
 
 .order-detail-container .invoice-title h2, .invoice-title h3 {
     display: inline-block;
diff --git a/hosting/static/hosting/img/icon-pdf.svg b/hosting/static/hosting/img/icon-pdf.svg
new file mode 100644
index 00000000..20fc9c48
--- /dev/null
+++ b/hosting/static/hosting/img/icon-pdf.svg
@@ -0,0 +1,18 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<svg width="492px" height="649px" viewBox="0 0 492 649" version="1.1" xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink">
+    <!-- Generator: Sketch 46.2 (44496) - http://www.bohemiancoding.com/sketch -->
+    <title>icon-pdf</title>
+    <desc>Created with Sketch.</desc>
+    <defs></defs>
+    <g id="Page-1" stroke="none" stroke-width="1" fill="none" fill-rule="evenodd">
+        <g id="icon-pdf" fill-rule="nonzero" fill="#000000">
+            <g id="Group" transform="translate(93.000000, 269.000000)">
+                <path d="M98,47.8 C98,54.8 97,61.7 95.1,66.6 C93.1,72.5 90.1,76.5 86.2,80.5 C82.2,84.5 76.3,87.4 70.4,89.4 C64.5,91.4 55.6,92.3 46.6,92.3 L34.7,92.3 L34.7,134 L0,134 L0,0.3 L45.5,0.3 C54.4,0.3 62.4,1.3 69.3,3.2 C76.2,5.2 81.2,8.2 85.1,12.1 C89.1,16.1 92.1,21 94,27 C96.9,32 98,38.9 98,47.8 Z M61.3,46.8 C61.3,42.8 61.3,39.9 60.3,37.9 C60.3,35.9 59.3,33.9 57.4,32 C56.4,31 54.5,30 52.4,29.1 C50.4,29.1 47.4,28.1 44.5,28.1 L34.6,28.1 L34.6,63.7 L45.5,63.7 C48.4,63.7 50.4,63.7 52.5,62.7 C54.5,61.7 56.5,61.7 57.5,59.8 C58.5,57.8 59.5,56.9 60.4,54.8 C61.3,53.8 61.3,50.8 61.3,46.8 Z" id="Shape"></path>
+                <path d="M214.8,66.6 C214.8,78.5 213.8,89.3 210.8,97.3 C208.8,106.2 204.9,113.1 199.9,118.1 C195,123.1 189,127 182.1,130 C175.2,132 167.3,134 157.3,134 L108.8,134 L108.8,0.3 L156.3,0.3 C166.2,0.3 175.1,1.3 182,4.3 C188.9,7.2 194.9,10.2 199.8,16.2 C204.8,21.2 207.7,28.1 209.7,37 C213.8,44.8 214.8,54.7 214.8,66.6 Z M178.1,65.6 C178.1,58.7 178.1,52.7 177.1,47.8 C176.1,42.8 175.1,39.9 174.2,36.9 C172.2,34 170.2,32.9 168.3,31.9 C165.4,30.9 162.4,30.9 158.4,30.9 L145.6,30.9 L145.6,103.2 L158.4,103.2 C162.4,103.2 165.4,103.2 168.3,102.2 C171.2,101.2 173.3,99.3 174.2,97.2 C176.2,94.3 177.1,91.3 178.2,86.3 C178.1,80.5 178.1,74.5 178.1,65.6 Z" id="Shape"></path>
+                <polygon id="Shape" points="264.3 32 264.3 55.8 304.9 55.8 304.9 85.5 264.3 85.5 264.3 135 229.7 135 229.7 0.3 312.9 0.3 313.9 31 264.4 31 264.4 32"></polygon>
+            </g>
+            <path d="M491.3,649 L0.7,649 L0.7,0 L346.1,0 L491.3,145.2 L491.3,649 L491.3,649 Z M44.7,605 L448.4,605 L448.4,162.8 L327.4,42.9 L44.7,42.9 L44.7,605 Z" id="Shape"></path>
+            <polygon id="Shape" points="469.3 176 315.3 176 315.3 20.9 359.3 20.9 359.3 132 469.3 132"></polygon>
+        </g>
+    </g>
+</svg>
\ No newline at end of file
diff --git a/hosting/static/hosting/img/icon-print.svg b/hosting/static/hosting/img/icon-print.svg
new file mode 100644
index 00000000..e440f326
--- /dev/null
+++ b/hosting/static/hosting/img/icon-print.svg
@@ -0,0 +1,17 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<svg width="612px" height="612px" viewBox="0 0 612 612" version="1.1" xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink">
+    <!-- Generator: Sketch 46.2 (44496) - http://www.bohemiancoding.com/sketch -->
+    <title>54471</title>
+    <desc>Created with Sketch.</desc>
+    <defs></defs>
+    <g id="Page-1" stroke="none" stroke-width="1" fill="none" fill-rule="evenodd">
+        <g id="54471" fill-rule="nonzero" fill="#000000">
+            <path d="M0,225.633 L0,386.367 C0,417.272 30.6,417.272 30.6,417.272 L83.454,417.272 L83.454,389.454 L27.818,389.454 L27.818,222.545 L584.181,222.545 L584.181,389.454 L528.545,389.454 L528.545,417.272 L581.4,417.272 C581.4,417.272 612,417.272 612,386.367 L612,225.633 C612,225.633 612,194.727 581.4,194.727 L30.6,194.727 C0,194.728 0,225.633 0,225.633 Z" id="Shape"></path>
+            <polygon id="Shape" points="500.728 166.909 500.728 0 111.273 0 111.273 166.909 139.091 166.909 139.091 27.818 472.909 27.818 472.909 166.909"></polygon>
+            <path d="M528.546,292.091 C528.546,278.182 514.358,278.182 514.358,278.182 L97.642,278.182 C97.642,278.182 83.455,278.182 83.455,292.091 C83.455,306 97.642,306 97.642,306 L514.359,306 C514.358,306 528.546,306 528.546,292.091 Z" id="Shape"></path>
+            <rect id="Rectangle-path" x="166.909" y="500.728" width="278.182" height="27.818"></rect>
+            <path d="M500.728,612 L500.728,389.454 L111.273,389.454 L111.273,612 L500.728,612 Z M139.091,417.272 L472.909,417.272 L472.909,584.181 L139.091,584.181 L139.091,417.272 Z" id="Shape"></path>
+            <rect id="Rectangle-path" x="166.909" y="445.091" width="278.182" height="27.818"></rect>
+        </g>
+    </g>
+</svg>
\ No newline at end of file
diff --git a/hosting/templates/hosting/includes/_navbar_user.html b/hosting/templates/hosting/includes/_navbar_user.html
index d06477ca..126dd1e6 100644
--- a/hosting/templates/hosting/includes/_navbar_user.html
+++ b/hosting/templates/hosting/includes/_navbar_user.html
@@ -37,11 +37,7 @@
                 </li>
                 <li>
                     {% get_current_language as LANGUAGE_CODE %}
-                    {% if LANGUAGE_CODE == 'en-us'%}
-                        <a href="{% change_lang 'de' %}"><i class="fa fa-fw fa-globe" aria-hidden="true"></i>&nbsp;&nbsp;Deutsch</a>
-                    {% else %}
-                        <a href="{% change_lang 'en-us' %}"><i class="fa fa-fw fa-globe" aria-hidden="true"></i>&nbsp;&nbsp;English</a>
-                    {% endif %}
+
                 </li>
             </ul>
         </div>
diff --git a/hosting/templates/hosting/order_detail.html b/hosting/templates/hosting/order_detail.html
index 39c59808..f07aa998 100644
--- a/hosting/templates/hosting/order_detail.html
+++ b/hosting/templates/hosting/order_detail.html
@@ -7,168 +7,163 @@
 
 <div class="order-detail-container">
     {% if messages %}
-    <div class="row">
-        <div class="col-xs-12 col-md-8 col-md-offset-2">
-            <br/>
-            <div class="alert alert-warning">
-                {% for message in messages %}
-                <span>{{ message }}</span>
-                {% endfor %}
-            </div>
+        <div class="alert alert-warning">
+            {% for message in messages %}
+            <span>{{ message }}</span>
+            {% endfor %}
         </div>
-    </div>
     {% endif %}
     {% if not error %}
-    <div class="row">
-        <div class="col-xs-12 col-md-8 col-md-offset-2">
-            <div class="invoice-title">
-                <h2>{{page_header_text}}</h2>
-                <h3 class="pull-right">
-                    {% if order %}
-                    {% trans "Order #"%} {{order.id}}
-                    {% endif %}
-                </h3>
-            </div>
-            <hr>
-            <div class="row">
-                <div class="col-xs-12 col-md-6 pull-right order-confirm-date">
-                    <address>
-                        <strong>{% trans "Date"%}:</strong><br>
-                        <span id="order-created_at">
-                                {% if order %}
-                                    {{order.created_at|date:'Y-m-d H:i'}}
-                                {% else %}
-                                    {% now "Y-m-d H:i" %}
-                                {% endif %}
-                            </span><br><br>
+        <div class="row">
+            <div class="col-xs-12 col-md-8 col-md-offset-2">
+                <div class="invoice-title">
+                    <h2>{{page_header_text}}</h2>
+                    <h3 class="pull-right">
                         {% if order %}
-                        <strong>{% trans "Status:"%}</strong><br>
-                        {% if order.status == 'Approved' %}
-                        <strong class="text-success">
-                            {% trans "Approved" %}
-                        </strong>
-                        {% else %}
-                        <strong class="text-danger">
-                            {% trans "Declined" %}
-                        </strong>
+                            {% trans "Order #"%} {{order.id}}
                         {% endif %}
-                        <br><br>
-                        {% endif %}
-                    </address>
+                    </h3>
+                </div>
+                <hr>
+                <div class="row">
+                    <div class="col-xs-12 col-md-6 pull-right order-confirm-date">
+                        <address>
+                            <strong>{% trans "Date"%}:</strong><br>
+                            <span id="order-created_at">
+                                    {% if order %}
+                                        {{order.created_at|date:'Y-m-d H:i'}}
+                                    {% else %}
+                                        {% now "Y-m-d H:i" %}
+                                    {% endif %}
+                                </span><br><br>
+                            {% if order %}
+                            <strong>{% trans "Status:"%}</strong><br>
+                            {% if order.status == 'Approved' %}
+                            <strong class="text-success">
+                                {% trans "Approved" %}
+                            </strong>
+                            {% else %}
+                            <strong class="text-danger">
+                                {% trans "Declined" %}
+                            </strong>
+                            {% endif %}
+                            <br><br>
+                            {% endif %}
+                        </address>
+
+                    </div>
+                    <div class="col-xs-12 col-md-6">
+                        <address>
+                            <h3><b>{% trans "Billed To:"%}</b></h3>
+                            {% if order %}
+                                {{user.name}}<br>
+                                {{order.billing_address.street_address}},{{order.billing_address.postal_code}}<br>
+                                {{order.billing_address.city}},
+                                {{order.billing_address.country}}.
+                            {% else %}
+                                {% with request.session.billing_address_data as billing_address %}
+                                {{billing_address.cardholder_name}}<br>
+                                {{billing_address.street_address}},
+                                {{billing_address.postal_code}}<br>
+                                {{billing_address.city}},
+                                {{billing_address.country}}.
+                                {% endwith %}
+                            {% endif %}
+                        </address>
+                    </div>
 
                 </div>
-                <div class="col-xs-12 col-md-6">
-                    <address>
-                        <h3><b>{% trans "Billed To:"%}</b></h3>
-                        {% if order %}
-                        {{user.name}}<br>
-                        {{order.billing_address.street_address}},{{order.billing_address.postal_code}}<br>
-                        {{order.billing_address.city}},
-                        {{order.billing_address.country}}.
-                        {% else %}
-                        {% with request.session.billing_address_data as billing_address %}
-                        {{billing_address|get_value_from_dict:'cardholder_name'}}<br>
-                        {{billing_address|get_value_from_dict:'street_address'}},
-                        {{billing_address|get_value_from_dict:'postal_code'}}<br>
-                        {{billing_address|get_value_from_dict:'city'}},
-                        {{billing_address|get_value_from_dict:'country'}}.
-                        {% endwith %}
-                        {% endif %}
-                    </address>
-                </div>
-
-            </div>
-            <div class="row">
-                <div class="col-xs-6">
-                    <address>
-                        <strong>{% trans "Payment Method:"%}</strong><br>
-                        {% if order %}
-                        {{order.cc_brand}} {% trans "ending in" %} ****
-                        {{order.last4}}<br>
-                        {{user.email}}
-                        {% else %}
-                        {{cc_brand}} {% trans "ending in" %} ****
-                        {{cc_last4}}<br>
-                        {{request.session.user.email}}
-                        {% endif %}
-                    </address>
+                <div class="row">
+                    <div class="col-xs-6">
+                        <address>
+                            <strong>{% trans "Payment Method:"%}</strong><br>
+                            {% if order %}
+                            {{order.cc_brand}} {% trans "ending in" %} ****
+                            {{order.last4}}<br>
+                            {{user.email}}
+                            {% else %}
+                            {{cc_brand}} {% trans "ending in" %} ****
+                            {{cc_last4}}<br>
+                            {{request.session.user.email}}
+                            {% endif %}
+                        </address>
+                    </div>
                 </div>
             </div>
         </div>
-    </div>
 
-    <div class="row">
-        <div class="col-md-8 col-md-offset-2">
-            <h3><b>{% trans "Order summary"%}</b></h3>
-            <hr>
-            <div class="content">
-                {% if request.session.specs %}
-                {% with request.session.specs as vm %}
-                <p><b>{% trans "Cores"%}</b>
-                    <span class="pull-right">{{vm.cpu}}</span>
-                </p>
+        <div class="row">
+            <div class="col-md-8 col-md-offset-2">
+                <h3><b>{% trans "Order summary"%}</b></h3>
                 <hr>
-                <p><b>{% trans "Memory"%}</b>
-                    <span class="pull-right">{{vm.memory}} GB</span>
-                </p>
-                <hr>
-                <p><b>{% trans "Disk space"%}</b>
-                    <span class="pull-right">{{vm.disk_size}} GB</span>
-                </p>
-                <hr>
-                <p><b>{% trans "Configuration"%}</b>
-                    <span class="pull-right">{{request.session.template.name}}</span>
-                </p>
-                <hr>
-                <h4>{% trans "Total"%}
-                    <p class="pull-right">
-                        <b>{{vm.price}} CHF</b>
-                        <span class="dcl-price-month"> /{% trans "Month" %}
-                                </span>
+                <div class="content">
+                    {% if request.session.specs %}
+                    {% with request.session.specs as vm %}
+                    <p><b>{% trans "Cores"%}</b>
+                        <span class="pull-right">{{vm.cpu}}</span>
                     </p>
-                </h4>
-                {% endwith %}
-                {% else %}
-                <p><b>{% trans "Cores"%}</b>
-                    <span class="pull-right">{{vm.cores}}</span>
-                </p>
-                <hr>
-                <p><b>{% trans "Memory"%}</b>
-                    <span class="pull-right">{{vm.memory}} GB</span>
-                </p>
-                <hr>
-                <p><b>{% trans "Disk space"%}</b>
-                    <span class="pull-right">{{vm.disk_size}} GB</span>
-                </p>
-                <hr>
-                <h4>{% trans "Total"%}<p class="pull-right"><b>{{vm.price}}
-                    CHF</b><span
-                        class="dcl-price-month"> /{% trans "Month" %}</span>
-                </p></h4>
+                    <hr>
+                    <p><b>{% trans "Memory"%}</b>
+                        <span class="pull-right">{{vm.memory}} GB</span>
+                    </p>
+                    <hr>
+                    <p><b>{% trans "Disk space"%}</b>
+                        <span class="pull-right">{{vm.disk_size}} GB</span>
+                    </p>
+                    <hr>
+                    <p><b>{% trans "Configuration"%}</b>
+                        <span class="pull-right">{{request.session.template.name}}</span>
+                    </p>
+                    <hr>
+                    <h4>{% trans "Total"%}
+                        <p class="pull-right">
+                            <b>{{vm.price}} CHF</b>
+                            <span class="dcl-price-month"> /{% trans "Month" %}
+                                    </span>
+                        </p>
+                    </h4>
+                    {% endwith %}
+                    {% else %}
+                    <p><b>{% trans "Cores"%}</b>
+                        <span class="pull-right">{{vm.cores}}</span>
+                    </p>
+                    <hr>
+                    <p><b>{% trans "Memory"%}</b>
+                        <span class="pull-right">{{vm.memory}} GB</span>
+                    </p>
+                    <hr>
+                    <p><b>{% trans "Disk space"%}</b>
+                        <span class="pull-right">{{vm.disk_size}} GB</span>
+                    </p>
+                    <hr>
+                    <h4>{% trans "Total"%}<p class="pull-right"><b>{{vm.price}}
+                        CHF</b><span
+                            class="dcl-price-month"> /{% trans "Month" %}</span>
+                    </p></h4>
+                    {% endif %}
+                </div>
+                <br/>
+                {% if not order %}
+                <form method="post" id="virtual_machine_create_form">
+                    {% csrf_token %}
+                    <div class="row">
+                        <div class="col-sm-8">
+                            <p class="dcl-place-order-text">{% blocktrans with vm_price=request.session.specs.price %}By clicking "Place order" this plan will charge your credit card account with the fee of {{ vm_price }}CHF/month{% endblocktrans %}.</p>
+                        </div>
+                        <div class="col-sm-4 content">
+                            <button class="btn btn-info pull-right"
+                                    id="btn-create-vm"
+                                    data-href="{% url 'hosting:order-confirmation' %}"
+                                    data-toggle="modal"
+                                    data-target="#createvm-modal">
+                                {% trans "Place order"%}
+                            </button>
+                        </div>
+                    </div>
+                </form>
                 {% endif %}
             </div>
-            <br/>
-            {% if not order %}
-            <form method="post" id="virtual_machine_create_form">
-                {% csrf_token %}
-                <div class="row">
-                    <div class="col-sm-8">
-                        <p class="dcl-place-order-text">{% blocktrans with vm_price=request.session.specs.price %}By clicking "Place order" this plan will charge your credit card account with the fee of {{ vm_price }}CHF/month{% endblocktrans %}.</p>
-                    </div>
-                    <div class="col-sm-4 content">
-                        <button class="btn btn-info pull-right"
-                                id="btn-create-vm"
-                                data-href="{% url 'hosting:order-confirmation' %}"
-                                data-toggle="modal"
-                                data-target="#createvm-modal">
-                            {% trans "Place order"%}
-                        </button>
-                    </div>
-                </div>
-            </form>
-            {% endif %}
         </div>
-    </div>
     {% endif %}
 </div>
 <!-- Create VM Modal -->
diff --git a/hosting/urls.py b/hosting/urls.py
index 2868c717..bc14c3a6 100644
--- a/hosting/urls.py
+++ b/hosting/urls.py
@@ -9,9 +9,10 @@ from .views import (
     HostingPricingView, CreateVirtualMachinesView, HostingBillListView,
     HostingBillDetailView, SSHKeyDeleteView, SSHKeyCreateView, SSHKeyListView,
     SSHKeyChoiceView, DashboardView, SettingsView)
-
+from django.views.generic import TemplateView
 
 urlpatterns = [
+    url(r'test/?$', TemplateView.as_view(template_name='hosting/order_detail.html')),
     url(r'index/?$', IndexView.as_view(), name='index'),
     url(r'django/?$', DjangoHostingView.as_view(), name='djangohosting'),
     url(r'dashboard/?$', DashboardView.as_view(), name='dashboard'),

From 37017dd31ad0adafda7a59106c3789f15c192ce3 Mon Sep 17 00:00:00 2001
From: Arvind Tiwari <tiwariav@gmail.com>
Date: Wed, 20 Sep 2017 23:06:51 +0530
Subject: [PATCH 35/82] minor mods

---
 hosting/static/hosting/css/order.css        |   7 +-
 hosting/templates/hosting/order_detail.html | 290 ++++++++++----------
 2 files changed, 148 insertions(+), 149 deletions(-)

diff --git a/hosting/static/hosting/css/order.css b/hosting/static/hosting/css/order.css
index f2f7993b..bdd124c9 100644
--- a/hosting/static/hosting/css/order.css
+++ b/hosting/static/hosting/css/order.css
@@ -1,4 +1,9 @@
-.order-detail-container {padding-top: 70px;padding-bottom: 70px;/* margin-bottom: 70px; */max-width: 720px;margin: 0 auto;}
+.order-detail-container {
+    max-width: 600px;
+    margin: 100px auto;
+    border: 1px solid #ccc;
+    padding: 30px;
+}
 
 .order-detail-container .invoice-title h2, .invoice-title h3 {
     display: inline-block;
diff --git a/hosting/templates/hosting/order_detail.html b/hosting/templates/hosting/order_detail.html
index f07aa998..3d1ffd35 100644
--- a/hosting/templates/hosting/order_detail.html
+++ b/hosting/templates/hosting/order_detail.html
@@ -9,161 +9,155 @@
     {% if messages %}
         <div class="alert alert-warning">
             {% for message in messages %}
-            <span>{{ message }}</span>
+                <span>{{ message }}</span>
             {% endfor %}
         </div>
     {% endif %}
     {% if not error %}
-        <div class="row">
-            <div class="col-xs-12 col-md-8 col-md-offset-2">
-                <div class="invoice-title">
-                    <h2>{{page_header_text}}</h2>
-                    <h3 class="pull-right">
-                        {% if order %}
-                            {% trans "Order #"%} {{order.id}}
-                        {% endif %}
-                    </h3>
-                </div>
-                <hr>
-                <div class="row">
-                    <div class="col-xs-12 col-md-6 pull-right order-confirm-date">
-                        <address>
-                            <strong>{% trans "Date"%}:</strong><br>
-                            <span id="order-created_at">
-                                    {% if order %}
-                                        {{order.created_at|date:'Y-m-d H:i'}}
-                                    {% else %}
-                                        {% now "Y-m-d H:i" %}
-                                    {% endif %}
-                                </span><br><br>
-                            {% if order %}
-                            <strong>{% trans "Status:"%}</strong><br>
-                            {% if order.status == 'Approved' %}
-                            <strong class="text-success">
-                                {% trans "Approved" %}
-                            </strong>
-                            {% else %}
-                            <strong class="text-danger">
-                                {% trans "Declined" %}
-                            </strong>
-                            {% endif %}
-                            <br><br>
-                            {% endif %}
-                        </address>
-
-                    </div>
-                    <div class="col-xs-12 col-md-6">
-                        <address>
-                            <h3><b>{% trans "Billed To:"%}</b></h3>
-                            {% if order %}
-                                {{user.name}}<br>
-                                {{order.billing_address.street_address}},{{order.billing_address.postal_code}}<br>
-                                {{order.billing_address.city}},
-                                {{order.billing_address.country}}.
-                            {% else %}
-                                {% with request.session.billing_address_data as billing_address %}
-                                {{billing_address.cardholder_name}}<br>
-                                {{billing_address.street_address}},
-                                {{billing_address.postal_code}}<br>
-                                {{billing_address.city}},
-                                {{billing_address.country}}.
-                                {% endwith %}
-                            {% endif %}
-                        </address>
-                    </div>
-
-                </div>
-                <div class="row">
-                    <div class="col-xs-6">
-                        <address>
-                            <strong>{% trans "Payment Method:"%}</strong><br>
-                            {% if order %}
-                            {{order.cc_brand}} {% trans "ending in" %} ****
-                            {{order.last4}}<br>
-                            {{user.email}}
-                            {% else %}
-                            {{cc_brand}} {% trans "ending in" %} ****
-                            {{cc_last4}}<br>
-                            {{request.session.user.email}}
-                            {% endif %}
-                        </address>
-                    </div>
-                </div>
-            </div>
-        </div>
-
-        <div class="row">
-            <div class="col-md-8 col-md-offset-2">
-                <h3><b>{% trans "Order summary"%}</b></h3>
-                <hr>
-                <div class="content">
-                    {% if request.session.specs %}
-                    {% with request.session.specs as vm %}
-                    <p><b>{% trans "Cores"%}</b>
-                        <span class="pull-right">{{vm.cpu}}</span>
-                    </p>
-                    <hr>
-                    <p><b>{% trans "Memory"%}</b>
-                        <span class="pull-right">{{vm.memory}} GB</span>
-                    </p>
-                    <hr>
-                    <p><b>{% trans "Disk space"%}</b>
-                        <span class="pull-right">{{vm.disk_size}} GB</span>
-                    </p>
-                    <hr>
-                    <p><b>{% trans "Configuration"%}</b>
-                        <span class="pull-right">{{request.session.template.name}}</span>
-                    </p>
-                    <hr>
-                    <h4>{% trans "Total"%}
-                        <p class="pull-right">
-                            <b>{{vm.price}} CHF</b>
-                            <span class="dcl-price-month"> /{% trans "Month" %}
-                                    </span>
-                        </p>
-                    </h4>
-                    {% endwith %}
-                    {% else %}
-                    <p><b>{% trans "Cores"%}</b>
-                        <span class="pull-right">{{vm.cores}}</span>
-                    </p>
-                    <hr>
-                    <p><b>{% trans "Memory"%}</b>
-                        <span class="pull-right">{{vm.memory}} GB</span>
-                    </p>
-                    <hr>
-                    <p><b>{% trans "Disk space"%}</b>
-                        <span class="pull-right">{{vm.disk_size}} GB</span>
-                    </p>
-                    <hr>
-                    <h4>{% trans "Total"%}<p class="pull-right"><b>{{vm.price}}
-                        CHF</b><span
-                            class="dcl-price-month"> /{% trans "Month" %}</span>
-                    </p></h4>
-                    {% endif %}
-                </div>
-                <br/>
-                {% if not order %}
-                <form method="post" id="virtual_machine_create_form">
-                    {% csrf_token %}
-                    <div class="row">
-                        <div class="col-sm-8">
-                            <p class="dcl-place-order-text">{% blocktrans with vm_price=request.session.specs.price %}By clicking "Place order" this plan will charge your credit card account with the fee of {{ vm_price }}CHF/month{% endblocktrans %}.</p>
-                        </div>
-                        <div class="col-sm-4 content">
-                            <button class="btn btn-info pull-right"
-                                    id="btn-create-vm"
-                                    data-href="{% url 'hosting:order-confirmation' %}"
-                                    data-toggle="modal"
-                                    data-target="#createvm-modal">
-                                {% trans "Place order"%}
-                            </button>
-                        </div>
-                    </div>
-                </form>
+        <h1 class="dashboard-title-thin">
+            {% blocktrans %}{{page_header_text|default:'Invoice'}}{% endblocktrans %}
+        </h1>
+        <div class="invoice-title">
+            <h3 class="pull-right">
+                {% if order %}
+                    {% trans "Order #"%} {{order.id}}
                 {% endif %}
+            </h3>
+        </div>
+        <hr>
+        <div class="row">
+            <div class="col-xs-12 col-md-6 pull-right order-confirm-date">
+                <address>
+                    <strong>{% trans "Date"%}:</strong><br>
+                    <span id="order-created_at">
+                            {% if order %}
+                                {{order.created_at|date:'Y-m-d H:i'}}
+                            {% else %}
+                                {% now "Y-m-d H:i" %}
+                            {% endif %}
+                        </span><br><br>
+                    {% if order %}
+                    <strong>{% trans "Status:"%}</strong><br>
+                    {% if order.status == 'Approved' %}
+                    <strong class="text-success">
+                        {% trans "Approved" %}
+                    </strong>
+                    {% else %}
+                    <strong class="text-danger">
+                        {% trans "Declined" %}
+                    </strong>
+                    {% endif %}
+                    <br><br>
+                    {% endif %}
+                </address>
+
+            </div>
+            <div class="col-xs-12 col-md-6">
+                <address>
+                    <h3><b>{% trans "Billed To:"%}</b></h3>
+                    {% if order %}
+                        {{user.name}}<br>
+                        {{order.billing_address.street_address}},{{order.billing_address.postal_code}}<br>
+                        {{order.billing_address.city}},
+                        {{order.billing_address.country}}.
+                    {% else %}
+                        {% with request.session.billing_address_data as billing_address %}
+                        {{billing_address.cardholder_name}}<br>
+                        {{billing_address.street_address}},
+                        {{billing_address.postal_code}}<br>
+                        {{billing_address.city}},
+                        {{billing_address.country}}.
+                        {% endwith %}
+                    {% endif %}
+                </address>
+            </div>
+
+        </div>
+        <div class="row">
+            <div class="col-xs-6">
+                <address>
+                    <strong>{% trans "Payment Method:"%}</strong><br>
+                    {% if order %}
+                    {{order.cc_brand}} {% trans "ending in" %} ****
+                    {{order.last4}}<br>
+                    {{user.email}}
+                    {% else %}
+                    {{cc_brand}} {% trans "ending in" %} ****
+                    {{cc_last4}}<br>
+                    {{request.session.user.email}}
+                    {% endif %}
+                </address>
             </div>
         </div>
+
+        <h3><b>{% trans "Order summary"%}</b></h3>
+        <hr>
+        <div class="content">
+            {% if request.session.specs %}
+            {% with request.session.specs as vm %}
+            <p><b>{% trans "Cores"%}</b>
+                <span class="pull-right">{{vm.cpu}}</span>
+            </p>
+            <hr>
+            <p><b>{% trans "Memory"%}</b>
+                <span class="pull-right">{{vm.memory}} GB</span>
+            </p>
+            <hr>
+            <p><b>{% trans "Disk space"%}</b>
+                <span class="pull-right">{{vm.disk_size}} GB</span>
+            </p>
+            <hr>
+            <p><b>{% trans "Configuration"%}</b>
+                <span class="pull-right">{{request.session.template.name}}</span>
+            </p>
+            <hr>
+            <h4>{% trans "Total"%}
+                <p class="pull-right">
+                    <b>{{vm.price}} CHF</b>
+                    <span class="dcl-price-month"> /{% trans "Month" %}
+                            </span>
+                </p>
+            </h4>
+            {% endwith %}
+            {% else %}
+            <p><b>{% trans "Cores"%}</b>
+                <span class="pull-right">{{vm.cores}}</span>
+            </p>
+            <hr>
+            <p><b>{% trans "Memory"%}</b>
+                <span class="pull-right">{{vm.memory}} GB</span>
+            </p>
+            <hr>
+            <p><b>{% trans "Disk space"%}</b>
+                <span class="pull-right">{{vm.disk_size}} GB</span>
+            </p>
+            <hr>
+            <h4>{% trans "Total"%}<p class="pull-right"><b>{{vm.price}}
+                CHF</b><span
+                    class="dcl-price-month"> /{% trans "Month" %}</span>
+            </p></h4>
+            {% endif %}
+        </div>
+        <br/>
+        {% if not order %}
+            <form method="post" id="virtual_machine_create_form">
+                {% csrf_token %}
+                <div class="row">
+                    <div class="col-sm-8">
+                        <p class="dcl-place-order-text">{% blocktrans with vm_price=request.session.specs.price %}By clicking "Place order" this plan will charge your credit card account with the fee of {{ vm_price }}CHF/month{% endblocktrans %}.</p>
+                    </div>
+                    <div class="col-sm-4 content">
+                        <button class="btn btn-info pull-right"
+                                id="btn-create-vm"
+                                data-href="{% url 'hosting:order-confirmation' %}"
+                                data-toggle="modal"
+                                data-target="#createvm-modal">
+                            {% trans "Place order"%}
+                        </button>
+                    </div>
+                </div>
+            </form>
+        {% endif %}
     {% endif %}
 </div>
 <!-- Create VM Modal -->

From ec354332f8b0159e62e6925a04e5d9bc700c66a8 Mon Sep 17 00:00:00 2001
From: Arvind Tiwari <tiwariav@gmail.com>
Date: Wed, 20 Sep 2017 23:28:36 +0530
Subject: [PATCH 36/82] translation fix

---
 hosting/locale/de/LC_MESSAGES/django.po | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/hosting/locale/de/LC_MESSAGES/django.po b/hosting/locale/de/LC_MESSAGES/django.po
index 006e8b20..b0cc0bf6 100644
--- a/hosting/locale/de/LC_MESSAGES/django.po
+++ b/hosting/locale/de/LC_MESSAGES/django.po
@@ -292,7 +292,7 @@ msgid "Toggle navigation"
 msgstr "Umschalten"
 
 msgid "Dashboard"
-msgstr "Mein Dashboard"
+msgstr "Dashboard"
 
 msgid "Logout"
 msgstr "Abmelden"

From 98eb2f85d8913d36733467eedea0f1dce9ed50df Mon Sep 17 00:00:00 2001
From: Arvind Tiwari <tiwariav@gmail.com>
Date: Thu, 21 Sep 2017 01:19:38 +0530
Subject: [PATCH 37/82] printing pdf

---
 hosting/static/hosting/css/order.css        |  16 +
 hosting/static/hosting/js/html2pdf.js       | 387 ++++++++++++++++++++
 hosting/templates/hosting/order_detail.html |  27 +-
 3 files changed, 421 insertions(+), 9 deletions(-)
 create mode 100644 hosting/static/hosting/js/html2pdf.js

diff --git a/hosting/static/hosting/css/order.css b/hosting/static/hosting/css/order.css
index bdd124c9..3e916cdd 100644
--- a/hosting/static/hosting/css/order.css
+++ b/hosting/static/hosting/css/order.css
@@ -20,3 +20,19 @@
 .order-detail-container .table > tbody > tr > .thick-line {
     border-top: 2px solid;
 }
+
+.order-detail-container .dashboard-title-thin {
+    margin-top: 0;
+}
+
+.order-detail-container .dashboard-title-thin .un-icon {
+    margin-top: -6px;
+}
+
+.order-detail-container .dashboard-title-thin .svg-img {
+    height: 20px;
+    margin-right: 5px;
+    margin-top: -2px;
+    width: 20px;
+    margin-top: -6px;
+}
\ No newline at end of file
diff --git a/hosting/static/hosting/js/html2pdf.js b/hosting/static/hosting/js/html2pdf.js
new file mode 100644
index 00000000..45ae5b0c
--- /dev/null
+++ b/hosting/static/hosting/js/html2pdf.js
@@ -0,0 +1,387 @@
+/**
+ * @license
+ *
+ * MIT License
+ *
+ * Copyright (c) 2017 Erik Koopmans
+ *
+ * Permission is hereby granted, free of charge, to any person obtaining a copy
+ * of this software and associated documentation files (the "Software"), to deal
+ * in the Software without restriction, including without limitation the rights
+ * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+ * copies of the Software, and to permit persons to whom the Software is
+ * furnished to do so, subject to the following conditions:
+ *
+ * The above copyright notice and this permission notice shall be included in all
+ * copies or substantial portions of the Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+ * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+ * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
+ * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
+ * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
+ * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
+ * SOFTWARE.
+ */
+
+/**
+ * Generate a PDF from an HTML element or string using html2canvas and jsPDF.
+ *
+ * @param {Element|string} source The source element or HTML string.
+ * @param {Object=} opt An object of optional settings: 'margin', 'filename',
+ *    'image' ('type' and 'quality'), and 'html2canvas' / 'jspdf', which are
+ *    sent as settings to their corresponding functions.
+ */
+var html2pdf = (function(html2canvas, jsPDF) {
+
+  /* ---------- MAIN FUNCTION ---------- */
+
+  var html2pdf = function(source, opt) {
+    // Handle input.
+    opt = objType(opt) === 'object' ? opt : {};
+    var source = html2pdf.parseInput(source, opt);
+
+    // Determine the PDF page size.
+    var pageSize = jsPDF.getPageSize(opt.jsPDF);
+    pageSize.inner = {
+      width:  pageSize.width - opt.margin[1] - opt.margin[3],
+      height: pageSize.height - opt.margin[0] - opt.margin[2]
+    };
+    pageSize.inner.ratio = pageSize.inner.height / pageSize.inner.width;
+
+    // Copy the source element into a PDF-styled container div.
+    var container = html2pdf.makeContainer(source, pageSize);
+    var overlay = container.parentElement;
+
+    // Get the locations of all hyperlinks.
+    if (opt.enableLinks) {
+      // Find all anchor tags and get the container's bounds for reference.
+      opt.links = [];
+      var links = container.querySelectorAll('a');
+      var containerRect = unitConvert(container.getBoundingClientRect(), pageSize.k);
+
+      // Treat each client rect as a separate link (for text-wrapping).
+      Array.prototype.forEach.call(links, function(link) {
+        var clientRects = link.getClientRects();
+        for (var i=0; i<clientRects.length; i++) {
+          var clientRect = unitConvert(clientRects[i], pageSize.k);
+          clientRect.left -= containerRect.left;
+          clientRect.top -= containerRect.top;
+          opt.links.push({ el: link, clientRect: clientRect });
+        }
+      });
+    }
+
+    // Render the canvas and pass the result to makePDF.
+    var onRendered = opt.html2canvas.onrendered || function() {};
+    opt.html2canvas.onrendered = function(canvas) {
+      onRendered(canvas);
+      document.body.removeChild(overlay);
+      html2pdf.makePDF(canvas, pageSize, opt);
+    }
+    html2canvas(container, opt.html2canvas);
+  };
+
+  html2pdf.parseInput = function(source, opt) {
+    // Parse the opt object.
+    opt.jsPDF = opt.jsPDF || {};
+    opt.html2canvas = opt.html2canvas || {};
+    opt.filename = opt.filename && objType(opt.filename) === 'string' ? opt.filename : 'file.pdf';
+    opt.enableLinks = opt.hasOwnProperty('enableLinks') ? opt.enableLinks : true;
+    opt.image = opt.image || {};
+    opt.image.type = opt.image.type || 'jpeg';
+    opt.image.quality = opt.image.quality || 0.95;
+
+    // Parse the margin property of the opt object.
+    switch (objType(opt.margin)) {
+      case 'undefined':
+        opt.margin = 0;
+      case 'number':
+        opt.margin = [opt.margin, opt.margin, opt.margin, opt.margin];
+        break;
+      case 'array':
+        if (opt.margin.length === 2) {
+          opt.margin = [opt.margin[0], opt.margin[1], opt.margin[0], opt.margin[1]];
+        }
+        if (opt.margin.length === 4) {
+          break;
+        }
+      default:
+        throw 'Invalid margin array.';
+    }
+
+    // Parse the source element/string.
+    if (!source) {
+      throw 'Missing source element or string.';
+    } else if (objType(source) === 'string') {
+      source = createElement('div', { innerHTML: source });
+    } else if (objType(source) === 'element') {
+      source = cloneNode(source, opt.html2canvas.javascriptEnabled);
+    } else {
+      throw 'Invalid source - please specify an HTML Element or string.';
+    }
+
+    // Return the parsed input (opt is modified in-place, no need to return).
+    return source;
+  };
+
+  html2pdf.makeContainer = function(source, pageSize) {
+    // Define the CSS styles for the container and its overlay parent.
+    var overlayCSS = {
+      position: 'fixed', overflow: 'hidden', zIndex: 1000,
+      left: 0, right: 0, bottom: 0, top: 0,
+      backgroundColor: 'rgba(0,0,0,0.8)'
+    };
+    var containerCSS = {
+      position: 'absolute', width: pageSize.inner.width + pageSize.unit,
+      left: 0, right: 0, top: 0, height: 'auto', margin: 'auto',
+      backgroundColor: 'white'
+    };
+
+    // Set the overlay to hidden (could be changed in the future to provide a print preview).
+    overlayCSS.opacity = 0;
+
+    // Create and attach the elements.
+    var overlay = createElement('div',   { className: 'html2pdf__overlay', style: overlayCSS });
+    var container = createElement('div', { className: 'html2pdf__container', style: containerCSS });
+    container.appendChild(source);
+    overlay.appendChild(container);
+    document.body.appendChild(overlay);
+
+    // Enable page-breaks.
+    var pageBreaks = source.querySelectorAll('.html2pdf__page-break');
+    var pxPageHeight = pageSize.inner.height * pageSize.k / 72 * 96;
+    Array.prototype.forEach.call(pageBreaks, function(el) {
+      el.style.display = 'block';
+      var clientRect = el.getBoundingClientRect();
+      el.style.height = pxPageHeight - (clientRect.top % pxPageHeight) + 'px';
+    }, this);
+
+    // Return the container.
+    return container;
+  };
+
+  html2pdf.makePDF = function(canvas, pageSize, opt) {
+    // Calculate the number of pages.
+    var ctx = canvas.getContext('2d');
+    var pxFullHeight = canvas.height;
+    var pxPageHeight = Math.floor(canvas.width * pageSize.inner.ratio);
+    var nPages = Math.ceil(pxFullHeight / pxPageHeight);
+
+    // Create a one-page canvas to split up the full image.
+    var pageCanvas = document.createElement('canvas');
+    var pageCtx = pageCanvas.getContext('2d');
+    var pageHeight = pageSize.inner.height;
+    pageCanvas.width = canvas.width;
+    pageCanvas.height = pxPageHeight;
+
+    // Initialize the PDF.
+    var pdf = new jsPDF(opt.jsPDF);
+
+    for (var page=0; page<nPages; page++) {
+      // Trim the final page to reduce file size.
+      if (page === nPages-1) {
+        pageCanvas.height = pxFullHeight % pxPageHeight;
+        pageHeight = pageCanvas.height * pageSize.inner.width / pageCanvas.width;
+      }
+
+      // Display the page.
+      var w = pageCanvas.width;
+      var h = pageCanvas.height;
+      pageCtx.fillStyle = 'white';
+      pageCtx.fillRect(0, 0, w, h);
+      pageCtx.drawImage(canvas, 0, page*pxPageHeight, w, h, 0, 0, w, h);
+
+      // Add the page to the PDF.
+      if (page)  pdf.addPage();
+      var imgData = pageCanvas.toDataURL('image/' + opt.image.type, opt.image.quality);
+      pdf.addImage(imgData, opt.image.type, opt.margin[1], opt.margin[0],
+                   pageSize.inner.width, pageHeight);
+
+      // Add hyperlinks.
+      if (opt.enableLinks) {
+        var pageTop = page * pageSize.inner.height;
+        opt.links.forEach(function(link) {
+          if (link.clientRect.top > pageTop && link.clientRect.top < pageTop + pageSize.inner.height) {
+            var left = opt.margin[1] + link.clientRect.left;
+            var top = opt.margin[0] + link.clientRect.top - pageTop;
+            pdf.link(left, top, link.clientRect.width, link.clientRect.height, { url: link.el.href });
+          }
+        });
+      }
+    }
+
+    // Finish the PDF.
+    pdf.save( opt.filename );
+  }
+
+
+  /* ---------- UTILS ---------- */
+
+  // Determine the type of a variable/object.
+  var objType = function(obj) {
+    if (typeof obj === 'undefined')                             return 'undefined';
+    else if (typeof obj === 'string' || obj instanceof String)  return 'string';
+    else if (typeof obj === 'number' || obj instanceof Number)  return 'number';
+    else if (!!obj && obj.constructor === Array)                return 'array';
+    else if (obj && obj.nodeType === 1)                         return 'element';
+    else if (typeof obj === 'object')                           return 'object';
+    else                                                        return 'unknown';
+  };
+
+  // Create an HTML element with optional className, innerHTML, and style.
+  var createElement = function(tagName, opt) {
+    var el = document.createElement(tagName);
+    if (opt.className)  el.className = opt.className;
+    if (opt.innerHTML) {
+      el.innerHTML = opt.innerHTML;
+      var scripts = el.getElementsByTagName('script');
+      for (var i = scripts.length; i-- > 0; null) {
+        scripts[i].parentNode.removeChild(scripts[i]);
+      }
+    }
+    for (var key in opt.style) {
+      el.style[key] = opt.style[key];
+    }
+    return el;
+  };
+
+  // Deep-clone a node and preserve contents/properties.
+  var cloneNode = function(node, javascriptEnabled) {
+    // Recursively clone the node.
+    var clone = node.nodeType === 3 ? document.createTextNode(node.nodeValue) : node.cloneNode(false);
+    for (var child = node.firstChild; child; child = child.nextSibling) {
+      if (javascriptEnabled === true || child.nodeType !== 1 || child.nodeName !== 'SCRIPT') {
+        clone.appendChild(cloneNode(child, javascriptEnabled));
+      }
+    }
+
+    if (node.nodeType === 1) {
+      // Preserve contents/properties of special nodes.
+      if (node.nodeName === 'CANVAS') {
+        clone.width = node.width;
+        clone.height = node.height;
+        clone.getContext('2d').drawImage(node, 0, 0);
+      } else if (node.nodeName === 'TEXTAREA' || node.nodeName === 'SELECT') {
+        clone.value = node.value;
+      }
+
+      // Preserve the node's scroll position when it loads.
+      clone.addEventListener('load', function() {
+        clone.scrollTop = node.scrollTop;
+        clone.scrollLeft = node.scrollLeft;
+      }, true);
+    }
+
+    // Return the cloned node.
+    return clone;
+  }
+
+  // Convert units using the conversion value 'k' from jsPDF.
+  var unitConvert = function(obj, k) {
+    var newObj = {};
+    for (var key in obj) {
+      newObj[key] = obj[key] * 72 / 96 / k;
+    }
+    return newObj;
+  };
+
+  // Get dimensions of a PDF page, as determined by jsPDF.
+  jsPDF.getPageSize = function(orientation, unit, format) {
+    // Decode options object
+    if (typeof orientation === 'object') {
+      var options = orientation;
+      orientation = options.orientation;
+      unit = options.unit || unit;
+      format = options.format || format;
+    }
+
+    // Default options
+    unit        = unit || 'mm';
+    format      = format || 'a4';
+    orientation = ('' + (orientation || 'P')).toLowerCase();
+    var format_as_string = ('' + format).toLowerCase();
+
+    // Size in pt of various paper formats
+    pageFormats = {
+      'a0'  : [2383.94, 3370.39], 'a1'  : [1683.78, 2383.94],
+      'a2'  : [1190.55, 1683.78], 'a3'  : [ 841.89, 1190.55],
+      'a4'  : [ 595.28,  841.89], 'a5'  : [ 419.53,  595.28],
+      'a6'  : [ 297.64,  419.53], 'a7'  : [ 209.76,  297.64],
+      'a8'  : [ 147.40,  209.76], 'a9'  : [ 104.88,  147.40],
+      'a10' : [  73.70,  104.88], 'b0'  : [2834.65, 4008.19],
+      'b1'  : [2004.09, 2834.65], 'b2'  : [1417.32, 2004.09],
+      'b3'  : [1000.63, 1417.32], 'b4'  : [ 708.66, 1000.63],
+      'b5'  : [ 498.90,  708.66], 'b6'  : [ 354.33,  498.90],
+      'b7'  : [ 249.45,  354.33], 'b8'  : [ 175.75,  249.45],
+      'b9'  : [ 124.72,  175.75], 'b10' : [  87.87,  124.72],
+      'c0'  : [2599.37, 3676.54], 'c1'  : [1836.85, 2599.37],
+      'c2'  : [1298.27, 1836.85], 'c3'  : [ 918.43, 1298.27],
+      'c4'  : [ 649.13,  918.43], 'c5'  : [ 459.21,  649.13],
+      'c6'  : [ 323.15,  459.21], 'c7'  : [ 229.61,  323.15],
+      'c8'  : [ 161.57,  229.61], 'c9'  : [ 113.39,  161.57],
+      'c10' : [  79.37,  113.39], 'dl'  : [ 311.81,  623.62],
+      'letter'            : [612,   792],
+      'government-letter' : [576,   756],
+      'legal'             : [612,  1008],
+      'junior-legal'      : [576,   360],
+      'ledger'            : [1224,  792],
+      'tabloid'           : [792,  1224],
+      'credit-card'       : [153,   243]
+    };
+
+    // Unit conversion
+    switch (unit) {
+      case 'pt':  k = 1;          break;
+      case 'mm':  k = 72 / 25.4;  break;
+      case 'cm':  k = 72 / 2.54;  break;
+      case 'in':  k = 72;         break;
+      case 'px':  k = 72 / 96;    break;
+      case 'pc':  k = 12;         break;
+      case 'em':  k = 12;         break;
+      case 'ex':  k = 6;          break;
+      default:
+        throw ('Invalid unit: ' + unit);
+    }
+
+    // Dimensions are stored as user units and converted to points on output
+    if (pageFormats.hasOwnProperty(format_as_string)) {
+      pageHeight = pageFormats[format_as_string][1] / k;
+      pageWidth = pageFormats[format_as_string][0] / k;
+    } else {
+      try {
+        pageHeight = format[1];
+        pageWidth = format[0];
+      } catch (err) {
+        throw new Error('Invalid format: ' + format);
+      }
+    }
+
+    // Handle page orientation
+    if (orientation === 'p' || orientation === 'portrait') {
+      orientation = 'p';
+      if (pageWidth > pageHeight) {
+        tmp = pageWidth;
+        pageWidth = pageHeight;
+        pageHeight = tmp;
+      }
+    } else if (orientation === 'l' || orientation === 'landscape') {
+      orientation = 'l';
+      if (pageHeight > pageWidth) {
+        tmp = pageWidth;
+        pageWidth = pageHeight;
+        pageHeight = tmp;
+      }
+    } else {
+      throw('Invalid orientation: ' + orientation);
+    }
+
+    // Return information (k is the unit conversion ratio from pts)
+    var info = { 'width': pageWidth, 'height': pageHeight, 'unit': unit, 'k': k };
+    return info;
+  };
+
+
+  // Expose the html2pdf function.
+  return html2pdf;
+}(html2canvas, jsPDF));
diff --git a/hosting/templates/hosting/order_detail.html b/hosting/templates/hosting/order_detail.html
index 3d1ffd35..8278db45 100644
--- a/hosting/templates/hosting/order_detail.html
+++ b/hosting/templates/hosting/order_detail.html
@@ -5,7 +5,7 @@
 
 {% block content %}
 
-<div class="order-detail-container">
+<div id="order-detail" class="order-detail-container">
     {% if messages %}
         <div class="alert alert-warning">
             {% for message in messages %}
@@ -14,17 +14,20 @@
         </div>
     {% endif %}
     {% if not error %}
-        <h1 class="dashboard-title-thin">
-            {% blocktrans %}{{page_header_text|default:'Invoice'}}{% endblocktrans %}
-        </h1>
+        <div class="dashboard-container-head">
+            <h1 class="dashboard-title-thin">
+                <img src="{% static 'hosting/img/billing.svg' %}" class="un-icon">{% blocktrans with page_header_text=page_header_text|default:"Invoice" %}{{page_header_text}}{% endblocktrans %}
+            </h1>
+
+            <button></button>
+                <img src="{% static 'hosting/img/icon-pdf.svg' %}" class="svg-img pull-right">
+                <img src="{% static 'hosting/img/icon-print.svg' %}" class="svg-img pull-right">
+        </div>
         <div class="invoice-title">
-            <h3 class="pull-right">
-                {% if order %}
-                    {% trans "Order #"%} {{order.id}}
-                {% endif %}
+            <h3>
+                {% trans "Order #"%} {{order.id}}
             </h3>
         </div>
-        <hr>
         <div class="row">
             <div class="col-xs-12 col-md-6 pull-right order-confirm-date">
                 <address>
@@ -202,5 +205,11 @@
     };
 
 </script>
+<script src="https://cdnjs.cloudflare.com/ajax/libs/jspdf/1.3.5/jspdf.min.js"></script>
+<script src="https://cdnjs.cloudflare.com/ajax/libs/html2canvas/0.4.1/html2canvas.min.js"></script>
+<script src="{% static 'hosting/js/html2pdf.js' %}"></script>
+<script>
+    html2pdf(document.getElementById('order-detail'));
+</script>
 {%endblock%}
 

From f0e50a4e948be7a86d025fae300071db059edece Mon Sep 17 00:00:00 2001
From: Arvind Tiwari <tiwariav@gmail.com>
Date: Thu, 21 Sep 2017 01:20:51 +0530
Subject: [PATCH 38/82] removed commented code

---
 datacenterlight/static/datacenterlight/js/main.js | 1 -
 hosting/static/hosting/js/createvm.js             | 1 -
 2 files changed, 2 deletions(-)

diff --git a/datacenterlight/static/datacenterlight/js/main.js b/datacenterlight/static/datacenterlight/js/main.js
index c508d76d..ab37a68b 100644
--- a/datacenterlight/static/datacenterlight/js/main.js
+++ b/datacenterlight/static/datacenterlight/js/main.js
@@ -147,7 +147,6 @@
 
     function _fetchPricing() {
         Object.keys(cardPricing).map(function(element) {
-            //$('#'+cardPricing[element].id).val(cardPricing[element].value);
             $('input[name=' + element + ']').val(cardPricing[element].value);
         });
         _calcPricing();
diff --git a/hosting/static/hosting/js/createvm.js b/hosting/static/hosting/js/createvm.js
index 344aedfb..726513ad 100644
--- a/hosting/static/hosting/js/createvm.js
+++ b/hosting/static/hosting/js/createvm.js
@@ -53,7 +53,6 @@
 
     function _fetchPricing() {
         Object.keys(cardPricing).map(function(element) {
-            //$('#'+cardPricing[element].id).val(cardPricing[element].value);
             $('input[name=' + element + ']').val(cardPricing[element].value);
         });
         _calcPricing();

From dd77f407074282c168ecd05a2f39c6a7d60df069 Mon Sep 17 00:00:00 2001
From: Arvind Tiwari <tiwariav@gmail.com>
Date: Thu, 21 Sep 2017 02:23:08 +0530
Subject: [PATCH 39/82] top options added

---
 hosting/static/hosting/css/commons.css      | 16 ++++++++++++++++
 hosting/static/hosting/css/order.css        | 16 ++++++++++++----
 hosting/static/hosting/img/icon-pdf.svg     |  4 ++--
 hosting/static/hosting/img/icon-print.svg   |  4 ++--
 hosting/templates/hosting/order_detail.html |  8 ++++----
 5 files changed, 36 insertions(+), 12 deletions(-)

diff --git a/hosting/static/hosting/css/commons.css b/hosting/static/hosting/css/commons.css
index 01ff5090..c70051b6 100644
--- a/hosting/static/hosting/css/commons.css
+++ b/hosting/static/hosting/css/commons.css
@@ -355,4 +355,20 @@
 
 .no-cards a {
   color: #7ca3d0;
+}
+
+.btn-plain {
+  background: transparent;
+  border: none;
+  fill: #595959;
+  color: #595959;
+  outline: none;
+}
+.btn-plain:hover,
+.btn-plain:focus,
+.btn-plain:active,
+.btn-plain:active:focus {
+  outline: none;
+  color: #999;
+  fill: #999;
 }
\ No newline at end of file
diff --git a/hosting/static/hosting/css/order.css b/hosting/static/hosting/css/order.css
index 3e916cdd..186f7c16 100644
--- a/hosting/static/hosting/css/order.css
+++ b/hosting/static/hosting/css/order.css
@@ -29,10 +29,18 @@
     margin-top: -6px;
 }
 
-.order-detail-container .dashboard-title-thin .svg-img {
+.order-detail-container .dashboard-container-head {
+    position: relative;
+    padding: 0;
+}
+
+.order-detail-container .dashboard-container-options {
+    position: absolute;
+    top: 10px;
+    right: 0;
+}
+.order-detail-container .dashboard-container-options .svg-img {
     height: 20px;
-    margin-right: 5px;
-    margin-top: -2px;
+    /* margin-right: 5px; */
     width: 20px;
-    margin-top: -6px;
 }
\ No newline at end of file
diff --git a/hosting/static/hosting/img/icon-pdf.svg b/hosting/static/hosting/img/icon-pdf.svg
index 20fc9c48..3743bbb8 100644
--- a/hosting/static/hosting/img/icon-pdf.svg
+++ b/hosting/static/hosting/img/icon-pdf.svg
@@ -4,8 +4,8 @@
     <title>icon-pdf</title>
     <desc>Created with Sketch.</desc>
     <defs></defs>
-    <g id="Page-1" stroke="none" stroke-width="1" fill="none" fill-rule="evenodd">
-        <g id="icon-pdf" fill-rule="nonzero" fill="#000000">
+    <g id="Page-1" stroke="none" stroke-width="1" fill-rule="evenodd">
+        <g id="icon-pdf" fill-rule="nonzero">
             <g id="Group" transform="translate(93.000000, 269.000000)">
                 <path d="M98,47.8 C98,54.8 97,61.7 95.1,66.6 C93.1,72.5 90.1,76.5 86.2,80.5 C82.2,84.5 76.3,87.4 70.4,89.4 C64.5,91.4 55.6,92.3 46.6,92.3 L34.7,92.3 L34.7,134 L0,134 L0,0.3 L45.5,0.3 C54.4,0.3 62.4,1.3 69.3,3.2 C76.2,5.2 81.2,8.2 85.1,12.1 C89.1,16.1 92.1,21 94,27 C96.9,32 98,38.9 98,47.8 Z M61.3,46.8 C61.3,42.8 61.3,39.9 60.3,37.9 C60.3,35.9 59.3,33.9 57.4,32 C56.4,31 54.5,30 52.4,29.1 C50.4,29.1 47.4,28.1 44.5,28.1 L34.6,28.1 L34.6,63.7 L45.5,63.7 C48.4,63.7 50.4,63.7 52.5,62.7 C54.5,61.7 56.5,61.7 57.5,59.8 C58.5,57.8 59.5,56.9 60.4,54.8 C61.3,53.8 61.3,50.8 61.3,46.8 Z" id="Shape"></path>
                 <path d="M214.8,66.6 C214.8,78.5 213.8,89.3 210.8,97.3 C208.8,106.2 204.9,113.1 199.9,118.1 C195,123.1 189,127 182.1,130 C175.2,132 167.3,134 157.3,134 L108.8,134 L108.8,0.3 L156.3,0.3 C166.2,0.3 175.1,1.3 182,4.3 C188.9,7.2 194.9,10.2 199.8,16.2 C204.8,21.2 207.7,28.1 209.7,37 C213.8,44.8 214.8,54.7 214.8,66.6 Z M178.1,65.6 C178.1,58.7 178.1,52.7 177.1,47.8 C176.1,42.8 175.1,39.9 174.2,36.9 C172.2,34 170.2,32.9 168.3,31.9 C165.4,30.9 162.4,30.9 158.4,30.9 L145.6,30.9 L145.6,103.2 L158.4,103.2 C162.4,103.2 165.4,103.2 168.3,102.2 C171.2,101.2 173.3,99.3 174.2,97.2 C176.2,94.3 177.1,91.3 178.2,86.3 C178.1,80.5 178.1,74.5 178.1,65.6 Z" id="Shape"></path>
diff --git a/hosting/static/hosting/img/icon-print.svg b/hosting/static/hosting/img/icon-print.svg
index e440f326..75eb175f 100644
--- a/hosting/static/hosting/img/icon-print.svg
+++ b/hosting/static/hosting/img/icon-print.svg
@@ -4,8 +4,8 @@
     <title>54471</title>
     <desc>Created with Sketch.</desc>
     <defs></defs>
-    <g id="Page-1" stroke="none" stroke-width="1" fill="none" fill-rule="evenodd">
-        <g id="54471" fill-rule="nonzero" fill="#000000">
+    <g id="Page-1" stroke="none" stroke-width="1" fill-rule="evenodd">
+        <g id="54471" fill-rule="nonzero">
             <path d="M0,225.633 L0,386.367 C0,417.272 30.6,417.272 30.6,417.272 L83.454,417.272 L83.454,389.454 L27.818,389.454 L27.818,222.545 L584.181,222.545 L584.181,389.454 L528.545,389.454 L528.545,417.272 L581.4,417.272 C581.4,417.272 612,417.272 612,386.367 L612,225.633 C612,225.633 612,194.727 581.4,194.727 L30.6,194.727 C0,194.728 0,225.633 0,225.633 Z" id="Shape"></path>
             <polygon id="Shape" points="500.728 166.909 500.728 0 111.273 0 111.273 166.909 139.091 166.909 139.091 27.818 472.909 27.818 472.909 166.909"></polygon>
             <path d="M528.546,292.091 C528.546,278.182 514.358,278.182 514.358,278.182 L97.642,278.182 C97.642,278.182 83.455,278.182 83.455,292.091 C83.455,306 97.642,306 97.642,306 L514.359,306 C514.358,306 528.546,306 528.546,292.091 Z" id="Shape"></path>
diff --git a/hosting/templates/hosting/order_detail.html b/hosting/templates/hosting/order_detail.html
index 8278db45..56154d29 100644
--- a/hosting/templates/hosting/order_detail.html
+++ b/hosting/templates/hosting/order_detail.html
@@ -18,10 +18,10 @@
             <h1 class="dashboard-title-thin">
                 <img src="{% static 'hosting/img/billing.svg' %}" class="un-icon">{% blocktrans with page_header_text=page_header_text|default:"Invoice" %}{{page_header_text}}{% endblocktrans %}
             </h1>
-
-            <button></button>
-                <img src="{% static 'hosting/img/icon-pdf.svg' %}" class="svg-img pull-right">
-                <img src="{% static 'hosting/img/icon-print.svg' %}" class="svg-img pull-right">
+            <div class="dashboard-container-options">
+                <button class="btn-plain"><img src="{% static 'hosting/img/icon-pdf.svg' %}" class="svg-img"></button>
+                <button class="btn-plain"><img src="{% static 'hosting/img/icon-print.svg' %}" class="svg-img"></button>
+            </div>
         </div>
         <div class="invoice-title">
             <h3>

From 1eff51099c09618e98c35144bc3fafacae269265 Mon Sep 17 00:00:00 2001
From: Arvind Tiwari <tiwariav@gmail.com>
Date: Thu, 21 Sep 2017 02:26:42 +0530
Subject: [PATCH 40/82] exception handling fix

---
 hosting/views.py | 7 ++-----
 1 file changed, 2 insertions(+), 5 deletions(-)

diff --git a/hosting/views.py b/hosting/views.py
index 06d5051c..21444b41 100644
--- a/hosting/views.py
+++ b/hosting/views.py
@@ -967,11 +967,8 @@ class VirtualMachineView(LoginRequiredMixin, View):
 
         try:
             vm_data = VirtualMachineSerializer(manager.get_vm(vm.id)).data
-        except BaseException:
-            return redirect(
-                reverse('hosting:virtual_machines',
-                        kwargs={'pk': opennebula_vm_id})
-            )
+        except WrongIdError:
+            return redirect(reverse('hosting:virtual_machines'))
 
         terminated = manager.delete_vm(vm.id)
 

From 6dfbf67d7d9c092fe2b8cfe47417985cd6c5b963 Mon Sep 17 00:00:00 2001
From: Arvind Tiwari <tiwariav@gmail.com>
Date: Thu, 21 Sep 2017 02:50:07 +0530
Subject: [PATCH 41/82] rearranging text

---
 hosting/templates/hosting/order_detail.html   | 133 +++++++++---------
 .../templates/hosting/virtual_machines.html   |  16 ++-
 2 files changed, 79 insertions(+), 70 deletions(-)

diff --git a/hosting/templates/hosting/order_detail.html b/hosting/templates/hosting/order_detail.html
index 56154d29..38b186db 100644
--- a/hosting/templates/hosting/order_detail.html
+++ b/hosting/templates/hosting/order_detail.html
@@ -23,81 +23,88 @@
                 <button class="btn-plain"><img src="{% static 'hosting/img/icon-print.svg' %}" class="svg-img"></button>
             </div>
         </div>
-        <div class="invoice-title">
-            <h3>
-                {% trans "Order #"%} {{order.id}}
-            </h3>
-        </div>
-        <div class="row">
-            <div class="col-xs-12 col-md-6 pull-right order-confirm-date">
-                <address>
-                    <strong>{% trans "Date"%}:</strong><br>
-                    <span id="order-created_at">
-                            {% if order %}
-                                {{order.created_at|date:'Y-m-d H:i'}}
-                            {% else %}
-                                {% now "Y-m-d H:i" %}
-                            {% endif %}
-                        </span><br><br>
+        <div class="order-details">
+            {% if order %}
+                <div>
+                    <strong>{% trans "Order #"%} {{order.id}}</strong>
+                </div>
+            {% endif %}
+            <div>
+                <strong>{% trans "Invoice Date"%}:</strong>
+                <span id="order-created_at">
                     {% if order %}
-                    <strong>{% trans "Status:"%}</strong><br>
+                        {{order.created_at|date:'Y-m-d H:i'}}
+                    {% else %}
+                        {% now "Y-m-d H:i" %}
+                    {% endif %}
+                </span>
+            </div>
+            {% if order %}
+
+            {% endif %}
+            <div>
+                <strong>{% trans "Status" %}: </strong>
+                <strong>
                     {% if order.status == 'Approved' %}
-                    <strong class="text-success">
-                        {% trans "Approved" %}
-                    </strong>
+                        <span class="vm-status-active">{% trans "Approved" %}</span>
                     {% else %}
-                    <strong class="text-danger">
-                        {% trans "Declined" %}
-                    </strong>
+                        <span class="vm-status-failed">{% trans "Declined" %}</span>
                     {% endif %}
-                    <br><br>
-                    {% endif %}
-                </address>
-
+                </strong>
             </div>
-            <div class="col-xs-12 col-md-6">
+            <hr>
+            <div>
                 <address>
-                    <h3><b>{% trans "Billed To:"%}</b></h3>
-                    {% if order %}
-                        {{user.name}}<br>
-                        {{order.billing_address.street_address}},{{order.billing_address.postal_code}}<br>
-                        {{order.billing_address.city}},
-                        {{order.billing_address.country}}.
-                    {% else %}
-                        {% with request.session.billing_address_data as billing_address %}
-                        {{billing_address.cardholder_name}}<br>
-                        {{billing_address.street_address}},
-                        {{billing_address.postal_code}}<br>
-                        {{billing_address.city}},
-                        {{billing_address.country}}.
-                        {% endwith %}
-                    {% endif %}
+                    <h4>{% trans "Billed to" %}:</h4>
+                    <div>
+                        {% if order %}
+                            {{user.name}}<br>
+                            {{order.billing_address.street_address}},{{order.billing_address.postal_code}}<br>
+                            {{order.billing_address.city}},
+                            {{order.billing_address.country}}.
+                        {% else %}
+                            {% with request.session.billing_address_data as billing_address %}
+                            {{billing_address.cardholder_name}}<br>
+                            {{billing_address.street_address}},
+                            {{billing_address.postal_code}}<br>
+                            {{billing_address.city}},
+                            {{billing_address.country}}.
+                            {% endwith %}
+                        {% endif %}
+                    </div>
                 </address>
             </div>
+            <hr>
+            <div>
+                <h4>{% trans "Payment method" %}:</h4>
+                <div>
+                    {% if order %}
+                        {{order.cc_brand}} {% trans "ending in" %} ****
+                        {{order.last4}}<br>
+                        {{user.email}}
+                    {% else %}
+                        {{cc_brand}} {% trans "ending in" %} ****
+                        {{cc_last4}}<br>
+                        {{request.session.user.email}}
+                    {% endif %}
+                </div>
+            </div>
+            <div>
+                <h4>{% trans "Order summary"%}</h4>
+                <div>
+                    {% if request.session.specs %}
+                        {% request.session.specs as vm %}
+                    {% endif %}
+                    <strong>{% trans "Product" %}:</strong> {{request.session.template.name}}
+                </div>
+            </div>
 
         </div>
-        <div class="row">
-            <div class="col-xs-6">
-                <address>
-                    <strong>{% trans "Payment Method:"%}</strong><br>
-                    {% if order %}
-                    {{order.cc_brand}} {% trans "ending in" %} ****
-                    {{order.last4}}<br>
-                    {{user.email}}
-                    {% else %}
-                    {{cc_brand}} {% trans "ending in" %} ****
-                    {{cc_last4}}<br>
-                    {{request.session.user.email}}
-                    {% endif %}
-                </address>
-            </div>
-        </div>
 
-        <h3><b>{% trans "Order summary"%}</b></h3>
+        <h3><b></b></h3>
         <hr>
         <div class="content">
-            {% if request.session.specs %}
-            {% with request.session.specs as vm %}
+
             <p><b>{% trans "Cores"%}</b>
                 <span class="pull-right">{{vm.cpu}}</span>
             </p>
@@ -195,7 +202,7 @@
 
 <script type="text/javascript">
     {% trans "Some problem encountered. Please try again later." as err_msg %}
-    var create_vm_error_message = '{{err_msg|safe}}.';
+    var create_vm_error_message = '{{err_msg|safe}}';
 
     window.onload = function () {
         var locale_date = moment.utc(document.getElementById("order-created_at").textContent, 'YYYY-MM-DD HH:mm').toDate();
diff --git a/hosting/templates/hosting/virtual_machines.html b/hosting/templates/hosting/virtual_machines.html
index f7461abe..622e7a55 100644
--- a/hosting/templates/hosting/virtual_machines.html
+++ b/hosting/templates/hosting/virtual_machines.html
@@ -41,13 +41,15 @@
                         <td data-header="IPv6">{{vm.ipv6}}</td>
                     {% endif %}
                     <td data-header="{% trans 'Status' %}">
-                        {% if vm.state == 'ACTIVE' %}
-                            <span class="vm-status-active"><strong>{{vm.state|title}}</strong></span>
-                        {% elif  vm.state == 'FAILED' %}
-                            <span class="vm-status-failed"><strong>{{vm.state|title}}</strong></span>
-                        {% else %}
-                            <span class="vm-status"><strong>{{vm.state|title}}</strong></span>
-                        {% endif %}
+                        <strong>
+                            {% if vm.state == 'ACTIVE' %}
+                                <span class="vm-status-active">{{vm.state|title}}</span>
+                            {% elif  vm.state == 'FAILED' %}
+                                <span class="vm-status-failed">{{vm.state|title}}</span>
+                            {% else %}
+                                <span class="vm-status">{{vm.state|title}}</span>
+                            {% endif %}
+                        </strong>
                     </td>
                     <td class="text-right last-td">
                         <a class="btn btn-vm-detail" href="{% url 'hosting:virtual_machines' vm.vm_id %}">{% trans "View Detail" %}</a>

From 6c381dd3fbc435a4741a0cc8634a7be4c40527e9 Mon Sep 17 00:00:00 2001
From: Arvind Tiwari <tiwariav@gmail.com>
Date: Thu, 21 Sep 2017 15:03:00 +0530
Subject: [PATCH 42/82] invoice page redesigned

---
 hosting/static/hosting/css/landing-page.css   |   4 +-
 hosting/static/hosting/css/order.css          |  34 ++-
 hosting/static/hosting/js/order.js            |  15 ++
 .../hosting/js/virtual_machine_detail.js      |   2 +
 hosting/templates/hosting/base_short.html     |   9 +-
 hosting/templates/hosting/order_detail.html   | 217 ++++++++----------
 hosting/views.py                              |   1 +
 7 files changed, 157 insertions(+), 125 deletions(-)
 create mode 100644 hosting/static/hosting/js/order.js

diff --git a/hosting/static/hosting/css/landing-page.css b/hosting/static/hosting/css/landing-page.css
index 71b7a33d..5c71b7ca 100644
--- a/hosting/static/hosting/css/landing-page.css
+++ b/hosting/static/hosting/css/landing-page.css
@@ -580,9 +580,9 @@ a.unlink:hover {
 }
 
 .dcl-place-order-text{
-   font-size: 13px;
+   /* font-size: 13px; */
    color: #808080;
-   margin-bottom: 15px;
+   /* margin-bottom: 15px; */
 }
 
 .dcl-order-table-total .tbl-total {
diff --git a/hosting/static/hosting/css/order.css b/hosting/static/hosting/css/order.css
index 186f7c16..0377bfac 100644
--- a/hosting/static/hosting/css/order.css
+++ b/hosting/static/hosting/css/order.css
@@ -1,6 +1,6 @@
 .order-detail-container {
     max-width: 600px;
-    margin: 100px auto;
+    margin: 100px auto 40px;
     border: 1px solid #ccc;
     padding: 30px;
 }
@@ -23,6 +23,7 @@
 
 .order-detail-container .dashboard-title-thin {
     margin-top: 0;
+    margin-left: -3px;
 }
 
 .order-detail-container .dashboard-title-thin .un-icon {
@@ -32,6 +33,7 @@
 .order-detail-container .dashboard-container-head {
     position: relative;
     padding: 0;
+    margin-bottom: 38px;
 }
 
 .order-detail-container .dashboard-container-options {
@@ -43,4 +45,34 @@
     height: 20px;
     /* margin-right: 5px; */
     width: 20px;
+}
+
+.order-detail-container .order-details {
+    margin-bottom: 30px;
+}
+
+.order-detail-container .order-details strong {
+    color: #777;
+}
+
+.order-detail-container h4 {
+    font-size: 16px;
+    font-weight: bold;
+    margin-bottom: 15px;
+}
+
+.order-detail-container p {
+    margin-bottom: 5px;
+    color: #595959;
+}
+
+.order-detail-container hr {
+    margin: 15px 0;
+}
+
+@media (max-width: 767px) {
+    .order-confirm-btn {
+        text-align: center;
+        margin-top: 10px;
+    }
 }
\ No newline at end of file
diff --git a/hosting/static/hosting/js/order.js b/hosting/static/hosting/js/order.js
new file mode 100644
index 00000000..e9de4cf9
--- /dev/null
+++ b/hosting/static/hosting/js/order.js
@@ -0,0 +1,15 @@
+$(document).ready(function() {
+    $('.btn-pdf').click(function(e) {
+        e.preventDefault();
+        var $target = $($(this).attr('data-target')) || $('body');
+        var fileName = $target.attr('id') + '.pdf';
+        html2pdf($target[0], {
+            filename: fileName,
+        });
+    });
+    $('.btn-print').click(function(e) {
+        e.preventDefault();
+        console.log('a');
+        window.print();
+    });
+});
\ No newline at end of file
diff --git a/hosting/static/hosting/js/virtual_machine_detail.js b/hosting/static/hosting/js/virtual_machine_detail.js
index b6202e97..7d66afaf 100644
--- a/hosting/static/hosting/js/virtual_machine_detail.js
+++ b/hosting/static/hosting/js/virtual_machine_detail.js
@@ -1,4 +1,5 @@
 $(document).ready(function () {
+    $('.modal-text').removeClass('hide');
     var create_vm_form = $('#virtual_machine_create_form');
     create_vm_form.submit(function () {
         $('#btn-create-vm').prop('disabled', true);
@@ -22,6 +23,7 @@ $(document).ready(function () {
                     fa_icon = $('.modal-icon > .fa');
                     fa_icon.attr('class', 'fa fa-times');
                     $('.modal-header > .close').attr('class', 'close');
+                    $('.modal-text').addClass('hide');
                     if (typeof(create_vm_error_message) !== 'undefined') {
                         $('#createvm-modal-title').text(create_vm_error_message);
                     }
diff --git a/hosting/templates/hosting/base_short.html b/hosting/templates/hosting/base_short.html
index 63a0681d..3906133b 100644
--- a/hosting/templates/hosting/base_short.html
+++ b/hosting/templates/hosting/base_short.html
@@ -94,6 +94,13 @@
     <!-- Init JavaScript -->
     <script src="{% static 'hosting/js/initial.js' %}"></script>
 
+    {% block js_extra %}
+        {% comment %}
+            this block is above some files, because on stripe error scripts below the stripe
+            script are not properly executed.
+        {% endcomment %}
+    {% endblock js_extra %}
+
     <script src="https://js.stripe.com/v3/"></script>
     <script src="https://js.stripe.com/v2/"></script>
     <!-- Stripe Lib -->
@@ -108,8 +115,6 @@
     <script type="text/javascript" src="//cdnjs.cloudflare.com/ajax/libs/moment.js/2.18.1/moment.min.js"></script>
     <script type="text/javascript" src="//cdnjs.cloudflare.com/ajax/libs/moment.js/2.18.1/moment-with-locales.js"></script>
 
-
-
 </body>
 
 </html>
diff --git a/hosting/templates/hosting/order_detail.html b/hosting/templates/hosting/order_detail.html
index 38b186db..49f7ba6b 100644
--- a/hosting/templates/hosting/order_detail.html
+++ b/hosting/templates/hosting/order_detail.html
@@ -5,7 +5,7 @@
 
 {% block content %}
 
-<div id="order-detail" class="order-detail-container">
+<div id="order-detail{{order.pk}}" class="order-detail-container">
     {% if messages %}
         <div class="alert alert-warning">
             {% for message in messages %}
@@ -19,18 +19,18 @@
                 <img src="{% static 'hosting/img/billing.svg' %}" class="un-icon">{% blocktrans with page_header_text=page_header_text|default:"Invoice" %}{{page_header_text}}{% endblocktrans %}
             </h1>
             <div class="dashboard-container-options">
-                <button class="btn-plain"><img src="{% static 'hosting/img/icon-pdf.svg' %}" class="svg-img"></button>
-                <button class="btn-plain"><img src="{% static 'hosting/img/icon-print.svg' %}" class="svg-img"></button>
+                <button type="button" class="btn-plain btn-pdf" data-target="#order-detail{{order.pk}}"><img src="{% static 'hosting/img/icon-pdf.svg' %}" class="svg-img"></button>
+                <button type="button" class="btn-plain btn-print"><img src="{% static 'hosting/img/icon-print.svg' %}" class="svg-img"></button>
             </div>
         </div>
         <div class="order-details">
             {% if order %}
-                <div>
-                    <strong>{% trans "Order #"%} {{order.id}}</strong>
-                </div>
             {% endif %}
-            <div>
-                <strong>{% trans "Invoice Date"%}:</strong>
+                <p>
+                    <strong>{% trans "Order #" %} {{order.id}}</strong>
+                </p>
+            <p>
+                <strong>{% trans "Invoice Date" %}:</strong>
                 <span id="order-created_at">
                     {% if order %}
                         {{order.created_at|date:'Y-m-d H:i'}}
@@ -38,46 +38,43 @@
                         {% now "Y-m-d H:i" %}
                     {% endif %}
                 </span>
-            </div>
+            </p>
             {% if order %}
 
             {% endif %}
-            <div>
+            <p>
                 <strong>{% trans "Status" %}: </strong>
                 <strong>
                     {% if order.status == 'Approved' %}
-                        <span class="vm-status-active">{% trans "Approved" %}</span>
+                        <span class="vm-color-online">{% trans "Approved" %}</span>
                     {% else %}
                         <span class="vm-status-failed">{% trans "Declined" %}</span>
                     {% endif %}
                 </strong>
-            </div>
+            </p>
             <hr>
             <div>
                 <address>
                     <h4>{% trans "Billed to" %}:</h4>
-                    <div>
+                    <p>
                         {% if order %}
                             {{user.name}}<br>
-                            {{order.billing_address.street_address}},{{order.billing_address.postal_code}}<br>
-                            {{order.billing_address.city}},
-                            {{order.billing_address.country}}.
+                            {{order.billing_address.street_address}}, {{order.billing_address.postal_code}}<br>
+                            {{order.billing_address.city}}, {{order.billing_address.country}}
                         {% else %}
                             {% with request.session.billing_address_data as billing_address %}
-                            {{billing_address.cardholder_name}}<br>
-                            {{billing_address.street_address}},
-                            {{billing_address.postal_code}}<br>
-                            {{billing_address.city}},
-                            {{billing_address.country}}.
+                                {{billing_address.cardholder_name}}<br>
+                                {{billing_address.street_address}}, {{billing_address.postal_code}}<br>
+                                {{billing_address.city}}, {{billing_address.country}}
                             {% endwith %}
                         {% endif %}
-                    </div>
+                    </p>
                 </address>
             </div>
             <hr>
             <div>
                 <h4>{% trans "Payment method" %}:</h4>
-                <div>
+                <p>
                     {% if order %}
                         {{order.cc_brand}} {% trans "ending in" %} ****
                         {{order.last4}}<br>
@@ -87,82 +84,55 @@
                         {{cc_last4}}<br>
                         {{request.session.user.email}}
                     {% endif %}
-                </div>
-            </div>
-            <div>
-                <h4>{% trans "Order summary"%}</h4>
-                <div>
-                    {% if request.session.specs %}
-                        {% request.session.specs as vm %}
-                    {% endif %}
-                    <strong>{% trans "Product" %}:</strong> {{request.session.template.name}}
-                </div>
-            </div>
-
-        </div>
-
-        <h3><b></b></h3>
-        <hr>
-        <div class="content">
-
-            <p><b>{% trans "Cores"%}</b>
-                <span class="pull-right">{{vm.cpu}}</span>
-            </p>
-            <hr>
-            <p><b>{% trans "Memory"%}</b>
-                <span class="pull-right">{{vm.memory}} GB</span>
-            </p>
-            <hr>
-            <p><b>{% trans "Disk space"%}</b>
-                <span class="pull-right">{{vm.disk_size}} GB</span>
-            </p>
-            <hr>
-            <p><b>{% trans "Configuration"%}</b>
-                <span class="pull-right">{{request.session.template.name}}</span>
-            </p>
-            <hr>
-            <h4>{% trans "Total"%}
-                <p class="pull-right">
-                    <b>{{vm.price}} CHF</b>
-                    <span class="dcl-price-month"> /{% trans "Month" %}
-                            </span>
                 </p>
-            </h4>
-            {% endwith %}
-            {% else %}
-            <p><b>{% trans "Cores"%}</b>
-                <span class="pull-right">{{vm.cores}}</span>
-            </p>
+            </div>
             <hr>
-            <p><b>{% trans "Memory"%}</b>
-                <span class="pull-right">{{vm.memory}} GB</span>
-            </p>
-            <hr>
-            <p><b>{% trans "Disk space"%}</b>
-                <span class="pull-right">{{vm.disk_size}} GB</span>
-            </p>
-            <hr>
-            <h4>{% trans "Total"%}<p class="pull-right"><b>{{vm.price}}
-                CHF</b><span
-                    class="dcl-price-month"> /{% trans "Month" %}</span>
-            </p></h4>
+            <div>
+                <h4>{% trans "Order summary" %}</h4>
+                <p>
+                    <strong>{% trans "Product" %}:</strong> {{vm.name}}
+                </p>
+                <div class="row">
+                    <div class="col-sm-6">
+                        {% comment %}
+                        <p>
+                            <span>{% trans "Period" %}</span>
+                            <span class="pull-right">{{vm.cpu}}</span>
+                        </p>
+                        {% endcomment %}
+                        <p>
+                            <span>{% trans "Cores" %}</span>
+                            <span class="pull-right">{{vm.cpu}}</span>
+                        </p>
+                        <p>
+                            <span>{% trans "Memory" %}</span>
+                            <span class="pull-right">{{vm.memory}} GB</span>
+                        </p>
+                        <p>
+                            <span>{% trans "Disk space" %}</span>
+                            <span class="pull-right">{{vm.disk_size}} GB</span>
+                        </p>
+                        <p>
+                            <span>{% trans "Total" %}</span>
+                            <span class="pull-right">{{vm.price}} CHF</span>
+                        </p>
+                    </div>
+                </div>
+            </div>
+            {% if not order %}
+                <hr>
             {% endif %}
         </div>
-        <br/>
         {% if not order %}
             <form method="post" id="virtual_machine_create_form">
                 {% csrf_token %}
                 <div class="row">
                     <div class="col-sm-8">
-                        <p class="dcl-place-order-text">{% blocktrans with vm_price=request.session.specs.price %}By clicking "Place order" this plan will charge your credit card account with the fee of {{ vm_price }}CHF/month{% endblocktrans %}.</p>
+                        <div class="dcl-place-order-text">{% blocktrans with vm_price=request.session.specs.price %}By clicking "Place order" this plan will charge your credit card account with the fee of {{ vm_price }}CHF/month{% endblocktrans %}.</div>
                     </div>
-                    <div class="col-sm-4 content">
-                        <button class="btn btn-info pull-right"
-                                id="btn-create-vm"
-                                data-href="{% url 'hosting:order-confirmation' %}"
-                                data-toggle="modal"
-                                data-target="#createvm-modal">
-                            {% trans "Place order"%}
+                    <div class="col-sm-4 order-confirm-btn text-right">
+                        <button class="btn choice-btn" id="btn-create-vm" data-href="{% url 'hosting:order-confirmation' %}" data-toggle="modal" data-target="#createvm-modal">
+                            {% trans "Place order" %}
                         </button>
                     </div>
                 </div>
@@ -170,35 +140,43 @@
         {% endif %}
     {% endif %}
 </div>
-<!-- Create VM Modal -->
-<div class="modal fade" id="createvm-modal" tabindex="-1" role="dialog"
-     aria-hidden="true" data-backdrop="static" data-keyboard="false">
-    <div class="modal-dialog">
-        <div class="modal-content">
-            <div class="modal-header">
-                <button type="button" class="close hidden" data-dismiss="modal"
-                        aria-label="create-vm-close">
-                    <span aria-hidden="true">&times;</span>
-                </button>
-            </div>
-            <div class="modal-body">
-                <div class="modal-icon">
-                    <i class="fa fa-cog fa-spin fa-3x fa-fw"></i>
-                    <span class="sr-only">{% trans "Processing..." %}</span>
+
+    <div class="text-center" style="margin-bottom: 50px;">
+        <a class="btn btn-vm-back" href="{% url 'hosting:orders' %}">{% trans "BACK TO LIST" %}</a>
+    </div>
+{% if order %}
+{% endif %}
+
+{% if not order %}
+    <!-- Create VM Modal -->
+    <div class="modal fade" id="createvm-modal" tabindex="-1" role="dialog"
+         aria-hidden="true" data-backdrop="static" data-keyboard="false">
+        <div class="modal-dialog">
+            <div class="modal-content">
+                <div class="modal-header">
+                    <button type="button" class="close hidden" data-dismiss="modal"
+                            aria-label="create-vm-close">
+                        <span aria-hidden="true">&times;</span>
+                    </button>
                 </div>
-                <h4 class="modal-title" id="createvm-modal-title">
-                </h4>
-                <div class="modal-text" id="createvm-modal-body">
-                    {% trans "Hold tight, we are processing your request" %}
-                </div>
-                <div class="modal-footer">
+                <div class="modal-body">
+                    <div class="modal-icon">
+                        <i class="fa fa-cog fa-spin fa-3x fa-fw"></i>
+                        <span class="sr-only">{% trans "Processing..." %}</span>
+                    </div>
+                    <h4 class="modal-title" id="createvm-modal-title">
+                    </h4>
+                    <div class="modal-text" id="createvm-modal-body">
+                        {% trans "Hold tight, we are processing your request" %}
+                    </div>
+                    <div class="modal-footer">
+                    </div>
                 </div>
             </div>
         </div>
     </div>
-</div>
-<!-- / Create VM Modal -->
-
+    <!-- / Create VM Modal -->
+{% endif %}
 
 <script type="text/javascript">
     {% trans "Some problem encountered. Please try again later." as err_msg %}
@@ -210,13 +188,12 @@
         document.getElementById('order-created_at').innerHTML = locale_date;
 
     };
-
-</script>
-<script src="https://cdnjs.cloudflare.com/ajax/libs/jspdf/1.3.5/jspdf.min.js"></script>
-<script src="https://cdnjs.cloudflare.com/ajax/libs/html2canvas/0.4.1/html2canvas.min.js"></script>
-<script src="{% static 'hosting/js/html2pdf.js' %}"></script>
-<script>
-    html2pdf(document.getElementById('order-detail'));
 </script>
 {%endblock%}
 
+{% block js_extra %}
+    <script src="https://cdnjs.cloudflare.com/ajax/libs/jspdf/1.3.5/jspdf.min.js"></script>
+    <script src="https://cdnjs.cloudflare.com/ajax/libs/html2canvas/0.4.1/html2canvas.min.js"></script>
+    <script src="{% static 'hosting/js/html2pdf.js' %}"></script>
+    <script src="{% static 'hosting/js/order.js' %}"></script>
+{% endblock js_extra %}
\ No newline at end of file
diff --git a/hosting/views.py b/hosting/views.py
index e1d2feb2..20c2cc78 100644
--- a/hosting/views.py
+++ b/hosting/views.py
@@ -698,6 +698,7 @@ class OrdersHostingDetailView(LoginRequiredMixin,
                 'last4')
             context['cc_brand'] = card_details.get('response_object').get(
                 'cc_brand')
+            context['vm'] = request.session.get('specs')
         return context
 
     def post(self, request):

From 2c4390767d99ca3e73a4c9fb3854a7c846909e18 Mon Sep 17 00:00:00 2001
From: Arvind Tiwari <tiwariav@gmail.com>
Date: Thu, 21 Sep 2017 15:14:15 +0530
Subject: [PATCH 43/82] minor fixes

---
 hosting/templates/hosting/includes/_navbar_user.html | 6 +++++-
 hosting/views.py                                     | 6 +++---
 2 files changed, 8 insertions(+), 4 deletions(-)

diff --git a/hosting/templates/hosting/includes/_navbar_user.html b/hosting/templates/hosting/includes/_navbar_user.html
index 126dd1e6..d06477ca 100644
--- a/hosting/templates/hosting/includes/_navbar_user.html
+++ b/hosting/templates/hosting/includes/_navbar_user.html
@@ -37,7 +37,11 @@
                 </li>
                 <li>
                     {% get_current_language as LANGUAGE_CODE %}
-
+                    {% if LANGUAGE_CODE == 'en-us'%}
+                        <a href="{% change_lang 'de' %}"><i class="fa fa-fw fa-globe" aria-hidden="true"></i>&nbsp;&nbsp;Deutsch</a>
+                    {% else %}
+                        <a href="{% change_lang 'en-us' %}"><i class="fa fa-fw fa-globe" aria-hidden="true"></i>&nbsp;&nbsp;English</a>
+                    {% endif %}
                 </li>
             </ul>
         </div>
diff --git a/hosting/views.py b/hosting/views.py
index 20c2cc78..4d2d4f42 100644
--- a/hosting/views.py
+++ b/hosting/views.py
@@ -698,7 +698,7 @@ class OrdersHostingDetailView(LoginRequiredMixin,
                 'last4')
             context['cc_brand'] = card_details.get('response_object').get(
                 'cc_brand')
-            context['vm'] = request.session.get('specs')
+            context['vm'] = self.request.session.get('specs')
         return context
 
     def post(self, request):
@@ -776,8 +776,8 @@ class OrdersHostingDetailView(LoginRequiredMixin,
             'redirect': reverse('hosting:virtual_machines'),
             'msg_title': str(_('Thank you for the order.')),
             'msg_body': str(_('Your VM will be up and running in a few moments.'
-                          ' We will send you a confirmation email as soon as'
-                          ' it is ready.'))
+                              ' We will send you a confirmation email as soon as'
+                              ' it is ready.'))
         }
 
         return HttpResponse(json.dumps(response),

From 5d8fb712153feffe5c7d31f49d53a256af1db264 Mon Sep 17 00:00:00 2001
From: Arvind Tiwari <tiwariav@gmail.com>
Date: Thu, 21 Sep 2017 16:38:54 +0530
Subject: [PATCH 44/82] removed redirects form get_context() to get()

---
 hosting/views.py | 64 ++++++++++++++++++++++++++++++------------------
 1 file changed, 40 insertions(+), 24 deletions(-)

diff --git a/hosting/views.py b/hosting/views.py
index 4d2d4f42..cbb2be1f 100644
--- a/hosting/views.py
+++ b/hosting/views.py
@@ -652,46 +652,42 @@ class OrdersHostingDetailView(LoginRequiredMixin,
         context = super(DetailView, self).get_context_data(**kwargs)
         obj = self.get_object()
         owner = self.request.user
-        if 'specs' not in self.request.session:
-            return HttpResponseRedirect(
-                reverse('hosting:create_virtual_machine'))
-        if 'token' not in self.request.session:
-            return HttpResponseRedirect(reverse('hosting:payment'))
         stripe_customer_id = self.request.session.get('customer')
         customer = StripeCustomer.objects.filter(id=stripe_customer_id).first()
         stripe_utils = StripeUtils()
-        card_details = stripe_utils.get_card_details(customer.stripe_id,
-                                                     self.request.session.get(
-                                                         'token'))
-        if not card_details.get('response_object'):
-            msg = card_details.get('error')
-            messages.add_message(self.request, messages.ERROR, msg,
-                                 extra_tags='failed_payment')
-            return HttpResponseRedirect(
-                reverse('hosting:payment') + '#payment_error')
+        card_details = stripe_utils.get_card_details(
+            customer.stripe_id,
+            self.request.session.get('token')
+        )
 
-        if self.request.GET.get('page', '') == 'payment':
+        if self.request.GET.get('page') == 'payment':
             context['page_header_text'] = _('Confirm Order')
         else:
             context['page_header_text'] = _('Invoice')
 
         if obj is not None:
             try:
-                manager = OpenNebulaManager(email=owner.email,
-                                            password=owner.password)
+                manager = OpenNebulaManager(
+                    email=owner.email, password=owner.password
+                )
                 vm = manager.get_vm(obj.vm_id)
                 context['vm'] = VirtualMachineSerializer(vm).data
             except WrongIdError:
-                messages.error(self.request,
-                               'The VM you are looking for is unavailable at the moment. \
-                                Please contact Data Center Light support.'
-                               )
+                messages.error(
+                    self.request,
+                    'The VM you are looking for is unavailable at the moment. \
+                     Please contact Data Center Light support.'
+                )
                 self.kwargs['error'] = 'WrongIdError'
                 context['error'] = 'WrongIdError'
             except ConnectionRefusedError:
-                messages.error(self.request,
-                               'In order to create a VM, you need to create/upload your SSH KEY first.'
-                               )
+                messages.error(
+                    self.request,
+                    'In order to create a VM, you need to create/upload your SSH KEY first.'
+                )
+        elif not card_details.get('response_object'):
+            context['failed_payment'] = True
+            context['card_details'] = card_details
         else:
             context['site_url'] = reverse('hosting:create_virtual_machine')
             context['cc_last4'] = card_details.get('response_object').get(
@@ -701,6 +697,26 @@ class OrdersHostingDetailView(LoginRequiredMixin,
             context['vm'] = self.request.session.get('specs')
         return context
 
+    def get(self, request, *args, **kwargs):
+        if 'specs' not in self.request.session:
+            return HttpResponseRedirect(
+                reverse('hosting:create_virtual_machine')
+            )
+        if 'token' not in self.request.session:
+            return HttpResponseRedirect(reverse('hosting:payment'))
+        self.object = self.get_object()
+        context = self.get_context_data(object=self.object)
+        if 'failed_payment' in context:
+            msg = context['card_details'].get('error')
+            messages.add_message(
+                self.request, messages.ERROR, msg,
+                extra_tags='failed_payment'
+            )
+            return HttpResponseRedirect(
+                reverse('hosting:payment') + '#payment_error'
+            )
+        return self.render_to_response(context)
+
     def post(self, request):
         template = request.session.get('template')
         specs = request.session.get('specs')

From a792911dea8872da79ae96016551a962f2ba0a47 Mon Sep 17 00:00:00 2001
From: Arvind Tiwari <tiwariav@gmail.com>
Date: Thu, 21 Sep 2017 17:22:02 +0530
Subject: [PATCH 45/82] hosting view fix

---
 hosting/templates/hosting/order_detail.html | 25 ++++++++++----------
 hosting/views.py                            | 26 +++++++++++++--------
 2 files changed, 28 insertions(+), 23 deletions(-)

diff --git a/hosting/templates/hosting/order_detail.html b/hosting/templates/hosting/order_detail.html
index 49f7ba6b..3ee79eaa 100644
--- a/hosting/templates/hosting/order_detail.html
+++ b/hosting/templates/hosting/order_detail.html
@@ -4,7 +4,7 @@
 {% load custom_tags %}
 
 {% block content %}
-
+{{order.pk}}
 <div id="order-detail{{order.pk}}" class="order-detail-container">
     {% if messages %}
         <div class="alert alert-warning">
@@ -25,10 +25,10 @@
         </div>
         <div class="order-details">
             {% if order %}
-            {% endif %}
                 <p>
                     <strong>{% trans "Order #" %} {{order.id}}</strong>
                 </p>
+            {% endif %}
             <p>
                 <strong>{% trans "Invoice Date" %}:</strong>
                 <span id="order-created_at">
@@ -40,18 +40,17 @@
                 </span>
             </p>
             {% if order %}
-
+                <p>
+                    <strong>{% trans "Status" %}: </strong>
+                    <strong>
+                        {% if order.status == 'Approved' %}
+                            <span class="vm-color-online">{% trans "Approved" %}</span>
+                        {% else %}
+                            <span class="vm-status-failed">{% trans "Declined" %}</span>
+                        {% endif %}
+                    </strong>
+                </p>
             {% endif %}
-            <p>
-                <strong>{% trans "Status" %}: </strong>
-                <strong>
-                    {% if order.status == 'Approved' %}
-                        <span class="vm-color-online">{% trans "Approved" %}</span>
-                    {% else %}
-                        <span class="vm-status-failed">{% trans "Declined" %}</span>
-                    {% endif %}
-                </strong>
-            </p>
             <hr>
             <div>
                 <address>
diff --git a/hosting/views.py b/hosting/views.py
index cbb2be1f..13b9fd80 100644
--- a/hosting/views.py
+++ b/hosting/views.py
@@ -655,10 +655,13 @@ class OrdersHostingDetailView(LoginRequiredMixin,
         stripe_customer_id = self.request.session.get('customer')
         customer = StripeCustomer.objects.filter(id=stripe_customer_id).first()
         stripe_utils = StripeUtils()
-        card_details = stripe_utils.get_card_details(
-            customer.stripe_id,
-            self.request.session.get('token')
-        )
+        if customer:
+            card_details = stripe_utils.get_card_details(
+                customer.stripe_id,
+                self.request.session.get('token')
+            )
+        else:
+            card_details = None
 
         if self.request.GET.get('page') == 'payment':
             context['page_header_text'] = _('Confirm Order')
@@ -666,6 +669,7 @@ class OrdersHostingDetailView(LoginRequiredMixin,
             context['page_header_text'] = _('Invoice')
 
         if obj is not None:
+            # invoice for previous order
             try:
                 manager = OpenNebulaManager(
                     email=owner.email, password=owner.password
@@ -686,9 +690,11 @@ class OrdersHostingDetailView(LoginRequiredMixin,
                     'In order to create a VM, you need to create/upload your SSH KEY first.'
                 )
         elif not card_details.get('response_object'):
+            # new order, failed to get card details
             context['failed_payment'] = True
             context['card_details'] = card_details
         else:
+            # new order, confirm payment
             context['site_url'] = reverse('hosting:create_virtual_machine')
             context['cc_last4'] = card_details.get('response_object').get(
                 'last4')
@@ -698,12 +704,12 @@ class OrdersHostingDetailView(LoginRequiredMixin,
         return context
 
     def get(self, request, *args, **kwargs):
-        if 'specs' not in self.request.session:
-            return HttpResponseRedirect(
-                reverse('hosting:create_virtual_machine')
-            )
-        if 'token' not in self.request.session:
-            return HttpResponseRedirect(reverse('hosting:payment'))
+        # if 'specs' not in self.request.session:
+        #     return HttpResponseRedirect(
+        #         reverse('hosting:create_virtual_machine')
+        #     )
+        # if 'token' not in self.request.session:
+        #     return HttpResponseRedirect(reverse('hosting:payment'))
         self.object = self.get_object()
         context = self.get_context_data(object=self.object)
         if 'failed_payment' in context:

From db3955ab94597b01f5cc404a5e00f7a0124ce964 Mon Sep 17 00:00:00 2001
From: Arvind Tiwari <tiwariav@gmail.com>
Date: Thu, 21 Sep 2017 17:45:12 +0530
Subject: [PATCH 46/82] error 500 fixed

---
 hosting/static/hosting/css/order.css        | 2 +-
 hosting/templates/hosting/order_detail.html | 4 ++--
 hosting/views.py                            | 2 +-
 3 files changed, 4 insertions(+), 4 deletions(-)

diff --git a/hosting/static/hosting/css/order.css b/hosting/static/hosting/css/order.css
index 0377bfac..8213610e 100644
--- a/hosting/static/hosting/css/order.css
+++ b/hosting/static/hosting/css/order.css
@@ -58,7 +58,7 @@
 .order-detail-container h4 {
     font-size: 16px;
     font-weight: bold;
-    margin-bottom: 15px;
+    margin-bottom: 10px;
 }
 
 .order-detail-container p {
diff --git a/hosting/templates/hosting/order_detail.html b/hosting/templates/hosting/order_detail.html
index 3ee79eaa..d5599fbe 100644
--- a/hosting/templates/hosting/order_detail.html
+++ b/hosting/templates/hosting/order_detail.html
@@ -96,12 +96,12 @@
                         {% comment %}
                         <p>
                             <span>{% trans "Period" %}</span>
-                            <span class="pull-right">{{vm.cpu}}</span>
+                            <span class="pull-right">{{}}</span>
                         </p>
                         {% endcomment %}
                         <p>
                             <span>{% trans "Cores" %}</span>
-                            <span class="pull-right">{{vm.cpu}}</span>
+                            <span class="pull-right">{{vm.cores}}</span>
                         </p>
                         <p>
                             <span>{% trans "Memory" %}</span>
diff --git a/hosting/views.py b/hosting/views.py
index 13b9fd80..0458464d 100644
--- a/hosting/views.py
+++ b/hosting/views.py
@@ -644,7 +644,7 @@ class OrdersHostingDetailView(LoginRequiredMixin,
     model = HostingOrder
 
     def get_object(self):
-        return HostingOrder.objects.filter(
+        return HostingOrder.objects.get(
             pk=self.kwargs.get('pk')) if self.kwargs.get('pk') else None
 
     def get_context_data(self, **kwargs):

From a16dbb50d8e1f9b2705c9f91bfa0b0d881046d86 Mon Sep 17 00:00:00 2001
From: Arvind Tiwari <tiwariav@gmail.com>
Date: Thu, 21 Sep 2017 19:17:10 +0530
Subject: [PATCH 47/82] design fixes

---
 hosting/static/hosting/css/order.css        | 22 ++++++++++++++++-----
 hosting/templates/hosting/order_detail.html | 10 +++++++---
 hosting/urls.py                             |  2 +-
 hosting/views.py                            | 14 ++++++-------
 4 files changed, 32 insertions(+), 16 deletions(-)

diff --git a/hosting/static/hosting/css/order.css b/hosting/static/hosting/css/order.css
index 8213610e..383b23f4 100644
--- a/hosting/static/hosting/css/order.css
+++ b/hosting/static/hosting/css/order.css
@@ -2,6 +2,10 @@
     max-width: 600px;
     margin: 100px auto 40px;
     border: 1px solid #ccc;
+    padding: 15px;
+}
+
+@media(min-width: 768px) {
     padding: 30px;
 }
 
@@ -42,9 +46,8 @@
     right: 0;
 }
 .order-detail-container .dashboard-container-options .svg-img {
-    height: 20px;
-    /* margin-right: 5px; */
-    width: 20px;
+    height: 22px;
+    width: 22px;
 }
 
 .order-detail-container .order-details {
@@ -52,7 +55,7 @@
 }
 
 .order-detail-container .order-details strong {
-    color: #777;
+    color: #595959;
 }
 
 .order-detail-container h4 {
@@ -75,4 +78,13 @@
         text-align: center;
         margin-top: 10px;
     }
-}
\ No newline at end of file
+    .order-detail-container .dashboard-container-options {
+        position: absolute;
+        top: 4px;
+        right: -4px;
+    }
+    .order-detail-container .dashboard-container-options .svg-img {
+        height: 16px;
+        width: 16px;
+    }
+}
diff --git a/hosting/templates/hosting/order_detail.html b/hosting/templates/hosting/order_detail.html
index d5599fbe..c4cf5892 100644
--- a/hosting/templates/hosting/order_detail.html
+++ b/hosting/templates/hosting/order_detail.html
@@ -81,7 +81,11 @@
                     {% else %}
                         {{cc_brand}} {% trans "ending in" %} ****
                         {{cc_last4}}<br>
-                        {{request.session.user.email}}
+                        {% if request.user.is_authenticated %}
+                            {{request.user.email}}
+                        {% else %}
+                            {{request.session.user.email}}
+                        {% endif %}
                     {% endif %}
                 </p>
             </div>
@@ -101,7 +105,7 @@
                         {% endcomment %}
                         <p>
                             <span>{% trans "Cores" %}</span>
-                            <span class="pull-right">{{vm.cores}}</span>
+                            <span class="pull-right">{{vm.cores|floatformat}}</span>
                         </p>
                         <p>
                             <span>{% trans "Memory" %}</span>
@@ -140,10 +144,10 @@
     {% endif %}
 </div>
 
+{% if order %}
     <div class="text-center" style="margin-bottom: 50px;">
         <a class="btn btn-vm-back" href="{% url 'hosting:orders' %}">{% trans "BACK TO LIST" %}</a>
     </div>
-{% if order %}
 {% endif %}
 
 {% if not order %}
diff --git a/hosting/urls.py b/hosting/urls.py
index bc14c3a6..a946fee1 100644
--- a/hosting/urls.py
+++ b/hosting/urls.py
@@ -12,7 +12,7 @@ from .views import (
 from django.views.generic import TemplateView
 
 urlpatterns = [
-    url(r'test/?$', TemplateView.as_view(template_name='hosting/order_detail.html')),
+    url(r'test/?$', TemplateView.as_view(template_name='hosting/order_detail.html'), name='test'),
     url(r'index/?$', IndexView.as_view(), name='index'),
     url(r'django/?$', DjangoHostingView.as_view(), name='djangohosting'),
     url(r'dashboard/?$', DashboardView.as_view(), name='dashboard'),
diff --git a/hosting/views.py b/hosting/views.py
index 0458464d..95304212 100644
--- a/hosting/views.py
+++ b/hosting/views.py
@@ -661,7 +661,7 @@ class OrdersHostingDetailView(LoginRequiredMixin,
                 self.request.session.get('token')
             )
         else:
-            card_details = None
+            card_details = {}
 
         if self.request.GET.get('page') == 'payment':
             context['page_header_text'] = _('Confirm Order')
@@ -704,12 +704,12 @@ class OrdersHostingDetailView(LoginRequiredMixin,
         return context
 
     def get(self, request, *args, **kwargs):
-        # if 'specs' not in self.request.session:
-        #     return HttpResponseRedirect(
-        #         reverse('hosting:create_virtual_machine')
-        #     )
-        # if 'token' not in self.request.session:
-        #     return HttpResponseRedirect(reverse('hosting:payment'))
+        if 'specs' not in self.request.session:
+            return HttpResponseRedirect(
+                reverse('hosting:create_virtual_machine')
+            )
+        if 'token' not in self.request.session:
+            return HttpResponseRedirect(reverse('hosting:payment'))
         self.object = self.get_object()
         context = self.get_context_data(object=self.object)
         if 'failed_payment' in context:

From 1c0f0da96eb3bb84d4adada1f563474c341bbd23 Mon Sep 17 00:00:00 2001
From: Arvind Tiwari <tiwariav@gmail.com>
Date: Thu, 21 Sep 2017 19:32:22 +0530
Subject: [PATCH 48/82] conditional texts

---
 hosting/locale/de/LC_MESSAGES/django.po     | 75 +++++++++++++++------
 hosting/templates/hosting/order_detail.html |  8 ++-
 hosting/urls.py                             |  3 +-
 hosting/views.py                            | 13 ++--
 4 files changed, 67 insertions(+), 32 deletions(-)

diff --git a/hosting/locale/de/LC_MESSAGES/django.po b/hosting/locale/de/LC_MESSAGES/django.po
index d684bec7..49ebedd2 100644
--- a/hosting/locale/de/LC_MESSAGES/django.po
+++ b/hosting/locale/de/LC_MESSAGES/django.po
@@ -8,7 +8,7 @@ msgid ""
 msgstr ""
 "Project-Id-Version: PACKAGE VERSION\n"
 "Report-Msgid-Bugs-To: \n"
-"POT-Creation-Date: 2017-09-14 12:27+0000\n"
+"POT-Creation-Date: 2017-09-21 19:20+0530\n"
 "PO-Revision-Date: YEAR-MO-DA HO:MI+ZONE\n"
 "Last-Translator: FULL NAME <EMAIL@ADDRESS>\n"
 "Language-Team: LANGUAGE <LL@li.org>\n"
@@ -321,10 +321,14 @@ msgstr "Als gelesen markieren"
 msgid "All notifications"
 msgstr "Alle Benachrichtigungen"
 
-msgid "Date"
-msgstr "Datum"
+#, python-format
+msgid "%(page_header_text)s"
+msgstr ""
 
-msgid "Status:"
+msgid "Invoice Date"
+msgstr "Rechnung Datum"
+
+msgid "Status"
 msgstr ""
 
 msgid "Approved"
@@ -333,10 +337,10 @@ msgstr "Akzeptiert"
 msgid "Declined"
 msgstr "Abgelehnt"
 
-msgid "Billed To:"
+msgid "Billed to"
 msgstr "Rechnungsadresse"
 
-msgid "Payment Method:"
+msgid "Payment method"
 msgstr "Bezahlmethode"
 
 msgid "ending in"
@@ -345,6 +349,9 @@ msgstr "endend in"
 msgid "Order summary"
 msgstr "Bestellungsübersicht"
 
+msgid "Product"
+msgstr ""
+
 msgid "Cores"
 msgstr "Prozessorkerne"
 
@@ -357,20 +364,40 @@ msgstr "Festplattenkapazität"
 msgid "Total"
 msgstr "Gesamt"
 
-msgid "Finish Configuration"
-msgstr "Konfiguration beenden"
+#, python-format
+msgid ""
+"By clicking \"Place order\" this plan will charge your credit card account "
+"with the fee of %(vm_price)sCHF/month"
+msgstr ""
+"Wenn Du \"bestellen\" auswählst, wird Deine Kreditkarte mit %(vm_price)sCHF "
+"pro Monat belastet"
+
+msgid "Place order"
+msgstr "Bestellen"
+
+msgid "BACK TO LIST"
+msgstr "ZURÜCK ZUR LISTE"
+
+msgid "Processing..."
+msgstr "Weiter..."
+
+msgid "Hold tight, we are processing your request"
+msgstr ""
+
+msgid "Some problem encountered. Please try again later."
+msgstr ""
 
 msgid "Order Nr."
 msgstr "Bestellung Nr."
 
+msgid "Date"
+msgstr "Datum"
+
 msgid "Amount"
 msgstr "Betrag"
 
-msgid "Status"
-msgstr ""
-
 msgid "See Invoice"
-msgstr "Rechnung"
+msgstr "Siehe Rechnung"
 
 msgid "Page"
 msgstr ""
@@ -555,9 +582,6 @@ msgstr "Wir sind hier, um Dir zu helfen!"
 msgid "CONTACT"
 msgstr "KONTACT"
 
-msgid "BACK TO LIST"
-msgstr "ZURÜCK ZUR LISTE"
-
 msgid "Terminate your Virtual Machine"
 msgstr "Deine Virtuelle Maschine beenden"
 
@@ -618,13 +642,17 @@ msgstr ""
 msgid "Invalid credit card"
 msgstr "Ungültige Kreditkarte"
 
-#, python-format
-msgid "Your New VM %(vm_name)s at Data Center Light"
-msgstr "Deine neue VM %(vm_name)s bei Data Center Light"
-
 msgid "Confirm Order"
 msgstr "Bestellung Bestätigen"
 
+msgid "Thank you for the order."
+msgstr "Danke für den Auftrag"
+
+msgid ""
+"Your VM will be up and running in a few moments. We will send you a "
+"confirmation email as soon as it is ready."
+msgstr ""
+
 msgid "In order to create a VM, you need to create/upload your SSH KEY first."
 msgstr ""
 "Um eine VM zu erstellen musst du zuerst einen SSH-Key erstellen / hochladen."
@@ -641,6 +669,12 @@ msgstr "VM Kündigung"
 msgid "VM %(VM_ID)s terminated successfully"
 msgstr "VM %(VM_ID)s erfolgreich beendet"
 
+#~ msgid "Finish Configuration"
+#~ msgstr "Konfiguration beenden"
+
+#~ msgid "Your New VM %(vm_name)s at Data Center Light"
+#~ msgstr "Deine neue VM %(vm_name)s bei Data Center Light"
+
 #~ msgid "My Virtual Machines"
 #~ msgstr "Meine virtuellen Maschinen"
 
@@ -734,9 +768,6 @@ msgstr "VM %(VM_ID)s erfolgreich beendet"
 #~ msgid "Payment Details"
 #~ msgstr "Rechnungsdetails"
 
-#~ msgid "Place Order"
-#~ msgstr "Bestelle"
-
 #~ msgid "CARD NUMBER"
 #~ msgstr "Kreditkartennummer"
 
diff --git a/hosting/templates/hosting/order_detail.html b/hosting/templates/hosting/order_detail.html
index c4cf5892..9466f396 100644
--- a/hosting/templates/hosting/order_detail.html
+++ b/hosting/templates/hosting/order_detail.html
@@ -79,7 +79,7 @@
                         {{order.last4}}<br>
                         {{user.email}}
                     {% else %}
-                        {{cc_brand}} {% trans "ending in" %} ****
+                        {{cc_brand|default:'Card'}} {% trans "ending in" %} ****
                         {{cc_last4}}<br>
                         {% if request.user.is_authenticated %}
                             {{request.user.email}}
@@ -105,7 +105,11 @@
                         {% endcomment %}
                         <p>
                             <span>{% trans "Cores" %}</span>
-                            <span class="pull-right">{{vm.cores|floatformat}}</span>
+                            {% if vm.cores %}
+                                <span class="pull-right">{{vm.cores|floatformat}}</span>
+                            {% else %}
+                                <span class="pull-right">{{vm.cpu|floatformat}}</span>
+                            {% endif %}
                         </p>
                         <p>
                             <span>{% trans "Memory" %}</span>
diff --git a/hosting/urls.py b/hosting/urls.py
index a946fee1..2868c717 100644
--- a/hosting/urls.py
+++ b/hosting/urls.py
@@ -9,10 +9,9 @@ from .views import (
     HostingPricingView, CreateVirtualMachinesView, HostingBillListView,
     HostingBillDetailView, SSHKeyDeleteView, SSHKeyCreateView, SSHKeyListView,
     SSHKeyChoiceView, DashboardView, SettingsView)
-from django.views.generic import TemplateView
+
 
 urlpatterns = [
-    url(r'test/?$', TemplateView.as_view(template_name='hosting/order_detail.html'), name='test'),
     url(r'index/?$', IndexView.as_view(), name='index'),
     url(r'django/?$', DjangoHostingView.as_view(), name='djangohosting'),
     url(r'dashboard/?$', DashboardView.as_view(), name='dashboard'),
diff --git a/hosting/views.py b/hosting/views.py
index 95304212..2f31442a 100644
--- a/hosting/views.py
+++ b/hosting/views.py
@@ -704,12 +704,13 @@ class OrdersHostingDetailView(LoginRequiredMixin,
         return context
 
     def get(self, request, *args, **kwargs):
-        if 'specs' not in self.request.session:
-            return HttpResponseRedirect(
-                reverse('hosting:create_virtual_machine')
-            )
-        if 'token' not in self.request.session:
-            return HttpResponseRedirect(reverse('hosting:payment'))
+        if not self.kwargs.get('pk'):
+            if 'specs' not in self.request.session:
+                return HttpResponseRedirect(
+                    reverse('hosting:create_virtual_machine')
+                )
+            if 'token' not in self.request.session:
+                return HttpResponseRedirect(reverse('hosting:payment'))
         self.object = self.get_object()
         context = self.get_context_data(object=self.object)
         if 'failed_payment' in context:

From 2b0dbfa1e50cdf97b3810872fe740152d9663a2e Mon Sep 17 00:00:00 2001
From: "M.Ravi" <mondi.ravi@gmail.com>
Date: Fri, 22 Sep 2017 08:47:42 +0200
Subject: [PATCH 49/82] Added /cms prefix to django-cms urls

---
 dynamicweb/urls.py | 14 ++++++++++----
 1 file changed, 10 insertions(+), 4 deletions(-)

diff --git a/dynamicweb/urls.py b/dynamicweb/urls.py
index 84f3fb3d..2adce271 100644
--- a/dynamicweb/urls.py
+++ b/dynamicweb/urls.py
@@ -5,7 +5,8 @@ from django.conf.urls.static import static
 from django.views import i18n, static as static_view
 
 from django.conf import settings
-from hosting.views import RailsHostingView, DjangoHostingView, NodeJSHostingView
+from hosting.views import RailsHostingView, DjangoHostingView, \
+    NodeJSHostingView
 from membership import urls as membership_urls
 from ungleich_page.views import LandingView
 from django.views.generic import RedirectView
@@ -49,9 +50,14 @@ urlpatterns += i18n_patterns(
         include('ungleich_page.urls',
                 namespace='ungleich_page'),
         name='ungleich_page'),
-    url(r'^blog/', include('ungleich.urls',
-                           namespace='ungleich')),
-    url(r'^', include('cms.urls'))
+    url(r'^cms/blog/',
+        include('ungleich.urls', namespace='ungleich')),
+    url(
+        r'^blog/(?P<year>\d{4})/(?P<month>\d{1,2})/(?P<day>\d{1,2})/(?P<slug>\w[-\w]*)/$',
+        RedirectView.as_view(pattern_name='ungleich:post-detail')),
+    url(r'^blog/|cms/$', RedirectView.as_view(
+        url=reverse_lazy('ungleich:post-list')), name='blog_list_view'),
+    url(r'^cms/', include('cms.urls')),
 )
 
 urlpatterns += [

From faa26a05dd8f66e726be5eb7cae03ad41f4ba79c Mon Sep 17 00:00:00 2001
From: "M.Ravi" <mondi.ravi@gmail.com>
Date: Fri, 22 Sep 2017 08:51:35 +0200
Subject: [PATCH 50/82] Reverted back some lines for preserving format

---
 dynamicweb/urls.py | 3 +--
 1 file changed, 1 insertion(+), 2 deletions(-)

diff --git a/dynamicweb/urls.py b/dynamicweb/urls.py
index 2adce271..699ce50b 100644
--- a/dynamicweb/urls.py
+++ b/dynamicweb/urls.py
@@ -5,8 +5,7 @@ from django.conf.urls.static import static
 from django.views import i18n, static as static_view
 
 from django.conf import settings
-from hosting.views import RailsHostingView, DjangoHostingView, \
-    NodeJSHostingView
+from hosting.views import RailsHostingView, DjangoHostingView, NodeJSHostingView
 from membership import urls as membership_urls
 from ungleich_page.views import LandingView
 from django.views.generic import RedirectView

From dec1f34250169b1e6ec1b4a8f1d70667365d67a4 Mon Sep 17 00:00:00 2001
From: PCoder <purple.coder@yahoo.co.uk>
Date: Sat, 23 Sep 2017 17:17:24 +0530
Subject: [PATCH 51/82] Updated Changelog with pre-1.2.3 text

---
 Changelog | 8 ++++++++
 1 file changed, 8 insertions(+)

diff --git a/Changelog b/Changelog
index 423517ee..ac3253f1 100644
--- a/Changelog
+++ b/Changelog
@@ -1,3 +1,11 @@
+Pre-changelog: 1.2.3 2017-09-20
+    * #3484: [dcl, hosting] Refactored account activation, password reset, VM order and cancellation email
+    * #3731: [dcl, hosting] Added cdist ssh key handler 
+    * #3628: [dcl] on hosting, VM is created at credit card info submit
+    * #3772: [dcl] Updated hosting app billing into monthly subscription and added new text and translations
+    * Feature: [cms, blog] Added /cms prefix for all the django-cms generated urls
+    * Bugfix: [dcl, hosting] added host to celery error mails
+    * Bugfix: [ungleich] Fixed wrong subdomain digitalglarus.ungleich.ch
 1.2.2: 2017-09-08
     * #3704: [hosting] Added my settings page
     * #3771: [datacenterlight] Fixed the inconsistency in navbar style in billing page and onward

From be0c50aa2f40de68a13f0fecb58cb6d2d429ff1c Mon Sep 17 00:00:00 2001
From: Arvind Tiwari <tiwariav@gmail.com>
Date: Sat, 23 Sep 2017 19:01:22 +0530
Subject: [PATCH 52/82] error msgs translation

---
 hosting/locale/de/LC_MESSAGES/django.po | 31 ++++++++++++++-----------
 hosting/views.py                        |  7 +++---
 2 files changed, 22 insertions(+), 16 deletions(-)

diff --git a/hosting/locale/de/LC_MESSAGES/django.po b/hosting/locale/de/LC_MESSAGES/django.po
index ad5c779d..7ad85a7d 100644
--- a/hosting/locale/de/LC_MESSAGES/django.po
+++ b/hosting/locale/de/LC_MESSAGES/django.po
@@ -8,7 +8,7 @@ msgid ""
 msgstr ""
 "Project-Id-Version: PACKAGE VERSION\n"
 "Report-Msgid-Bugs-To: \n"
-"POT-Creation-Date: 2017-09-21 19:20+0530\n"
+"POT-Creation-Date: 2017-09-23 19:00+0530\n"
 "PO-Revision-Date: YEAR-MO-DA HO:MI+ZONE\n"
 "Last-Translator: FULL NAME <EMAIL@ADDRESS>\n"
 "Language-Team: LANGUAGE <LL@li.org>\n"
@@ -361,15 +361,9 @@ msgstr "Arbeitsspeicher"
 msgid "Disk space"
 msgstr "Festplattenkapazität"
 
-msgid "Configuration"
-msgstr "Konfiguration"
-
 msgid "Total"
 msgstr "Gesamt"
 
-msgid "Month"
-msgstr "Monat"
-
 #, python-format
 msgid ""
 "By clicking \"Place order\" this plan will charge your credit card account "
@@ -414,9 +408,15 @@ msgstr ""
 msgid "Your Order"
 msgstr "Deine Bestellung"
 
+msgid "Configuration"
+msgstr "Konfiguration"
+
 msgid "including VAT"
 msgstr "inkl. Mehrwertsteuer"
 
+msgid "Month"
+msgstr "Monat"
+
 msgid "Billing Address"
 msgstr "Rechnungsadresse"
 
@@ -645,6 +645,15 @@ msgstr "Ungültige Kreditkarte"
 msgid "Confirm Order"
 msgstr "Bestellung Bestätigen"
 
+msgid ""
+"The VM you are looking for is unavailable at the moment. Please contact Data "
+"Center Light support."
+msgstr ""
+
+msgid "In order to create a VM, you need to create/upload your SSH KEY first."
+msgstr ""
+"Um eine VM zu erstellen musst du zuerst einen SSH-Key erstellen / hochladen."
+
 msgid "Thank you for the order."
 msgstr "Danke für Deine Bestellung."
 
@@ -652,12 +661,8 @@ msgid ""
 "Your VM will be up and running in a few moments. We will send you a "
 "confirmation email as soon as it is ready."
 msgstr ""
-"Deine VM ist gleich bereit. Wir senden Dir eine Bestätigungsemail, "
-"sobald Du auf sie zugreifen kannst."
-
-msgid "In order to create a VM, you need to create/upload your SSH KEY first."
-msgstr ""
-"Um eine VM zu erstellen musst du zuerst einen SSH-Key erstellen / hochladen."
+"Deine VM ist gleich bereit. Wir senden Dir eine Bestätigungsemail, sobald Du "
+"auf sie zugreifen kannst."
 
 msgid ""
 "We could not find the requested VM. Please                            "
diff --git a/hosting/views.py b/hosting/views.py
index 2f31442a..c736a576 100644
--- a/hosting/views.py
+++ b/hosting/views.py
@@ -679,15 +679,16 @@ class OrdersHostingDetailView(LoginRequiredMixin,
             except WrongIdError:
                 messages.error(
                     self.request,
-                    'The VM you are looking for is unavailable at the moment. \
-                     Please contact Data Center Light support.'
+                    _('The VM you are looking for is unavailable at the '
+                      'moment. Please contact Data Center Light support.')
                 )
                 self.kwargs['error'] = 'WrongIdError'
                 context['error'] = 'WrongIdError'
             except ConnectionRefusedError:
                 messages.error(
                     self.request,
-                    'In order to create a VM, you need to create/upload your SSH KEY first.'
+                    _('In order to create a VM, you need to create/upload '
+                      'your SSH KEY first.')
                 )
         elif not card_details.get('response_object'):
             # new order, failed to get card details

From 3685bf591dad6554a2130f0569a99d5b15729c5b Mon Sep 17 00:00:00 2001
From: Arvind Tiwari <tiwariav@gmail.com>
Date: Sat, 23 Sep 2017 19:02:23 +0530
Subject: [PATCH 53/82] error msgs translation

---
 hosting/locale/de/LC_MESSAGES/django.po | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/hosting/locale/de/LC_MESSAGES/django.po b/hosting/locale/de/LC_MESSAGES/django.po
index 7ad85a7d..37b29cbd 100644
--- a/hosting/locale/de/LC_MESSAGES/django.po
+++ b/hosting/locale/de/LC_MESSAGES/django.po
@@ -648,7 +648,7 @@ msgstr "Bestellung Bestätigen"
 msgid ""
 "The VM you are looking for is unavailable at the moment. Please contact Data "
 "Center Light support."
-msgstr ""
+msgstr "Kontaktiere den Data Center Light Support."
 
 msgid "In order to create a VM, you need to create/upload your SSH KEY first."
 msgstr ""

From e9721705ca1e72e592f218b4639263129dc30999 Mon Sep 17 00:00:00 2001
From: Arvind Tiwari <tiwariav@gmail.com>
Date: Sat, 23 Sep 2017 20:30:53 +0530
Subject: [PATCH 54/82] margin fix

---
 hosting/static/hosting/css/order.css        | 4 +++-
 hosting/templates/hosting/order_detail.html | 1 -
 2 files changed, 3 insertions(+), 2 deletions(-)

diff --git a/hosting/static/hosting/css/order.css b/hosting/static/hosting/css/order.css
index 383b23f4..8e9226e2 100644
--- a/hosting/static/hosting/css/order.css
+++ b/hosting/static/hosting/css/order.css
@@ -6,7 +6,9 @@
 }
 
 @media(min-width: 768px) {
-    padding: 30px;
+    .order-detail-container {
+        padding: 30px;
+    }
 }
 
 .order-detail-container .invoice-title h2, .invoice-title h3 {
diff --git a/hosting/templates/hosting/order_detail.html b/hosting/templates/hosting/order_detail.html
index 9466f396..345632d2 100644
--- a/hosting/templates/hosting/order_detail.html
+++ b/hosting/templates/hosting/order_detail.html
@@ -4,7 +4,6 @@
 {% load custom_tags %}
 
 {% block content %}
-{{order.pk}}
 <div id="order-detail{{order.pk}}" class="order-detail-container">
     {% if messages %}
         <div class="alert alert-warning">

From 487af6e1c825da3443882ea1faf880910d295d66 Mon Sep 17 00:00:00 2001
From: Arvind Tiwari <tiwariav@gmail.com>
Date: Sat, 23 Sep 2017 20:44:53 +0530
Subject: [PATCH 55/82] Update Changelog

---
 Changelog | 1 +
 1 file changed, 1 insertion(+)

diff --git a/Changelog b/Changelog
index ac3253f1..4bbcba4d 100644
--- a/Changelog
+++ b/Changelog
@@ -3,6 +3,7 @@ Pre-changelog: 1.2.3 2017-09-20
     * #3731: [dcl, hosting] Added cdist ssh key handler 
     * #3628: [dcl] on hosting, VM is created at credit card info submit
     * #3772: [dcl] Updated hosting app billing into monthly subscription and added new text and translations
+    * #3786: [hosting] Redesigned the hosting invoice and order-confirmation page
     * Feature: [cms, blog] Added /cms prefix for all the django-cms generated urls
     * Bugfix: [dcl, hosting] added host to celery error mails
     * Bugfix: [ungleich] Fixed wrong subdomain digitalglarus.ungleich.ch

From eca7ba01c583b053d75ad5aee34aeb06ad18c5c9 Mon Sep 17 00:00:00 2001
From: Arvind Tiwari <tiwariav@gmail.com>
Date: Sat, 23 Sep 2017 22:54:17 +0530
Subject: [PATCH 56/82] fixed duplicate translation

---
 hosting/locale/de/LC_MESSAGES/django.po | 3 ---
 1 file changed, 3 deletions(-)

diff --git a/hosting/locale/de/LC_MESSAGES/django.po b/hosting/locale/de/LC_MESSAGES/django.po
index 5231b04d..16babbfa 100644
--- a/hosting/locale/de/LC_MESSAGES/django.po
+++ b/hosting/locale/de/LC_MESSAGES/django.po
@@ -417,9 +417,6 @@ msgstr "Konfiguration"
 msgid "including VAT"
 msgstr "inkl. Mehrwertsteuer"
 
-msgid "Month"
-msgstr "Monat"
-
 msgid "Billing Address"
 msgstr "Rechnungsadresse"
 

From cd3fdcf9356c6bdf8f14d5a56fa769ba8d217e2e Mon Sep 17 00:00:00 2001
From: Arvind Tiwari <tiwariav@gmail.com>
Date: Sat, 23 Sep 2017 23:33:48 +0530
Subject: [PATCH 57/82] Updated pre-changelog 1.2.3

---
 Changelog | 2 ++
 1 file changed, 2 insertions(+)

diff --git a/Changelog b/Changelog
index 4bbcba4d..33184f98 100644
--- a/Changelog
+++ b/Changelog
@@ -4,6 +4,8 @@ Pre-changelog: 1.2.3 2017-09-20
     * #3628: [dcl] on hosting, VM is created at credit card info submit
     * #3772: [dcl] Updated hosting app billing into monthly subscription and added new text and translations
     * #3786: [hosting] Redesigned the hosting invoice and order-confirmation page
+    * #3728: [hosting] VM Termination animation added
+    * #3777: [hosting] Create new VM calculator added like dcl landing
     * Feature: [cms, blog] Added /cms prefix for all the django-cms generated urls
     * Bugfix: [dcl, hosting] added host to celery error mails
     * Bugfix: [ungleich] Fixed wrong subdomain digitalglarus.ungleich.ch

From 313b2b2f576a741f3fa2e161ad24e1f1e02083d7 Mon Sep 17 00:00:00 2001
From: Arvind Tiwari <tiwariav@gmail.com>
Date: Sat, 23 Sep 2017 23:47:25 +0530
Subject: [PATCH 58/82] fixed vreate vm error

---
 hosting/views.py | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/hosting/views.py b/hosting/views.py
index d7c4c168..e0fe041e 100644
--- a/hosting/views.py
+++ b/hosting/views.py
@@ -17,7 +17,7 @@ from django.shortcuts import redirect, render
 from django.utils.http import urlsafe_base64_decode
 from django.utils.safestring import mark_safe
 from django.utils.translation import ugettext_lazy as _
-from django.utils.translation import ugettext
+from django.utils.translation import ugettext, get_language
 from django.views.generic import (
     View, CreateView, FormView, ListView, DetailView, DeleteView,
     TemplateView, UpdateView

From afc368e9dd6cf470a3aaa547a5f6a63e2768e816 Mon Sep 17 00:00:00 2001
From: PCoder <purple.coder@yahoo.co.uk>
Date: Sun, 24 Sep 2017 15:49:40 +0530
Subject: [PATCH 59/82] Added ResendActivationEmailView

---
 hosting/views.py | 17 ++++++++++++++---
 1 file changed, 14 insertions(+), 3 deletions(-)

diff --git a/hosting/views.py b/hosting/views.py
index d7c4c168..02e68bbd 100644
--- a/hosting/views.py
+++ b/hosting/views.py
@@ -33,12 +33,15 @@ from membership.models import CustomUser, StripeCustomer
 from opennebula_api.models import OpenNebulaManager
 from opennebula_api.serializers import VirtualMachineSerializer, \
     VirtualMachineTemplateSerializer, VMTemplateSerializer
-from utils.forms import BillingAddressForm, PasswordResetRequestForm, \
-    UserBillingAddressForm
+from utils.forms import (
+    BillingAddressForm, PasswordResetRequestForm, UserBillingAddressForm,
+    ResendActivationEmailForm
+)
 from utils.mailer import BaseEmail
 from utils.stripe_utils import StripeUtils
 from utils.views import (
-    PasswordResetViewMixin, PasswordResetConfirmViewMixin, LoginViewMixin
+    PasswordResetViewMixin, PasswordResetConfirmViewMixin, LoginViewMixin,
+    ResendActivationLinkViewMixin
 )
 from .forms import HostingUserSignupForm, HostingUserLoginForm, \
     UserHostingKeyForm, generate_ssh_key_name
@@ -282,6 +285,14 @@ class SignupValidatedView(SignupValidateView):
         return context
 
 
+class ResendActivationEmailView(ResendActivationLinkViewMixin):
+    template_name = 'hosting/resend_activation_link.html'
+    form_class = ResendActivationEmailForm
+    success_url = reverse_lazy('hosting:login')
+    email_template_path = 'datacenterlight/emails/'
+    email_template_name = 'user_activation'
+
+
 class PasswordResetView(PasswordResetViewMixin):
     site = 'dcl'
     template_name = 'hosting/reset_password.html'

From 324761613752d77a2824df67feec22047b445722 Mon Sep 17 00:00:00 2001
From: PCoder <purple.coder@yahoo.co.uk>
Date: Sun, 24 Sep 2017 15:53:08 +0530
Subject: [PATCH 60/82] Added resend activation link url

---
 hosting/urls.py | 5 +++--
 1 file changed, 3 insertions(+), 2 deletions(-)

diff --git a/hosting/urls.py b/hosting/urls.py
index 2868c717..f40e803a 100644
--- a/hosting/urls.py
+++ b/hosting/urls.py
@@ -8,8 +8,7 @@ from .views import (
     MarkAsReadNotificationView, PasswordResetView, PasswordResetConfirmView,
     HostingPricingView, CreateVirtualMachinesView, HostingBillListView,
     HostingBillDetailView, SSHKeyDeleteView, SSHKeyCreateView, SSHKeyListView,
-    SSHKeyChoiceView, DashboardView, SettingsView)
-
+    SSHKeyChoiceView, DashboardView, SettingsView, ResendActivationEmailView)
 
 urlpatterns = [
     url(r'index/?$', IndexView.as_view(), name='index'),
@@ -52,6 +51,8 @@ urlpatterns = [
     url(r'signup/?$', SignupView.as_view(), name='signup'),
     url(r'signup-validate/?$', SignupValidateView.as_view(),
         name='signup-validate'),
+    url(r'resend-activation-link/?$', ResendActivationEmailView.as_view(),
+        name='resend_activation_link'),
     url(r'reset-password/?$', PasswordResetView.as_view(),
         name='reset_password'),
     url(r'reset-password-confirm/(?P<uidb64>[0-9A-Za-z]+)-(?P<token>.+)/$',

From af426c5b7a19f943f95a174f51924c5d52360c78 Mon Sep 17 00:00:00 2001
From: PCoder <purple.coder@yahoo.co.uk>
Date: Sun, 24 Sep 2017 15:54:38 +0530
Subject: [PATCH 61/82] Added ResendActivationEmailForm and translation
 function to untranslated texts

---
 utils/forms.py | 32 +++++++++++++++++++++++++-------
 1 file changed, 25 insertions(+), 7 deletions(-)

diff --git a/utils/forms.py b/utils/forms.py
index c3f3b6db..a12034dd 100644
--- a/utils/forms.py
+++ b/utils/forms.py
@@ -18,7 +18,8 @@ class SignupFormMixin(forms.ModelForm):
         model = CustomUser
         fields = ['name', 'email', 'password']
         widgets = {
-            'name': forms.TextInput(attrs={'placeholder': _('Enter your name or company name')}),
+            'name': forms.TextInput(
+                attrs={'placeholder': _('Enter your name or company name')}),
         }
 
     def clean_confirm_password(self):
@@ -42,7 +43,7 @@ class LoginFormMixin(forms.Form):
         is_auth = authenticate(email=email, password=password)
         if not is_auth:
             raise forms.ValidationError(
-                "Your username and/or password were incorrect.")
+                _("Your username and/or password were incorrect."))
         return self.cleaned_data
 
     def clean_email(self):
@@ -51,7 +52,24 @@ class LoginFormMixin(forms.Form):
             CustomUser.objects.get(email=email)
             return email
         except CustomUser.DoesNotExist:
-            raise forms.ValidationError("User does not exist")
+            raise forms.ValidationError(_("User does not exist"))
+
+
+class ResendActivationEmailForm(forms.Form):
+    email = forms.CharField(widget=forms.EmailInput())
+
+    class Meta:
+        fields = ['email']
+
+    def clean_email(self):
+        email = self.cleaned_data.get('email')
+        try:
+            c = CustomUser.objects.get(email=email)
+            if c.validated == 1:
+                raise forms.ValidationError(_("The account is already active."))
+            return email
+        except CustomUser.DoesNotExist:
+            raise forms.ValidationError(_("User does not exist"))
 
 
 class PasswordResetRequestForm(forms.Form):
@@ -66,7 +84,7 @@ class PasswordResetRequestForm(forms.Form):
             CustomUser.objects.get(email=email)
             return email
         except CustomUser.DoesNotExist:
-            raise forms.ValidationError("User does not exist")
+            raise forms.ValidationError(_("User does not exist"))
 
 
 class SetPasswordForm(forms.Form):
@@ -75,11 +93,11 @@ class SetPasswordForm(forms.Form):
     password
     """
     error_messages = {
-        'password_mismatch': ("The two password fields didn't match."),
+        'password_mismatch': _("The two password fields didn't match."),
     }
-    new_password1 = forms.CharField(label=("New password"),
+    new_password1 = forms.CharField(label=_("New password"),
                                     widget=forms.PasswordInput)
-    new_password2 = forms.CharField(label=("New password confirmation"),
+    new_password2 = forms.CharField(label=_("New password confirmation"),
                                     widget=forms.PasswordInput)
 
     def clean_new_password2(self):

From 3e32e5127be5eebc9107edd7c791ad3f87f9a1c9 Mon Sep 17 00:00:00 2001
From: PCoder <purple.coder@yahoo.co.uk>
Date: Sun, 24 Sep 2017 15:55:52 +0530
Subject: [PATCH 62/82] Added ResendActivationLinkViewMixin

---
 utils/views.py | 45 +++++++++++++++++++++++++++++++++++++++------
 1 file changed, 39 insertions(+), 6 deletions(-)

diff --git a/utils/views.py b/utils/views.py
index 3150fa6d..4ec39bce 100644
--- a/utils/views.py
+++ b/utils/views.py
@@ -2,6 +2,7 @@ from django.conf import settings
 from django.contrib import messages
 from django.contrib.auth import authenticate, login
 from django.contrib.auth.tokens import default_token_generator
+from django.core.urlresolvers import reverse_lazy
 from django.http import HttpResponseRedirect
 from django.utils.encoding import force_bytes
 from django.utils.http import urlsafe_base64_encode, urlsafe_base64_decode
@@ -63,9 +64,45 @@ class LoginViewMixin(FormView):
         return super(LoginViewMixin, self).get(request, *args, **kwargs)
 
 
+class ResendActivationLinkViewMixin(FormView):
+    success_message = _(
+        "An email with the activation link has been sent to your email")
+
+    def generate_email_context(self, user):
+        context = {
+            'base_url': "{0}://{1}".format(self.request.scheme,
+                                           self.request.get_host()),
+            'activation_link': reverse_lazy(
+                'hosting:validate',
+                kwargs={'validate_slug': user.validation_slug}
+            ),
+            'dcl_text': settings.DCL_TEXT,
+        }
+        return context
+
+    def form_valid(self, form):
+        email = form.cleaned_data.get('email')
+        user = CustomUser.objects.get(email=email)
+        messages.add_message(self.request, messages.SUCCESS,
+                             self.success_message)
+        context = self.generate_email_context(user)
+        email_data = {
+            'subject': '{dcl_text} {account_activation}'.format(
+                dcl_text=settings.DCL_TEXT,
+                account_activation=_('Account Activation')
+            ),
+            'to': email,
+            'context': context,
+            'template_name': self.email_template_name,
+            'template_path': self.email_template_path,
+            'from_address': settings.DCL_SUPPORT_FROM_ADDRESS
+        }
+        email = BaseEmail(**email_data)
+        email.send()
+        return HttpResponseRedirect(self.get_success_url())
+
+
 class PasswordResetViewMixin(FormView):
-    # template_name = 'hosting/reset_password.html'
-    # form_class = PasswordResetRequestForm
     success_message = _(
         "The link to reset your email has been sent to your email")
     site = ''
@@ -78,7 +115,6 @@ class PasswordResetViewMixin(FormView):
             'site_name': 'ungleich' if self.site != 'dcl' else settings.DCL_TEXT,
             'base_url': "{0}://{1}".format(self.request.scheme,
                                            self.request.get_host())
-
         }
         return context
 
@@ -104,11 +140,8 @@ class PasswordResetViewMixin(FormView):
 
 
 class PasswordResetConfirmViewMixin(FormView):
-    # template_name = 'hosting/confirm_reset_password.html'
     form_class = SetPasswordForm
 
-    # success_url = reverse_lazy('hosting:login')
-
     def post(self, request, uidb64=None, token=None, *arg, **kwargs):
         try:
             uid = urlsafe_base64_decode(uidb64)

From 24522908e0332b6135fadc7c789df662a591d85f Mon Sep 17 00:00:00 2001
From: PCoder <purple.coder@yahoo.co.uk>
Date: Sun, 24 Sep 2017 16:02:06 +0530
Subject: [PATCH 63/82] Added resend activation link to login page

---
 hosting/templates/hosting/login.html | 2 ++
 1 file changed, 2 insertions(+)

diff --git a/hosting/templates/hosting/login.html b/hosting/templates/hosting/login.html
index 9f18fda9..82056d2f 100644
--- a/hosting/templates/hosting/login.html
+++ b/hosting/templates/hosting/login.html
@@ -44,6 +44,8 @@
                         <a class="unlink" href="{% url 'hosting:signup' %}">{% trans "Sign up"%}</a>
                         <span class="text"> or </span>
                         <a class="unlink" href="{% url 'hosting:reset_password' %}">{% trans "Forgot your password ? "%}</a>
+                        <span class="text"> or </span><br/>
+                        <a class="unlink" href="{% url 'hosting:resend_activation_link' %}">{% trans "Resend activation link"%}</a>
                     </div>
                 </div>
             </div>

From 84db1606a346707ec50464a5c7d9dd16a95ffec1 Mon Sep 17 00:00:00 2001
From: PCoder <purple.coder@yahoo.co.uk>
Date: Sun, 24 Sep 2017 18:04:11 +0530
Subject: [PATCH 64/82] Added resend_activation_link.html template file

---
 .../hosting/resend_activation_link.html       | 36 +++++++++++++++++++
 1 file changed, 36 insertions(+)
 create mode 100644 hosting/templates/hosting/resend_activation_link.html

diff --git a/hosting/templates/hosting/resend_activation_link.html b/hosting/templates/hosting/resend_activation_link.html
new file mode 100644
index 00000000..fffb6e59
--- /dev/null
+++ b/hosting/templates/hosting/resend_activation_link.html
@@ -0,0 +1,36 @@
+{% extends "hosting/base_short.html" %}
+{% load staticfiles bootstrap3%}
+{% load i18n %}
+
+{% block navbar %}
+    {% include  'hosting/includes/_navbar_transparent.html' %}
+{% endblock navbar %}
+
+
+{% block content %}
+<div class="auth-container">
+   <div class="auth-bg"></div>
+        <div class="auth-center">
+            <div class="auth-title">
+                <h2>{% trans "Your VM hosted in Switzerland"%}</h2>
+            </div>
+            <div class="auth-content">
+                <div class="intro-message auth-box sign-up">
+                    <h2  class="section-heading">{% trans "Resend activation link"%}</h2>
+                    <form action="{% url 'hosting:resend_activation_link' %}" method="post" class="form" novalidate>
+                        {% csrf_token %}
+                        {% for field in form %}
+                            {% bootstrap_field field show_label=False %}
+                        {% endfor %}
+                        {% buttons %}
+                            <button type="submit" class="btn btn-block btn-success">
+                                {% trans "Submit"%}
+                            </button>
+                        {% endbuttons %}
+                    </form>
+
+                </div>
+            </div>
+        </div>
+</div>
+{% endblock %}

From cd5607b44e9f062707450601026e99fcdf9f0246 Mon Sep 17 00:00:00 2001
From: PCoder <purple.coder@yahoo.co.uk>
Date: Sun, 24 Sep 2017 19:04:18 +0530
Subject: [PATCH 65/82] Updated hosting django.po

---
 hosting/locale/de/LC_MESSAGES/django.po | 12 +++++++++---
 1 file changed, 9 insertions(+), 3 deletions(-)

diff --git a/hosting/locale/de/LC_MESSAGES/django.po b/hosting/locale/de/LC_MESSAGES/django.po
index b273dbcf..0db6580d 100644
--- a/hosting/locale/de/LC_MESSAGES/django.po
+++ b/hosting/locale/de/LC_MESSAGES/django.po
@@ -8,7 +8,7 @@ msgid ""
 msgstr ""
 "Project-Id-Version: PACKAGE VERSION\n"
 "Report-Msgid-Bugs-To: \n"
-"POT-Creation-Date: 2017-09-23 19:00+0530\n"
+"POT-Creation-Date: 2017-09-24 12:34+0000\n"
 "PO-Revision-Date: YEAR-MO-DA HO:MI+ZONE\n"
 "Last-Translator: FULL NAME <EMAIL@ADDRESS>\n"
 "Language-Team: LANGUAGE <LL@li.org>\n"
@@ -306,6 +306,9 @@ msgstr "Registrieren"
 msgid "Forgot your password ? "
 msgstr "Passwort vergessen?"
 
+msgid "Resend activation link"
+msgstr ""
+
 msgid "Notifications"
 msgstr "Benachrichtigungen"
 
@@ -601,8 +604,11 @@ msgstr ""
 
 #, python-format
 msgid ""
-"Your Virtual Machine %(virtual_machine.name)s is successfully terminated!"
-msgstr "Deine Virtuelle Machine (VM) %(virtual_machine.name)s wurde erfolgreich beendet!"
+"Your Virtual Machine <strong>%(machine_name)s</strong> is successfully "
+"terminated!"
+msgstr ""
+"Deine Virtuelle Machine (VM) <strong>%(machine_name)s</strong> wurde erfolgreich "
+"beendet!"
 
 msgid "Virtual Machines"
 msgstr "Virtuelle Maschinen"

From 70d5efb21a230c53de61f1c51219a75567d63d5f Mon Sep 17 00:00:00 2001
From: PCoder <purple.coder@yahoo.co.uk>
Date: Mon, 25 Sep 2017 02:09:49 +0530
Subject: [PATCH 66/82] Update hosting django.po with a de translation

---
 hosting/locale/de/LC_MESSAGES/django.po | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/hosting/locale/de/LC_MESSAGES/django.po b/hosting/locale/de/LC_MESSAGES/django.po
index 0db6580d..ec11986b 100644
--- a/hosting/locale/de/LC_MESSAGES/django.po
+++ b/hosting/locale/de/LC_MESSAGES/django.po
@@ -307,7 +307,7 @@ msgid "Forgot your password ? "
 msgstr "Passwort vergessen?"
 
 msgid "Resend activation link"
-msgstr ""
+msgstr "Aktivierungslink noch einmal senden"
 
 msgid "Notifications"
 msgstr "Benachrichtigungen"

From a73bcaef05053ee585fe5d08e03716ab964bc0f2 Mon Sep 17 00:00:00 2001
From: "M.Ravi" <mondi.ravi@gmail.com>
Date: Mon, 25 Sep 2017 09:35:18 +0200
Subject: [PATCH 67/82] Store hash

---
 hosting/views.py         | 2 +-
 opennebula_api/models.py | 4 ++--
 2 files changed, 3 insertions(+), 3 deletions(-)

diff --git a/hosting/views.py b/hosting/views.py
index d7c4c168..887a4bb6 100644
--- a/hosting/views.py
+++ b/hosting/views.py
@@ -319,7 +319,7 @@ class PasswordResetConfirmView(PasswordResetConfirmViewMixin):
                 messages.success(request, _('Password has been reset.'))
 
                 # Change opennebula password
-                opennebula_client.change_user_password(new_password)
+                opennebula_client.change_user_password(user.password)
 
                 return self.form_valid(form)
             else:
diff --git a/opennebula_api/models.py b/opennebula_api/models.py
index d584bf26..057139c0 100644
--- a/opennebula_api/models.py
+++ b/opennebula_api/models.py
@@ -438,11 +438,11 @@ class OpenNebulaManager():
         self.oneadmin_client.call(oca.VmTemplate.METHODS[
                                       'delete'], template_id, False)
 
-    def change_user_password(self, new_password):
+    def change_user_password(self, passwd_hash):
         self.oneadmin_client.call(
             oca.User.METHODS['passwd'],
             self.opennebula_user.id,
-            new_password
+            passwd_hash
         )
 
     def add_public_key(self, user, public_key='', merge=False):

From 04c29d0622f491641f0633c3054d49164fe86495 Mon Sep 17 00:00:00 2001
From: verysanghee <verysanghee@gmail.com>
Date: Mon, 25 Sep 2017 20:17:12 +0200
Subject: [PATCH 68/82] Update django.po

---
 utils/locale/de/LC_MESSAGES/django.po | 8 ++++----
 1 file changed, 4 insertions(+), 4 deletions(-)

diff --git a/utils/locale/de/LC_MESSAGES/django.po b/utils/locale/de/LC_MESSAGES/django.po
index fdc21502..92593c40 100644
--- a/utils/locale/de/LC_MESSAGES/django.po
+++ b/utils/locale/de/LC_MESSAGES/django.po
@@ -772,13 +772,13 @@ msgid "The link to reset your email has been sent to your email"
 msgstr "Der Link zum Zur?cksetzen deines Passwortes wurde an deine E-Mail gesendet"
 
 msgid "Password Reset"
-msgstr ""
+msgstr "Passwort zurücksetzen"
 
 msgid "Password has been reset."
-msgstr "Das Passwort wurde zur?ckgesetzt."
+msgstr "Das Passwort wurde zurückgesetzt."
 
 msgid "Password reset has not been successful."
-msgstr "Das Zur?cksetzen war nicht erfolgreich."
+msgstr "Das Zurücksetzen war nicht erfolgreich."
 
 msgid "The reset password link is no longer valid."
-msgstr "Der Link zum Zur?cksetzen deines Passwortes ist nicht l?nger g?ltig."
+msgstr "Der Link zum Zurücksetzen Deines Passwortes ist nicht länger gültig."

From bb8c1a72fde2f7da13cfbc63e6abb08637b16b8f Mon Sep 17 00:00:00 2001
From: PCoder <purple.coder@yahoo.co.uk>
Date: Mon, 25 Sep 2017 23:52:40 +0530
Subject: [PATCH 69/82] Add missing import get_language

---
 hosting/views.py | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/hosting/views.py b/hosting/views.py
index d7c4c168..7ce66e57 100644
--- a/hosting/views.py
+++ b/hosting/views.py
@@ -16,7 +16,7 @@ from django.http import Http404, HttpResponseRedirect, HttpResponse
 from django.shortcuts import redirect, render
 from django.utils.http import urlsafe_base64_decode
 from django.utils.safestring import mark_safe
-from django.utils.translation import ugettext_lazy as _
+from django.utils.translation import get_language, ugettext_lazy as _
 from django.utils.translation import ugettext
 from django.views.generic import (
     View, CreateView, FormView, ListView, DetailView, DeleteView,

From c2844d25ed53ee5b1834b2bc47176698cc05c9b4 Mon Sep 17 00:00:00 2001
From: PCoder <purple.coder@yahoo.co.uk>
Date: Tue, 26 Sep 2017 00:06:17 +0530
Subject: [PATCH 70/82] Corrected a de spelling

---
 utils/locale/de/LC_MESSAGES/django.po | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/utils/locale/de/LC_MESSAGES/django.po b/utils/locale/de/LC_MESSAGES/django.po
index 92593c40..794b5fd9 100644
--- a/utils/locale/de/LC_MESSAGES/django.po
+++ b/utils/locale/de/LC_MESSAGES/django.po
@@ -769,7 +769,7 @@ msgid "Message"
 msgstr "Nachricht"
 
 msgid "The link to reset your email has been sent to your email"
-msgstr "Der Link zum Zur?cksetzen deines Passwortes wurde an deine E-Mail gesendet"
+msgstr "Der Link zum Zurücksetzen deines Passwortes wurde an deine E-Mail gesendet"
 
 msgid "Password Reset"
 msgstr "Passwort zurücksetzen"

From e2779314b053c142764839c2f545ddc1b2474ac5 Mon Sep 17 00:00:00 2001
From: PCoder <purple.coder@yahoo.co.uk>
Date: Tue, 26 Sep 2017 00:25:54 +0530
Subject: [PATCH 71/82] Fix cancel vm modal text translation

---
 hosting/locale/de/LC_MESSAGES/django.po | 3 ++-
 1 file changed, 2 insertions(+), 1 deletion(-)

diff --git a/hosting/locale/de/LC_MESSAGES/django.po b/hosting/locale/de/LC_MESSAGES/django.po
index b273dbcf..f28fe9db 100644
--- a/hosting/locale/de/LC_MESSAGES/django.po
+++ b/hosting/locale/de/LC_MESSAGES/django.po
@@ -602,7 +602,8 @@ msgstr ""
 #, python-format
 msgid ""
 "Your Virtual Machine %(virtual_machine.name)s is successfully terminated!"
-msgstr "Deine Virtuelle Machine (VM) %(virtual_machine.name)s wurde erfolgreich beendet!"
+msgstr ""
+"Deine Virtuelle Machine (VM) %(virtual_machine.name)s wurde erfolgreich beendet!"
 
 msgid "Virtual Machines"
 msgstr "Virtuelle Maschinen"

From 889d737c7ca779c4285967020d5b21d622008693 Mon Sep 17 00:00:00 2001
From: verysanghee <verysanghee@gmail.com>
Date: Mon, 25 Sep 2017 20:58:59 +0200
Subject: [PATCH 72/82] Update django.po

---
 hosting/locale/de/LC_MESSAGES/django.po | 6 +++---
 1 file changed, 3 insertions(+), 3 deletions(-)

diff --git a/hosting/locale/de/LC_MESSAGES/django.po b/hosting/locale/de/LC_MESSAGES/django.po
index b273dbcf..8d4db60e 100644
--- a/hosting/locale/de/LC_MESSAGES/django.po
+++ b/hosting/locale/de/LC_MESSAGES/django.po
@@ -644,13 +644,13 @@ msgid "Sorry. Your request is invalid."
 msgstr "Entschuldigung, deine Anfrage ist ungültig."
 
 msgid "Password has been reset."
-msgstr ""
+msgstr "Dein Passwort wurde erfolgreich zurückgesetzt."
 
 msgid "Password reset has not been successful."
-msgstr ""
+msgstr "Dein Passwort konnte nicht zurückgesetzt werden."
 
 msgid "The reset password link is no longer valid."
-msgstr ""
+msgstr "Der Link zum Zurücksetzen Deines Passwortes ist nicht mehr gültig."
 
 msgid "Invalid credit card"
 msgstr "Ungültige Kreditkarte"

From a9755ccbff787df6f85d471f01ea7570f7c89125 Mon Sep 17 00:00:00 2001
From: PCoder <purple.coder@yahoo.co.uk>
Date: Tue, 26 Sep 2017 00:34:33 +0530
Subject: [PATCH 73/82] Updated hosting django.po

---
 hosting/locale/de/LC_MESSAGES/django.po | 9 ++++++---
 1 file changed, 6 insertions(+), 3 deletions(-)

diff --git a/hosting/locale/de/LC_MESSAGES/django.po b/hosting/locale/de/LC_MESSAGES/django.po
index 8d4db60e..d6b01d6e 100644
--- a/hosting/locale/de/LC_MESSAGES/django.po
+++ b/hosting/locale/de/LC_MESSAGES/django.po
@@ -8,7 +8,7 @@ msgid ""
 msgstr ""
 "Project-Id-Version: PACKAGE VERSION\n"
 "Report-Msgid-Bugs-To: \n"
-"POT-Creation-Date: 2017-09-23 19:00+0530\n"
+"POT-Creation-Date: 2017-09-25 19:00+0000\n"
 "PO-Revision-Date: YEAR-MO-DA HO:MI+ZONE\n"
 "Last-Translator: FULL NAME <EMAIL@ADDRESS>\n"
 "Language-Team: LANGUAGE <LL@li.org>\n"
@@ -601,8 +601,11 @@ msgstr ""
 
 #, python-format
 msgid ""
-"Your Virtual Machine %(virtual_machine.name)s is successfully terminated!"
-msgstr "Deine Virtuelle Machine (VM) %(virtual_machine.name)s wurde erfolgreich beendet!"
+"Your Virtual Machine <strong>%(machine_name)s</strong> is successfully "
+"terminated!"
+msgstr ""
+"Deine Virtuelle Machine (VM) <strong>%(machine_name)s</strong> wurde erfolgreich "
+"beendet!"
 
 msgid "Virtual Machines"
 msgstr "Virtuelle Maschinen"

From 2f4b7bb7492bd43d78e3c887de6d2834de327c8f Mon Sep 17 00:00:00 2001
From: verysanghee <verysanghee@gmail.com>
Date: Mon, 25 Sep 2017 21:07:33 +0200
Subject: [PATCH 74/82] Update django.po

---
 hosting/locale/de/LC_MESSAGES/django.po | 24 ++++++++++++------------
 1 file changed, 12 insertions(+), 12 deletions(-)

diff --git a/hosting/locale/de/LC_MESSAGES/django.po b/hosting/locale/de/LC_MESSAGES/django.po
index 8d4db60e..34129d5b 100644
--- a/hosting/locale/de/LC_MESSAGES/django.po
+++ b/hosting/locale/de/LC_MESSAGES/django.po
@@ -353,7 +353,7 @@ msgid "Order summary"
 msgstr "Bestellungsübersicht"
 
 msgid "Product"
-msgstr ""
+msgstr "Produkt"
 
 msgid "Cores"
 msgstr "Prozessorkerne"
@@ -588,7 +588,7 @@ msgid "We are here to help you!"
 msgstr "Wir sind hier, um Dir zu helfen!"
 
 msgid "CONTACT"
-msgstr "KONTACT"
+msgstr "KONTAKT"
 
 msgid "Terminate your Virtual Machine"
 msgstr "Deine Virtuelle Maschine beenden"
@@ -707,7 +707,7 @@ msgstr "VM Kündigung"
 #~ msgstr "VM %(VM_ID)s erfolgreich beendet"
 
 #~ msgid "days"
-#~ msgstr "tage"
+#~ msgstr "Tage"
 
 #~ msgid "New Virtual Machine"
 #~ msgstr "Neue virtuelle Maschine"
@@ -740,7 +740,7 @@ msgstr "VM Kündigung"
 #~ msgstr "Meine Bestellungen"
 
 #~ msgid "SSH Keys"
-#~ msgstr "SSH Key"
+#~ msgstr "SSH Keys"
 
 #~ msgid "Notifications "
 #~ msgstr "Benachrichtigungen"
@@ -788,19 +788,19 @@ msgstr "VM Kündigung"
 #~ msgstr "Hinzufügen"
 
 #~ msgid "Keys"
-#~ msgstr "Schlüssel"
+#~ msgstr "Keys"
 
 #~ msgid "Log in"
 #~ msgstr "Anmelden"
 
 #~ msgid "You haven been logged out"
-#~ msgstr "Sie wurden abgmeldet"
+#~ msgstr "Du wurdest abgemeldet"
 
 #~ msgid "How it works"
 #~ msgstr "So funktioniert es"
 
 #~ msgid "Your infrastructure"
-#~ msgstr "deine Infrastruktur"
+#~ msgstr "Deine Infrastruktur"
 
 #~ msgid "Our inftrastructure"
 #~ msgstr "Unsere Infrastruktur"
@@ -808,11 +808,11 @@ msgstr "VM Kündigung"
 #~ msgid "Pricing"
 #~ msgstr "Preise"
 
-#~ msgid "Access Key"
-#~ msgstr "Zugriffsschlüssel"
+#~ msgid "SSH Key"
+#~ msgstr "SSH Key"
 
 #~ msgid "Upload your own key. "
-#~ msgstr "Lade deinen Key hoch"
+#~ msgstr "Lade Deinen Key hoch"
 
 #~ msgid "Generate Key Pair"
 #~ msgstr "Schlüsselpaar generieren"
@@ -836,5 +836,5 @@ msgstr "VM Kündigung"
 #~ "Your SSH private key was already generated and downloaded, if you lost "
 #~ "it, contact us. "
 #~ msgstr ""
-#~ "Dein privater SSH Schlüssel wurde bereits generiert und heruntergeladen. "
-#~ "Falls du ihn verloren hast, kontaktiere uns."
+#~ "Dein privater SSH Key wurde bereits generiert und heruntergeladen. "
+#~ "Falls Du ihn verloren hast, kontaktiere uns."

From e85a7c9e2a2a8ac52362c6e07f7650ab75c28800 Mon Sep 17 00:00:00 2001
From: verysanghee <verysanghee@gmail.com>
Date: Mon, 25 Sep 2017 21:14:19 +0200
Subject: [PATCH 75/82] Update django.po

---
 hosting/locale/de/LC_MESSAGES/django.po | 6 +++---
 1 file changed, 3 insertions(+), 3 deletions(-)

diff --git a/hosting/locale/de/LC_MESSAGES/django.po b/hosting/locale/de/LC_MESSAGES/django.po
index 34129d5b..e4300f27 100644
--- a/hosting/locale/de/LC_MESSAGES/django.po
+++ b/hosting/locale/de/LC_MESSAGES/django.po
@@ -28,10 +28,10 @@ msgid "User does not exist"
 msgstr "Der Benutzer existiert nicht"
 
 msgid "Paste here your public key"
-msgstr "Füge deinen Public Key ein"
+msgstr "Füge Deinen Public Key ein"
 
 msgid "Give a name to your key"
-msgstr "Gebe deinem SSH-Key einen Name"
+msgstr "Gebe Deinem SSH-Key einen Name"
 
 msgid "Key name"
 msgstr "Key-Name"
@@ -808,7 +808,7 @@ msgstr "VM Kündigung"
 #~ msgid "Pricing"
 #~ msgstr "Preise"
 
-#~ msgid "SSH Key"
+#~ msgid "Access Key"
 #~ msgstr "SSH Key"
 
 #~ msgid "Upload your own key. "

From f35663b5ac4bde37b7095b203298d11f45a956c6 Mon Sep 17 00:00:00 2001
From: verysanghee <verysanghee@gmail.com>
Date: Mon, 25 Sep 2017 21:18:46 +0200
Subject: [PATCH 76/82] Update django.po

---
 hosting/locale/de/LC_MESSAGES/django.po | 30 ++++++++++++-------------
 1 file changed, 15 insertions(+), 15 deletions(-)

diff --git a/hosting/locale/de/LC_MESSAGES/django.po b/hosting/locale/de/LC_MESSAGES/django.po
index e4300f27..27ff9bb2 100644
--- a/hosting/locale/de/LC_MESSAGES/django.po
+++ b/hosting/locale/de/LC_MESSAGES/django.po
@@ -156,10 +156,10 @@ msgid "Upload"
 msgstr "Hochladen"
 
 msgid "Your VM hosted in Switzerland"
-msgstr "deine VM in der Schweiz"
+msgstr "Deine VM in der Schweiz"
 
 msgid "Set your new password"
-msgstr "Setze dein neues Passwort"
+msgstr "Setze Dein neues Passwort"
 
 msgid "Reset"
 msgstr "Zurücksetzen"
@@ -180,7 +180,7 @@ msgid "My VMs"
 msgstr "Meine VMs"
 
 msgid "My SSH Keys"
-msgstr "Meine SSH Keys"
+msgstr "Meine SSH-Keys"
 
 msgid "My Bills"
 msgstr "Meine Rechnungen"
@@ -229,10 +229,10 @@ msgid ""
 "Thank you!\n"
 msgstr ""
 "\n"
-"Du erhälst diese E-Mail da du dein Passwort für deinen Account bei "
+"Du erhälst diese E-Mail da Du Dein Passwort für Deinen Account bei "
 "%(site_name)s zurücksetzen möchtest.<br/>\n"
 "Bitte folge diesem Link und wähle ein neues Passwort: %(base_url)s"
-"%(password_reset_url)s Solltest du kein neues Passwort angefordert haben, "
+"%(password_reset_url)s Solltest Du kein neues Passwort angefordert haben, "
 "dann ignoriere diese E-Mail.<br/>\n"
 "Dankeschön!\n"
 
@@ -245,10 +245,10 @@ msgid ""
 "If you didn't request a new password, ignore this e-mail.\n"
 "Thank you!\n"
 msgstr ""
-"Du erhälst diese E-Mail da du dein Passwort für deinen Account bei "
+"Du erhälst diese E-Mail da Du Dein Passwort für Deinen Account bei "
 "%(site_name)s zurücksetzen möchtest.\n"
 "Bitte folge diesem Link und wähle ein neues Passwort: %(base_url)s"
-"%(password_reset_url)s Solltest du kein neues Passwort angefordert haben, "
+"%(password_reset_url)s Solltest Du kein neues Passwort angefordert haben, "
 "dann ignoriere diese E-Mail.\n"
 "Dankeschön!\n"
 
@@ -260,11 +260,11 @@ msgid ""
 "If you want to order a new virtual machine, you can do it by clicking <a "
 "href=\"%(base_url)s%(my_virtual_machines_url)s\">this link</a>.<br/>\n"
 msgstr ""
-"Du erhälst diese E-Mail, da deine virtuelle Maschine [%(vm_name)s] gekündigt "
+"Du erhälst diese E-Mail, Da Deine virtuelle Maschine [%(vm_name)s] gekündigt "
 "wurde.<br/>\n"
-"Um deinen Auftragsstatus zu sehen, klicke auf die [my VM page] unten.<br/>\n"
-"Falls du eine neue virtuelle Maschine bestellen möchtest, kannst du dies "
-"tun, indem du <a href=\"%(base_url)s%(my_virtual_machines_url)s\">diesen "
+"Um Deinen Auftragsstatus zu sehen, klicke auf die [my VM page] unten.<br/>\n"
+"Falls Du eine neue virtuelle Maschine bestellen möchtest, kannst Du dies "
+"tun, indem Du <a href=\"%(base_url)s%(my_virtual_machines_url)s\">diesen "
 "Link klickst</a>.<br/>\n"
 
 msgid "My VM page"
@@ -280,12 +280,12 @@ msgid ""
 "link.\n"
 "%(base_url)s%(my_virtual_machines_url)s\n"
 msgstr ""
-"Du erhälst diese E-Mail, da deine virtuelle Maschine [%(vm_name)s] gekündigt "
+"Du erhälst diese E-Mail, da Deine virtuelle Maschine [%(vm_name)s] gekündigt "
 "wurde.\n"
-"Um deinen Auftragsstatus zu sehen, klicke hier.\n"
+"Um Deinen Auftragsstatus zu sehen, klicke hier.\n"
 "%(base_url)s%(vm_order_url)s\n"
-"Falls du eine neue virtuelle Maschine bestellen möchtest, kannst du dies "
-"tun, indem du diesen Link klickst.\n"
+"Falls Du eine neue virtuelle Maschine bestellen möchtest, kannst Du dies "
+"tun, indem Du diesen Link klickst.\n"
 "%(base_url)s%(my_virtual_machines_url)s\n"
 
 msgid "Toggle navigation"

From 25f3118126f8777ed166e93c46b9b48f1060355d Mon Sep 17 00:00:00 2001
From: PCoder <purple.coder@yahoo.co.uk>
Date: Tue, 26 Sep 2017 01:06:35 +0530
Subject: [PATCH 77/82] Updated Changelog

---
 Changelog | 1 +
 1 file changed, 1 insertion(+)

diff --git a/Changelog b/Changelog
index 33184f98..7ba5e634 100644
--- a/Changelog
+++ b/Changelog
@@ -6,6 +6,7 @@ Pre-changelog: 1.2.3 2017-09-20
     * #3786: [hosting] Redesigned the hosting invoice and order-confirmation page
     * #3728: [hosting] VM Termination animation added
     * #3777: [hosting] Create new VM calculator added like dcl landing
+    * #3806: [hosting] Fix can not create VMs after password reset
     * Feature: [cms, blog] Added /cms prefix for all the django-cms generated urls
     * Bugfix: [dcl, hosting] added host to celery error mails
     * Bugfix: [ungleich] Fixed wrong subdomain digitalglarus.ungleich.ch

From 75ff7e4ea86f14bce202d2cf0dc202734a1e2872 Mon Sep 17 00:00:00 2001
From: PCoder <purple.coder@yahoo.co.uk>
Date: Tue, 26 Sep 2017 01:53:19 +0530
Subject: [PATCH 78/82] Added some translations

---
 utils/locale/de/LC_MESSAGES/django.po | 30 +++++++++++++++++++++++++--
 1 file changed, 28 insertions(+), 2 deletions(-)

diff --git a/utils/locale/de/LC_MESSAGES/django.po b/utils/locale/de/LC_MESSAGES/django.po
index 794b5fd9..04d1f4dc 100644
--- a/utils/locale/de/LC_MESSAGES/django.po
+++ b/utils/locale/de/LC_MESSAGES/django.po
@@ -8,7 +8,7 @@ msgid ""
 msgstr ""
 "Project-Id-Version: PACKAGE VERSION\n"
 "Report-Msgid-Bugs-To: \n"
-"POT-Creation-Date: 2017-09-02 11:50+0000\n"
+"POT-Creation-Date: 2017-09-25 20:11+0000\n"
 "PO-Revision-Date: YEAR-MO-DA HO:MI+ZONE\n"
 "Last-Translator: FULL NAME <EMAIL@ADDRESS>\n"
 "Language-Team: LANGUAGE <LL@li.org>\n"
@@ -738,6 +738,24 @@ msgstr ""
 msgid "Enter your name or company name"
 msgstr "Geben Sie Ihren Namen oder der Ihrer Firma ein"
 
+msgid "Your username and/or password were incorrect."
+msgstr "Dein Benutzername und/oder Dein Passwort ist falsch."
+
+msgid "User does not exist"
+msgstr "Der Benutzer existiert nicht"
+
+msgid "The account is already active."
+msgstr ""
+
+msgid "The two password fields didn't match."
+msgstr ""
+
+msgid "New password"
+msgstr ""
+
+msgid "New password confirmation"
+msgstr ""
+
 msgid "Cardholder Name"
 msgstr "Name des Kartenbesitzer"
 
@@ -768,8 +786,16 @@ msgstr "Telefon"
 msgid "Message"
 msgstr "Nachricht"
 
+msgid "An email with the activation link has been sent to your email"
+msgstr ""
+"Der Link zum Zurücksetzen deines Passwortes wurde an deine E-Mail gesendet"
+
+msgid "Account Activation"
+msgstr "Accountaktivierung"
+
 msgid "The link to reset your email has been sent to your email"
-msgstr "Der Link zum Zurücksetzen deines Passwortes wurde an deine E-Mail gesendet"
+msgstr ""
+"Der Link zum Zurücksetzen deines Passwortes wurde an deine E-Mail gesendet"
 
 msgid "Password Reset"
 msgstr "Passwort zurücksetzen"

From 6bf89669eff4b8faef57eba42097a97778a5e33c Mon Sep 17 00:00:00 2001
From: PCoder <purple.coder@yahoo.co.uk>
Date: Tue, 26 Sep 2017 02:07:28 +0530
Subject: [PATCH 79/82] some more de translations

---
 utils/locale/de/LC_MESSAGES/django.po | 8 ++++----
 1 file changed, 4 insertions(+), 4 deletions(-)

diff --git a/utils/locale/de/LC_MESSAGES/django.po b/utils/locale/de/LC_MESSAGES/django.po
index 04d1f4dc..f8374e4e 100644
--- a/utils/locale/de/LC_MESSAGES/django.po
+++ b/utils/locale/de/LC_MESSAGES/django.po
@@ -745,16 +745,16 @@ msgid "User does not exist"
 msgstr "Der Benutzer existiert nicht"
 
 msgid "The account is already active."
-msgstr ""
+msgstr "Das Benutzerkonto ist bereits aktiv."
 
 msgid "The two password fields didn't match."
-msgstr ""
+msgstr "Die beiden Passwörter stimmen nicht überein."
 
 msgid "New password"
-msgstr ""
+msgstr "Neues Passwort"
 
 msgid "New password confirmation"
-msgstr ""
+msgstr "Neues Passwort Bestätigung"
 
 msgid "Cardholder Name"
 msgstr "Name des Kartenbesitzer"

From 7933584942bee21a167c46e21c0f06f75410249d Mon Sep 17 00:00:00 2001
From: PCoder <purple.coder@yahoo.co.uk>
Date: Tue, 26 Sep 2017 02:13:49 +0530
Subject: [PATCH 80/82] Updated changelog

---
 Changelog | 1 +
 1 file changed, 1 insertion(+)

diff --git a/Changelog b/Changelog
index 7ba5e634..7f4394dd 100644
--- a/Changelog
+++ b/Changelog
@@ -6,6 +6,7 @@ Pre-changelog: 1.2.3 2017-09-20
     * #3786: [hosting] Redesigned the hosting invoice and order-confirmation page
     * #3728: [hosting] VM Termination animation added
     * #3777: [hosting] Create new VM calculator added like dcl landing
+    * #3781: [hosting] Resend activation mail
     * #3806: [hosting] Fix can not create VMs after password reset
     * Feature: [cms, blog] Added /cms prefix for all the django-cms generated urls
     * Bugfix: [dcl, hosting] added host to celery error mails

From 29a45e81bf943beeeaf43260b096f0c38bbc32af Mon Sep 17 00:00:00 2001
From: PCoder <purple.coder@yahoo.co.uk>
Date: Tue, 26 Sep 2017 02:24:17 +0530
Subject: [PATCH 81/82] Include cdist 4.7.0 in requirements.txt

---
 requirements.txt | 3 +--
 1 file changed, 1 insertion(+), 2 deletions(-)

diff --git a/requirements.txt b/requirements.txt
index 6446a5c9..89285c83 100644
--- a/requirements.txt
+++ b/requirements.txt
@@ -96,5 +96,4 @@ pyflakes==1.5.0
 billiard==3.5.0.3
 amqp==2.2.1
 vine==1.1.4
-#git+https://github.com/ungleich/cdist.git#egg=cdist
-file:///home/app/cdist#egg=cdist
+cdist==4.7.0

From 543465e89bbb154d0845f3287d64967e0320ca77 Mon Sep 17 00:00:00 2001
From: PCoder <purple.coder@yahoo.co.uk>
Date: Tue, 26 Sep 2017 02:34:10 +0530
Subject: [PATCH 82/82] Update Changelog for 1.2.3

---
 Changelog | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/Changelog b/Changelog
index 7f4394dd..f03a04ed 100644
--- a/Changelog
+++ b/Changelog
@@ -1,4 +1,4 @@
-Pre-changelog: 1.2.3 2017-09-20
+1.2.3: 2017-09-25
     * #3484: [dcl, hosting] Refactored account activation, password reset, VM order and cancellation email
     * #3731: [dcl, hosting] Added cdist ssh key handler 
     * #3628: [dcl] on hosting, VM is created at credit card info submit