diff --git a/.dockerignore b/.dockerignore new file mode 100644 index 00000000..6b8710a7 --- /dev/null +++ b/.dockerignore @@ -0,0 +1 @@ +.git diff --git a/Changelog b/Changelog index 8102c8b5..44c4dee4 100644 --- a/Changelog +++ b/Changelog @@ -1,3 +1,8 @@ +3.2: 2021-02-07 + * 8816: Update order confirmation text to better prepared for payment dispute + * supportticket#22990: Fix: can't add a deleted card +3.1: 2021-01-11 + * 8781: Fix error is setting a default card (MR!746) 3.0: 2021-01-07 * 8393: Implement SCA for stripe payments (MR!745) * 8691: Implment check_vm_templates management command (MR!744) diff --git a/Dockerfile b/Dockerfile new file mode 100644 index 00000000..50b81cbb --- /dev/null +++ b/Dockerfile @@ -0,0 +1,18 @@ +FROM python:3.10.0-alpine3.15 + +WORKDIR /usr/src/app + +RUN apk add --update --no-cache \ + git \ + build-base \ + openldap-dev \ + python3-dev \ + libpq-dev \ + && rm -rf /var/cache/apk/* + +# FIX https://github.com/python-ldap/python-ldap/issues/432 +RUN echo 'INPUT ( libldap.so )' > /usr/lib/libldap_r.so + +COPY requirements.txt ./ +RUN pip install --no-cache-dir -r requirements.txt +COPY ./ . diff --git a/Makefile b/Makefile index 67c0c15b..68ff014e 100644 --- a/Makefile +++ b/Makefile @@ -14,6 +14,12 @@ help: @echo ' make rsync_upload ' @echo ' make install_debian_packages ' +buildimage: + docker build -t dynamicweb:$$(git describe) . + +releaseimage: buildimage + ./release.sh + collectstatic: $(PY?) $(BASEDIR)/manage.py collectstatic diff --git a/datacenterlight/locale/de/LC_MESSAGES/django.po b/datacenterlight/locale/de/LC_MESSAGES/django.po index 2dce7582..cd7fab99 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: 2020-03-24 07:02+0000\n" +"POT-Creation-Date: 2021-02-07 11:10+0000\n" "PO-Revision-Date: 2018-03-30 23:22+0000\n" "Last-Translator: b'Anonymous User '\n" "Language-Team: LANGUAGE \n" @@ -451,38 +451,43 @@ msgstr "Dein Gesamtpreis" #, python-format msgid "" -"By clicking \"Place order\" this plan will charge your credit card account " -"with %(total_price)s CHF/year" +" By clicking \"Place order\" you agree to our Terms of Service and " +"this plan will charge your credit card account with %(total_price)s CHF/year" msgstr "" -"Wenn Du \"bestellen\" auswählst, wird Deine Kreditkarte mit %(total_price)s " -"CHF pro Jahr belastet" +"Indem Du auf \"Bestellung aufgeben\" klickst, erklärst Du dich mit unseren Nutzungsbedingungen einverstanden und Dein Kreditkartenkonto wird mit %(total_price)s CHF/Jahr belastet." #, python-format msgid "" -"By clicking \"Place order\" this plan will charge your credit card account " -"with %(total_price)s CHF/month" +"\n" +" By clicking \"Place order\" you agree to " +"our Terms " +"of Service and this plan will charge your credit card account with " +"%(total_price)s CHF/month" msgstr "" -"Wenn Du \"bestellen\" auswählst, wird Deine Kreditkarte mit %(total_price)s " -"CHF pro Monat belastet" - -#, fuzzy, python-format -#| msgid "" -#| "By clicking \"Place order\" this payment will charge your credit card " -#| "account with a one time amount of %(total_price)s CHF" -msgid "" -"By clicking \"Place order\" this payment will charge your credit card " -"account with a one time amount of %(total_price)s CHF" -msgstr "" -"Wenn Du \"bestellen\" auswählst, wird Deine Kreditkarte mit " -"%(vm_total_price)s CHF pro Monat belastet" +"\n" +"Indem Du auf \"Bestellung aufgeben\" klickst, erklärst Du dich mit unseren Nutzungsbedingungen einverstanden und Dein Kreditkartenkonto wird mit %(total_price)s CHF/Monat belastet." #, python-format msgid "" -"By clicking \"Place order\" this plan will charge your credit card account " -"with %(vm_total_price)s CHF/month" +"By clicking \"Place order\" you agree to our Terms of Service and " +"this plan will charge your credit card account with %(total_price)s CHF" msgstr "" -"Wenn Du \"bestellen\" auswählst, wird Deine Kreditkarte mit " -"%(vm_total_price)s CHF pro Monat belastet" +"Indem Du auf \"Bestellung aufgeben\" klickst, erklärst Du dich mit unseren Nutzungsbedingungen einverstanden und Dein Kreditkartenkonto wird mit %(total_price)s CHF belastet." + +#, python-format +msgid "" +"By clicking \"Place order\" you agree to our Terms of Service and " +"this plan will charge your credit card account with %(vm_total_price)s CHF/" +"month" +msgstr "" +"Indem Du auf \"Bestellung aufgeben\" klickst, erklärst Du dich mit unseren Nutzungsbedingungen einverstanden und Dein Kreditkartenkonto wird mit %(vm_total_price)s CHF/Monat belastet" msgid "Place order" msgstr "Bestellen" @@ -601,16 +606,22 @@ msgid "Incorrect pricing name. Please contact support{support_email}" msgstr "" "Ungültige Preisbezeichnung. Bitte kontaktiere den Support{support_email}" -#, python-brace-format -msgid "{user} does not have permission to access the card" -msgstr "{user} hat keine Erlaubnis auf diese Karte zuzugreifen" - -msgid "An error occurred. Details: {}" -msgstr "Ein Fehler ist aufgetreten. Details: {}" - msgid "Confirm Order" msgstr "Bestellung Bestätigen" +#, fuzzy +#| msgid "Thank you!" +msgid "Thank you !" +msgstr "Vielen Dank!" + +msgid "Your product will be provisioned as soon as we receive the payment." +msgstr "" + +#, python-brace-format +msgid "An error occurred while associating the card. Details: {details}" +msgstr "" +"Beim Verbinden der Karte ist ein Fehler aufgetreten. Details: {details}" + msgid "Error." msgstr "" @@ -621,10 +632,21 @@ msgstr "" "Es ist ein Fehler bei der Zahlung betreten. Du wirst nach dem Schliessen vom " "Popup zur Bezahlseite weitergeleitet." -#, python-brace-format -msgid "An error occurred while associating the card. Details: {details}" +msgid "Thank you for the order." +msgstr "Danke für Deine Bestellung." + +msgid "" +"Your product will be provisioned as soon as we receive a payment " +"confirmation from Stripe. We will send you a confirmation email. You can " +"always contact us at support@datacenterlight.ch" msgstr "" -"Beim Verbinden der Karte ist ein Fehler aufgetreten. Details: {details}" + +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 " This is a monthly recurring plan." msgstr "Dies ist ein monatlich wiederkehrender Plan." @@ -664,15 +686,31 @@ msgstr "" "Du wirst bald eine Bestätigungs-E-Mail über die Zahlung erhalten. Du kannst " "jederzeit unter info@ungleich.ch kontaktieren." -msgid "Thank you for the order." -msgstr "Danke für Deine Bestellung." +#, python-format +#~ msgid "" +#~ "By clicking \"Place order\" this plan will charge your credit card " +#~ "account with %(total_price)s CHF/month" +#~ msgstr "" +#~ "Wenn Du \"bestellen\" auswählst, wird Deine Kreditkarte mit " +#~ "%(total_price)s CHF pro Monat belastet" -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." +#, fuzzy, python-format +#~| msgid "" +#~| "By clicking \"Place order\" this payment will charge your credit card " +#~| "account with a one time amount of %(total_price)s CHF" +#~ msgid "" +#~ "By clicking \"Place order\" this payment will charge your credit card " +#~ "account with a one time amount of %(total_price)s CHF" +#~ msgstr "" +#~ "Wenn Du \"bestellen\" auswählst, wird Deine Kreditkarte mit " +#~ "%(vm_total_price)s CHF pro Monat belastet" + +#, python-brace-format +#~ msgid "{user} does not have permission to access the card" +#~ msgstr "{user} hat keine Erlaubnis auf diese Karte zuzugreifen" + +#~ msgid "An error occurred. Details: {}" +#~ msgstr "Ein Fehler ist aufgetreten. Details: {}" #~ msgid "Price" #~ msgstr "Preise" @@ -748,9 +786,6 @@ msgstr "" #~ "Wir werden dann sobald als möglich Ihren Beta-Zugang erstellen und Sie " #~ "daraufhin kontaktieren.Bis dahin bitten wir Sie um etwas Geduld." -#~ msgid "Thank you!" -#~ msgstr "Vielen Dank!" - #~ msgid "Thank you for order! Our team will contact you via email" #~ msgstr "" #~ "Vielen Dank für die Bestellung. Unser Team setzt sich sobald wie möglich " diff --git a/datacenterlight/tasks.py b/datacenterlight/tasks.py index 9c98b729..899b506f 100644 --- a/datacenterlight/tasks.py +++ b/datacenterlight/tasks.py @@ -195,7 +195,7 @@ def handle_metadata_and_emails(order_id, vm_id, manager, user, specs, email_data = { 'subject': settings.DCL_TEXT + " Order from %s" % context['email'], 'from_email': settings.DCL_SUPPORT_FROM_ADDRESS, - 'to': ['info@ungleich.ch'], + 'to': ['dcl-orders@ungleich.ch'], 'body': "\n".join( ["%s=%s" % (k, v) for (k, v) in context.items()]), 'reply_to': [context['email']], @@ -233,4 +233,4 @@ def handle_metadata_and_emails(order_id, vm_id, manager, user, specs, logger.debug("New VM ID is {vm_id}".format(vm_id=vm_id)) if vm_id > 0: - get_or_create_vm_detail(custom_user, manager, vm_id) \ No newline at end of file + get_or_create_vm_detail(custom_user, manager, vm_id) diff --git a/datacenterlight/templates/datacenterlight/order_detail.html b/datacenterlight/templates/datacenterlight/order_detail.html index d6c87266..1f7a3cda 100644 --- a/datacenterlight/templates/datacenterlight/order_detail.html +++ b/datacenterlight/templates/datacenterlight/order_detail.html @@ -278,15 +278,16 @@ {% if generic_payment_details %} {% if generic_payment_details.recurring %} {% if generic_payment_details.recurring_interval == 'year' %} -
{% blocktrans with total_price=generic_payment_details.amount|floatformat:2|intcomma %}By clicking "Place order" this plan will charge your credit card account with {{total_price}} CHF/year{% endblocktrans %}.
+
{% blocktrans with total_price=generic_payment_details.amount|floatformat:2|intcomma %} By clicking "Place order" you agree to our Terms of Service and this plan will charge your credit card account with {{ total_price }} CHF/year{% endblocktrans %}.
{% else %} -
{% blocktrans with total_price=generic_payment_details.amount|floatformat:2|intcomma %}By clicking "Place order" this plan will charge your credit card account with {{total_price}} CHF/month{% endblocktrans %}.
+
{% blocktrans with total_price=generic_payment_details.amount|floatformat:2|intcomma %} + By clicking "Place order" you agree to our Terms of Service and this plan will charge your credit card account with {{ total_price }} CHF/month{% endblocktrans %}.
{% endif %} {% else %} -
{% blocktrans with total_price=generic_payment_details.amount|floatformat:2|intcomma %}By clicking "Place order" this payment will charge your credit card account with a one time amount of {{total_price}} CHF{% endblocktrans %}.
+
{% blocktrans with total_price=generic_payment_details.amount|floatformat:2|intcomma %}By clicking "Place order" you agree to our Terms of Service and this plan will charge your credit card account with {{ total_price }} CHF{% endblocktrans %}.
{% endif %} {% else %} -
{% blocktrans with vm_total_price=vm.total_price|floatformat:2|intcomma %}By clicking "Place order" this plan will charge your credit card account with {{vm_total_price}} CHF/month{% endblocktrans %}.
+
{% blocktrans with vm_total_price=vm.total_price|floatformat:2|intcomma %}By clicking "Place order" you agree to our Terms of Service and this plan will charge your credit card account with {{ vm_total_price }} CHF/month{% endblocktrans %}.
{% endif %}
diff --git a/datacenterlight/utils.py b/datacenterlight/utils.py index 6a0e45ca..4e8094c0 100644 --- a/datacenterlight/utils.py +++ b/datacenterlight/utils.py @@ -20,7 +20,7 @@ logger = logging.getLogger(__name__) eu_countries = ['at', 'be', 'bg', 'ch', 'cy', 'cz', 'hr', 'dk', 'ee', 'fi', 'fr', 'mc', 'de', 'gr', 'hu', 'ie', 'it', - 'lv', 'lu', 'mt', 'nl', 'po', 'pt', 'ro','sk', 'si', 'es', + 'lv', 'lu', 'mt', 'nl', 'pl', 'pt', 'ro','sk', 'si', 'es', 'se', 'gb'] diff --git a/datacenterlight/views.py b/datacenterlight/views.py index e149bfc4..5bf68e0a 100644 --- a/datacenterlight/views.py +++ b/datacenterlight/views.py @@ -1333,7 +1333,7 @@ def do_provisioning_generic( 'subject': (settings.DCL_TEXT + " Payment received from %s" % context['email']), 'from_email': settings.DCL_SUPPORT_FROM_ADDRESS, - 'to': ['info@ungleich.ch'], + 'to': ['dcl-orders@ungleich.ch'], 'body': "\n".join( ["%s=%s" % (k, v) for (k, v) in context.items()]), 'reply_to': [context['email']], @@ -1507,7 +1507,7 @@ def do_provisioning(request, stripe_api_cus_id, card_details_response, 'subject': (settings.DCL_TEXT + " Payment received from %s" % context['email']), 'from_email': settings.DCL_SUPPORT_FROM_ADDRESS, - 'to': ['info@ungleich.ch'], + 'to': ['dcl-orders@ungleich.ch'], 'body': "\n".join( ["%s=%s" % (k, v) for (k, v) in context.items()]), 'reply_to': [context['email']], diff --git a/digitalglarus/locale/de/LC_MESSAGES/django.po b/digitalglarus/locale/de/LC_MESSAGES/django.po index ec96f5dc..ef7a46b5 100644 --- a/digitalglarus/locale/de/LC_MESSAGES/django.po +++ b/digitalglarus/locale/de/LC_MESSAGES/django.po @@ -376,8 +376,6 @@ msgid "" " digitalglarus.ch
\n" " hack4lgarus.ch
\n" " ipv6onlyhosting.com
\n" -" ipv6onlyhosting.ch
\n" -" ipv6onlyhosting.net
\n" " django-hosting.ch
\n" " rails-hosting.ch
\n" " node-hosting.ch
\n" @@ -636,8 +634,8 @@ msgstr "" "Internetangebot der ungleich glarus ag, welches unter den nachfolgenden " "Domains erreichbar ist:

ungleich.ch
datacenterlight.ch
devuanhosting.com
devuanhosting.ch
digitalglarus.ch
hack4lgarus." -"ch
ipv6onlyhosting.com
ipv6onlyhosting.ch
ipv6onlyhosting.net
django-hosting.ch
rails-hosting.ch
node-hosting.ch
blog." +"ch
ipv6onlyhosting.com
django-hosting.ch
rails-hosting.ch" +"
node-hosting.ch
blog." "ungleich.ch

Der Datenschutzbeauftragte des Verantwortlichen ist:

Sanghee Kim
ungleich glarus ag
Bahnhofstrasse 1
8783 " "Linthal (CH)
E-Mail: sanghee." @@ -838,3 +836,4 @@ msgstr "" #~ msgid "index/?$" #~ msgstr "index/?$" + diff --git a/dynamicweb/settings/base.py b/dynamicweb/settings/base.py index 03013ea5..62fe2897 100644 --- a/dynamicweb/settings/base.py +++ b/dynamicweb/settings/base.py @@ -631,8 +631,6 @@ GOOGLE_ANALYTICS_PROPERTY_IDS = { 'datacenterlight.ch': 'UA-62285904-8', 'devuanhosting.ch': 'UA-62285904-9', 'devuanhosting.com': 'UA-62285904-9', - 'ipv6onlyhosting.ch': 'UA-62285904-10', - 'ipv6onlyhosting.net': 'UA-62285904-10', 'ipv6onlyhosting.com': 'UA-62285904-10', 'comic.ungleich.ch': 'UA-62285904-13', '127.0.0.1:8000': 'localhost', diff --git a/dynamicweb/settings/prod.py b/dynamicweb/settings/prod.py index 445748ad..0590ca27 100644 --- a/dynamicweb/settings/prod.py +++ b/dynamicweb/settings/prod.py @@ -28,9 +28,7 @@ ALLOWED_HOSTS = [ ".devuanhosting.ch", ".devuanhosting.com", ".digitalezukunft.ch", - ".ipv6onlyhosting.ch", ".ipv6onlyhosting.com", - ".ipv6onlyhosting.net", ".digitalglarus.ch", ".hack4glarus.ch", ".xn--nglarus-n2a.ch" diff --git a/hosting/locale/de/LC_MESSAGES/django.po b/hosting/locale/de/LC_MESSAGES/django.po index 08bcdd7a..11c4a2a5 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: 2019-11-15 16:40+0000\n" +"POT-Creation-Date: 2021-02-07 10:19+0000\n" "PO-Revision-Date: YEAR-MO-DA HO:MI+ZONE\n" "Last-Translator: FULL NAME \n" "Language-Team: LANGUAGE \n" @@ -211,6 +211,9 @@ msgstr "Bezahlbares VM Hosting in der Schweiz" msgid "My Dashboard" msgstr "Mein Dashboard" +msgid "Welcome" +msgstr "" + msgid "My VMs" msgstr "Meine VMs" @@ -364,6 +367,11 @@ msgstr "Abgelehnt" msgid "Billed to" msgstr "Rechnungsadresse" +#, fuzzy +#| msgid "Card Number" +msgid "VAT Number" +msgstr "Kreditkartennummer" + msgid "Payment method" msgstr "Bezahlmethode" @@ -391,6 +399,9 @@ msgstr "Festplattenkapazität" msgid "Subtotal" msgstr "Zwischensumme" +msgid "VAT for" +msgstr "" + msgid "VAT" msgstr "Mehrwertsteuer" @@ -424,18 +435,22 @@ msgstr "ZURÜCK ZUR LISTE" msgid "Some problem encountered. Please try again later." msgstr "Ein Problem ist aufgetreten. Bitte versuche es später noch einmal." +#, fuzzy +#| msgid "Description" +msgid "Subscriptions" +msgstr "Beschreibung" + +#, fuzzy +#| msgid "One time payment" +msgid "One-time payments" +msgstr "Einmalzahlung" + msgid "VM ID" msgstr "" msgid "IP Address" msgstr "IP-Adresse" -msgid "See Invoice" -msgstr "Siehe Rechnung" - -msgid "Page" -msgstr "Seite" - msgid "Log in" msgstr "Anmelden" @@ -480,11 +495,13 @@ msgstr "Bestellungsübersicht" #, python-format msgid "" -"By clicking \"Place order\" this plan will charge your credit card account " -"with %(vm_price)s CHF/month" +"By clicking \"Place order\" you agree to our Terms of Service and " +"this plan will charge your credit card account with %(vm_price)s CHF/month." msgstr "" -"Wenn Du \"bestellen\" auswählst, wird Deine Kreditkarte mit %(vm_price)s CHF " -"pro Monat belastet" +"Indem Du auf \"Bestellung aufgeben\" klickst, erklärst Du dich mit unseren" +" Nutzungsbedingungen einverstanden und Dein Kreditkartenkonto wird mit %(vm_price)s CHF/Monat belastet." msgid "Place order" msgstr "Bestellen" @@ -504,6 +521,12 @@ msgstr "Schliessen" msgid "Order Nr." msgstr "Bestellung Nr." +msgid "See Invoice" +msgstr "Siehe Rechnung" + +msgid "Page" +msgstr "Seite" + msgid "Your Order" msgstr "Deine Bestellung" @@ -572,6 +595,19 @@ msgstr "Absenden" msgid "Password reset" msgstr "Passwort zurücksetzen" +#, fuzzy +#| msgid "Key name" +msgid "My Username" +msgstr "Key-Name" + +msgid "Your VAT number has been verified" +msgstr "" + +msgid "" +"Your VAT number is under validation. VAT will be adjusted, once the " +"validation is complete." +msgstr "" + msgid "UPDATE" msgstr "AKTUALISIEREN" @@ -773,21 +809,15 @@ msgstr "Dein Passwort konnte nicht zurückgesetzt werden." msgid "The reset password link is no longer valid." msgstr "Der Link zum Zurücksetzen Deines Passwortes ist nicht mehr gültig." +msgid "Could not set a default card." +msgstr "" + msgid "Card deassociation successful" msgstr "Die Verbindung mit der Karte wurde erfolgreich aufgehoben" -msgid "You are not permitted to do this operation" -msgstr "Du hast keine Erlaubnis um diese Operation durchzuführen" - -msgid "The selected card does not exist" -msgstr "Die ausgewählte Karte existiert nicht" - msgid "Billing address updated successfully" msgstr "Die Rechnungsadresse wurde erfolgreich aktualisiert" -msgid "You seem to have already added this card" -msgstr "Es scheint, als hättest du diese Karte bereits hinzugefügt" - #, python-brace-format msgid "An error occurred while associating the card. Details: {details}" msgstr "" @@ -852,7 +882,8 @@ msgstr "Ungültige Speicher-Grösse" #, python-brace-format msgid "Incorrect pricing name. Please contact support{support_email}" -msgstr "Ungültige Preisbezeichnung. Bitte kontaktiere den Support{support_email}" +msgstr "" +"Ungültige Preisbezeichnung. Bitte kontaktiere den Support{support_email}" msgid "" "We could not find the requested VM. Please " @@ -871,7 +902,9 @@ msgstr "Fehler beenden VM" msgid "" "VM terminate action timed out. Please contact support@datacenterlight.ch for " "further information." -msgstr "VM beendet wegen Zeitüberschreitung. Bitte kontaktiere support@datacenterlight.ch für weitere Informationen." +msgstr "" +"VM beendet wegen Zeitüberschreitung. Bitte kontaktiere " +"support@datacenterlight.ch für weitere Informationen." #, python-format msgid "Virtual Machine %(vm_name)s Cancelled" @@ -882,6 +915,15 @@ msgstr "" "Es gab einen Fehler bei der Bearbeitung Deine Anfrage. Bitte versuche es " "noch einmal." +#~ msgid "You are not permitted to do this operation" +#~ msgstr "Du hast keine Erlaubnis um diese Operation durchzuführen" + +#~ msgid "The selected card does not exist" +#~ msgstr "Die ausgewählte Karte existiert nicht" + +#~ msgid "You seem to have already added this card" +#~ msgstr "Es scheint, als hättest du diese Karte bereits hinzugefügt" + #, python-format #~ msgid "This key exists already with the name \"%(name)s\"" #~ msgstr "Der SSH-Key mit dem Name \"%(name)s\" existiert bereits" diff --git a/hosting/templates/hosting/order_detail.html b/hosting/templates/hosting/order_detail.html index 9256271a..dee453d5 100644 --- a/hosting/templates/hosting/order_detail.html +++ b/hosting/templates/hosting/order_detail.html @@ -218,7 +218,7 @@ {% csrf_token %}
-
{% blocktrans with vm_price=vm.total_price|floatformat:2|intcomma %}By clicking "Place order" this plan will charge your credit card account with {{ vm_price }} CHF/month{% endblocktrans %}.
+
{% blocktrans with vm_price=vm.total_price|floatformat:2|intcomma %}By clicking "Place order" you agree to our Terms of Service and this plan will charge your credit card account with {{ vm_price }} CHF/month.{% endblocktrans %}.