1
0
Fork 0
mirror of https://github.com/retspen/webvirtcloud synced 2024-12-24 23:25:24 +00:00

Merge pull request #344 from catborise/console_enrichments

vnc console options added
This commit is contained in:
Anatoliy Guskov 2020-07-20 11:40:51 +03:00 committed by GitHub
commit 618d5ec7c1
No known key found for this signature in database
GPG key ID: 4AEE18F83AFDEB23
24 changed files with 257 additions and 100 deletions

View file

@ -17,7 +17,6 @@ jobs:
# The type of runner that the job will run on # The type of runner that the job will run on
runs-on: ubuntu-latest runs-on: ubuntu-latest
# Steps represent a sequence of tasks that will be executed as part of the job # Steps represent a sequence of tasks that will be executed as part of the job
steps: steps:
# Checks-out your repository under $GITHUB_WORKSPACE, so your job can access it # Checks-out your repository under $GITHUB_WORKSPACE, so your job can access it
@ -35,16 +34,21 @@ jobs:
python3 -m pip install --upgrade pip python3 -m pip install --upgrade pip
if [ -f dev/requirements.txt ]; then pip3 install -r dev/requirements.txt; fi if [ -f dev/requirements.txt ]; then pip3 install -r dev/requirements.txt; fi
- name: Super-Linter - name: Super-Linter
uses: docker://github/super-linter:v2.2.0 uses: docker://github/super-linter:v3.3.2
env: env:
VALIDATE_ANSIBLE: false VALIDATE_ANSIBLE: false
VALIDATE_CLOJURE: false VALIDATE_CLOJURE: false
VALIDATE_COFFEE: false VALIDATE_COFFEE: false
VALIDATE_DART: false
VALIDATE_GO: false VALIDATE_GO: false
VALIDATE_POWERSHELL: false VALIDATE_JSX: false
VALIDATE_KOTLIN: false VALIDATE_KOTLIN: false
VALIDATE_RUBY: false VALIDATE_POWERSHELL: false
VALIDATE_PERL: false VALIDATE_PERL: false
VALIDATE_PHP: false VALIDATE_PHP: false
VALIDATE_RAKU: false
VALIDATE_RUBY: false
VALIDATE_TSX: false
VALIDATE_TERRAFORM: false VALIDATE_TERRAFORM: false

View file

@ -2,14 +2,14 @@ language: python
python: python:
- "3.6" - "3.6"
env: env:
- DJANGO=2.2.12 - DJANGO=2.2.14
install: install:
- pip install -r dev/requirements.txt - pip install -r dev/requirements.txt
script: script:
- pep8 --exclude=IPy.py --ignore=E501 vrtManager accounts computes \ - pep8 --exclude=IPy.py --ignore=E501 vrtManager accounts admin appsettings computes \
console create datasource instances interfaces \ console create datasource instances interfaces \
logs networks nwfilters secrets storages logs networks nwfilters secrets storages
- pyflakes vrtManager accounts computes console create datasource instances interfaces \ - pyflakes vrtManager accounts admin appsettings computes console create datasource instances interfaces \
nwfilters networks secrets storages logs nwfilters networks secrets storages logs
- python manage.py migrate - python manage.py migrate
- python manage.py test --settings=webvirtcloud.settings-dev - python manage.py test --settings=webvirtcloud.settings-dev

View file

@ -1,5 +1,5 @@
## WebVirtCloud ## WebVirtCloud
###### Python3 & Django 2.2.12 ###### Python3 & Django 2.2
## Features ## Features
* QEMU/KVM Hypervisor Management * QEMU/KVM Hypervisor Management
@ -301,7 +301,7 @@ datasource:
``` ```
### Reverse-Proxy ### Reverse-Proxy
Edit WS_PUBLIC_PORT at settings.py file to expose redirect to 80. Default: 6080 Edit WS_PUBLIC_PORT at settings.py file to expose redirect to 80 or 443. Default: 6080
``` ```
WS_PUBLIC_PORT = 80 WS_PUBLIC_PORT = 80
``` ```
@ -330,7 +330,7 @@ pip install -r conf/requirements.txt
``` ```
Run tests Run tests
```bash ```bash
python menage.py test python manage.py test
``` ```
### Screenshots ### Screenshots

View file

@ -6,6 +6,7 @@ from django.utils.translation import ugettext_lazy as _
from instances.models import Instance from instances.models import Instance
class UserInstanceManager(models.Manager): class UserInstanceManager(models.Manager):
def get_queryset(self): def get_queryset(self):
return super().get_queryset().select_related('instance', 'user') return super().get_queryset().select_related('instance', 'user')

View file

@ -0,0 +1,35 @@
# Generated by Django 2.2.13 on 2020-07-16 06:37
from django.db import migrations
from django.utils.translation import ugettext_lazy as _
def add_default_settings(apps, schema_editor):
setting = apps.get_model("appsettings", "AppSettings")
db_alias = schema_editor.connection.alias
setting.objects.using(db_alias).bulk_create([
setting(27, _("Console Scale"), "CONSOLE_SCALE", "False", "True,False", _("Allow console to scaling view")),
setting(28, _("Console View-Only"), "CONSOLE_VIEW_ONLY", "False", "True,False", _("Allow only view not modify")),
setting(29, _("Console Resize Session"), "CONSOLE_RESIZE_SESSION", "False", "True,False", _("Allow to resize session for console")),
setting(30, _("Console Clip Viewport"), "CONSOLE_CLIP_VIEWPORT", "False", "True,False", _("Clip console viewport")),
])
def del_default_settings(apps, schema_editor):
setting = apps.get_model("appsettings", "AppSettings")
db_alias = schema_editor.connection.alias
setting.objects.using(db_alias).filter(key="CONSOLE_SCALE").delete()
setting.objects.using(db_alias).filter(key="CONSOLE_VIEW_ONLY").delete()
setting.objects.using(db_alias).filter(key="CONSOLE_RESIZE_SESSION").delete()
setting.objects.using(db_alias).filter(key="CONSOLE_CLIP_VIEWPORT").delete()
class Migration(migrations.Migration):
dependencies = [
('appsettings', '0003_auto_20200615_0637'),
]
operations = [
migrations.RunPython(add_default_settings, del_default_settings),
]

View file

@ -112,10 +112,5 @@
{% endblock %} {% endblock %}
{% block script %} {% block script %}
<script src="{% static "js/sortable.min.js" %}"></script> <script src="{% static "js/sortable.min.js" %}"></script>
<script>
function open_console(uuid) {
window.open("{% url 'console' %}?token=" + uuid, "", "width=850,height=685");
}
</script>
<script src="{% static 'js/filter-table.js' %}"></script> <script src="{% static 'js/filter-table.js' %}"></script>
{% endblock %} {% endblock %}

View file

@ -1,19 +0,0 @@
beautifulsoup4==4.9.1
coverage==5.1
Django==2.2.13
django-bootstrap4==2.0.1
django-debug-toolbar==2.2
django-icons==2.0.0
django-login-required-middleware==0.5.0
gunicorn==20.0.4
libsass==0.20.0
libvirt-python==6.3.0
lxml==4.5.0
numpy==1.18.4
pytz==2020.1
rwlock==0.0.7
six==1.15.0
soupsieve==2.0.1
sqlparse==0.3.1
websockify==0.9.0
yapf==0.30.0

View file

@ -1,13 +1,13 @@
beautifulsoup4==4.9.1 beautifulsoup4==4.9.1
Django==2.2.13 Django==2.2.14
django-bootstrap4==2.0.1 django-bootstrap4==2.2.0
django-icons==2.0.0 django-icons==2.1.1
django-login-required-middleware==0.5.0 django-login-required-middleware==0.5.0
gunicorn==20.0.4 gunicorn==20.0.4
libsass==0.20.0 libsass==0.20.0
libvirt-python==6.3.0 libvirt-python==6.4.0
lxml==4.5.0 lxml==4.5.2
numpy==1.18.4 numpy==1.18.5
pytz==2020.1 pytz==2020.1
rwlock==0.0.7 rwlock==0.0.7
six==1.15.0 six==1.15.0

View file

@ -199,7 +199,11 @@
<label for="port">{% trans 'Port' %}:</label> <label for="port">{% trans 'Port' %}:</label>
<input type='text' id='port' value='{{ ws_port }}'> <input type='text' id='port' value='{{ ws_port }}'>
<label for="password">{% trans 'Password' %}:</label> <label for="password">{% trans 'Password' %}:</label>
<input type='password' id='password'> {% if perms.instances.passwordless_console %}
<input type='password' id='password' value='{{ console_passwd }}'>
{% else %}
<input type='password' id='password'>
{% endif %}
<label for="show_console">{% trans 'Show console' %}</label> <label for="show_console">{% trans 'Show console' %}</label>
<input type="checkbox" id="show_console" value="1" onchange="toggle_console()" checked> <input type="checkbox" id="show_console" value="1" onchange="toggle_console()" checked>
<button id="connectButton">{% trans 'Start' %}</button> <button id="connectButton">{% trans 'Start' %}</button>

View file

@ -93,7 +93,11 @@
} }
if (password === undefined) { if (password === undefined) {
password = spice_query_var('password', ''); {% if perms.instances.passwordless_console %}
password = '{{ console_passwd }}';
{% else %}
password = prompt('{% trans "Password" %}');
{% endif %}
//password = '{{ console_passwd | safe }}'; //password = '{{ console_passwd | safe }}';
} }
if (password === 'None') password = ''; if (password === 'None') password = '';

View file

@ -297,7 +297,11 @@
<ul> <ul>
<li> <li>
<label>Password:</label> <label>Password:</label>
<input id="noVNC_password_input" type="password" /> {% if perms.instances.passwordless_console %}
<input id="noVNC_password_input" type="password" value='{{ console_passwd }}' />
{% else %}
<input id="noVNC_password_input" type="password" />
{% endif %}
</li> </li>
<li> <li>
<input id="noVNC_password_button" type="submit" value="Send Password" class="noVNC_submit" /> <input id="noVNC_password_button" type="submit" value="Send Password" class="noVNC_submit" />

View file

@ -167,7 +167,13 @@
// By default, use the host and port of server that served this file // By default, use the host and port of server that served this file
const host = readQueryVariable('host', '{{ ws_host }}'); const host = readQueryVariable('host', '{{ ws_host }}');
let port = readQueryVariable('port', '{{ ws_port }}'); let port = readQueryVariable('port', '{{ ws_port }}');
const password = readQueryVariable('password');
{% if perms.instances.passwordless_console %}
const password = '{{ console_passwd }}';
{% else %}
const password = readQueryVariable('password');
{% endif %}
//const path = readQueryVariable('path', 'websockify'); //const path = readQueryVariable('path', 'websockify');
const path = readQueryVariable('path', '{{ ws_path }}'); const path = readQueryVariable('path', '{{ ws_path }}');
@ -202,10 +208,10 @@
rfb.addEventListener("capabilities", function () { updatePowerButtons(); }); rfb.addEventListener("capabilities", function () { updatePowerButtons(); });
// Set parameters that can be changed on an active connection // Set parameters that can be changed on an active connection
rfb.viewOnly = readQueryVariable('view_only', {{ view_only }}); rfb.scaleViewport = {{ scale }};
rfb.scaleViewport = readQueryVariable('scale', {{ scale }}); rfb.viewOnly = {{ view_only }};
rfb.resizeSession = readQueryVariable('resize', {{ resize_session }}); rfb.resizeSession = {{ resize_session }};
rfb.clipViewport = readQueryVariable('clip_viewport', {{ clip_viewport }}); rfb.clipViewport = {{ clip_viewport }};
</script> </script>
{% endblock %} {% endblock %}

View file

@ -1,9 +1,13 @@
import re import re
from django.shortcuts import render from django.shortcuts import render
from libvirt import libvirtError from libvirt import libvirtError
from appsettings.settings import app_settings
from instances.models import Instance from instances.models import Instance
from vrtManager.instance import wvmInstance from vrtManager.instance import wvmInstance
from webvirtcloud.settings import WS_PUBLIC_PATH, WS_PUBLIC_PORT, WS_PUBLIC_HOST from webvirtcloud.settings import (WS_PUBLIC_HOST, WS_PUBLIC_PATH,
WS_PUBLIC_PORT)
def console(request): def console(request):
@ -16,10 +20,10 @@ def console(request):
if request.method == 'GET': if request.method == 'GET':
token = request.GET.get('token', '') token = request.GET.get('token', '')
view_type = request.GET.get('view', 'lite') view_type = request.GET.get('view', 'lite')
view_only = request.GET.get('view_only', 0) view_only = request.GET.get('view_only', app_settings.CONSOLE_VIEW_ONLY.lower())
scale = request.GET.get('scale', 0) scale = request.GET.get('scale', app_settings.CONSOLE_SCALE.lower())
resize_session = request.GET.get('resize_session', 0) resize_session = request.GET.get('resize_session', app_settings.CONSOLE_RESIZE_SESSION.lower())
clip_viewport = request.GET.get('clip_viewport', 0) clip_viewport = request.GET.get('clip_viewport', app_settings.CONSOLE_CLIP_VIEWPORT.lower())
try: try:
temptoken = token.split('-', 1) temptoken = token.split('-', 1)

View file

@ -1,5 +1,7 @@
-r ../conf/requirements.txt -r ../conf/requirements.txt
coverage==5.1 coverage==5.2
pycodestyle django-debug-toolbar==2.2
pycodestyle==2.6.0
pyflakes==2.2.0 pyflakes==2.2.0
pylint==2.5.2 pylint==2.5.3
yapf==0.30.0

View file

@ -22,6 +22,18 @@ def migrate_can_clone_instances(sender, **kwargs):
user.user_permissions.add(permission) user.user_permissions.add(permission)
break break
def apply_passwordless_console(sender, **kwargs):
'''
Apply new passwordless_console permission for all users
'''
from django.conf import settings
from django.contrib.auth.models import User, Permission
print('\033[92mApplying permission passwordless_console for all users\033[0m')
users = User.objects.all()
permission = Permission.objects.get(codename='passwordless_console')
for user in users:
user.user_permissions.add(permission)
class InstancesConfig(AppConfig): class InstancesConfig(AppConfig):
name = 'instances' name = 'instances'
@ -29,3 +41,4 @@ class InstancesConfig(AppConfig):
def ready(self): def ready(self):
post_migrate.connect(migrate_can_clone_instances, sender=self) post_migrate.connect(migrate_can_clone_instances, sender=self)
post_migrate.connect(apply_passwordless_console, sender=self)

View file

@ -0,0 +1,17 @@
# Generated by Django 2.2.13 on 2020-07-17 05:24
from django.db import migrations
class Migration(migrations.Migration):
dependencies = [
('instances', '0008_auto_20200708_0950'),
]
operations = [
migrations.AlterModelOptions(
name='permissionset',
options={'default_permissions': (), 'managed': False, 'permissions': [('clone_instances', 'Can clone instances'), ('passwordless_console', 'Can access console without password')]},
),
]

View file

@ -211,6 +211,8 @@ class PermissionSet(models.Model):
""" """
class Meta: class Meta:
default_permissions = () default_permissions = ()
permissions = (('clone_instances', _('Can clone instances')), ) permissions = [('clone_instances', 'Can clone instances'),
('passwordless_console', _('Can access console without password')),
]
managed = False managed = False

View file

@ -38,11 +38,6 @@
{% endblock content %} {% endblock content %}
{% block script %} {% block script %}
<script src="{% static "js/sortable.min.js" %}"></script> <script src="{% static "js/sortable.min.js" %}"></script>
<script>
function open_console(uuid) {
window.open("{% url 'console' %}?token=" + uuid, "", "width=850,height=485");
}
</script>
<script src="{% static 'js/filter-table.js' %}"></script> <script src="{% static 'js/filter-table.js' %}"></script>
{% if request.user.is_superuser %} {% if request.user.is_superuser %}
<script> <script>

View file

@ -166,11 +166,6 @@
input.val(editor.getSession().getValue()); input.val(editor.getSession().getValue());
}); });
</script> </script>
<script>
function open_console(view_style) {
window.open('{% url 'console' %}?token={{ compute.id }}-{{ instance.get_uuid }}&view=' + view_style +'', '', 'width=850,height=600')
}
</script>
<script> <script>
function random_mac(net) { function random_mac(net) {
$.getJSON('{% url 'instances:random_mac_address' %}', function (data) { $.getJSON('{% url 'instances:random_mac_address' %}', function (data) {

View file

@ -42,4 +42,12 @@
<span class="fa fa-eye"></span> <span class="fa fa-eye"></span>
</button> </button>
{% endif %} {% endif %}
</form> </form>
{% block script %}
<script>
function open_console(uuid) {
url = '{% url 'console' %}?token=' + uuid + '';
window.open(url, '', 'width=850,height=650')
}
</script>
{% endblock script %}

View file

@ -4,13 +4,15 @@
<!-- Nav tabs --> <!-- Nav tabs -->
<ul class="nav nav-tabs" role="tablist"> <ul class="nav nav-tabs" role="tablist">
<li class="nav-item"> <li class="nav-item">
<a class="nav-link text-secondary active" href="#vnconsole" aria-controls="vnconsole" role="tab" data-toggle="tab"> <a class="nav-link text-secondary active" href="#vnconsole" aria-controls="vnconsole" role="tab"
data-toggle="tab">
{% trans "Console" %} {% trans "Console" %}
</a> </a>
</li> </li>
{% if app_settings.SHOW_ACCESS_ROOT_PASSWORD == 'True' %} {% if app_settings.SHOW_ACCESS_ROOT_PASSWORD == 'True' %}
<li class="nav-item"> <li class="nav-item">
<a class="nav-link text-secondary" href="#rootpasswd" aria-controls="rootpasswd" role="tab" data-toggle="tab"> <a class="nav-link text-secondary" href="#rootpasswd" aria-controls="rootpasswd" role="tab"
data-toggle="tab">
{% trans "Root Password" %} {% trans "Root Password" %}
</a> </a>
</li> </li>
@ -24,7 +26,8 @@
{% endif %} {% endif %}
{% if instance.status == 1 %} {% if instance.status == 1 %}
<li class="nav-item"> <li class="nav-item">
<a class="nav-link text-secondary" href="#vdiconsole" aria-controls="vdiconsole" role="tab" data-toggle="tab"> <a class="nav-link text-secondary" href="#vdiconsole" aria-controls="vdiconsole" role="tab"
data-toggle="tab">
{% trans "VDI" %} {% trans "VDI" %}
</a> </a>
</li> </li>
@ -33,38 +36,83 @@
<!-- Tab panes --> <!-- Tab panes -->
<div class="tab-content"> <div class="tab-content">
<div role="tabpanel" class="tab-pane tab-pane-bordered active" id="vnconsole"> <div role="tabpanel" class="tab-pane tab-pane-bordered active" id="vnconsole">
<p>{% trans "This action opens a new window with a VNC connection to the console of the instance." %}</p> <p>{% blocktrans with type=instance.console_type|upper %} This action opens a new window with a {{ type }} connection to the console of the instance.{% endblocktrans %}
{% if instance.status == 1 %} </p>
<!-- Split button --> {% if instance.console_type == 'vnc' %}
<div class="btn-group float-right"> <div class="ml-3 form-row">
<button type="button" id="consoleBtnGroup" class="btn btn-lg btn-success" onclick="open_console('lite')">{% trans 'Console' %}</button> <div class="custom-control custom-switch">
<button type="button" class="btn btn-success dropdown-toggle dropdown-toggle-split" data-toggle="dropdown" aria-haspopup="true" aria-expanded="false"> <input class="custom-control-input" type="checkbox" name="scale"
<span class="sr-only">{% trans 'Toggle Dropdown' %}</span> {% if app_settings.CONSOLE_SCALE == 'True' %} checked {% endif %}
</button> id="scale">
<div class="dropdown-menu"> <label class="custom-control-label font-weight-bold" for="scale">{% trans "Scale" %}</label>
<a class="dropdown-item" href="#" title="{% trans "Console port" %}: {{ instance.console_port }}" onclick="open_console('lite')">{% trans "Console" %} - {% trans "Lite" %}</a>
<a class="dropdown-item" href="#" title="{% trans "Console port" %}: {{ instance.console_port }}" onclick="open_console('full')">{% trans "Console" %} - {% trans "Full" %}</a>
</div> </div>
</div> </div>
<div class="ml-3 form-row">
<div class="custom-control custom-switch">
<input class="custom-control-input" type="checkbox" name="view_only"
{% if app_settings.CONSOLE_VIEW_ONLY == 'True' %} checked {% endif %}
id="view_only">
<label class="custom-control-label font-weight-bold" for="view_only">{% trans "View Only" %}</label>
</div>
</div>
<div class="ml-3 form-row">
<div class="custom-control custom-switch">
<input class="custom-control-input" type="checkbox" name="resize_session"
{% if app_settings.CONSOLE_RESIZE_SESSION == 'True' %} checked {% endif %}
id="resize_session">
<label class="custom-control-label font-weight-bold" for="resize_session">{% trans "Resize Session" %}</label>
</div>
</div>
<div class="ml-3 form-row">
<div class="custom-control custom-switch">
<input class="custom-control-input" type="checkbox" name="clip_viewport"
{% if app_settings.CONSOLE_CLIP_VIEWPORT == 'True' %} checked {% endif %}
id="clip_viewport">
<label class="custom-control-label font-weight-bold" for="clip_viewport">{% trans "View Clipboard" %}</label>
</div>
</div>
{% endif %}
{% if instance.status == 1 %}
<!-- Split button -->
<div class="btn-group float-right">
<button type="button" id="consoleBtnGroup" class="btn btn-lg btn-success"
onclick="open_console('lite')">{% trans 'Console' %}</button>
<button type="button" class="btn btn-success dropdown-toggle dropdown-toggle-split"
data-toggle="dropdown" aria-haspopup="true" aria-expanded="false">
<span class="sr-only">{% trans 'Toggle Dropdown' %}</span>
</button>
<div class="dropdown-menu">
<a class="dropdown-item" href="#"
title="{% trans "Console port" %}: {{ instance.console_port }}"
onclick="open_console('lite')">{% trans "Console" %} - {% trans "Lite" %}</a>
<a class="dropdown-item" href="#"
title="{% trans "Console port" %}: {{ instance.console_port }}"
onclick="open_console('full')">{% trans "Console" %} - {% trans "Full" %}</a>
</div>
</div>
{% else %} {% else %}
<button class="btn btn-lg btn-success float-right disabled">{% trans "Console" %}</button> <button class="btn btn-lg btn-success float-right disabled">{% trans "Console" %}</button>
{% endif %} {% endif %}
<div class="clearfix"></div> <div class="clearfix"></div>
</div> </div>
{% if app_settings.SHOW_ACCESS_SSH_KEYS == 'True' %} {% if app_settings.SHOW_ACCESS_ROOT_PASSWORD == 'True' %}
<div role="tabpanel" class="tab-pane tab-pane-bordered" id="rootpasswd"> <div role="tabpanel" class="tab-pane tab-pane-bordered" id="rootpasswd">
<p>{% trans "You need shut down your instance and enter a new root password." %}</p> <p>{% trans "You need shut down your instance and enter a new root password." %}</p>
<form action="{% url 'instances:rootpasswd' instance.id %}" class="form-inline" method="post" role="form" aria-label="Add root password to instance form"> <form action="{% url 'instances:rootpasswd' instance.id %}" class="form-inline" method="post"
role="form" aria-label="Add root password to instance form">
{% csrf_token %} {% csrf_token %}
<div class="form-group row"> <div class="form-group row">
<div class="col-sm-12"> <div class="col-sm-12">
<input type="text" class="form-control-lg" name="passwd" placeholder="{% trans "Enter Password" %}" maxlength="24"> <input type="text" class="form-control-lg" name="passwd"
placeholder="{% trans "Enter Password" %}" maxlength="24">
</div> </div>
</div> </div>
{% if instance.status == 5 %} {% if instance.status == 5 %}
<input type="submit" class="btn btn-lg btn-success float-right" name="rootpasswd" value="{% trans "Reset Root Password" %}"> <input type="submit" class="btn btn-lg btn-success float-right" name="rootpasswd"
value="{% trans "Reset Root Password" %}">
{% else %} {% else %}
<button class="btn btn-lg btn-success float-right disabled">{% trans "Reset Root Password" %}</button> <button
class="btn btn-lg btn-success float-right disabled">{% trans "Reset Root Password" %}</button>
{% endif %} {% endif %}
</form> </form>
<div class="clearfix"></div> <div class="clearfix"></div>
@ -73,25 +121,27 @@
{% if app_settings.SHOW_ACCESS_SSH_KEYS == 'True' %} {% if app_settings.SHOW_ACCESS_SSH_KEYS == 'True' %}
<div role="tabpanel" class="tab-pane tab-pane-bordered" id="sshkeys"> <div role="tabpanel" class="tab-pane tab-pane-bordered" id="sshkeys">
<p>{% trans "You need shut down your instance and choose your public key." %}</p> <p>{% trans "You need shut down your instance and choose your public key." %}</p>
<form action="{% url 'instances:add_public_key' instance.id %}" class="form-inline" method="post" role="form" aria-label="Add public key to instance form"> <form action="{% url 'instances:add_public_key' instance.id %}" class="form-inline" method="post"
role="form" aria-label="Add public key to instance form">
{% csrf_token %} {% csrf_token %}
<div class="form-group row"> <div class="form-group row">
<div class="col-sm-12"> <div class="col-sm-12">
<select name="sshkeyid" class="form-control-lg keyselect"> <select name="sshkeyid" class="form-control-lg keyselect">
{% if publickeys %} {% if publickeys %}
{% for key in publickeys %} {% for key in publickeys %}
<option value="{{ key.id }}">{{ key.keyname }}</option> <option value="{{ key.id }}">{{ key.keyname }}</option>
{% endfor %} {% endfor %}
{% else %} {% else %}
<option value="None">{% trans "None" %}</option> <option value="None">{% trans "None" %}</option>
{% endif %} {% endif %}
</select> </select>
</div> </div>
</div> </div>
{% if instance.status == 5 %} {% if instance.status == 5 %}
<input type="submit" class="btn btn-lg btn-success float-right" name="addpublickey" value="{% trans "Add Public Key" %}"> <input type="submit" class="btn btn-lg btn-success float-right" name="addpublickey"
value="{% trans "Add Public Key" %}">
{% else %} {% else %}
<button class="btn btn-lg btn-success float-right disabled">{% trans "Add Public Key" %}</button> <button class="btn btn-lg btn-success float-right disabled">{% trans "Add Public Key" %}</button>
{% endif %} {% endif %}
</form> </form>
<div class="clearfix"></div> <div class="clearfix"></div>
@ -101,9 +151,9 @@
<div role="tabpanel" class="tab-pane tab-pane-bordered" id="vdiconsole"> <div role="tabpanel" class="tab-pane tab-pane-bordered" id="vdiconsole">
<p>{% trans "This action opens a remote viewer with a connection to the console of the instance." %}</p> <p>{% trans "This action opens a remote viewer with a connection to the console of the instance." %}</p>
<div class="input-group"> <div class="input-group">
<input type="text" class="input-lg disabled form-control" disabled id="vdi_url_input"/> <input type="text" class="input-lg disabled form-control" disabled id="vdi_url_input" />
<span class="input-group-append"> <span class="input-group-append">
<a href="#" class="btn btn-success" id="vdi_url" >{% trans "VDI" %}</a> <a href="#" class="btn btn-success" id="vdi_url">{% trans "VDI" %}</a>
</span> </span>
</div> </div>
<div class="clearfix"></div> <div class="clearfix"></div>
@ -112,3 +162,15 @@
</div> </div>
</div> </div>
</div> </div>
{% block script %}
<script>
function open_console(view_style) {
const sc = $("#scale").is(':checked');
const vo = $("#view_only").is(':checked');
const rs = $("#resize_session").is(':checked');
const cv = $("#clip_viewport").is(':checked');
url = '{% url 'console' %}?token={{ compute.id }}-{{ instance.get_uuid }}&view=' + view_style + '' + '&view_only=' + vo + '' + '&scale=' + sc + '' + '&clip_viewport=' + cv + '' + '&resize_session=' + rs + '';
window.open(url, '', 'width=850,height=600')
}
</script>
{% endblock %}

View file

@ -9,3 +9,20 @@ from webvirtcloud.settings import *
DEBUG = True DEBUG = True
TEMPLATE_DEBUG = True TEMPLATE_DEBUG = True
INSTALLED_APPS += [
'debug_toolbar',
]
MIDDLEWARE += [
'debug_toolbar.middleware.DebugToolbarMiddleware',
]
# DebugToolBar
INTERNAL_IPS = (
'127.0.0.1',
)
DEBUG_TOOLBAR_CONFIG = {
'INTERCEPT_REDIRECTS': False,
}

View file

@ -10,7 +10,7 @@ BASE_DIR = os.path.dirname(os.path.dirname(os.path.abspath(__file__)))
SECRET_KEY = '' SECRET_KEY = ''
DEBUG = True DEBUG = False
ALLOWED_HOSTS = ['*'] ALLOWED_HOSTS = ['*']

View file

@ -1,8 +1,9 @@
from django.conf import settings
from django.urls import include, path from django.urls import include, path
from instances.views import index
from console.views import console
from appsettings.views import appsettings from appsettings.views import appsettings
from console.views import console
from instances.views import index
urlpatterns = [ urlpatterns = [
path('', index, name='index'), path('', index, name='index'),
@ -16,3 +17,10 @@ urlpatterns = [
path('i18n/', include('django.conf.urls.i18n')), path('i18n/', include('django.conf.urls.i18n')),
path('logs/', include('logs.urls')), path('logs/', include('logs.urls')),
] ]
if settings.DEBUG:
import debug_toolbar
urlpatterns += [
path('__debug__/', include(debug_toolbar.urls)),
]