Compare commits

...

11 commits
v0.1.0 ... main

Author SHA1 Message Date
Matthew Penning 919f510f1f
Merge pull request #10 from PenningLabs/v0.4.0
V0.4.0
2023-11-14 22:18:32 -05:00
matthewalanpenning 08eb67e0d4 v0.4.0 2023-11-11 13:34:27 -05:00
matthewalanpenning 058485d5b1 v0.4.0 2023-11-01 06:21:44 -04:00
matthewalanpenning a06e67f489 v0.4.0 2023-10-31 06:34:14 -04:00
matthewalanpenning c74597cb0c v0.4.0 2023-10-31 05:50:26 -04:00
matthewalanpenning d25c685760 v0.4.0 2023-10-29 22:52:51 -04:00
matthewalanpenning 287d28fb10 v0.4.0 2023-10-24 05:28:27 -04:00
matthewalanpenning a51b003a2a v0.3.0 2023-10-07 19:39:42 -04:00
matthewalanpenning f9eebfef5e v0.3.0 2023-10-07 19:30:17 -04:00
matthewalanpenning a463cd670c v0.2.1 2023-06-08 19:46:41 -04:00
matthewalanpenning bdc878e1b6 v0.2.0 2023-06-04 15:52:38 -04:00
2094 changed files with 7486 additions and 688893 deletions

View file

@ -1,3 +1,33 @@
# 0.4.0
- Upgraded Bootstrap from version 4 to version 5
- Converted containers and virtual-machines endpoints to instances endpoint to support Incus
- Combined containers and virtual-machines pages to instances page
- Datatable errors now display on console.log rather than the default alert
- Handled 404 error for logs on a new virtual machine
- Fixed several undefined value errors that may occur
- Updated virtual-machine cpu and memory functions to no longer use sleep
# 0.3.0
- Improved Dockerfile for quicker builds
- Added version specific flask and werkzeug to requirements due to build error in dependencies
- Added a Network Zones page
- Added a Network page with DHCP Leases, Network Load Balancers, Forwards, and Peers
- Added missing parameters in API for creating a network
- Upgraded jQuery to version 3.7.1
- Updated layout to container and virtual machines pages
# 0.2.1
- Updated local xterm.js packages to version 5.1.0 and loading from local file
- Modified CSS to hide terminal scrollbar in chrome based browsers
- Added dynamic resize of terminal when sidebar is toggled
# 0.2.0
- Added cluster groups
- Added evacuate and restore options for cluster members
- Added cluster members roles to tables
- Added cluster members actions
- Removed serializeJSON library in favor of jquery serialize
# 0.1.0
- Corrected image unit size, changing GiB to MiB
- Added option filter for storage volumes by adding filter=custom to URL

View file

@ -1,13 +1,14 @@
FROM python:3.10.6
RUN mkdir -p /opt/lxconsole
ADD lxconsole /opt/lxconsole/lxconsole
COPY requirements.txt /opt/lxconsole/requirements.txt
COPY run.py /opt/lxconsole/run.py
COPY requirements.txt /opt/lxconsole/requirements.txt
RUN pip install --upgrade pip
RUN pip3 install -r /opt/lxconsole/requirements.txt
ADD lxconsole /opt/lxconsole/lxconsole
COPY run.py /opt/lxconsole/run.py
RUN apt update
RUN apt install sqlite3

View file

@ -2,21 +2,22 @@ from flask import Flask, Blueprint
from . import server
from . import servers
from . import certificates
from . import cluster_groups
from . import cluster_members
from . import images
from . import container
from . import containers
from . import instance
from . import instances
from . import network
from . import networks
from . import network_acl
from . import network_acls
from . import network_zones
from . import profiles
from . import operations
from . import projects
from . import simplestreams
from . import storage_pools
from . import storage_volumes
from . import virtual_machine
from . import virtual_machines
from . import users
from . import groups
@ -29,24 +30,25 @@ api = Blueprint('api', __name__, url_prefix='/api')
# URLs are prefixed with /api...
api.add_url_rule('/container/<endpoint>', view_func=container.api_container_endpoint, methods=['GET', 'POST'])
api.add_url_rule('/containers/<endpoint>', view_func=containers.api_containers_endpoint, methods=['GET', 'POST'])
api.add_url_rule('/instance/<endpoint>', view_func=instance.api_instance_endpoint, methods=['GET', 'POST'])
api.add_url_rule('/instances/<endpoint>', view_func=instances.api_instances_endpoint, methods=['GET', 'POST'])
api.add_url_rule('/servers/<endpoint>', view_func=servers.api_servers_endpoint, methods=['GET', 'POST'])
api.add_url_rule('/server/<endpoint>', view_func=server.api_server_endpoint)
api.add_url_rule('/certificates/<endpoint>', view_func=certificates.api_certificates_endpoint, methods=['GET', 'POST'])
api.add_url_rule('/cluster-groups/<endpoint>', view_func=cluster_groups.api_cluster_groups_endpoint, methods=['GET', 'POST'])
api.add_url_rule('/cluster-members/<endpoint>', view_func=cluster_members.api_cluster_members_endpoint, methods=['GET', 'POST'])
api.add_url_rule('/images/<endpoint>', view_func=images.api_images_endpoint, methods=['GET', 'POST'])
api.add_url_rule('/network/<endpoint>', view_func=network.api_network_endpoint, methods=['GET', 'POST'])
api.add_url_rule('/networks/<endpoint>', view_func=networks.api_networks_endpoint, methods=['GET', 'POST'])
api.add_url_rule('/network-acl/<endpoint>', view_func=network_acl.api_network_acl_endpoint, methods=['GET', 'POST'])
api.add_url_rule('/network-acls/<endpoint>', view_func=network_acls.api_network_acls_endpoint, methods=['GET', 'POST'])
api.add_url_rule('/network-zones/<endpoint>', view_func=network_zones.api_network_zones_endpoint, methods=['GET', 'POST'])
api.add_url_rule('/profiles/<endpoint>', view_func=profiles.api_profiles_endpoint, methods=['GET', 'POST'])
api.add_url_rule('/operations/<endpoint>', view_func=operations.api_operations_endpoint, methods=['GET', 'POST'])
api.add_url_rule('/projects/<endpoint>', view_func=projects.api_projects_endpoint, methods=['GET', 'POST'])
api.add_url_rule('/simplestreams/<endpoint>', view_func=simplestreams.api_simplestreams_endpoint, methods=['GET', 'POST'])
api.add_url_rule('/storage-pools/<endpoint>', view_func=storage_pools.api_storage_pools_endpoint, methods=['GET', 'POST'])
api.add_url_rule('/storage-volumes/<endpoint>', view_func=storage_volumes.api_storage_volumes_endpoint, methods=['GET', 'POST'])
api.add_url_rule('/virtual-machine/<endpoint>', view_func=virtual_machine.api_virtual_machine_endpoint, methods=['GET', 'POST'])
api.add_url_rule('/virtual-machines/<endpoint>', view_func=virtual_machines.api_virtual_machines_endpoint, methods=['GET', 'POST'])
api.add_url_rule('/users/<endpoint>', view_func=users.api_users_endpoint, methods=['GET', 'POST'])
api.add_url_rule('/groups/<endpoint>', view_func=groups.api_groups_endpoint, methods=['GET', 'POST'])

View file

@ -11,6 +11,7 @@ def privilege_check(privilege, server_id = 0):
'Auditor' : [
#'add_access_control',
#'add_certificate',
#'add_cluster_group',
#'add_cluster_member',
#'add_group',
#'add_server',
@ -23,6 +24,10 @@ def privilege_check(privilege, server_id = 0):
#'add_instance_usb_device',
#'add_instance',
#'add_network_acl',
#'add_network_zone',
#'add_network_load_balancer',
#'add_network_forward',
#'add_network_peer',
#'add_network',
#'add_profile',
#'add_project',
@ -32,13 +37,16 @@ def privilege_check(privilege, server_id = 0):
#'add_storage_volume',
#'add_user',
#'attach_instance_profile',
#'change_cluster_member_state',
#'change_instance_state',
#'copy_instance',
'copy_instance_proc_stat',
#'create_instance_backup',
#'create_instance_snapshot_instance',
#'create_instance_snapshot',
#'delete_access_control',
#'delete_certificate',
#'delete_cluster_group',
#'delete_cluster_member',
#'delete_group',
#'delete_image',
@ -49,6 +57,10 @@ def privilege_check(privilege, server_id = 0):
#'delete_instance',
#'delete_instance',
#'delete_network_acl',
#'delete_network_zone',
#'delete_network_load_balancer',
#'delete_network_forward',
#'delete_network_peer',
#'delete_network',
#'delete_operation',
#'delete_profile',
@ -65,18 +77,18 @@ def privilege_check(privilege, server_id = 0):
#'export_instance_backup',
'get_access_control',
'get_group',
'get_network_state',
'get_server_info',
'get_server_initial_project',
'get_server_resources',
'get_server_warnings',
'get_server',
'get_instance_cpu_percentage',
'get_instance_cpu_usage',
'get_instance_disk_devices',
'get_instance_gpu_devices',
'get_instance_interfaces',
'get_instance_memory_percentage',
'get_instance_network_devices',
'get_instance_proc_stat',
'get_instance_proxy_devices',
'get_instance_state',
'get_instance_unix_devices',
@ -88,6 +100,7 @@ def privilege_check(privilege, server_id = 0):
'is_cluster_member_enabled',
'list_access_controls',
'list_certificates',
'list_cluster_groups',
'list_cluster_members',
'list_groups',
'list_servers',
@ -98,6 +111,11 @@ def privilege_check(privilege, server_id = 0):
'list_instances',
'list_logs',
'list_network_acls',
'list_network_forwards',
'list_network_leases',
'list_network_load_balancers',
'list_network_peers',
'list_network_zones',
'list_network_managed_devices',
'list_networks',
'list_operations',
@ -110,10 +128,16 @@ def privilege_check(privilege, server_id = 0):
'list_storage_volumes',
'list_users',
'load_certificate',
'load_cluster_group',
'load_cluster_member',
'load_image',
'load_instance',
'load_network_acl',
'load_network_forward',
'load_network_lease',
'load_network_load_balancer',
'load_network_peer',
'load_network_zone',
'load_network',
'load_operation',
'load_profile',
@ -129,12 +153,18 @@ def privilege_check(privilege, server_id = 0):
#'restore_instance_snapshot',
#'update_access_control',
#'update_certificate',
#'update_cluster_group',
#'update_cluster_member',
#'update_group',
#'update_server',
#'update_image',
#'update_instance',
#'update_network_acl',
#'update_network_forward',
#'update_network_lease',
#'update_network_load_balancer',
#'update_network_peer',
#'update_network_zone',
#'update_network',
#'update_profile',
#'update_project',
@ -147,6 +177,7 @@ def privilege_check(privilege, server_id = 0):
'User': [
#'add_access_control',
#'add_certificate',
#'add_cluster_group',
#'add_cluster_member',
#'add_group',
#'add_server',
@ -159,6 +190,10 @@ def privilege_check(privilege, server_id = 0):
#'add_instance_usb_device',
#'add_instance',
#'add_network_acl',
#'add_network_zone',
#'add_network_load_balancer',
#'add_network_forward',
#'add_network_peer',
#'add_network',
#'add_profile',
#'add_project',
@ -168,13 +203,16 @@ def privilege_check(privilege, server_id = 0):
#'add_storage_volume',
#'add_user',
#'attach_instance_profile',
'change_cluster_member_state',
'change_instance_state',
'copy_instance',
'copy_instance_proc_stat',
'create_instance_backup',
'create_instance_snapshot_instance',
'create_instance_snapshot',
#'delete_access_control',
#'delete_certificate',
#'delete_cluster_group',
#'delete_cluster_member',
#'delete_group',
#'delete_image',
@ -185,6 +223,10 @@ def privilege_check(privilege, server_id = 0):
#'delete_instance',
#'delete_instance',
#'delete_network_acl',
#'delete_network_zone',
#'delete_network_load_balancer',
#'delete_network_forward',
#'delete_network_peer',
#'delete_network',
#'delete_operation',
#'delete_profile',
@ -201,18 +243,18 @@ def privilege_check(privilege, server_id = 0):
'export_instance_backup',
'get_access_control',
'get_group',
'get_network_state',
'get_server_info',
'get_server_initial_project',
'get_server_resources',
'get_server_warnings',
'get_server',
'get_instance_cpu_percentage',
'get_instance_cpu_usage',
'get_instance_disk_devices',
'get_instance_gpu_devices',
'get_instance_interfaces',
'get_instance_memory_percentage',
'get_instance_network_devices',
'get_instance_proc_stat',
'get_instance_proxy_devices',
'get_instance_state',
'get_instance_unix_devices',
@ -224,6 +266,7 @@ def privilege_check(privilege, server_id = 0):
'is_cluster_member_enabled',
'list_access_controls',
'list_certificates',
'list_cluster_groups',
'list_cluster_members',
'list_groups',
'list_servers',
@ -234,6 +277,11 @@ def privilege_check(privilege, server_id = 0):
'list_instances',
'list_logs',
'list_network_acls',
'list_network_forwards',
'list_network_leases',
'list_network_load_balancers',
'list_network_peers',
'list_network_zones',
'list_network_managed_devices',
'list_networks',
'list_operations',
@ -246,10 +294,16 @@ def privilege_check(privilege, server_id = 0):
'list_storage_volumes',
'list_users',
'load_certificate',
'load_cluster_group',
'load_cluster_member',
'load_image',
'load_instance',
'load_network_acl',
'load_network_forward',
'load_network_lease',
'load_network_load_balancer',
'load_network_peer',
'load_network_zone',
'load_network',
'load_operation',
'load_profile',
@ -265,12 +319,18 @@ def privilege_check(privilege, server_id = 0):
'restore_instance_snapshot',
#'update_access_control',
#'update_certificate',
#'update_cluster_group',
#'update_cluster_member',
#'update_group',
#'update_server',
#'update_image',
#'update_instance',
#'update_network_acl',
#'update_network_forward',
#'update_network_lease',
#'update_network_load_balancer',
#'update_network_peer',
#'update_network_zone',
#'update_network',
#'update_profile',
#'update_project',
@ -283,6 +343,7 @@ def privilege_check(privilege, server_id = 0):
'Operator': [
#'add_access_control',
'add_certificate',
'add_cluster_group',
'add_cluster_member',
#'add_group',
'add_server',
@ -295,6 +356,10 @@ def privilege_check(privilege, server_id = 0):
'add_instance_usb_device',
'add_instance',
'add_network_acl',
'add_network_zone',
'add_network_load_balancer',
'add_network_forward',
'add_network_peer',
'add_network',
'add_profile',
'add_project',
@ -304,13 +369,16 @@ def privilege_check(privilege, server_id = 0):
'add_storage_volume',
#'add_user',
'attach_instance_profile',
'change_cluster_member_state',
'change_instance_state',
'copy_instance',
'copy_instance_proc_stat',
'create_instance_backup',
'create_instance_snapshot_instance',
'create_instance_snapshot',
#'delete_access_control',
'delete_certificate',
'delete_cluster_group',
'delete_cluster_member',
#'delete_group',
#'delete_image',
@ -321,6 +389,10 @@ def privilege_check(privilege, server_id = 0):
'delete_instance',
'delete_instance',
'delete_network_acl',
'delete_network_zone',
'delete_network_load_balancer',
'delete_network_forward',
'delete_network_peer',
'delete_network',
'delete_operation',
'delete_profile',
@ -337,18 +409,18 @@ def privilege_check(privilege, server_id = 0):
'export_instance_backup',
'get_access_control',
'get_group',
'get_network_state',
'get_server_info',
'get_server_initial_project',
'get_server_resources',
'get_server_warnings',
'get_server',
'get_instance_cpu_percentage',
'get_instance_cpu_usage',
'get_instance_disk_devices',
'get_instance_gpu_devices',
'get_instance_interfaces',
'get_instance_memory_percentage',
'get_instance_network_devices',
'get_instance_proc_stat',
'get_instance_proxy_devices',
'get_instance_state',
'get_instance_unix_devices',
@ -360,6 +432,7 @@ def privilege_check(privilege, server_id = 0):
'is_cluster_member_enabled',
'list_access_controls',
'list_certificates',
'list_cluster_groups',
'list_cluster_members',
'list_groups',
'list_servers',
@ -370,6 +443,11 @@ def privilege_check(privilege, server_id = 0):
'list_instances',
'list_logs',
'list_network_acls',
'list_network_forwards',
'list_network_leases',
'list_network_load_balancers',
'list_network_peers',
'list_network_zones',
'list_network_managed_devices',
'list_networks',
'list_operations',
@ -382,10 +460,16 @@ def privilege_check(privilege, server_id = 0):
'list_storage_volumes',
'list_users',
'load_certificate',
'load_cluster_group',
'load_cluster_member',
'load_image',
'load_instance',
'load_network_acl',
'load_network_forward',
'load_network_lease',
'load_network_load_balancer',
'load_network_peer',
'load_network_zone',
'load_network',
'load_operation',
'load_profile',
@ -401,12 +485,18 @@ def privilege_check(privilege, server_id = 0):
'restore_instance_snapshot',
#'update_access_control',
'update_certificate',
'update_cluster_group',
'update_cluster_member',
#'update_group',
'update_server',
'update_image',
'update_instance',
'update_network_acl',
'update_network_forward',
'update_network_lease',
'update_network_load_balancer',
'update_network_peer',
'update_network_zone',
'update_network',
'update_profile',
'update_project',
@ -419,6 +509,7 @@ def privilege_check(privilege, server_id = 0):
'Administrator': [
'add_access_control',
'add_certificate',
'add_cluster_group',
'add_cluster_member',
'add_group',
'add_server',
@ -431,6 +522,10 @@ def privilege_check(privilege, server_id = 0):
'add_instance_usb_device',
'add_instance',
'add_network_acl',
'add_network_zone',
'add_network_load_balancer',
'add_network_forward',
'add_network_peer',
'add_network',
'add_profile',
'add_project',
@ -440,13 +535,16 @@ def privilege_check(privilege, server_id = 0):
'add_storage_volume',
'add_user',
'attach_instance_profile',
'change_cluster_member_state',
'change_instance_state',
'copy_instance',
'copy_instance_proc_stat',
'create_instance_backup',
'create_instance_snapshot_instance',
'create_instance_snapshot',
'delete_access_control',
'delete_certificate',
'delete_cluster_group',
'delete_cluster_member',
'delete_group',
'delete_image',
@ -457,6 +555,10 @@ def privilege_check(privilege, server_id = 0):
'delete_instance',
'delete_instance',
'delete_network_acl',
'delete_network_zone',
'delete_network_load_balancer',
'delete_network_forward',
'delete_network_peer',
'delete_network',
'delete_operation',
'delete_profile',
@ -473,18 +575,18 @@ def privilege_check(privilege, server_id = 0):
'export_instance_backup',
'get_access_control',
'get_group',
'get_network_state',
'get_server_info',
'get_server_initial_project',
'get_server_resources',
'get_server_warnings',
'get_server',
'get_instance_cpu_percentage',
'get_instance_cpu_usage',
'get_instance_disk_devices',
'get_instance_gpu_devices',
'get_instance_interfaces',
'get_instance_memory_percentage',
'get_instance_network_devices',
'get_instance_proc_stat',
'get_instance_proxy_devices',
'get_instance_state',
'get_instance_unix_devices',
@ -496,6 +598,7 @@ def privilege_check(privilege, server_id = 0):
'is_cluster_member_enabled',
'list_access_controls',
'list_certificates',
'list_cluster_groups',
'list_cluster_members',
'list_groups',
'list_servers',
@ -506,6 +609,11 @@ def privilege_check(privilege, server_id = 0):
'list_instances',
'list_logs',
'list_network_acls',
'list_network_forwards',
'list_network_leases',
'list_network_load_balancers',
'list_network_peers',
'list_network_zones',
'list_network_managed_devices',
'list_networks',
'list_operations',
@ -518,10 +626,16 @@ def privilege_check(privilege, server_id = 0):
'list_storage_volumes',
'list_users',
'load_certificate',
'load_cluster_group',
'load_cluster_member',
'load_image',
'load_instance',
'load_network_acl',
'load_network_forward',
'load_network_lease',
'load_network_load_balancer',
'load_network_peer',
'load_network_zone',
'load_network',
'load_operation',
'load_profile',
@ -537,12 +651,18 @@ def privilege_check(privilege, server_id = 0):
'restore_instance_snapshot',
'update_access_control',
'update_certificate',
'update_cluster_group',
'update_cluster_member',
'update_group',
'update_server',
'update_image',
'update_instance',
'update_network_acl',
'update_network_forward',
'update_network_lease',
'update_network_load_balancer',
'update_network_peer',
'update_network_zone',
'update_network',
'update_profile',
'update_project',

View file

@ -0,0 +1,118 @@
from flask import jsonify, request
import requests
from lxconsole import db
from lxconsole.models import Server
from flask_login import login_required
from lxconsole.api.access_controls import privilege_check
def get_client_crt():
return 'certs/client.crt'
def get_client_key():
return 'certs/client.key'
@login_required
def api_cluster_groups_endpoint(endpoint):
if not privilege_check(endpoint, request.args.get('id')):
return jsonify({'data': [], 'metadata':[], 'error': 'not authorized', 'error_code': 403})
if endpoint == 'add_cluster_group':
id = request.args.get('id')
project = request.args.get('project')
server = Server.query.filter_by(id=id).first()
url = 'https://' + server.addr + ':' + str(server.port) + '/1.0/cluster/groups?project=' + project
client_cert = get_client_crt()
client_key = get_client_key()
if request.form.get('json'):
data = request.form.get('json')
results = requests.post(url, verify=server.ssl_verify, cert=(client_cert, client_key), data=data)
return jsonify(results.json())
data = {}
data.update({'name': request.form.get('name')})
data.update({'description': request.form.get('description')})
data.update({'members': request.form.getlist('members')})
results = requests.post(url, verify=server.ssl_verify, cert=(client_cert, client_key), json=data)
return jsonify(results.json())
if endpoint == 'delete_cluster_group':
id = request.args.get('id')
project = request.args.get('project')
name = request.form.get('name')
server = Server.query.filter_by(id=id).first()
url = 'https://' + server.addr + ':' + str(server.port) + '/1.0/cluster/groups/' + name + '?project=' + project
client_cert = get_client_crt()
client_key = get_client_key()
results = requests.delete(url, verify=server.ssl_verify, cert=(client_cert, client_key))
return jsonify(results.json())
if endpoint == 'is_cluster_member_enabled':
id = request.args.get('id')
project = request.args.get('project')
server = Server.query.filter_by(id=id).first()
url = 'https://' + server.addr + ':' + str(server.port) + '/1.0/cluster?project=' + project
client_cert = get_client_crt()
client_key = get_client_key()
results = requests.get(url, verify=server.ssl_verify, cert=(client_cert, client_key))
data = results.json()['metadata']
return str(data['enabled'])
if endpoint == 'list_cluster_groups':
if api_cluster_groups_endpoint('is_cluster_member_enabled') == 'True':
id = request.args.get('id')
project = request.args.get('project')
server = Server.query.filter_by(id=id).first()
recursion = request.args.get('recursion')
if recursion == '1':
url = 'https://' + server.addr + ':' + str(server.port) + '/1.0/cluster/groups?recursion=1&project=' + project
else:
url = 'https://' + server.addr + ':' + str(server.port) + '/1.0/cluster/groups?project=' + project
client_cert = get_client_crt()
client_key = get_client_key()
results = requests.get(url, verify=server.ssl_verify, cert=(client_cert, client_key))
return jsonify(results.json())
data = { "metadata": []}
return jsonify(data)
if endpoint == 'load_cluster_group':
id = request.args.get('id')
project = request.args.get('project')
name = request.form.get('name')
server = Server.query.filter_by(id=id).first()
url = 'https://' + server.addr + ':' + str(server.port) + '/1.0/cluster/groups/' + name + '?project=' + project
client_cert = get_client_crt()
client_key = get_client_key()
results = requests.get(url, verify=server.ssl_verify, cert=(client_cert, client_key))
return jsonify(results.json())
if endpoint == 'update_cluster_group':
id = request.args.get('id')
project = request.args.get('project')
name = request.args.get('name')
server = Server.query.filter_by(id=id).first()
url = 'https://' + server.addr + ':' + str(server.port) + '/1.0/cluster/groups/' + name + '?project=' + project
client_cert = get_client_crt()
client_key = get_client_key()
if request.form.get('json'):
data = request.form.get('json')
results = requests.put(url, verify=server.ssl_verify, cert=(client_cert, client_key), data=data)
return jsonify(results.json())
if request.form.get('name'):
data = {}
data.update({'name': request.form.get('name')})
results = requests.post(url, verify=server.ssl_verify, cert=(client_cert, client_key), json=data)
return jsonify(results.json())
return False

View file

@ -18,6 +18,36 @@ def api_cluster_members_endpoint(endpoint):
if not privilege_check(endpoint, request.args.get('id')):
return jsonify({'data': [], 'metadata':[], 'error': 'not authorized', 'error_code': 403})
if endpoint == 'change_cluster_member_state':
id = request.args.get('id')
project = request.args.get('project')
name = request.form.get('name')
server = Server.query.filter_by(id=id).first()
url = 'https://' + server.addr + ':' + str(server.port) + '/1.0/cluster/members/' + name + '/state?project=' + project
client_cert = get_client_crt()
client_key = get_client_key()
data = {}
data.update({'action': request.form.get('action')})
results = requests.post(url, verify=server.ssl_verify, cert=(client_cert, client_key), json=data)
return jsonify(results.json())
if endpoint == 'delete_cluster_member':
id = request.args.get('id')
project = request.args.get('project')
name = request.form.get('name')
server = Server.query.filter_by(id=id).first()
if request.form.get('force') == 'true':
url = 'https://' + server.addr + ':' + str(server.port) + '/1.0/cluster/members/' + name + '?force=1&project=' + project
else:
url = 'https://' + server.addr + ':' + str(server.port) + '/1.0/cluster/members/' + name + '?project=' + project
client_cert = get_client_crt()
client_key = get_client_key()
results = requests.delete(url, verify=server.ssl_verify, cert=(client_cert, client_key))
return jsonify(results.json())
if endpoint == 'is_cluster_member_enabled':
id = request.args.get('id')
project = request.args.get('project')
@ -47,3 +77,36 @@ def api_cluster_members_endpoint(endpoint):
data = { "metadata": []}
return jsonify(data)
if endpoint == 'load_cluster_member':
id = request.args.get('id')
project = request.args.get('project')
name = request.form.get('name')
server = Server.query.filter_by(id=id).first()
url = 'https://' + server.addr + ':' + str(server.port) + '/1.0/cluster/members/' + name + '?project=' + project
client_cert = get_client_crt()
client_key = get_client_key()
results = requests.get(url, verify=server.ssl_verify, cert=(client_cert, client_key))
return jsonify(results.json())
if endpoint == 'update_cluster_member':
id = request.args.get('id')
project = request.args.get('project')
name = request.args.get('name')
server = Server.query.filter_by(id=id).first()
url = 'https://' + server.addr + ':' + str(server.port) + '/1.0/cluster/members/' + name + '?project=' + project
client_cert = get_client_crt()
client_key = get_client_key()
if request.form.get('json'):
data = request.form.get('json')
results = requests.put(url, verify=server.ssl_verify, cert=(client_cert, client_key), data=data)
return jsonify(results.json())
if request.form.get('server_name'):
data = {}
data.update({'server_name': request.form.get('server_name')})
results = requests.post(url, verify=server.ssl_verify, cert=(client_cert, client_key), json=data)
return jsonify(results.json())
return False

View file

@ -2,6 +2,7 @@ from flask import jsonify, request
import json
import requests
import os
import time
from lxconsole import db
from lxconsole.models import Server
from datetime import datetime
@ -16,7 +17,7 @@ def get_client_key():
return 'certs/client.key'
@login_required
def api_container_endpoint(endpoint):
def api_instance_endpoint(endpoint):
if not privilege_check(endpoint, request.args.get('id')):
return jsonify({'data': [], 'metadata':[], 'error': 'not authorized', 'error_code': 403})
@ -27,7 +28,7 @@ def api_container_endpoint(endpoint):
project = request.args.get('project')
instance = request.args.get('instance')
server = Server.query.filter_by(id=id).first()
url = 'https://' + server.addr + ':' + str(server.port) + '/1.0/containers/' + instance + '?project=' + project
url = 'https://' + server.addr + ':' + str(server.port) + '/1.0/instances/' + instance + '?project=' + project
client_cert = get_client_crt()
client_key = get_client_key()
results = requests.get(url, verify=server.ssl_verify, cert=(client_cert, client_key))
@ -71,7 +72,7 @@ def api_container_endpoint(endpoint):
project = request.args.get('project')
instance = request.args.get('instance')
server = Server.query.filter_by(id=id).first()
url = 'https://' + server.addr + ':' + str(server.port) + '/1.0/containers/' + instance + '?project=' + project
url = 'https://' + server.addr + ':' + str(server.port) + '/1.0/instances/' + instance + '?project=' + project
client_cert = get_client_crt()
client_key = get_client_key()
results = requests.get(url, verify=server.ssl_verify, cert=(client_cert, client_key))
@ -107,7 +108,7 @@ def api_container_endpoint(endpoint):
project = request.args.get('project')
instance = request.args.get('instance')
server = Server.query.filter_by(id=id).first()
url = 'https://' + server.addr + ':' + str(server.port) + '/1.0/containers/' + instance + '?project=' + project
url = 'https://' + server.addr + ':' + str(server.port) + '/1.0/instances/' + instance + '?project=' + project
client_cert = get_client_crt()
client_key = get_client_key()
results = requests.get(url, verify=server.ssl_verify, cert=(client_cert, client_key))
@ -171,7 +172,7 @@ def api_container_endpoint(endpoint):
project = request.args.get('project')
instance = request.args.get('instance')
server = Server.query.filter_by(id=id).first()
url = 'https://' + server.addr + ':' + str(server.port) + '/1.0/containers/' + instance + '?project=' + project
url = 'https://' + server.addr + ':' + str(server.port) + '/1.0/instances/' + instance + '?project=' + project
client_cert = get_client_crt()
client_key = get_client_key()
results = requests.get(url, verify=server.ssl_verify, cert=(client_cert, client_key))
@ -207,7 +208,7 @@ def api_container_endpoint(endpoint):
project = request.args.get('project')
instance = request.args.get('instance')
server = Server.query.filter_by(id=id).first()
url = 'https://' + server.addr + ':' + str(server.port) + '/1.0/containers/' + instance + '?project=' + project
url = 'https://' + server.addr + ':' + str(server.port) + '/1.0/instances/' + instance + '?project=' + project
client_cert = get_client_crt()
client_key = get_client_key()
results = requests.get(url, verify=server.ssl_verify, cert=(client_cert, client_key))
@ -241,7 +242,7 @@ def api_container_endpoint(endpoint):
project = request.args.get('project')
instance = request.args.get('instance')
server = Server.query.filter_by(id=id).first()
url = 'https://' + server.addr + ':' + str(server.port) + '/1.0/containers/' + instance + '?project=' + project
url = 'https://' + server.addr + ':' + str(server.port) + '/1.0/instances/' + instance + '?project=' + project
client_cert = get_client_crt()
client_key = get_client_key()
results = requests.get(url, verify=server.ssl_verify, cert=(client_cert, client_key))
@ -272,7 +273,7 @@ def api_container_endpoint(endpoint):
project = request.args.get('project')
instance = request.args.get('instance')
server = Server.query.filter_by(id=id).first()
url = 'https://' + server.addr + ':' + str(server.port) + '/1.0/containers/' + instance + '?project=' + project
url = 'https://' + server.addr + ':' + str(server.port) + '/1.0/instances/' + instance + '?project=' + project
client_cert = get_client_crt()
client_key = get_client_key()
results = requests.get(url, verify=server.ssl_verify, cert=(client_cert, client_key))
@ -296,7 +297,7 @@ def api_container_endpoint(endpoint):
action = request.form.get('action')
force = request.form.get('force')
server = Server.query.filter_by(id=id).first()
url = 'https://' + server.addr + ':' + str(server.port) + '/1.0/containers/' + instance + '/state?project=' + project
url = 'https://' + server.addr + ':' + str(server.port) + '/1.0/instances/' + instance + '/state?project=' + project
client_cert = get_client_crt()
client_key = get_client_key()
if force == 'true':
@ -315,9 +316,9 @@ def api_container_endpoint(endpoint):
location = request.args.get('location')
#Target location is needed for clustered servers and not allowed on non-clustered servers
if location == 'none':
url = 'https://' + server.addr + ':' + str(server.port) + '/1.0/containers?project=' + project
url = 'https://' + server.addr + ':' + str(server.port) + '/1.0/instances?project=' + project
else:
url = 'https://' + server.addr + ':' + str(server.port) + '/1.0/containers?target='+location+'&project=' + project
url = 'https://' + server.addr + ':' + str(server.port) + '/1.0/instances?target='+location+'&project=' + project
client_cert = get_client_crt()
client_key = get_client_key()
data = {}
@ -336,7 +337,7 @@ def api_container_endpoint(endpoint):
project = request.args.get('project')
instance = request.args.get('instance')
server = Server.query.filter_by(id=id).first()
url = 'https://' + server.addr + ':' + str(server.port) + '/1.0/containers/' + instance + '/backups?project=' + project
url = 'https://' + server.addr + ':' + str(server.port) + '/1.0/instances/' + instance + '/backups?project=' + project
client_cert = get_client_crt()
client_key = get_client_key()
@ -379,7 +380,7 @@ def api_container_endpoint(endpoint):
project = request.args.get('project')
instance = request.args.get('instance')
server = Server.query.filter_by(id=id).first()
url = 'https://' + server.addr + ':' + str(server.port) + '/1.0/containers/' + instance + '/snapshots?project=' + project
url = 'https://' + server.addr + ':' + str(server.port) + '/1.0/instances/' + instance + '/snapshots?project=' + project
client_cert = get_client_crt()
client_key = get_client_key()
data = {}
@ -400,9 +401,9 @@ def api_container_endpoint(endpoint):
location = request.args.get('location')
#Target location is needed for clustered servers and not allowed on non-clustered servers
if location == 'none':
url = 'https://' + server.addr + ':' + str(server.port) + '/1.0/containers?project=' + project
url = 'https://' + server.addr + ':' + str(server.port) + '/1.0/instances?project=' + project
else:
url = 'https://' + server.addr + ':' + str(server.port) + '/1.0/containers?target='+location+'&project=' + project
url = 'https://' + server.addr + ':' + str(server.port) + '/1.0/instances?target='+location+'&project=' + project
client_cert = get_client_crt()
client_key = get_client_key()
data = {}
@ -423,7 +424,7 @@ def api_container_endpoint(endpoint):
instance = request.args.get('instance')
backup = request.args.get('backup')
server = Server.query.filter_by(id=id).first()
url = 'https://' + server.addr + ':' + str(server.port) + '/1.0/containers/' + instance + '/backups/' + backup + '?project=' + project
url = 'https://' + server.addr + ':' + str(server.port) + '/1.0/instances/' + instance + '/backups/' + backup + '?project=' + project
client_cert = get_client_crt()
client_key = get_client_key()
if os.path.isfile('backups/' + str(server.id) + '/' + project + '/' + instance + '/' + backup):
@ -438,7 +439,7 @@ def api_container_endpoint(endpoint):
instance = request.args.get('instance')
device = request.args.get('device')
server = Server.query.filter_by(id=id).first()
url = 'https://' + server.addr + ':' + str(server.port) + '/1.0/containers/' + instance + '?project=' + project
url = 'https://' + server.addr + ':' + str(server.port) + '/1.0/instances/' + instance + '?project=' + project
client_cert = get_client_crt()
client_key = get_client_key()
results = requests.get(url, verify=server.ssl_verify, cert=(client_cert, client_key))
@ -455,7 +456,7 @@ def api_container_endpoint(endpoint):
project = request.args.get('project')
instance = request.form.get('instance')
server = Server.query.filter_by(id=id).first()
url = 'https://' + server.addr + ':' + str(server.port) + '/1.0/containers/' + instance + '?project=' + project
url = 'https://' + server.addr + ':' + str(server.port) + '/1.0/instances/' + instance + '?project=' + project
client_cert = get_client_crt()
client_key = get_client_key()
results = requests.delete(url, verify=server.ssl_verify, cert=(client_cert, client_key))
@ -480,7 +481,7 @@ def api_container_endpoint(endpoint):
instance = request.args.get('instance')
snapshot = request.args.get('snapshot')
server = Server.query.filter_by(id=id).first()
url = 'https://' + server.addr + ':' + str(server.port) + '/1.0/containers/' + instance + '/snapshots/' + snapshot + '?project=' + project
url = 'https://' + server.addr + ':' + str(server.port) + '/1.0/instances/' + instance + '/snapshots/' + snapshot + '?project=' + project
client_cert = get_client_crt()
client_key = get_client_key()
results = requests.delete(url, verify=server.ssl_verify, cert=(client_cert, client_key))
@ -493,7 +494,7 @@ def api_container_endpoint(endpoint):
instance = request.args.get('instance')
profile = request.args.get('profile')
server = Server.query.filter_by(id=id).first()
url = 'https://' + server.addr + ':' + str(server.port) + '/1.0/containers/' + instance + '?project=' + project
url = 'https://' + server.addr + ':' + str(server.port) + '/1.0/instances/' + instance + '?project=' + project
client_cert = get_client_crt()
client_key = get_client_key()
results = requests.get(url, verify=server.ssl_verify, cert=(client_cert, client_key))
@ -527,7 +528,7 @@ def api_container_endpoint(endpoint):
project = request.args.get('project')
instance = request.args.get('instance')
server = Server.query.filter_by(id=id).first()
url = 'https://' + server.addr + ':' + str(server.port) + '/1.0/containers/' + instance + '/console?project=' + project
url = 'https://' + server.addr + ':' + str(server.port) + '/1.0/instances/' + instance + '/console?project=' + project
client_cert = get_client_crt()
client_key = get_client_key()
data = {}
@ -550,7 +551,7 @@ def api_container_endpoint(endpoint):
project = request.args.get('project')
instance = request.args.get('instance')
server = Server.query.filter_by(id=id).first()
url = 'https://' + server.addr + ':' + str(server.port) + '/1.0/containers/' + instance + '/exec?project=' + project
url = 'https://' + server.addr + ':' + str(server.port) + '/1.0/instances/' + instance + '/exec?project=' + project
client_cert = get_client_crt()
client_key = get_client_key()
data = {}
@ -584,7 +585,7 @@ def api_container_endpoint(endpoint):
server = Server.query.filter_by(id=id).first()
instance = request.args.get('instance')
backup = request.args.get('backup')
url = 'https://' + server.addr + ':' + str(server.port) + '/1.0/containers/' + instance + '/backups/' + backup + '/export?project=' + project
url = 'https://' + server.addr + ':' + str(server.port) + '/1.0/instances/' + instance + '/backups/' + backup + '/export?project=' + project
client_cert = get_client_crt()
client_key = get_client_key()
os.system('mkdir -p backups/' + str(server.id) + '/' + project + '/' + instance)
@ -597,8 +598,23 @@ def api_container_endpoint(endpoint):
return jsonify({"status": "Ok", "status_code": 200, "metadata": "{}"})
if endpoint == 'get_instance_cpu_usage':
if endpoint == 'get_instance':
id = request.args.get('id')
project = request.args.get('project')
server = Server.query.filter_by(id=id).first()
name = request.args.get('name')
recursion = request.args.get('recursion')
if recursion == '1':
url = 'https://' + server.addr + ':' + str(server.port) + '/1.0/instances/' + name + '?recursion=1&project=' + project
else:
url = 'https://' + server.addr + ':' + str(server.port) + '/1.0/instances/' + name + '?project=' + project
client_cert = get_client_crt()
client_key = get_client_key()
results = requests.get(url, verify=server.ssl_verify, cert=(client_cert, client_key))
return jsonify(results.json())
# Virtual Machine only
if endpoint == 'copy_instance_proc_stat':
id = request.args.get('id')
project = request.args.get('project')
server = Server.query.filter_by(id=id).first()
@ -606,8 +622,79 @@ def api_container_endpoint(endpoint):
client_cert = get_client_crt()
client_key = get_client_key()
#Get instance state to retrieve container cpu usage
url = 'https://' + server.addr + ':' + str(server.port) + '/1.0/containers/' + name + '/state?project=' + project
# Unable to read /proc/stat directly on virtual machines use lxd files api...getting an EOF error
# So we will copy /proc/stat to /tmp/stat and then read that file as a work around
data = {}
data.update({'command': ['/bin/sh', '-c', 'cat /proc/stat \u003e /tmp/stat' ]})
#data.update({'command': ['cat', '/proc/stat']})
#data.update({'command': ['cp', '/proc/stat', '/tmp/stat']})
data.update({'wait-for-websocket': False})
data.update({'interactive': False})
data.update({'width': 80 })
data.update({'height': 24 })
data.update({'user': 0 })
data.update({'group': 0 })
data.update({'cwd': "/" })
data.update({'record-output': False })
data.update({'environment': {} })
url = 'https://' + server.addr + ':' + str(server.port) + '/1.0/instances/' + name + '/exec?project=' + project
results = requests.post(url, verify=server.ssl_verify, cert=(client_cert, client_key), json=data)
#Using record-output no longer appears to work, but it looks like lxd has code to use a new method of recording logs with exec-output as an option in the near future
#Set record-output: true in command
#exec_rtn = json.dumps(results.json())
#exec_rtn = json.loads(exec_rtn)
#Use operation to check for return value and get log output information
#operation = exec_rtn['operation']
#Check the logs/exec-ouput with get request to see if log exists /1.0/instances/{name}/logs/exec-output
#url = 'https://' + server.addr + ':' + str(server.port) + '/1.0/instances/' + name + '/logs/exec-output?project=' + project
#results = requests.get(url, verify=server.ssl_verify, cert=(client_cert, client_key))
#results return a list of urls of exec-output files. Should be able to match operation to a file in the list
#example url: url = 'https://' + server.addr + ':' + str(server.port) + '/1.0/instances/test/logs/exec-output/exec_fea46679-fdaa-48f4-9079-502a090c4fb5.stdout'
#results = requests.get(url, verify=server.ssl_verify, cert=(client_cert, client_key))
#The returned value should be text: return results.text
#Check stdout log with get request "/1.0/instances/foo/logs/exec-output/exec_d0a89537-0617-4ed6-a79b-c2e88a970965.stdout",
#return results.text
#Check stderr log with get request "/1.0/instances/foo/logs/exec-output/exec_d0a89537-0617-4ed6-a79b-c2e88a970965.stderr",
#Else delete to delete log at /1.0/instances/{name}/logs/exec-output/{filename}
return jsonify(results.json())
# Virtual Machine only
if endpoint == 'get_instance_proc_stat':
id = request.args.get('id')
project = request.args.get('project')
server = Server.query.filter_by(id=id).first()
name = request.args.get('name')
client_cert = get_client_crt()
client_key = get_client_key()
#Get /proc/stat information but from /tmp/stat
url = 'https://' + server.addr + ':' + str(server.port) + '/1.0/instances/' + name + '/files?project=' + project + '&path=/tmp/stat'
results = requests.get(url, verify=server.ssl_verify, cert=(client_cert, client_key))
if 'cpu' in results.text:
results = results.text.split('\n')
for result in results:
stats = result.split()
if 'cpu' in stats:
user_time = int(stats[1])
system_time= int(stats[3])
idle_time = int(stats[4])
return jsonify({'user_time':user_time, 'system_time':system_time, 'idle_time':idle_time})
return jsonify({'user_time':0, 'system_time':0, 'idle_time':0})
if endpoint == 'get_instance_cpu_usage':
id = request.args.get('id')
project = request.args.get('project')
server = Server.query.filter_by(id=id).first()
name = request.args.get('name')
client_cert = get_client_crt()
client_key = get_client_key()
#Get instance state to retrieve instance cpu usage
url = 'https://' + server.addr + ':' + str(server.port) + '/1.0/instances/' + name + '/state?project=' + project
results = requests.get(url, verify=server.ssl_verify, cert=(client_cert, client_key))
results = json.dumps(results.json())
results = json.loads(results)
@ -622,7 +709,7 @@ def api_container_endpoint(endpoint):
instance_cpu_time = 0
#Get /proc/stat information
url = 'https://' + server.addr + ':' + str(server.port) + '/1.0/containers/' + name + '/files?project=' + project + '&path=/proc/stat'
url = 'https://' + server.addr + ':' + str(server.port) + '/1.0/instances/' + name + '/files?project=' + project + '&path=/proc/stat'
results = requests.get(url, verify=server.ssl_verify, cert=(client_cert, client_key))
if 'cpu' in results.text:
results = results.text.split('\n')
@ -644,22 +731,6 @@ def api_container_endpoint(endpoint):
return jsonify({'instance_cpu_time':0,'host_cpu_time': 0})
if endpoint == 'get_instance':
id = request.args.get('id')
project = request.args.get('project')
server = Server.query.filter_by(id=id).first()
name = request.args.get('name')
recursion = request.args.get('recursion')
if recursion == '1':
url = 'https://' + server.addr + ':' + str(server.port) + '/1.0/containers/' + name + '?recursion=1&project=' + project
else:
url = 'https://' + server.addr + ':' + str(server.port) + '/1.0/containers/' + name + '?project=' + project
client_cert = get_client_crt()
client_key = get_client_key()
results = requests.get(url, verify=server.ssl_verify, cert=(client_cert, client_key))
return jsonify(results.json())
if endpoint == 'get_instance_disk_devices':
id = request.args.get('id')
project = request.args.get('project')
@ -667,9 +738,9 @@ def api_container_endpoint(endpoint):
name = request.args.get('name')
recursion = request.args.get('recursion')
if recursion == '1':
url = 'https://' + server.addr + ':' + str(server.port) + '/1.0/containers/' + name + '?recursion=1&project=' + project
url = 'https://' + server.addr + ':' + str(server.port) + '/1.0/instances/' + name + '?recursion=1&project=' + project
else:
url = 'https://' + server.addr + ':' + str(server.port) + '/1.0/containers/' + name + '?project=' + project
url = 'https://' + server.addr + ':' + str(server.port) + '/1.0/instances/' + name + '?project=' + project
client_cert = get_client_crt()
client_key = get_client_key()
results = requests.get(url, verify=server.ssl_verify, cert=(client_cert, client_key))
@ -677,7 +748,7 @@ def api_container_endpoint(endpoint):
instance = json.loads(instance)
expanded_devices = instance['metadata']['expanded_devices']
devices = []
instance_state_url = 'https://' + server.addr + ':' + str(server.port) + '/1.0/containers/' + name + '/state?project=' + project
instance_state_url = 'https://' + server.addr + ':' + str(server.port) + '/1.0/instances/' + name + '/state?project=' + project
instance_state = requests.get(instance_state_url, verify=server.ssl_verify, cert=(client_cert, client_key))
instance_state = json.dumps(instance_state.json())
instance_state = json.loads(instance_state)
@ -706,9 +777,9 @@ def api_container_endpoint(endpoint):
name = request.args.get('name')
recursion = request.args.get('recursion')
if recursion == '1':
url = 'https://' + server.addr + ':' + str(server.port) + '/1.0/containers/' + name + '?recursion=1&project=' + project
url = 'https://' + server.addr + ':' + str(server.port) + '/1.0/instances/' + name + '?recursion=1&project=' + project
else:
url = 'https://' + server.addr + ':' + str(server.port) + '/1.0/containers/' + name + '?project=' + project
url = 'https://' + server.addr + ':' + str(server.port) + '/1.0/instances/' + name + '?project=' + project
client_cert = get_client_crt()
client_key = get_client_key()
results = requests.get(url, verify=server.ssl_verify, cert=(client_cert, client_key))
@ -753,9 +824,9 @@ def api_container_endpoint(endpoint):
name = request.args.get('name')
recursion = request.args.get('recursion')
if recursion == '1':
url = 'https://' + server.addr + ':' + str(server.port) + '/1.0/containers/' + name + '/state?recursion=1&project=' + project
url = 'https://' + server.addr + ':' + str(server.port) + '/1.0/instances/' + name + '/state?recursion=1&project=' + project
else:
url = 'https://' + server.addr + ':' + str(server.port) + '/1.0/containers/' + name + '/state?project=' + project
url = 'https://' + server.addr + ':' + str(server.port) + '/1.0/instances/' + name + '/state?project=' + project
client_cert = get_client_crt()
client_key = get_client_key()
results = requests.get(url, verify=server.ssl_verify, cert=(client_cert, client_key))
@ -790,9 +861,9 @@ def api_container_endpoint(endpoint):
name = request.args.get('name')
recursion = request.args.get('recursion')
if recursion == '1':
url = 'https://' + server.addr + ':' + str(server.port) + '/1.0/containers/' + name + '?recursion=1&project=' + project
url = 'https://' + server.addr + ':' + str(server.port) + '/1.0/instances/' + name + '?recursion=1&project=' + project
else:
url = 'https://' + server.addr + ':' + str(server.port) + '/1.0/containers/' + name + '?project=' + project
url = 'https://' + server.addr + ':' + str(server.port) + '/1.0/instances/' + name + '?project=' + project
client_cert = get_client_crt()
client_key = get_client_key()
results = requests.get(url, verify=server.ssl_verify, cert=(client_cert, client_key))
@ -825,9 +896,9 @@ def api_container_endpoint(endpoint):
name = request.args.get('name')
recursion = request.args.get('recursion')
if recursion == '1':
url = 'https://' + server.addr + ':' + str(server.port) + '/1.0/containers/' + name + '?recursion=1&project=' + project
url = 'https://' + server.addr + ':' + str(server.port) + '/1.0/instances/' + name + '?recursion=1&project=' + project
else:
url = 'https://' + server.addr + ':' + str(server.port) + '/1.0/containers/' + name + '?project=' + project
url = 'https://' + server.addr + ':' + str(server.port) + '/1.0/instances/' + name + '?project=' + project
client_cert = get_client_crt()
client_key = get_client_key()
results = requests.get(url, verify=server.ssl_verify, cert=(client_cert, client_key))
@ -856,15 +927,15 @@ def api_container_endpoint(endpoint):
name = request.args.get('name')
recursion = request.args.get('recursion')
if recursion == '1':
url = 'https://' + server.addr + ':' + str(server.port) + '/1.0/containers/' + name + '/state?recursion=1&project=' + project
url = 'https://' + server.addr + ':' + str(server.port) + '/1.0/instances/' + name + '/state?recursion=1&project=' + project
else:
url = 'https://' + server.addr + ':' + str(server.port) + '/1.0/containers/' + name + '/state?project=' + project
url = 'https://' + server.addr + ':' + str(server.port) + '/1.0/instances/' + name + '/state?project=' + project
client_cert = get_client_crt()
client_key = get_client_key()
results = requests.get(url, verify=server.ssl_verify, cert=(client_cert, client_key))
return jsonify(results.json())
# Container only
if endpoint == 'get_instance_unix_devices':
id = request.args.get('id')
project = request.args.get('project')
@ -872,9 +943,9 @@ def api_container_endpoint(endpoint):
name = request.args.get('name')
recursion = request.args.get('recursion')
if recursion == '1':
url = 'https://' + server.addr + ':' + str(server.port) + '/1.0/containers/' + name + '?recursion=1&project=' + project
url = 'https://' + server.addr + ':' + str(server.port) + '/1.0/instances/' + name + '?recursion=1&project=' + project
else:
url = 'https://' + server.addr + ':' + str(server.port) + '/1.0/containers/' + name + '?project=' + project
url = 'https://' + server.addr + ':' + str(server.port) + '/1.0/instances/' + name + '?project=' + project
client_cert = get_client_crt()
client_key = get_client_key()
results = requests.get(url, verify=server.ssl_verify, cert=(client_cert, client_key))
@ -915,9 +986,9 @@ def api_container_endpoint(endpoint):
name = request.args.get('name')
recursion = request.args.get('recursion')
if recursion == '1':
url = 'https://' + server.addr + ':' + str(server.port) + '/1.0/containers/' + name + '?recursion=1&project=' + project
url = 'https://' + server.addr + ':' + str(server.port) + '/1.0/instances/' + name + '?recursion=1&project=' + project
else:
url = 'https://' + server.addr + ':' + str(server.port) + '/1.0/containers/' + name + '?project=' + project
url = 'https://' + server.addr + ':' + str(server.port) + '/1.0/instances/' + name + '?project=' + project
client_cert = get_client_crt()
client_key = get_client_key()
results = requests.get(url, verify=server.ssl_verify, cert=(client_cert, client_key))
@ -960,9 +1031,9 @@ def api_container_endpoint(endpoint):
name = request.args.get('name')
recursion = request.args.get('recursion')
if recursion == '1':
url = 'https://' + server.addr + ':' + str(server.port) + '/1.0/containers/' + name + '/backups?recursion=1&project=' + project
url = 'https://' + server.addr + ':' + str(server.port) + '/1.0/instances/' + name + '/backups?recursion=1&project=' + project
else:
url = 'https://' + server.addr + ':' + str(server.port) + '/1.0/containers/' + name + '/backups?project=' + project
url = 'https://' + server.addr + ':' + str(server.port) + '/1.0/instances/' + name + '/backups?project=' + project
client_cert = get_client_crt()
client_key = get_client_key()
results = requests.get(url, verify=server.ssl_verify, cert=(client_cert, client_key))
@ -988,13 +1059,19 @@ def api_container_endpoint(endpoint):
name = request.args.get('name')
recursion = request.args.get('recursion')
if recursion == '1':
url = 'https://' + server.addr + ':' + str(server.port) + '/1.0/containers/' + name + '/logs?recursion=1&project=' + project
url = 'https://' + server.addr + ':' + str(server.port) + '/1.0/instances/' + name + '/logs?recursion=1&project=' + project
else:
url = 'https://' + server.addr + ':' + str(server.port) + '/1.0/containers/' + name + '/logs?project=' + project
url = 'https://' + server.addr + ':' + str(server.port) + '/1.0/instances/' + name + '/logs?project=' + project
client_cert = get_client_crt()
client_key = get_client_key()
results = requests.get(url, verify=server.ssl_verify, cert=(client_cert, client_key))
return jsonify(results.json())
# Newly created VMs will not have logs until it starts, causing a 404 error
results = json.dumps(results.json())
results = json.loads(results)
if results['metadata'] is None:
return jsonify({"metadata":[]})
return jsonify(results)
if endpoint == 'list_instance_snapshots':
@ -1004,9 +1081,9 @@ def api_container_endpoint(endpoint):
name = request.args.get('name')
recursion = request.args.get('recursion')
if recursion == '1':
url = 'https://' + server.addr + ':' + str(server.port) + '/1.0/containers/' + name + '/snapshots?recursion=1&project=' + project
url = 'https://' + server.addr + ':' + str(server.port) + '/1.0/instances/' + name + '/snapshots?recursion=1&project=' + project
else:
url = 'https://' + server.addr + ':' + str(server.port) + '/1.0/containers/' + name + '/snapshots?project=' + project
url = 'https://' + server.addr + ':' + str(server.port) + '/1.0/instances/' + name + '/snapshots?project=' + project
client_cert = get_client_crt()
client_key = get_client_key()
results = requests.get(url, verify=server.ssl_verify, cert=(client_cert, client_key))
@ -1019,7 +1096,7 @@ def api_container_endpoint(endpoint):
instance = request.args.get('instance')
server = Server.query.filter_by(id=id).first()
location = request.args.get('location')
url = 'https://' + server.addr + ':' + str(server.port) + '/1.0/containers/' + instance + '?target='+location+'&project=' + project
url = 'https://' + server.addr + ':' + str(server.port) + '/1.0/instances/' + instance + '?target='+location+'&project=' + project
client_cert = get_client_crt()
client_key = get_client_key()
data = {}
@ -1088,7 +1165,7 @@ def api_container_endpoint(endpoint):
project = request.args.get('project')
instance = request.args.get('instance')
server = Server.query.filter_by(id=id).first()
url = 'https://' + server.addr + ':' + str(server.port) + '/1.0/containers/' + instance + '?project=' + project
url = 'https://' + server.addr + ':' + str(server.port) + '/1.0/instances/' + instance + '?project=' + project
client_cert = get_client_crt()
client_key = get_client_key()
data = {}
@ -1102,7 +1179,7 @@ def api_container_endpoint(endpoint):
project = request.args.get('project')
instance = request.args.get('instance')
server = Server.query.filter_by(id=id).first()
url = 'https://' + server.addr + ':' + str(server.port) + '/1.0/containers/' + instance + '?project=' + project
url = 'https://' + server.addr + ':' + str(server.port) + '/1.0/instances/' + instance + '?project=' + project
client_cert = get_client_crt()
client_key = get_client_key()
@ -1118,7 +1195,7 @@ def api_container_endpoint(endpoint):
project = request.args.get('project')
instance = request.args.get('instance')
server = Server.query.filter_by(id=id).first()
url = 'https://' + server.addr + ':' + str(server.port) + '/1.0/containers/' + instance + '?project=' + project
url = 'https://' + server.addr + ':' + str(server.port) + '/1.0/instances/' + instance + '?project=' + project
client_cert = get_client_crt()
client_key = get_client_key()

View file

@ -13,7 +13,7 @@ def get_client_key():
return 'certs/client.key'
@login_required
def api_containers_endpoint(endpoint):
def api_instances_endpoint(endpoint):
if not privilege_check(endpoint, request.args.get('id')):
return jsonify({'data': [], 'metadata':[], 'error': 'not authorized', 'error_code': 403})
@ -25,9 +25,9 @@ def api_containers_endpoint(endpoint):
server = Server.query.filter_by(id=id).first()
location = request.form.get('location')
if location == 'none':
url = 'https://' + server.addr + ':' + str(server.port) + '/1.0/containers?project=' + project
url = 'https://' + server.addr + ':' + str(server.port) + '/1.0/instances?project=' + project
else:
url = 'https://' + server.addr + ':' + str(server.port) + '/1.0/containers?target=' + location + '&project=' + project
url = 'https://' + server.addr + ':' + str(server.port) + '/1.0/instances?target=' + location + '&project=' + project
client_cert = get_client_crt()
client_key = get_client_key()
@ -40,7 +40,7 @@ def api_containers_endpoint(endpoint):
data.update({'name': request.form.get('name')})
data.update({'description': request.form.get('description')})
data.update({'location': request.form.get('location')})
#data.update({'type': request.form.get('type')})
data.update({'type': request.form.get('type')})
data.update({'instance_type': request.form.get('instance_type')})
profiles = []
profiles.append(request.form.get('profiles'))
@ -56,48 +56,51 @@ def api_containers_endpoint(endpoint):
data.update({'source': source})
config = {}
#Options shared between containers and virtual machines
config.update({'boot.autostart': request.form.get('boot.autostart')}) if request.form.get('boot.autostart') else False
config.update({'boot.autostart.delay': request.form.get('boot.autostart.delay')}) if request.form.get('boot.autostart.delay') else False
config.update({'boot.autostart.priority': request.form.get('boot.autostart.priority')}) if request.form.get('boot.autostart.priority') else False
config.update({'boot.host_shutdown_timeout': request.form.get('boot.host_shutdown_timeout')}) if request.form.get('boot.host_shutdown_timeout') else False
config.update({'boot.stop.priority': request.form.get('boot.stop.priority')}) if request.form.get('boot.stop.priority') else False
config.update({'cloud-init.network-config': request.form.get('cloud-init.network-config')}) if request.form.get('cloud-init.network-config') else False
config.update({'cloud-init.user-data': request.form.get('cloud-init.user-data')}) if request.form.get('cloud-init.user-data') else False
config.update({'cloud-init.vendor-data': request.form.get('cloud-init.vendor-data')}) if request.form.get('cloud-init.vendor-data') else False
config.update({'cluster.evacuate': request.form.get('cluster.evacuate')}) if request.form.get('cluster.evacuate') else False
config.update({'limits.cpu': request.form.get('limits.cpu')}) if request.form.get('limits.cpu') else False
config.update({'limits.disk.priority': request.form.get('limits.disk.priority')}) if request.form.get('limits.disk.priority') else False
config.update({'limits.memory': request.form.get('limits.memory')}) if request.form.get('limits.memory') else False
config.update({'limits.network.priority': request.form.get('limits.network.priority')}) if request.form.get('limits.network.priority') else False
config.update({'raw.apparmor': request.form.get('raw.apparmor')}) if request.form.get('raw.apparmor') else False
config.update({'security.devlxd': request.form.get('security.devlxd')}) if request.form.get('security.devlxd') else False
config.update({'security.protection.shift': request.form.get('security.protection.shift')}) if request.form.get('security.protection.shift') else False
config.update({'snapshots.schedule': request.form.get('snapshots.schedule')}) if request.form.get('snapshots.schedule') else False
config.update({'snapshots.schedule.stopped': request.form.get('snapshots.schedule.stopped')}) if request.form.get('snapshots.schedule.stopped') else False
config.update({'snapshots.pattern': request.form.get('snapshots.pattern')}) if request.form.get('snapshots.pattern') else False
config.update({'snapshots.expiry': request.form.get('snapshots.expiry')}) if request.form.get('snapshots.expiry') else False
#Container only options
config.update({'limits.cpu.allowance': request.form.get('limits.cpu.allowance')}) if request.form.get('limits.cpu.allowance') else False
config.update({'limits.cpu.priority': request.form.get('limits.cpu.priority')}) if request.form.get('limits.cpu.priority') else False
config.update({'limits.disk.priority': request.form.get('limits.disk.priority')}) if request.form.get('limits.disk.priority') else False
config.update({'limits.hugepages.64KB': request.form.get('limits.hugepages.64KB')}) if request.form.get('limits.hugepages.64KB') else False
config.update({'limits.hugepages.1MB': request.form.get('limits.hugepages.1MB')}) if request.form.get('limits.hugepages.1MB') else False
config.update({'limits.hugepages.2MB': request.form.get('limits.hugepages.2MB')}) if request.form.get('limits.hugepages.2MB') else False
config.update({'limits.hugepages.1GB': request.form.get('limits.hugepages.1GB')}) if request.form.get('limits.hugepages.1GB') else False
config.update({'limits.memory': request.form.get('limits.memory')}) if request.form.get('limits.memory') else False
config.update({'limits.memory.enforce': request.form.get('limits.memory.enforce')}) if request.form.get('limits.memory.enforce') else False
config.update({'limits.memory.swap.priority': request.form.get('limits.memory.swap.priority')}) if request.form.get('limits.memory.swap.priority') else False
config.update({'limits.memory.swap': request.form.get('limits.memory.swap')}) if request.form.get('limits.memory.swap') else False
config.update({'limits.network.priority': request.form.get('limits.network.priority')}) if request.form.get('limits.network.priority') else False
config.update({'limits.processes': request.form.get('limits.processes')}) if request.form.get('limits.processes') else False
config.update({'linux.kernel_modules': request.form.get('linux.kernel_modules')}) if request.form.get('linux.kernel_modules') else False
config.update({'migration.incremental.memory': request.form.get('migration.incremental.memory')}) if request.form.get('migration.incremental.memory') else False
config.update({'migration.incremental.memory.goal': request.form.get('migration.incremental.memory.goal')}) if request.form.get('migration.incremental.memory.goal') else False
config.update({'migration.incremental.memory.iterations': request.form.get('migration.incremental.memory.iterations')}) if request.form.get('migration.incremental.memory.iterations') else False
config.update({'nvidia.driver.capabilities': request.form.get('nvidia.driver.capabilities')}) if request.form.get('nvidia.driver.capabilities') else False
config.update({'nvidia.runtime': request.form.get('nvidia.runtime')}) if request.form.get('nvidia.runtime') else False
config.update({'nvidia.require.cuda': request.form.get('nvidia.require.cuda')}) if request.form.get('nvidia.require.cuda') else False
config.update({'nvidia.require.driver': request.form.get('nvidia.require.driver')}) if request.form.get('nvidia.require.driver') else False
config.update({'cluster.evacuate': request.form.get('cluster.evacuate')}) if request.form.get('cluster.evacuate') else False
config.update({'linux.kernel_modules': request.form.get('linux.kernel_modules')}) if request.form.get('linux.kernel_modules') else False
config.update({'raw.apparmor': request.form.get('raw.apparmor')}) if request.form.get('raw.apparmor') else False
config.update({'raw.idmap': request.form.get('raw.idmap')}) if request.form.get('raw.idmap') else False
config.update({'raw.lxc': request.form.get('raw.lxc')}) if request.form.get('raw.lxc') else False
config.update({'raw.seccomp': request.form.get('raw.seccomp')}) if request.form.get('raw.seccomp') else False
config.update({'security.devlxd': request.form.get('security.devlxd')}) if request.form.get('security.devlxd') else False
config.update({'security.devlxd.images': request.form.get('security.devlxd.images')}) if request.form.get('security.devlxd.images') else False
config.update({'security.idmap.base': request.form.get('security.idmap.base')}) if request.form.get('security.idmap.base') else False
@ -107,7 +110,6 @@ def api_containers_endpoint(endpoint):
config.update({'security.privileged': request.form.get('security.privileged')}) if request.form.get('security.privileged') else False
config.update({'security.protection.delete': request.form.get('security.protection.delete')}) if request.form.get('security.protection.delete') else False
config.update({'security.protection.shift': request.form.get('security.protection.shift')}) if request.form.get('security.protection.shift') else False
config.update({'security.syscalls.allow': request.form.get('security.syscalls.allow')}) if request.form.get('security.syscalls.allow') else False
config.update({'security.syscalls.deny': request.form.get('security.syscalls.deny')}) if request.form.get('security.syscalls.deny') else False
config.update({'security.syscalls.deny_compat': request.form.get('security.syscalls.deny_compat')}) if request.form.get('security.syscalls.deny_compat') else False
@ -120,12 +122,15 @@ def api_containers_endpoint(endpoint):
config.update({'security.syscalls.intercept.mount.fuse': request.form.get('security.syscalls.intercept.mount.fuse')}) if request.form.get('security.syscalls.intercept.mount.fuse') else False
config.update({'security.syscalls.intercept.mount.shift': request.form.get('security.syscalls.intercept.mount.shift')}) if request.form.get('security.syscalls.intercept.mount.shift') else False
config.update({'security.syscalls.intercept.setxattr': request.form.get('security.syscalls.intercept.setxattr')}) if request.form.get('security.syscalls.intercept.setxattr') else False
config.update({'snapshots.schedule': request.form.get('snapshots.schedule')}) if request.form.get('snapshots.schedule') else False
config.update({'snapshots.schedule.stopped': request.form.get('snapshots.schedule.stopped')}) if request.form.get('snapshots.schedule.stopped') else False
config.update({'snapshots.pattern': request.form.get('snapshots.pattern')}) if request.form.get('snapshots.pattern') else False
config.update({'snapshots.expiry': request.form.get('snapshots.expiry')}) if request.form.get('snapshots.expiry') else False
#Virtual Machine only options
config.update({'limits.memory.hugepages': request.form.get('limits.memory.hugepages')}) if request.form.get('limits.memory.hugepages') else False
config.update({'migration.stateful': request.form.get('migration.stateful')}) if request.form.get('migration.stateful') else False
config.update({'raw.qemu': request.form.get('raw.qemu')}) if request.form.get('raw.qemu') else False
config.update({'raw.qemu.conf': request.form.get('raw.qemu.conf')}) if request.form.get('raw.qemu.conf') else False
config.update({'security.agent.metrics': request.form.get('security.agent.metrics')}) if request.form.get('security.agent.metrics') else False
config.update({'security.secureboot': request.form.get('security.secureboot')}) if request.form.get('security.secureboot') else False
data.update({'config': config})
results = requests.post(url, verify=server.ssl_verify, cert=(client_cert, client_key), json=data)
@ -137,7 +142,7 @@ def api_containers_endpoint(endpoint):
project = request.args.get('project')
name = request.form.get('name')
server = Server.query.filter_by(id=id).first()
url = 'https://' + server.addr + ':' + str(server.port) + '/1.0/containers/' + name + '?project=' + project
url = 'https://' + server.addr + ':' + str(server.port) + '/1.0/instances/' + name + '?project=' + project
client_cert = get_client_crt()
client_key = get_client_key()
results = requests.delete(url, verify=server.ssl_verify, cert=(client_cert, client_key))
@ -149,12 +154,20 @@ def api_containers_endpoint(endpoint):
project = request.args.get('project')
server = Server.query.filter_by(id=id).first()
recursion = request.args.get('recursion')
if request.args.get('filter') == "container":
filter = "type+eq+container"
elif request.args.get('filter') == "virtual-machine":
filter = "type+eq+virtual-machine"
else:
filter = ""
if recursion == '1':
url = 'https://' + server.addr + ':' + str(server.port) + '/1.0/containers?recursion=1&project=' + project
url = 'https://' + server.addr + ':' + str(server.port) + '/1.0/instances?filter=' + filter + '&recursion=1&project=' + project
elif recursion == '2':
url = 'https://' + server.addr + ':' + str(server.port) + '/1.0/containers?recursion=2&project=' + project
url = 'https://' + server.addr + ':' + str(server.port) + '/1.0/instances?filter=' + filter + '&recursion=2&project=' + project
else:
url = 'https://' + server.addr + ':' + str(server.port) + '/1.0/containers?project=' + project
url = 'https://' + server.addr + ':' + str(server.port) + '/1.0/instances?filter=' + filter + '&project=' + project
client_cert = get_client_crt()
client_key = get_client_key()
results = requests.get(url, verify=server.ssl_verify, cert=(client_cert, client_key))
@ -180,7 +193,8 @@ def api_containers_endpoint(endpoint):
# Set disk information if exists
if 'disk' in instance['state'].keys():
if 'root' in instance['state']['disk'].keys():
# instance['state']['disk'] may exists but have have any .keys()
if instance['state']['disk'] and 'root' in instance['state']['disk'].keys():
if 'usage' in instance['state']['disk']['root'].keys():
disk = instance['state']['disk']['root']['usage']
if disk:
@ -211,7 +225,7 @@ def api_containers_endpoint(endpoint):
project = request.args.get('project')
name = request.form.get('name')
server = Server.query.filter_by(id=id).first()
url = 'https://' + server.addr + ':' + str(server.port) + '/1.0/containers/' + name + '?project=' + project
url = 'https://' + server.addr + ':' + str(server.port) + '/1.0/instances/' + name + '?project=' + project
client_cert = get_client_crt()
client_key = get_client_key()
results = requests.get(url, verify=server.ssl_verify, cert=(client_cert, client_key))
@ -237,7 +251,7 @@ def api_containers_endpoint(endpoint):
project = request.args.get('project')
name = request.args.get('name')
server = Server.query.filter_by(id=id).first()
url = 'https://' + server.addr + ':' + str(server.port) + '/1.0/containers/' + name + '?project=' + project
url = 'https://' + server.addr + ':' + str(server.port) + '/1.0/instances/' + name + '?project=' + project
client_cert = get_client_crt()
client_key = get_client_key()

392
lxconsole/api/network.py Normal file
View file

@ -0,0 +1,392 @@
from flask import jsonify, request
import json
import requests
import os
from lxconsole import db
from lxconsole.models import Server
from datetime import datetime
from flask_login import login_required
from lxconsole.api.access_controls import privilege_check
def get_client_crt():
return 'certs/client.crt'
def get_client_key():
return 'certs/client.key'
@login_required
def api_network_endpoint(endpoint):
if not privilege_check(endpoint, request.args.get('id')):
return jsonify({'data': [], 'metadata':[], 'error': 'not authorized', 'error_code': 403})
if endpoint == 'add_network_forward':
id = request.args.get('id')
project = request.args.get('project')
network = request.args.get('network')
server = Server.query.filter_by(id=id).first()
url = 'https://' + server.addr + ':' + str(server.port) + '/1.0/networks/' + network + '/forwards?project=' + project
client_cert = get_client_crt()
client_key = get_client_key()
if request.form.get('json'):
data = request.form.get('json')
results = requests.post(url, verify=server.ssl_verify, cert=(client_cert, client_key), data=data)
return jsonify(results.json())
data = {}
data.update({'listen_address': request.form.get('listen_address')})
data.update({'description': request.form.get('description')})
#config = {}
#config.update({'user.mykey': request.form.get('user.mykey')}) if request.form.get('user.mykey') else False
port = {}
port.update({'description': request.form.get('port_description')}) if request.form.get('port_description') else False
port.update({'listen_port': request.form.get('port_listen_port')}) if request.form.get('port_listen_port') else False
port.update({'protocol': request.form.get('port_protocol')}) if request.form.get('port_protocol') else False
port.update({'target_address': [ request.form.get('port_target_address') ]}) if request.form.get('port_target_address') else False
port.update({'target_port': [ request.form.get('port_target_port') ]}) if request.form.get('port_target_port') else False
#data.update({'config': config})
data.update({'ports': [ port ]})
results = requests.post(url, verify=server.ssl_verify, cert=(client_cert, client_key), json=data)
return jsonify(results.json())
if endpoint == 'add_network_load_balancer':
id = request.args.get('id')
project = request.args.get('project')
network = request.args.get('network')
server = Server.query.filter_by(id=id).first()
url = 'https://' + server.addr + ':' + str(server.port) + '/1.0/networks/' + network + '/load-balancers?project=' + project
client_cert = get_client_crt()
client_key = get_client_key()
if request.form.get('json'):
data = request.form.get('json')
results = requests.post(url, verify=server.ssl_verify, cert=(client_cert, client_key), data=data)
return jsonify(results.json())
data = {}
data.update({'listen_address': request.form.get('listen_address')})
data.update({'description': request.form.get('description')})
backend = {}
backend.update({'description': request.form.get('backend_description')}) if request.form.get('backend_description') else False
backend.update({'name': request.form.get('backend_name')}) if request.form.get('backend_name') else False
backend.update({'target_address': request.form.get('backend_target_address')}) if request.form.get('backend_target_address') else False
backend.update({'target_port': request.form.get('backend_target_port')}) if request.form.get('backend_target_port') else False
#config = {}
#config.update({'user.mykey': request.form.get('user.mykey')}) if request.form.get('user.mykey') else False
port = {}
port.update({'description': request.form.get('port_description')}) if request.form.get('port_description') else False
port.update({'listen_port': request.form.get('port_listen_port')}) if request.form.get('port_listen_port') else False
port.update({'protocol': request.form.get('port_protocol')}) if request.form.get('port_protocol') else False
port.update({'target_backend': [ request.form.get('port_target_backend') ]}) if request.form.get('port_target_backend') else False
data.update({'backends': [ backend ]})
#data.update({'config': config})
data.update({'ports': [ port ]})
results = requests.post(url, verify=server.ssl_verify, cert=(client_cert, client_key), json=data)
return jsonify(results.json())
if endpoint == 'add_network_peer':
id = request.args.get('id')
project = request.args.get('project')
network = request.args.get('network')
server = Server.query.filter_by(id=id).first()
url = 'https://' + server.addr + ':' + str(server.port) + '/1.0/networks/' + network + '/peers?project=' + project
client_cert = get_client_crt()
client_key = get_client_key()
if request.form.get('json'):
data = request.form.get('json')
results = requests.post(url, verify=server.ssl_verify, cert=(client_cert, client_key), data=data)
return jsonify(results.json())
data = {}
data.update({'name': request.form.get('name')})
data.update({'description': request.form.get('description')})
data.update({'target_network': request.form.get('target_network')})
data.update({'target_project': request.form.get('target_network')})
#config = {}
#config.update({'user.mykey': request.form.get('user.mykey')}) if request.form.get('user.mykey') else False
#data.update({'config': config})
results = requests.post(url, verify=server.ssl_verify, cert=(client_cert, client_key), json=data)
return jsonify(results.json())
if endpoint == 'delete_network_forward':
id = request.args.get('id')
project = request.args.get('project')
network = request.args.get('network')
name = request.form.get('name')
server = Server.query.filter_by(id=id).first()
url = 'https://' + server.addr + ':' + str(server.port) + '/1.0/networks/' + network + '/forwards/' + name + '?project=' + project
client_cert = get_client_crt()
client_key = get_client_key()
results = requests.delete(url, verify=server.ssl_verify, cert=(client_cert, client_key))
return jsonify(results.json())
if endpoint == 'delete_network_load_balancer':
id = request.args.get('id')
project = request.args.get('project')
network = request.args.get('network')
name = request.form.get('name')
server = Server.query.filter_by(id=id).first()
url = 'https://' + server.addr + ':' + str(server.port) + '/1.0/networks/' + network + '/load-balancers/' + name + '?project=' + project
client_cert = get_client_crt()
client_key = get_client_key()
results = requests.delete(url, verify=server.ssl_verify, cert=(client_cert, client_key))
return jsonify(results.json())
if endpoint == 'delete_network_peer':
id = request.args.get('id')
project = request.args.get('project')
network = request.args.get('network')
name = request.form.get('name')
server = Server.query.filter_by(id=id).first()
url = 'https://' + server.addr + ':' + str(server.port) + '/1.0/networks/' + network + '/peers/' + name + '?project=' + project
client_cert = get_client_crt()
client_key = get_client_key()
results = requests.delete(url, verify=server.ssl_verify, cert=(client_cert, client_key))
return jsonify(results.json())
if endpoint == 'get_network_state':
id = request.args.get('id')
project = request.args.get('project')
server = Server.query.filter_by(id=id).first()
name = request.args.get('name')
recursion = request.args.get('recursion')
if recursion == '1':
url = 'https://' + server.addr + ':' + str(server.port) + '/1.0/networks/' + name + '/state?recursion=1&project=' + project
else:
url = 'https://' + server.addr + ':' + str(server.port) + '/1.0/networks/' + name + '/state?project=' + project
client_cert = get_client_crt()
client_key = get_client_key()
try:
results = requests.get(url, verify=server.ssl_verify, cert=(client_cert, client_key), timeout=5)
results.raise_for_status()
except requests.exceptions.RequestException as errex:
return jsonify({'metadata': []})
return jsonify(results.json())
if endpoint == 'list_network_forwards':
id = request.args.get('id')
project = request.args.get('project')
server = Server.query.filter_by(id=id).first()
name = request.args.get('name')
recursion = request.args.get('recursion')
if recursion == '1':
url = 'https://' + server.addr + ':' + str(server.port) + '/1.0/networks/' + name + '/forwards?recursion=1&project=' + project
else:
url = 'https://' + server.addr + ':' + str(server.port) + '/1.0/networks/' + name + '/forwards?project=' + project
client_cert = get_client_crt()
client_key = get_client_key()
try:
results = requests.get(url, verify=server.ssl_verify, cert=(client_cert, client_key), timeout=5)
results.raise_for_status()
except requests.exceptions.RequestException as errex:
return jsonify({'metadata': []})
forwards = json.dumps(results.json())
forwards = json.loads(forwards)
if forwards['metadata']:
return jsonify(results.json())
else:
return jsonify({'metadata': []})
if endpoint == 'list_network_leases':
id = request.args.get('id')
project = request.args.get('project')
server = Server.query.filter_by(id=id).first()
name = request.args.get('name')
recursion = request.args.get('recursion')
if recursion == '1':
url = 'https://' + server.addr + ':' + str(server.port) + '/1.0/networks/' + name + '/leases?recursion=1&project=' + project
else:
url = 'https://' + server.addr + ':' + str(server.port) + '/1.0/networks/' + name + '/leases?project=' + project
client_cert = get_client_crt()
client_key = get_client_key()
try:
results = requests.get(url, verify=server.ssl_verify, cert=(client_cert, client_key), timeout=5)
results.raise_for_status()
except requests.exceptions.RequestException as errex:
return jsonify({'metadata': []})
leases = json.dumps(results.json())
leases = json.loads(leases)
if leases['metadata']:
return jsonify(results.json())
else:
return jsonify({'metadata': []})
if endpoint == 'list_network_load_balancers':
id = request.args.get('id')
project = request.args.get('project')
server = Server.query.filter_by(id=id).first()
name = request.args.get('name')
recursion = request.args.get('recursion')
if recursion == '1':
url = 'https://' + server.addr + ':' + str(server.port) + '/1.0/networks/' + name + '/load-balancers?recursion=1&project=' + project
else:
url = 'https://' + server.addr + ':' + str(server.port) + '/1.0/networks/' + name + '/load-balancers?project=' + project
client_cert = get_client_crt()
client_key = get_client_key()
try:
results = requests.get(url, verify=server.ssl_verify, cert=(client_cert, client_key), timeout=5)
results.raise_for_status()
except requests.exceptions.RequestException as errex:
return jsonify({'metadata': []})
load_balancers = json.dumps(results.json())
load_balancers = json.loads(load_balancers)
if load_balancers['metadata']:
return jsonify(results.json())
else:
return jsonify({'metadata': []})
if endpoint == 'list_network_peers':
id = request.args.get('id')
project = request.args.get('project')
server = Server.query.filter_by(id=id).first()
name = request.args.get('name')
recursion = request.args.get('recursion')
if recursion == '1':
url = 'https://' + server.addr + ':' + str(server.port) + '/1.0/networks/' + name + '/peers?recursion=1&project=' + project
else:
url = 'https://' + server.addr + ':' + str(server.port) + '/1.0/networks/' + name + '/peers?project=' + project
client_cert = get_client_crt()
client_key = get_client_key()
try:
results = requests.get(url, verify=server.ssl_verify, cert=(client_cert, client_key), timeout=5)
results.raise_for_status()
except requests.exceptions.RequestException as errex:
return jsonify({'metadata': []})
peers = json.dumps(results.json())
peers = json.loads(peers)
if peers['metadata']:
return jsonify(results.json())
else:
return jsonify({'metadata': []})
if endpoint == 'load_network_forward':
id = request.args.get('id')
project = request.args.get('project')
network = request.args.get('network')
name = request.form.get('name')
server = Server.query.filter_by(id=id).first()
url = 'https://' + server.addr + ':' + str(server.port) + '/1.0/networks/' + network + '/forwards/' + name + '?project=' + project
client_cert = get_client_crt()
client_key = get_client_key()
results = requests.get(url, verify=server.ssl_verify, cert=(client_cert, client_key))
return jsonify(results.json())
if endpoint == 'load_network_load_balancer':
id = request.args.get('id')
project = request.args.get('project')
network = request.args.get('network')
name = request.form.get('name')
server = Server.query.filter_by(id=id).first()
url = 'https://' + server.addr + ':' + str(server.port) + '/1.0/networks/' + network + '/load-balancers/' + name + '?project=' + project
client_cert = get_client_crt()
client_key = get_client_key()
results = requests.get(url, verify=server.ssl_verify, cert=(client_cert, client_key))
return jsonify(results.json())
if endpoint == 'load_network_peer':
id = request.args.get('id')
project = request.args.get('project')
network = request.args.get('network')
name = request.form.get('name')
server = Server.query.filter_by(id=id).first()
url = 'https://' + server.addr + ':' + str(server.port) + '/1.0/networks/' + network + '/peers/' + name + '?project=' + project
client_cert = get_client_crt()
client_key = get_client_key()
results = requests.get(url, verify=server.ssl_verify, cert=(client_cert, client_key))
return jsonify(results.json())
if endpoint == 'update_network_forward':
id = request.args.get('id')
project = request.args.get('project')
name = request.args.get('name')
server = Server.query.filter_by(id=id).first()
network = request.args.get('network')
url = 'https://' + server.addr + ':' + str(server.port) + '/1.0/networks/' + network + '/forwards/' + name + '?project=' + project
client_cert = get_client_crt()
client_key = get_client_key()
if request.form.get('json'):
data = request.form.get('json')
results = requests.put(url, verify=server.ssl_verify, cert=(client_cert, client_key), data=data)
return jsonify(results.json())
data = {}
data.update({'name': request.form.get('name')})
results = requests.post(url, verify=server.ssl_verify, cert=(client_cert, client_key), json=data)
return jsonify(results.json())
if endpoint == 'update_network_load_balancer':
id = request.args.get('id')
project = request.args.get('project')
name = request.args.get('name')
server = Server.query.filter_by(id=id).first()
network = request.args.get('network')
url = 'https://' + server.addr + ':' + str(server.port) + '/1.0/networks/' + network + '/load-balancers/' + name + '?project=' + project
client_cert = get_client_crt()
client_key = get_client_key()
if request.form.get('json'):
data = request.form.get('json')
results = requests.put(url, verify=server.ssl_verify, cert=(client_cert, client_key), data=data)
return jsonify(results.json())
data = {}
data.update({'name': request.form.get('name')})
results = requests.post(url, verify=server.ssl_verify, cert=(client_cert, client_key), json=data)
return jsonify(results.json())
if endpoint == 'update_network_peer':
id = request.args.get('id')
project = request.args.get('project')
name = request.args.get('name')
server = Server.query.filter_by(id=id).first()
network = request.args.get('network')
url = 'https://' + server.addr + ':' + str(server.port) + '/1.0/networks/' + network + '/peers/' + name + '?project=' + project
client_cert = get_client_crt()
client_key = get_client_key()
if request.form.get('json'):
data = request.form.get('json')
results = requests.put(url, verify=server.ssl_verify, cert=(client_cert, client_key), data=data)
return jsonify(results.json())
data = {}
data.update({'name': request.form.get('name')})
results = requests.post(url, verify=server.ssl_verify, cert=(client_cert, client_key), json=data)
return jsonify(results.json())

View file

@ -0,0 +1,103 @@
from flask import jsonify, request
import requests
from lxconsole import db
from lxconsole.models import Server
from flask_login import login_required
from lxconsole.api.access_controls import privilege_check
def get_client_crt():
return 'certs/client.crt'
def get_client_key():
return 'certs/client.key'
@login_required
def api_network_zones_endpoint(endpoint):
if not privilege_check(endpoint, request.args.get('id')):
return jsonify({'data': [], 'metadata':[], 'error': 'not authorized', 'error_code': 403})
if endpoint == 'add_network_zone':
id = request.args.get('id')
project = request.args.get('project')
server = Server.query.filter_by(id=id).first()
url = 'https://' + server.addr + ':' + str(server.port) + '/1.0/network-zones?project=' + project
client_cert = get_client_crt()
client_key = get_client_key()
if request.form.get('json'):
data = request.form.get('json')
results = requests.post(url, verify=server.ssl_verify, cert=(client_cert, client_key), data=data)
return jsonify(results.json())
data = {}
data.update({'name': request.form.get('name')})
data.update({'description': request.form.get('description')})
results = requests.post(url, verify=server.ssl_verify, cert=(client_cert, client_key), json=data)
return jsonify(results.json())
if endpoint == 'delete_network_zone':
id = request.args.get('id')
project = request.args.get('project')
name = request.form.get('name')
server = Server.query.filter_by(id=id).first()
url = 'https://' + server.addr + ':' + str(server.port) + '/1.0/network-zones/' + name + '?project=' + project
client_cert = get_client_crt()
client_key = get_client_key()
results = requests.delete(url, verify=server.ssl_verify, cert=(client_cert, client_key))
return jsonify(results.json())
if endpoint == 'list_network_zones':
id = request.args.get('id')
project = request.args.get('project')
server = Server.query.filter_by(id=id).first()
recursion = request.args.get('recursion')
if recursion == '1':
url = 'https://' + server.addr + ':' + str(server.port) + '/1.0/network-zones?recursion=1&project=' + project
else:
url = 'https://' + server.addr + ':' + str(server.port) + '/1.0/network-zones?project=' + project
client_cert = get_client_crt()
client_key = get_client_key()
results = requests.get(url, verify=server.ssl_verify, cert=(client_cert, client_key))
return jsonify(results.json())
if endpoint == 'load_network_zone':
id = request.args.get('id')
project = request.args.get('project')
name = request.form.get('name')
server = Server.query.filter_by(id=id).first()
url = 'https://' + server.addr + ':' + str(server.port) + '/1.0/network-zones/' + name + '?project=' + project
client_cert = get_client_crt()
client_key = get_client_key()
results = requests.get(url, verify=server.ssl_verify, cert=(client_cert, client_key))
return jsonify(results.json())
if endpoint == 'update_network_zone':
id = request.args.get('id')
project = request.args.get('project')
name = request.args.get('name')
server = Server.query.filter_by(id=id).first()
url = 'https://' + server.addr + ':' + str(server.port) + '/1.0/network-zones/' + name + '?project=' + project
client_cert = get_client_crt()
client_key = get_client_key()
if request.form.get('json'):
data = request.form.get('json')
results = requests.put(url, verify=server.ssl_verify, cert=(client_cert, client_key), data=data)
return jsonify(results.json())
if request.form.get('name'):
data = {}
data.update({'name': request.form.get('name')})
results = requests.post(url, verify=server.ssl_verify, cert=(client_cert, client_key), json=data)
return jsonify(results.json())
return False

View file

@ -34,8 +34,65 @@ def api_networks_endpoint(endpoint):
return jsonify(results.json())
data = {}
data.update({'name': request.form.get('name')})
data.update({'description': request.form.get('description')})
data.update({'name': request.form.get('name')}) if request.form.get('name') else False
data.update({'description': request.form.get('description')}) if request.form.get('description') else False
data.update({'type': request.form.get('type')}) if request.form.get('type') else False
data.update({'parent': request.form.get('parent')}) if request.form.get('parent') else False
data.update({'network': request.form.get('network')}) if request.form.get('network') else False
data.update({'mtu': request.form.get('mtu')}) if request.form.get('mtu') else False
data.update({'vlan': request.form.get('vlan')}) if request.form.get('vlan') else False
data.update({'bridge.driver': request.form.get('bridge.driver')}) if request.form.get('bridge.driver') else False
data.update({'bridge.external.interfaces': request.form.get('bridge.external.interfaces')}) if request.form.get('bridge.external.interfaces') else False
data.update({'bridge.hwaddr': request.form.get('bridge.hwaddr')}) if request.form.get('bridge.hwaddr') else False
data.update({'bridge.mode': request.form.get('bridge.mode')}) if request.form.get('bridge.mode') else False
data.update({'bridge.mtu': request.form.get('bridge.mtu')}) if request.form.get('bridge.mtu') else False
data.update({'dns.domain': request.form.get('dns.domain')}) if request.form.get('dns.domain') else False
data.update({'dns.mode': request.form.get('dns.mode')}) if request.form.get('dns.mode') else False
data.update({'dns.nameservers': request.form.get('dns.nameservers')}) if request.form.get('dns.nameservers') else False
data.update({'dns.search': request.form.get('dns.search')}) if request.form.get('dns.search') else False
data.update({'fan.overlay.subnet': request.form.get('fan.overlay.subnet')}) if request.form.get('fan.overlay.subnet') else False
data.update({'fan.type': request.form.get('fan.type')}) if request.form.get('fan.type') else False
data.update({'fan.underlay.subnet': request.form.get('fan.underlay.subnet')}) if request.form.get('fan.underlay.subnet') else False
data.update({'ipv4.address': request.form.get('ipv4.address')}) if request.form.get('ipv4.address') else False
data.update({'ipv4.dhcp': request.form.get('ipv4.dhcp')}) if request.form.get('ipv4.dhcp') else False
data.update({'ipv4.dhcp.expiry': request.form.get('ipv4.dhcp.expiry')}) if request.form.get('ipv4.dhcp.expiry') else False
data.update({'ipv4.dhcp.gateway': request.form.get('ipv4.dhcp.gateway')}) if request.form.get('ipv4.dhcp.gateway') else False
data.update({'ipv4.dhcp.ranges': request.form.get('ipv4.dhcp.ranges')}) if request.form.get('ipv4.dhcp.ranges') else False
data.update({'ipv4.firewall': request.form.get('ipv4.firewall')}) if request.form.get('ipv4.firewall') else False
data.update({'ipv4.nat.address': request.form.get('ipv4.nat.address')}) if request.form.get('ipv4.nat.address') else False
data.update({'ipv4.nat': request.form.get('ipv4.nat')}) if request.form.get('ipv4.nat') else False
data.update({'ipv4.nat.order': request.form.get('ipv4.nat.order')}) if request.form.get('ipv4.nat.order') else False
data.update({'ipv4.ovn.ranges': request.form.get('ipv4.ovn.ranges')}) if request.form.get('ipv4.ovn.ranges') else False
data.update({'ipv4.gateway': request.form.get('ipv4.gateway')}) if request.form.get('ipv4.gateway') else False
data.update({'ipv4.routes.anycast': request.form.get('ipv4.routes.anycast')}) if request.form.get('ipv4.routes.anycast') else False
data.update({'ipv4.routes': request.form.get('ipv4.routes')}) if request.form.get('ipv4.routes') else False
data.update({'ipv4.routing': request.form.get('ipv4.routing')}) if request.form.get('ipv4.routing') else False
data.update({'ipv6.address': request.form.get('ipv6.address')}) if request.form.get('ipv6.address') else False
data.update({'ipv6.dhcp': request.form.get('ipv6.dhcp')}) if request.form.get('ipv6.dhcp') else False
data.update({'ipv6.dhcp.expiry': request.form.get('ipv6.dhcp.expiry')}) if request.form.get('ipv6.dhcp.expiry') else False
data.update({'ipv6.dhcp.ranges': request.form.get('ipv6.dhcp.ranges')}) if request.form.get('ipv6.dhcp.ranges') else False
data.update({'ipv6.dhcp.stateful': request.form.get('ipv6.dhcp.stateful')}) if request.form.get('ipv6.dhcp.stateful') else False
data.update({'ipv6.firewall': request.form.get('ipv6.firewall')}) if request.form.get('ipv6.firewall') else False
data.update({'ipv6.nat.address': request.form.get('ipv6.nat.address')}) if request.form.get('ipv6.nat.address') else False
data.update({'ipv6.nat': request.form.get('ipv6.nat')}) if request.form.get('ipv6.nat') else False
data.update({'ipv6.nat.order': request.form.get('ipv6.nat.order')}) if request.form.get('ipv6.nat.order') else False
data.update({'ipv6.ovn.ranges': request.form.get('ipv6.ovn.ranges')}) if request.form.get('ipv6.ovn.ranges') else False
data.update({'ipv6.gateway': request.form.get('ipv6.gateway')}) if request.form.get('ipv6.gateway') else False
data.update({'ipv6.routes.anycast': request.form.get('ipv6.routes.anycast')}) if request.form.get('ipv6.routes.anycast') else False
data.update({'ipv6.routes': request.form.get('ipv6.routes')}) if request.form.get('ipv6.routes') else False
data.update({'ipv6.routing': request.form.get('ipv6.routing')}) if request.form.get('ipv6.routing') else False
data.update({'maas.subnet.ipv4': request.form.get('maas.subnet.ipv4')}) if request.form.get('maas.subnet.ipv4') else False
data.update({'maas.subnet.ipv6': request.form.get('maas.subnet.ipv6')}) if request.form.get('maas.subnet.ipv6') else False
data.update({'raw.dnsmasq': request.form.get('raw.dnsmasq')}) if request.form.get('raw.dnsmasq') else False
data.update({'ovn.ingress.mode': request.form.get('ovn.ingress.mode')}) if request.form.get('ovn.ingress.mode') else False
results = requests.post(url, verify=server.ssl_verify, cert=(client_cert, client_key), json=data)
return jsonify(results.json())

File diff suppressed because it is too large Load diff

View file

@ -1,217 +0,0 @@
from flask import jsonify, request
import json
import requests
from lxconsole import db
from lxconsole.models import Server
from flask_login import login_required
from lxconsole.api.access_controls import privilege_check
def get_client_crt():
return 'certs/client.crt'
def get_client_key():
return 'certs/client.key'
@login_required
def api_virtual_machines_endpoint(endpoint):
if not privilege_check(endpoint, request.args.get('id')):
return jsonify({'data': [], 'metadata':[], 'error': 'not authorized', 'error_code': 403})
if endpoint == 'add_instance':
id = request.args.get('id')
project = request.args.get('project')
server = Server.query.filter_by(id=id).first()
location = request.form.get('location')
if location == 'none':
url = 'https://' + server.addr + ':' + str(server.port) + '/1.0/virtual-machines?project=' + project
else:
url = 'https://' + server.addr + ':' + str(server.port) + '/1.0/virtual-machines?target=' + location + '&project=' + project
client_cert = get_client_crt()
client_key = get_client_key()
if request.form.get('json'):
data = request.form.get('json')
results = requests.post(url, verify=server.ssl_verify, cert=(client_cert, client_key), data=data)
return jsonify(results.json())
data = {}
data.update({'name': request.form.get('name')})
data.update({'description': request.form.get('description')})
data.update({'location': request.form.get('location')})
#data.update({'type': request.form.get('type')})
data.update({'instance_type': request.form.get('instance_type')})
profiles = []
profiles.append(request.form.get('profiles'))
data.update({'profiles': profiles})
source = {}
if request.form.get('image') == 'none':
source.update({'type': request.form.get('image')})
data.update({'source': source})
else:
source.update({'type': 'image'})
source.update({'fingerprint': request.form.get('image')})
data.update({'source': source})
config = {}
config.update({'boot.autostart': request.form.get('boot.autostart')}) if request.form.get('boot.autostart') else False
config.update({'boot.autostart.delay': request.form.get('boot.autostart.delay')}) if request.form.get('boot.autostart.delay') else False
config.update({'boot.autostart.priority': request.form.get('boot.autostart.priority')}) if request.form.get('boot.autostart.priority') else False
config.update({'boot.host_shutdown_timeout': request.form.get('boot.host_shutdown_timeout')}) if request.form.get('boot.host_shutdown_timeout') else False
config.update({'boot.stop.priority': request.form.get('boot.stop.priority')}) if request.form.get('boot.stop.priority') else False
config.update({'cloud-init.network-config': request.form.get('cloud-init.network-config')}) if request.form.get('cloud-init.network-config') else False
config.update({'cloud-init.user-data': request.form.get('cloud-init.user-data')}) if request.form.get('cloud-init.user-data') else False
config.update({'cloud-init.vendor-data': request.form.get('cloud-init.vendor-data')}) if request.form.get('cloud-init.vendor-data') else False
config.update({'limits.cpu': request.form.get('limits.cpu')}) if request.form.get('limits.cpu') else False
config.update({'limits.disk.priority': request.form.get('limits.disk.priority')}) if request.form.get('limits.disk.priority') else False
config.update({'limits.memory': request.form.get('limits.memory')}) if request.form.get('limits.memory') else False
config.update({'limits.memory.hugepages': request.form.get('limits.memory.hugepages')}) if request.form.get('limits.memory.hugepages') else False
config.update({'limits.network.priority': request.form.get('limits.network.priority')}) if request.form.get('limits.network.priority') else False
config.update({'migration.stateful': request.form.get('migration.stateful')}) if request.form.get('migration.stateful') else False
config.update({'cluster.evacuate': request.form.get('cluster.evacuate')}) if request.form.get('cluster.evacuate') else False
config.update({'raw.apparmor': request.form.get('raw.apparmor')}) if request.form.get('raw.apparmor') else False
config.update({'raw.qemu': request.form.get('raw.qemu')}) if request.form.get('raw.qemu') else False
config.update({'raw.qemu.conf': request.form.get('raw.qemu.conf')}) if request.form.get('raw.qemu.conf') else False
config.update({'security.devlxd': request.form.get('security.devlxd')}) if request.form.get('security.devlxd') else False
config.update({'security.protection.shift': request.form.get('security.protection.shift')}) if request.form.get('security.protection.shift') else False
config.update({'security.agent.metrics': request.form.get('security.agent.metrics')}) if request.form.get('security.agent.metrics') else False
config.update({'security.secureboot': request.form.get('security.secureboot')}) if request.form.get('security.secureboot') else False
config.update({'snapshots.schedule': request.form.get('snapshots.schedule')}) if request.form.get('snapshots.schedule') else False
config.update({'snapshots.schedule.stopped': request.form.get('snapshots.schedule.stopped')}) if request.form.get('snapshots.schedule.stopped') else False
config.update({'snapshots.pattern': request.form.get('snapshots.pattern')}) if request.form.get('snapshots.pattern') else False
config.update({'snapshots.expiry': request.form.get('snapshots.expiry')}) if request.form.get('snapshots.expiry') else False
data.update({'config': config})
results = requests.post(url, verify=server.ssl_verify, cert=(client_cert, client_key), json=data)
return jsonify(results.json())
if endpoint == 'delete_instance':
id = request.args.get('id')
project = request.args.get('project')
name = request.form.get('name')
server = Server.query.filter_by(id=id).first()
url = 'https://' + server.addr + ':' + str(server.port) + '/1.0/virtual-machines/' + name + '?project=' + project
client_cert = get_client_crt()
client_key = get_client_key()
results = requests.delete(url, verify=server.ssl_verify, cert=(client_cert, client_key))
return jsonify(results.json())
if endpoint == 'list_instances':
id = request.args.get('id')
project = request.args.get('project')
server = Server.query.filter_by(id=id).first()
recursion = request.args.get('recursion')
if recursion == '1':
url = 'https://' + server.addr + ':' + str(server.port) + '/1.0/virtual-machines?recursion=1&project=' + project
elif recursion == '2':
url = 'https://' + server.addr + ':' + str(server.port) + '/1.0/virtual-machines?recursion=2&project=' + project
else:
url = 'https://' + server.addr + ':' + str(server.port) + '/1.0/virtual-machines?project=' + project
client_cert = get_client_crt()
client_key = get_client_key()
results = requests.get(url, verify=server.ssl_verify, cert=(client_cert, client_key))
instances = json.dumps(results.json())
instances = json.loads(instances)
if recursion == '0' or recursion == '1':
return jsonify(instances)
i = 0
for instance in instances['metadata']:
instances['metadata'][i]['memory'] = ''
instances['metadata'][i]['disk'] = ''
instances['metadata'][i]['ipv4_addresses'] = []
instances['metadata'][i]['ipv6_addresses'] = []
if 'state' in instance.keys():
# Set memory information if exists
if 'memory' in instance['state'].keys():
if 'usage' in instance['state']['memory'].keys():
memory = instance['state']['memory']['usage']
if memory:
instances['metadata'][i]['memory'] = memory
# Set disk information if exists
if 'disk' in instance['state'].keys():
if 'root' in instance['state']['disk'].keys():
if 'usage' in instance['state']['disk']['root'].keys():
disk = instance['state']['disk']['root']['usage']
if disk:
instances['metadata'][i]['disk'] = disk
# Set network information if exists
if 'network' in instance['state'].keys():
networks = instance['state']['network']
if networks:
instances['metadata'][i]['ipv4_addresses'] = []
for network in networks.keys():
addresses = networks[network]['addresses']
for address in addresses:
if address['family'] == 'inet' and address['scope'] == 'global':
instances['metadata'][i]['ipv4_addresses'] += [ address['address'] + ' (' + network + ')' ]
instances['metadata'][i]['ipv6_addresses'] = []
for network in networks.keys():
addresses = networks[network]['addresses']
for address in addresses:
if address['family'] == 'inet6' and address['scope'] == 'global':
instances['metadata'][i]['ipv6_addresses'] += [ address['address'] + ' (' + network + ')' ]
i += 1
return jsonify(instances)
if endpoint == 'load_instance':
id = request.args.get('id')
project = request.args.get('project')
name = request.form.get('name')
server = Server.query.filter_by(id=id).first()
url = 'https://' + server.addr + ':' + str(server.port) + '/1.0/virtual-machines/' + name + '?project=' + project
client_cert = get_client_crt()
client_key = get_client_key()
results = requests.get(url, verify=server.ssl_verify, cert=(client_cert, client_key))
return jsonify(results.json())
if endpoint == 'change_instance_state':
id = request.args.get('id')
project = request.args.get('project')
name = request.form.get('name')
action = request.form.get('action')
server = Server.query.filter_by(id=id).first()
url = 'https://' + server.addr + ':' + str(server.port) + '/1.0/instances/' + name + '/state?project=' + project
client_cert = get_client_crt()
client_key = get_client_key()
data = { 'action': action }
results = requests.put(url, verify=server.ssl_verify, cert=(client_cert, client_key), json=data)
return jsonify(results.json())
if endpoint == 'update_instance':
id = request.args.get('id')
project = request.args.get('project')
name = request.args.get('name')
server = Server.query.filter_by(id=id).first()
url = 'https://' + server.addr + ':' + str(server.port) + '/1.0/virtual-machines/' + name + '?project=' + project
client_cert = get_client_crt()
client_key = get_client_key()
if request.form.get('json'):
data = request.form.get('json')
results = requests.put(url, verify=server.ssl_verify, cert=(client_cert, client_key), data=data)
return jsonify(results.json())
data = {}
data.update({'name': request.form.get('name')})
results = requests.post(url, verify=server.ssl_verify, cert=(client_cert, client_key), json=data)
return jsonify(results.json())

View file

@ -49,26 +49,26 @@ def home():
def certificates():
return render_template('certificates.html', page_title='Certificates', page_user_id=current_user.id, page_username=current_user.username,)
@app.route("/cluster-groups")
@login_required
def cluster_groups():
return render_template('cluster-groups.html', page_title='Cluster Groups', page_user_id=current_user.id, page_username=current_user.username,)
@app.route("/cluster-members")
@login_required
def cluster_members():
return render_template('cluster-members.html', page_title='Cluster Members', page_user_id=current_user.id, page_username=current_user.username,)
@app.route("/container")
@login_required
def container():
return render_template('container.html', page_title='Container: ', page_user_id=current_user.id, page_username=current_user.username,)
@app.route("/containers")
@login_required
def containers():
return render_template('containers.html', page_title='Containers', page_user_id=current_user.id, page_username=current_user.username,)
@app.route("/images")
@login_required
def images():
return render_template('images.html', page_title='Images', page_user_id=current_user.id, page_username=current_user.username,)
@app.route("/instance")
@login_required
def instance():
return render_template('instance.html', page_title='Instance', page_user_id=current_user.id, page_username=current_user.username,)
@app.route("/instances")
@login_required
def instances():
@ -84,6 +84,16 @@ def network_acl():
def network_acls():
return render_template('network-acls.html', page_title='Network ACLs', page_user_id=current_user.id, page_username=current_user.username,)
@app.route("/network-zones")
@login_required
def network_zones():
return render_template('network-zones.html', page_title='Network Zones', page_user_id=current_user.id, page_username=current_user.username,)
@app.route("/network")
@login_required
def network():
return render_template('network.html', page_title='Network', page_user_id=current_user.id, page_username=current_user.username,)
@app.route("/networks")
@login_required
def networks():
@ -129,17 +139,6 @@ def storage_pools():
def storage_volumes():
return render_template('storage-volumes.html', page_title='Storage Volumes', page_user_id=current_user.id, page_username=current_user.username,)
@app.route("/virtual-machine")
@login_required
def virtual_machine():
return render_template('virtual-machine.html', page_title='Virtual Machine: ', page_user_id=current_user.id, page_username=current_user.username,)
@app.route("/virtual-machines")
@login_required
def virtual_machines():
return render_template('virtual-machines.html', page_title='Virtual Machines', page_user_id=current_user.id, page_username=current_user.username,)
@app.route("/backups/<serverId>/<project>/<instance>/<filename>")
@login_required
def backups(serverId, project, instance, filename):

File diff suppressed because one or more lines are too long

File diff suppressed because one or more lines are too long

File diff suppressed because one or more lines are too long

View file

@ -57,3 +57,23 @@ code {
color: #ff0000 !important;
word-break: break-word;
}
.terminal .xterm-viewport {
overflow-y: hidden;
}
td.details-control {
text-align:center;
color:#007bff ;
cursor: pointer;
}
tr.shown td.details-control {
text-align:center;
color:#ff0000 ;
}
.table-hover tbody tr:hover td, .table-hover tbody tr:hover th {
background-color: #fefefe;
}

File diff suppressed because one or more lines are too long

File diff suppressed because it is too large Load diff

File diff suppressed because one or more lines are too long

File diff suppressed because one or more lines are too long

File diff suppressed because it is too large Load diff

File diff suppressed because one or more lines are too long

File diff suppressed because one or more lines are too long

File diff suppressed because one or more lines are too long

View file

@ -1,184 +0,0 @@
/*! DataTables Bootstrap 4 integration
* ©2011-2017 SpryMedia Ltd - datatables.net/license
*/
/**
* DataTables integration for Bootstrap 4. This requires Bootstrap 4 and
* DataTables 1.10 or newer.
*
* This file sets the defaults and adds options to DataTables to style its
* controls using Bootstrap. See http://datatables.net/manual/styling/bootstrap
* for further information.
*/
(function( factory ){
if ( typeof define === 'function' && define.amd ) {
// AMD
define( ['jquery', 'datatables.net'], function ( $ ) {
return factory( $, window, document );
} );
}
else if ( typeof exports === 'object' ) {
// CommonJS
module.exports = function (root, $) {
if ( ! root ) {
root = window;
}
if ( ! $ || ! $.fn.dataTable ) {
// Require DataTables, which attaches to jQuery, including
// jQuery if needed and have a $ property so we can access the
// jQuery object that is used
$ = require('datatables.net')(root, $).$;
}
return factory( $, root, root.document );
};
}
else {
// Browser
factory( jQuery, window, document );
}
}(function( $, window, document, undefined ) {
'use strict';
var DataTable = $.fn.dataTable;
/* Set the defaults for DataTables initialisation */
$.extend( true, DataTable.defaults, {
dom:
"<'row'<'col-sm-12 col-md-6'l><'col-sm-12 col-md-6'f>>" +
"<'row'<'col-sm-12'tr>>" +
"<'row'<'col-sm-12 col-md-5'i><'col-sm-12 col-md-7'p>>",
renderer: 'bootstrap'
} );
/* Default class modification */
$.extend( DataTable.ext.classes, {
sWrapper: "dataTables_wrapper dt-bootstrap4",
sFilterInput: "form-control form-control-sm",
sLengthSelect: "custom-select custom-select-sm form-control form-control-sm",
sProcessing: "dataTables_processing card",
sPageButton: "paginate_button page-item"
} );
/* Bootstrap paging button renderer */
DataTable.ext.renderer.pageButton.bootstrap = function ( settings, host, idx, buttons, page, pages ) {
var api = new DataTable.Api( settings );
var classes = settings.oClasses;
var lang = settings.oLanguage.oPaginate;
var aria = settings.oLanguage.oAria.paginate || {};
var btnDisplay, btnClass, counter=0;
var attach = function( container, buttons ) {
var i, ien, node, button;
var clickHandler = function ( e ) {
e.preventDefault();
if ( !$(e.currentTarget).hasClass('disabled') && api.page() != e.data.action ) {
api.page( e.data.action ).draw( 'page' );
}
};
for ( i=0, ien=buttons.length ; i<ien ; i++ ) {
button = buttons[i];
if ( Array.isArray( button ) ) {
attach( container, button );
}
else {
btnDisplay = '';
btnClass = '';
switch ( button ) {
case 'ellipsis':
btnDisplay = '&#x2026;';
btnClass = 'disabled';
break;
case 'first':
btnDisplay = lang.sFirst;
btnClass = button + (page > 0 ?
'' : ' disabled');
break;
case 'previous':
btnDisplay = lang.sPrevious;
btnClass = button + (page > 0 ?
'' : ' disabled');
break;
case 'next':
btnDisplay = lang.sNext;
btnClass = button + (page < pages-1 ?
'' : ' disabled');
break;
case 'last':
btnDisplay = lang.sLast;
btnClass = button + (page < pages-1 ?
'' : ' disabled');
break;
default:
btnDisplay = button + 1;
btnClass = page === button ?
'active' : '';
break;
}
if ( btnDisplay ) {
node = $('<li>', {
'class': classes.sPageButton+' '+btnClass,
'id': idx === 0 && typeof button === 'string' ?
settings.sTableId +'_'+ button :
null
} )
.append( $('<a>', {
'href': '#',
'aria-controls': settings.sTableId,
'aria-label': aria[ button ],
'data-dt-idx': counter,
'tabindex': settings.iTabIndex,
'class': 'page-link'
} )
.html( btnDisplay )
)
.appendTo( container );
settings.oApi._fnBindAction(
node, {action: button}, clickHandler
);
counter++;
}
}
}
};
// IE9 throws an 'unknown error' if document.activeElement is used
// inside an iframe or frame.
var activeEl;
try {
// Because this approach is destroying and recreating the paging
// elements, focus is lost on the select button which is bad for
// accessibility. So we want to restore focus once the draw has
// completed
activeEl = $(host).find(document.activeElement).data('dt-idx');
}
catch (e) {}
attach(
$(host).empty().html('<ul class="pagination"/>').children('ul'),
buttons
);
if ( activeEl !== undefined ) {
$(host).find( '[data-dt-idx='+activeEl+']' ).trigger('focus');
}
};
return DataTable;
}));

View file

@ -1,8 +0,0 @@
/*!
DataTables Bootstrap 4 integration
©2011-2017 SpryMedia Ltd - datatables.net/license
*/
(function(c){"function"===typeof define&&define.amd?define(["jquery","datatables.net"],function(a){return c(a,window,document)}):"object"===typeof exports?module.exports=function(a,d){a||(a=window);if(!d||!d.fn.dataTable)d=require("datatables.net")(a,d).$;return c(d,a,a.document)}:c(jQuery,window,document)})(function(c,a,d,m){var f=c.fn.dataTable;c.extend(!0,f.defaults,{dom:"<'row'<'col-sm-12 col-md-6'l><'col-sm-12 col-md-6'f>><'row'<'col-sm-12'tr>><'row'<'col-sm-12 col-md-5'i><'col-sm-12 col-md-7'p>>",
renderer:"bootstrap"});c.extend(f.ext.classes,{sWrapper:"dataTables_wrapper dt-bootstrap4",sFilterInput:"form-control form-control-sm",sLengthSelect:"custom-select custom-select-sm form-control form-control-sm",sProcessing:"dataTables_processing card",sPageButton:"paginate_button page-item"});f.ext.renderer.pageButton.bootstrap=function(a,h,r,s,j,n){var o=new f.Api(a),t=a.oClasses,k=a.oLanguage.oPaginate,u=a.oLanguage.oAria.paginate||{},e,g,p=0,q=function(d,f){var l,h,i,b,m=function(a){a.preventDefault();
!c(a.currentTarget).hasClass("disabled")&&o.page()!=a.data.action&&o.page(a.data.action).draw("page")};l=0;for(h=f.length;l<h;l++)if(b=f[l],Array.isArray(b))q(d,b);else{g=e="";switch(b){case "ellipsis":e="&#x2026;";g="disabled";break;case "first":e=k.sFirst;g=b+(0<j?"":" disabled");break;case "previous":e=k.sPrevious;g=b+(0<j?"":" disabled");break;case "next":e=k.sNext;g=b+(j<n-1?"":" disabled");break;case "last":e=k.sLast;g=b+(j<n-1?"":" disabled");break;default:e=b+1,g=j===b?"active":""}e&&(i=c("<li>",
{"class":t.sPageButton+" "+g,id:0===r&&"string"===typeof b?a.sTableId+"_"+b:null}).append(c("<a>",{href:"#","aria-controls":a.sTableId,"aria-label":u[b],"data-dt-idx":p,tabindex:a.iTabIndex,"class":"page-link"}).html(e)).appendTo(d),a.oApi._fnBindAction(i,{action:b},m),p++)}},i;try{i=c(h).find(d.activeElement).data("dt-idx")}catch(v){}q(c(h).empty().html('<ul class="pagination"/>').children("ul"),s);i!==m&&c(h).find("[data-dt-idx="+i+"]").trigger("focus")};return f});

View file

@ -0,0 +1,4 @@
/*! DataTables Bootstrap 5 integration
* 2020 SpryMedia Ltd - datatables.net/license
*/
!function(t){var n,r;"function"==typeof define&&define.amd?define(["jquery","datatables.net"],function(e){return t(e,window,document)}):"object"==typeof exports?(n=require("jquery"),r=function(e,a){a.fn.dataTable||require("datatables.net")(e,a)},"undefined"==typeof window?module.exports=function(e,a){return e=e||window,a=a||n(e),r(e,a),t(a,0,e.document)}:(r(window,n),module.exports=t(n,window,window.document))):t(jQuery,window,document)}(function(x,e,r,o){"use strict";var i=x.fn.dataTable;return x.extend(!0,i.defaults,{dom:"<'row'<'col-sm-12 col-md-6'l><'col-sm-12 col-md-6'f>><'row dt-row'<'col-sm-12'tr>><'row'<'col-sm-12 col-md-5'i><'col-sm-12 col-md-7'p>>",renderer:"bootstrap"}),x.extend(i.ext.classes,{sWrapper:"dataTables_wrapper dt-bootstrap5",sFilterInput:"form-control form-control-sm",sLengthSelect:"form-select form-select-sm",sProcessing:"dataTables_processing card",sPageButton:"paginate_button page-item"}),i.ext.renderer.pageButton.bootstrap=function(d,e,s,a,l,c){function u(e,a){for(var t,n,r=function(e){e.preventDefault(),x(e.currentTarget).hasClass("disabled")||b.page()==e.data.action||b.page(e.data.action).draw("page")},o=0,i=a.length;o<i;o++)if(t=a[o],Array.isArray(t))u(e,t);else{switch(f=p="",t){case"ellipsis":p="&#x2026;",f="disabled";break;case"first":p=g.sFirst,f=t+(0<l?"":" disabled");break;case"previous":p=g.sPrevious,f=t+(0<l?"":" disabled");break;case"next":p=g.sNext,f=t+(l<c-1?"":" disabled");break;case"last":p=g.sLast,f=t+(l<c-1?"":" disabled");break;default:p=t+1,f=l===t?"active":""}p&&(n=-1!==f.indexOf("disabled"),n=x("<li>",{class:m.sPageButton+" "+f,id:0===s&&"string"==typeof t?d.sTableId+"_"+t:null}).append(x("<a>",{href:n?null:"#","aria-controls":d.sTableId,"aria-disabled":n?"true":null,"aria-label":w[t],role:"link","aria-current":"active"===f?"page":null,"data-dt-idx":t,tabindex:n?-1:d.iTabIndex,class:"page-link"}).html(p)).appendTo(e),d.oApi._fnBindAction(n,{action:t},r))}}var p,f,t,b=new i.Api(d),m=d.oClasses,g=d.oLanguage.oPaginate,w=d.oLanguage.oAria.paginate||{},e=x(e);try{t=e.find(r.activeElement).data("dt-idx")}catch(e){}var n=e.children("ul.pagination");n.length?n.empty():n=e.html("<ul/>").children("ul").addClass("pagination"),u(n,a),t!==o&&e.find("[data-dt-idx="+t+"]").trigger("focus")},i});

File diff suppressed because one or more lines are too long

File diff suppressed because it is too large Load diff

View file

@ -1,168 +0,0 @@
/*!
DataTables 1.10.22
©2008-2020 SpryMedia Ltd - datatables.net/license
*/
(function(h){"function"===typeof define&&define.amd?define(["jquery"],function(E){return h(E,window,document)}):"object"===typeof exports?module.exports=function(E,H){E||(E=window);H||(H="undefined"!==typeof window?require("jquery"):require("jquery")(E));return h(H,E,E.document)}:h(jQuery,window,document)})(function(h,E,H,k){function $(a){var b,c,d={};h.each(a,function(e){if((b=e.match(/^([^A-Z]+?)([A-Z])/))&&-1!=="a aa ai ao as b fn i m o s ".indexOf(b[1]+" "))c=e.replace(b[0],b[2].toLowerCase()),
d[c]=e,"o"===b[1]&&$(a[e])});a._hungarianMap=d}function J(a,b,c){a._hungarianMap||$(a);var d;h.each(b,function(e){d=a._hungarianMap[e];if(d!==k&&(c||b[d]===k))"o"===d.charAt(0)?(b[d]||(b[d]={}),h.extend(!0,b[d],b[e]),J(a[d],b[d],c)):b[d]=b[e]})}function Ea(a){var b=n.defaults.oLanguage,c=b.sDecimal;c&&Fa(c);if(a){var d=a.sZeroRecords;!a.sEmptyTable&&(d&&"No data available in table"===b.sEmptyTable)&&F(a,a,"sZeroRecords","sEmptyTable");!a.sLoadingRecords&&(d&&"Loading..."===b.sLoadingRecords)&&F(a,
a,"sZeroRecords","sLoadingRecords");a.sInfoThousands&&(a.sThousands=a.sInfoThousands);(a=a.sDecimal)&&c!==a&&Fa(a)}}function gb(a){A(a,"ordering","bSort");A(a,"orderMulti","bSortMulti");A(a,"orderClasses","bSortClasses");A(a,"orderCellsTop","bSortCellsTop");A(a,"order","aaSorting");A(a,"orderFixed","aaSortingFixed");A(a,"paging","bPaginate");A(a,"pagingType","sPaginationType");A(a,"pageLength","iDisplayLength");A(a,"searching","bFilter");"boolean"===typeof a.sScrollX&&(a.sScrollX=a.sScrollX?"100%":
"");"boolean"===typeof a.scrollX&&(a.scrollX=a.scrollX?"100%":"");if(a=a.aoSearchCols)for(var b=0,c=a.length;b<c;b++)a[b]&&J(n.models.oSearch,a[b])}function hb(a){A(a,"orderable","bSortable");A(a,"orderData","aDataSort");A(a,"orderSequence","asSorting");A(a,"orderDataType","sortDataType");var b=a.aDataSort;"number"===typeof b&&!Array.isArray(b)&&(a.aDataSort=[b])}function ib(a){if(!n.__browser){var b={};n.__browser=b;var c=h("<div/>").css({position:"fixed",top:0,left:-1*h(E).scrollLeft(),height:1,
width:1,overflow:"hidden"}).append(h("<div/>").css({position:"absolute",top:1,left:1,width:100,overflow:"scroll"}).append(h("<div/>").css({width:"100%",height:10}))).appendTo("body"),d=c.children(),e=d.children();b.barWidth=d[0].offsetWidth-d[0].clientWidth;b.bScrollOversize=100===e[0].offsetWidth&&100!==d[0].clientWidth;b.bScrollbarLeft=1!==Math.round(e.offset().left);b.bBounding=c[0].getBoundingClientRect().width?!0:!1;c.remove()}h.extend(a.oBrowser,n.__browser);a.oScroll.iBarWidth=n.__browser.barWidth}
function jb(a,b,c,d,e,f){var g,j=!1;c!==k&&(g=c,j=!0);for(;d!==e;)a.hasOwnProperty(d)&&(g=j?b(g,a[d],d,a):a[d],j=!0,d+=f);return g}function Ga(a,b){var c=n.defaults.column,d=a.aoColumns.length,c=h.extend({},n.models.oColumn,c,{nTh:b?b:H.createElement("th"),sTitle:c.sTitle?c.sTitle:b?b.innerHTML:"",aDataSort:c.aDataSort?c.aDataSort:[d],mData:c.mData?c.mData:d,idx:d});a.aoColumns.push(c);c=a.aoPreSearchCols;c[d]=h.extend({},n.models.oSearch,c[d]);la(a,d,h(b).data())}function la(a,b,c){var b=a.aoColumns[b],
d=a.oClasses,e=h(b.nTh);if(!b.sWidthOrig){b.sWidthOrig=e.attr("width")||null;var f=(e.attr("style")||"").match(/width:\s*(\d+[pxem%]+)/);f&&(b.sWidthOrig=f[1])}c!==k&&null!==c&&(hb(c),J(n.defaults.column,c,!0),c.mDataProp!==k&&!c.mData&&(c.mData=c.mDataProp),c.sType&&(b._sManualType=c.sType),c.className&&!c.sClass&&(c.sClass=c.className),c.sClass&&e.addClass(c.sClass),h.extend(b,c),F(b,c,"sWidth","sWidthOrig"),c.iDataSort!==k&&(b.aDataSort=[c.iDataSort]),F(b,c,"aDataSort"));var g=b.mData,j=S(g),i=
b.mRender?S(b.mRender):null,c=function(a){return"string"===typeof a&&-1!==a.indexOf("@")};b._bAttrSrc=h.isPlainObject(g)&&(c(g.sort)||c(g.type)||c(g.filter));b._setter=null;b.fnGetData=function(a,b,c){var d=j(a,b,k,c);return i&&b?i(d,b,a,c):d};b.fnSetData=function(a,b,c){return N(g)(a,b,c)};"number"!==typeof g&&(a._rowReadObject=!0);a.oFeatures.bSort||(b.bSortable=!1,e.addClass(d.sSortableNone));a=-1!==h.inArray("asc",b.asSorting);c=-1!==h.inArray("desc",b.asSorting);!b.bSortable||!a&&!c?(b.sSortingClass=
d.sSortableNone,b.sSortingClassJUI=""):a&&!c?(b.sSortingClass=d.sSortableAsc,b.sSortingClassJUI=d.sSortJUIAscAllowed):!a&&c?(b.sSortingClass=d.sSortableDesc,b.sSortingClassJUI=d.sSortJUIDescAllowed):(b.sSortingClass=d.sSortable,b.sSortingClassJUI=d.sSortJUI)}function aa(a){if(!1!==a.oFeatures.bAutoWidth){var b=a.aoColumns;Ha(a);for(var c=0,d=b.length;c<d;c++)b[c].nTh.style.width=b[c].sWidth}b=a.oScroll;(""!==b.sY||""!==b.sX)&&ma(a);t(a,null,"column-sizing",[a])}function ba(a,b){var c=na(a,"bVisible");
return"number"===typeof c[b]?c[b]:null}function ca(a,b){var c=na(a,"bVisible"),c=h.inArray(b,c);return-1!==c?c:null}function W(a){var b=0;h.each(a.aoColumns,function(a,d){d.bVisible&&"none"!==h(d.nTh).css("display")&&b++});return b}function na(a,b){var c=[];h.map(a.aoColumns,function(a,e){a[b]&&c.push(e)});return c}function Ia(a){var b=a.aoColumns,c=a.aoData,d=n.ext.type.detect,e,f,g,j,i,h,l,q,u;e=0;for(f=b.length;e<f;e++)if(l=b[e],u=[],!l.sType&&l._sManualType)l.sType=l._sManualType;else if(!l.sType){g=
0;for(j=d.length;g<j;g++){i=0;for(h=c.length;i<h;i++){u[i]===k&&(u[i]=B(a,i,e,"type"));q=d[g](u[i],a);if(!q&&g!==d.length-1)break;if("html"===q)break}if(q){l.sType=q;break}}l.sType||(l.sType="string")}}function kb(a,b,c,d){var e,f,g,j,i,m,l=a.aoColumns;if(b)for(e=b.length-1;0<=e;e--){m=b[e];var q=m.targets!==k?m.targets:m.aTargets;Array.isArray(q)||(q=[q]);f=0;for(g=q.length;f<g;f++)if("number"===typeof q[f]&&0<=q[f]){for(;l.length<=q[f];)Ga(a);d(q[f],m)}else if("number"===typeof q[f]&&0>q[f])d(l.length+
q[f],m);else if("string"===typeof q[f]){j=0;for(i=l.length;j<i;j++)("_all"==q[f]||h(l[j].nTh).hasClass(q[f]))&&d(j,m)}}if(c){e=0;for(a=c.length;e<a;e++)d(e,c[e])}}function O(a,b,c,d){var e=a.aoData.length,f=h.extend(!0,{},n.models.oRow,{src:c?"dom":"data",idx:e});f._aData=b;a.aoData.push(f);for(var g=a.aoColumns,j=0,i=g.length;j<i;j++)g[j].sType=null;a.aiDisplayMaster.push(e);b=a.rowIdFn(b);b!==k&&(a.aIds[b]=f);(c||!a.oFeatures.bDeferRender)&&Ja(a,e,c,d);return e}function oa(a,b){var c;b instanceof
h||(b=h(b));return b.map(function(b,e){c=Ka(a,e);return O(a,c.data,e,c.cells)})}function B(a,b,c,d){var e=a.iDraw,f=a.aoColumns[c],g=a.aoData[b]._aData,j=f.sDefaultContent,i=f.fnGetData(g,d,{settings:a,row:b,col:c});if(i===k)return a.iDrawError!=e&&null===j&&(K(a,0,"Requested unknown parameter "+("function"==typeof f.mData?"{function}":"'"+f.mData+"'")+" for row "+b+", column "+c,4),a.iDrawError=e),j;if((i===g||null===i)&&null!==j&&d!==k)i=j;else if("function"===typeof i)return i.call(g);return null===
i&&"display"==d?"":i}function lb(a,b,c,d){a.aoColumns[c].fnSetData(a.aoData[b]._aData,d,{settings:a,row:b,col:c})}function La(a){return h.map(a.match(/(\\.|[^\.])+/g)||[""],function(a){return a.replace(/\\\./g,".")})}function S(a){if(h.isPlainObject(a)){var b={};h.each(a,function(a,c){c&&(b[a]=S(c))});return function(a,c,f,g){var j=b[c]||b._;return j!==k?j(a,c,f,g):a}}if(null===a)return function(a){return a};if("function"===typeof a)return function(b,c,f,g){return a(b,c,f,g)};if("string"===typeof a&&
(-1!==a.indexOf(".")||-1!==a.indexOf("[")||-1!==a.indexOf("("))){var c=function(a,b,f){var g,j;if(""!==f){j=La(f);for(var i=0,h=j.length;i<h;i++){f=j[i].match(da);g=j[i].match(X);if(f){j[i]=j[i].replace(da,"");""!==j[i]&&(a=a[j[i]]);g=[];j.splice(0,i+1);j=j.join(".");if(Array.isArray(a)){i=0;for(h=a.length;i<h;i++)g.push(c(a[i],b,j))}a=f[0].substring(1,f[0].length-1);a=""===a?g:g.join(a);break}else if(g){j[i]=j[i].replace(X,"");a=a[j[i]]();continue}if(null===a||a[j[i]]===k)return k;a=a[j[i]]}}return a};
return function(b,e){return c(b,e,a)}}return function(b){return b[a]}}function N(a){if(h.isPlainObject(a))return N(a._);if(null===a)return function(){};if("function"===typeof a)return function(b,d,e){a(b,"set",d,e)};if("string"===typeof a&&(-1!==a.indexOf(".")||-1!==a.indexOf("[")||-1!==a.indexOf("("))){var b=function(a,d,e){var e=La(e),f;f=e[e.length-1];for(var g,j,i=0,h=e.length-1;i<h;i++){if("__proto__"===e[i])throw Error("Cannot set prototype values");g=e[i].match(da);j=e[i].match(X);if(g){e[i]=
e[i].replace(da,"");a[e[i]]=[];f=e.slice();f.splice(0,i+1);g=f.join(".");if(Array.isArray(d)){j=0;for(h=d.length;j<h;j++)f={},b(f,d[j],g),a[e[i]].push(f)}else a[e[i]]=d;return}j&&(e[i]=e[i].replace(X,""),a=a[e[i]](d));if(null===a[e[i]]||a[e[i]]===k)a[e[i]]={};a=a[e[i]]}if(f.match(X))a[f.replace(X,"")](d);else a[f.replace(da,"")]=d};return function(c,d){return b(c,d,a)}}return function(b,d){b[a]=d}}function Ma(a){return C(a.aoData,"_aData")}function pa(a){a.aoData.length=0;a.aiDisplayMaster.length=
0;a.aiDisplay.length=0;a.aIds={}}function qa(a,b,c){for(var d=-1,e=0,f=a.length;e<f;e++)a[e]==b?d=e:a[e]>b&&a[e]--; -1!=d&&c===k&&a.splice(d,1)}function ea(a,b,c,d){var e=a.aoData[b],f,g=function(c,d){for(;c.childNodes.length;)c.removeChild(c.firstChild);c.innerHTML=B(a,b,d,"display")};if("dom"===c||(!c||"auto"===c)&&"dom"===e.src)e._aData=Ka(a,e,d,d===k?k:e._aData).data;else{var j=e.anCells;if(j)if(d!==k)g(j[d],d);else{c=0;for(f=j.length;c<f;c++)g(j[c],c)}}e._aSortData=null;e._aFilterData=null;g=
a.aoColumns;if(d!==k)g[d].sType=null;else{c=0;for(f=g.length;c<f;c++)g[c].sType=null;Na(a,e)}}function Ka(a,b,c,d){var e=[],f=b.firstChild,g,j,i=0,h,l=a.aoColumns,q=a._rowReadObject,d=d!==k?d:q?{}:[],u=function(a,b){if("string"===typeof a){var c=a.indexOf("@");-1!==c&&(c=a.substring(c+1),N(a)(d,b.getAttribute(c)))}},G=function(a){if(c===k||c===i)j=l[i],h=a.innerHTML.trim(),j&&j._bAttrSrc?(N(j.mData._)(d,h),u(j.mData.sort,a),u(j.mData.type,a),u(j.mData.filter,a)):q?(j._setter||(j._setter=N(j.mData)),
j._setter(d,h)):d[i]=h;i++};if(f)for(;f;){g=f.nodeName.toUpperCase();if("TD"==g||"TH"==g)G(f),e.push(f);f=f.nextSibling}else{e=b.anCells;f=0;for(g=e.length;f<g;f++)G(e[f])}if(b=b.firstChild?b:b.nTr)(b=b.getAttribute("id"))&&N(a.rowId)(d,b);return{data:d,cells:e}}function Ja(a,b,c,d){var e=a.aoData[b],f=e._aData,g=[],j,i,m,l,q,k;if(null===e.nTr){j=c||H.createElement("tr");e.nTr=j;e.anCells=g;j._DT_RowIndex=b;Na(a,e);l=0;for(q=a.aoColumns.length;l<q;l++){m=a.aoColumns[l];i=(k=c?!1:!0)?H.createElement(m.sCellType):
d[l];i._DT_CellIndex={row:b,column:l};g.push(i);if(k||(!c||m.mRender||m.mData!==l)&&(!h.isPlainObject(m.mData)||m.mData._!==l+".display"))i.innerHTML=B(a,b,l,"display");m.sClass&&(i.className+=" "+m.sClass);m.bVisible&&!c?j.appendChild(i):!m.bVisible&&c&&i.parentNode.removeChild(i);m.fnCreatedCell&&m.fnCreatedCell.call(a.oInstance,i,B(a,b,l),f,b,l)}t(a,"aoRowCreatedCallback",null,[j,f,b,g])}e.nTr.setAttribute("role","row")}function Na(a,b){var c=b.nTr,d=b._aData;if(c){var e=a.rowIdFn(d);e&&(c.id=
e);d.DT_RowClass&&(e=d.DT_RowClass.split(" "),b.__rowc=b.__rowc?ra(b.__rowc.concat(e)):e,h(c).removeClass(b.__rowc.join(" ")).addClass(d.DT_RowClass));d.DT_RowAttr&&h(c).attr(d.DT_RowAttr);d.DT_RowData&&h(c).data(d.DT_RowData)}}function mb(a){var b,c,d,e,f,g=a.nTHead,j=a.nTFoot,i=0===h("th, td",g).length,m=a.oClasses,l=a.aoColumns;i&&(e=h("<tr/>").appendTo(g));b=0;for(c=l.length;b<c;b++)f=l[b],d=h(f.nTh).addClass(f.sClass),i&&d.appendTo(e),a.oFeatures.bSort&&(d.addClass(f.sSortingClass),!1!==f.bSortable&&
(d.attr("tabindex",a.iTabIndex).attr("aria-controls",a.sTableId),Oa(a,f.nTh,b))),f.sTitle!=d[0].innerHTML&&d.html(f.sTitle),Pa(a,"header")(a,d,f,m);i&&fa(a.aoHeader,g);h(g).children("tr").attr("role","row");h(g).children("tr").children("th, td").addClass(m.sHeaderTH);h(j).children("tr").children("th, td").addClass(m.sFooterTH);if(null!==j){a=a.aoFooter[0];b=0;for(c=a.length;b<c;b++)f=l[b],f.nTf=a[b].cell,f.sClass&&h(f.nTf).addClass(f.sClass)}}function ga(a,b,c){var d,e,f,g=[],j=[],i=a.aoColumns.length,
m;if(b){c===k&&(c=!1);d=0;for(e=b.length;d<e;d++){g[d]=b[d].slice();g[d].nTr=b[d].nTr;for(f=i-1;0<=f;f--)!a.aoColumns[f].bVisible&&!c&&g[d].splice(f,1);j.push([])}d=0;for(e=g.length;d<e;d++){if(a=g[d].nTr)for(;f=a.firstChild;)a.removeChild(f);f=0;for(b=g[d].length;f<b;f++)if(m=i=1,j[d][f]===k){a.appendChild(g[d][f].cell);for(j[d][f]=1;g[d+i]!==k&&g[d][f].cell==g[d+i][f].cell;)j[d+i][f]=1,i++;for(;g[d][f+m]!==k&&g[d][f].cell==g[d][f+m].cell;){for(c=0;c<i;c++)j[d+c][f+m]=1;m++}h(g[d][f].cell).attr("rowspan",
i).attr("colspan",m)}}}}function P(a){var b=t(a,"aoPreDrawCallback","preDraw",[a]);if(-1!==h.inArray(!1,b))D(a,!1);else{var b=[],c=0,d=a.asStripeClasses,e=d.length,f=a.oLanguage,g=a.iInitDisplayStart,j="ssp"==y(a),i=a.aiDisplay;a.bDrawing=!0;g!==k&&-1!==g&&(a._iDisplayStart=j?g:g>=a.fnRecordsDisplay()?0:g,a.iInitDisplayStart=-1);var g=a._iDisplayStart,m=a.fnDisplayEnd();if(a.bDeferLoading)a.bDeferLoading=!1,a.iDraw++,D(a,!1);else if(j){if(!a.bDestroying&&!nb(a))return}else a.iDraw++;if(0!==i.length){f=
j?a.aoData.length:m;for(j=j?0:g;j<f;j++){var l=i[j],q=a.aoData[l];null===q.nTr&&Ja(a,l);var u=q.nTr;if(0!==e){var G=d[c%e];q._sRowStripe!=G&&(h(u).removeClass(q._sRowStripe).addClass(G),q._sRowStripe=G)}t(a,"aoRowCallback",null,[u,q._aData,c,j,l]);b.push(u);c++}}else c=f.sZeroRecords,1==a.iDraw&&"ajax"==y(a)?c=f.sLoadingRecords:f.sEmptyTable&&0===a.fnRecordsTotal()&&(c=f.sEmptyTable),b[0]=h("<tr/>",{"class":e?d[0]:""}).append(h("<td />",{valign:"top",colSpan:W(a),"class":a.oClasses.sRowEmpty}).html(c))[0];
t(a,"aoHeaderCallback","header",[h(a.nTHead).children("tr")[0],Ma(a),g,m,i]);t(a,"aoFooterCallback","footer",[h(a.nTFoot).children("tr")[0],Ma(a),g,m,i]);d=h(a.nTBody);d.children().detach();d.append(h(b));t(a,"aoDrawCallback","draw",[a]);a.bSorted=!1;a.bFiltered=!1;a.bDrawing=!1}}function T(a,b){var c=a.oFeatures,d=c.bFilter;c.bSort&&ob(a);d?ha(a,a.oPreviousSearch):a.aiDisplay=a.aiDisplayMaster.slice();!0!==b&&(a._iDisplayStart=0);a._drawHold=b;P(a);a._drawHold=!1}function pb(a){var b=a.oClasses,
c=h(a.nTable),c=h("<div/>").insertBefore(c),d=a.oFeatures,e=h("<div/>",{id:a.sTableId+"_wrapper","class":b.sWrapper+(a.nTFoot?"":" "+b.sNoFooter)});a.nHolding=c[0];a.nTableWrapper=e[0];a.nTableReinsertBefore=a.nTable.nextSibling;for(var f=a.sDom.split(""),g,j,i,m,l,q,k=0;k<f.length;k++){g=null;j=f[k];if("<"==j){i=h("<div/>")[0];m=f[k+1];if("'"==m||'"'==m){l="";for(q=2;f[k+q]!=m;)l+=f[k+q],q++;"H"==l?l=b.sJUIHeader:"F"==l&&(l=b.sJUIFooter);-1!=l.indexOf(".")?(m=l.split("."),i.id=m[0].substr(1,m[0].length-
1),i.className=m[1]):"#"==l.charAt(0)?i.id=l.substr(1,l.length-1):i.className=l;k+=q}e.append(i);e=h(i)}else if(">"==j)e=e.parent();else if("l"==j&&d.bPaginate&&d.bLengthChange)g=qb(a);else if("f"==j&&d.bFilter)g=rb(a);else if("r"==j&&d.bProcessing)g=sb(a);else if("t"==j)g=tb(a);else if("i"==j&&d.bInfo)g=ub(a);else if("p"==j&&d.bPaginate)g=vb(a);else if(0!==n.ext.feature.length){i=n.ext.feature;q=0;for(m=i.length;q<m;q++)if(j==i[q].cFeature){g=i[q].fnInit(a);break}}g&&(i=a.aanFeatures,i[j]||(i[j]=
[]),i[j].push(g),e.append(g))}c.replaceWith(e);a.nHolding=null}function fa(a,b){var c=h(b).children("tr"),d,e,f,g,j,i,m,l,q,k;a.splice(0,a.length);f=0;for(i=c.length;f<i;f++)a.push([]);f=0;for(i=c.length;f<i;f++){d=c[f];for(e=d.firstChild;e;){if("TD"==e.nodeName.toUpperCase()||"TH"==e.nodeName.toUpperCase()){l=1*e.getAttribute("colspan");q=1*e.getAttribute("rowspan");l=!l||0===l||1===l?1:l;q=!q||0===q||1===q?1:q;g=0;for(j=a[f];j[g];)g++;m=g;k=1===l?!0:!1;for(j=0;j<l;j++)for(g=0;g<q;g++)a[f+g][m+j]=
{cell:e,unique:k},a[f+g].nTr=d}e=e.nextSibling}}}function sa(a,b,c){var d=[];c||(c=a.aoHeader,b&&(c=[],fa(c,b)));for(var b=0,e=c.length;b<e;b++)for(var f=0,g=c[b].length;f<g;f++)if(c[b][f].unique&&(!d[f]||!a.bSortCellsTop))d[f]=c[b][f].cell;return d}function ta(a,b,c){t(a,"aoServerParams","serverParams",[b]);if(b&&Array.isArray(b)){var d={},e=/(.*?)\[\]$/;h.each(b,function(a,b){var c=b.name.match(e);c?(c=c[0],d[c]||(d[c]=[]),d[c].push(b.value)):d[b.name]=b.value});b=d}var f,g=a.ajax,j=a.oInstance,
i=function(b){t(a,null,"xhr",[a,b,a.jqXHR]);c(b)};if(h.isPlainObject(g)&&g.data){f=g.data;var m="function"===typeof f?f(b,a):f,b="function"===typeof f&&m?m:h.extend(!0,b,m);delete g.data}m={data:b,success:function(b){var c=b.error||b.sError;c&&K(a,0,c);a.json=b;i(b)},dataType:"json",cache:!1,type:a.sServerMethod,error:function(b,c){var d=t(a,null,"xhr",[a,null,a.jqXHR]);-1===h.inArray(!0,d)&&("parsererror"==c?K(a,0,"Invalid JSON response",1):4===b.readyState&&K(a,0,"Ajax error",7));D(a,!1)}};a.oAjaxData=
b;t(a,null,"preXhr",[a,b]);a.fnServerData?a.fnServerData.call(j,a.sAjaxSource,h.map(b,function(a,b){return{name:b,value:a}}),i,a):a.sAjaxSource||"string"===typeof g?a.jqXHR=h.ajax(h.extend(m,{url:g||a.sAjaxSource})):"function"===typeof g?a.jqXHR=g.call(j,b,i,a):(a.jqXHR=h.ajax(h.extend(m,g)),g.data=f)}function nb(a){return a.bAjaxDataGet?(a.iDraw++,D(a,!0),ta(a,wb(a),function(b){xb(a,b)}),!1):!0}function wb(a){var b=a.aoColumns,c=b.length,d=a.oFeatures,e=a.oPreviousSearch,f=a.aoPreSearchCols,g,j=
[],i,m,l,k=Y(a);g=a._iDisplayStart;i=!1!==d.bPaginate?a._iDisplayLength:-1;var u=function(a,b){j.push({name:a,value:b})};u("sEcho",a.iDraw);u("iColumns",c);u("sColumns",C(b,"sName").join(","));u("iDisplayStart",g);u("iDisplayLength",i);var G={draw:a.iDraw,columns:[],order:[],start:g,length:i,search:{value:e.sSearch,regex:e.bRegex}};for(g=0;g<c;g++)m=b[g],l=f[g],i="function"==typeof m.mData?"function":m.mData,G.columns.push({data:i,name:m.sName,searchable:m.bSearchable,orderable:m.bSortable,search:{value:l.sSearch,
regex:l.bRegex}}),u("mDataProp_"+g,i),d.bFilter&&(u("sSearch_"+g,l.sSearch),u("bRegex_"+g,l.bRegex),u("bSearchable_"+g,m.bSearchable)),d.bSort&&u("bSortable_"+g,m.bSortable);d.bFilter&&(u("sSearch",e.sSearch),u("bRegex",e.bRegex));d.bSort&&(h.each(k,function(a,b){G.order.push({column:b.col,dir:b.dir});u("iSortCol_"+a,b.col);u("sSortDir_"+a,b.dir)}),u("iSortingCols",k.length));b=n.ext.legacy.ajax;return null===b?a.sAjaxSource?j:G:b?j:G}function xb(a,b){var c=ua(a,b),d=b.sEcho!==k?b.sEcho:b.draw,e=
b.iTotalRecords!==k?b.iTotalRecords:b.recordsTotal,f=b.iTotalDisplayRecords!==k?b.iTotalDisplayRecords:b.recordsFiltered;if(d!==k){if(1*d<a.iDraw)return;a.iDraw=1*d}pa(a);a._iRecordsTotal=parseInt(e,10);a._iRecordsDisplay=parseInt(f,10);d=0;for(e=c.length;d<e;d++)O(a,c[d]);a.aiDisplay=a.aiDisplayMaster.slice();a.bAjaxDataGet=!1;P(a);a._bInitComplete||va(a,b);a.bAjaxDataGet=!0;D(a,!1)}function ua(a,b){var c=h.isPlainObject(a.ajax)&&a.ajax.dataSrc!==k?a.ajax.dataSrc:a.sAjaxDataProp;return"data"===c?
b.aaData||b[c]:""!==c?S(c)(b):b}function rb(a){var b=a.oClasses,c=a.sTableId,d=a.oLanguage,e=a.oPreviousSearch,f=a.aanFeatures,g='<input type="search" class="'+b.sFilterInput+'"/>',j=d.sSearch,j=j.match(/_INPUT_/)?j.replace("_INPUT_",g):j+g,b=h("<div/>",{id:!f.f?c+"_filter":null,"class":b.sFilter}).append(h("<label/>").append(j)),i=function(){var b=!this.value?"":this.value;b!=e.sSearch&&(ha(a,{sSearch:b,bRegex:e.bRegex,bSmart:e.bSmart,bCaseInsensitive:e.bCaseInsensitive}),a._iDisplayStart=0,P(a))},
f=null!==a.searchDelay?a.searchDelay:"ssp"===y(a)?400:0,m=h("input",b).val(e.sSearch).attr("placeholder",d.sSearchPlaceholder).on("keyup.DT search.DT input.DT paste.DT cut.DT",f?Qa(i,f):i).on("mouseup",function(){setTimeout(function(){i.call(m[0])},10)}).on("keypress.DT",function(a){if(13==a.keyCode)return!1}).attr("aria-controls",c);h(a.nTable).on("search.dt.DT",function(b,c){if(a===c)try{m[0]!==H.activeElement&&m.val(e.sSearch)}catch(d){}});return b[0]}function ha(a,b,c){var d=a.oPreviousSearch,
e=a.aoPreSearchCols,f=function(a){d.sSearch=a.sSearch;d.bRegex=a.bRegex;d.bSmart=a.bSmart;d.bCaseInsensitive=a.bCaseInsensitive};Ia(a);if("ssp"!=y(a)){yb(a,b.sSearch,c,b.bEscapeRegex!==k?!b.bEscapeRegex:b.bRegex,b.bSmart,b.bCaseInsensitive);f(b);for(b=0;b<e.length;b++)zb(a,e[b].sSearch,b,e[b].bEscapeRegex!==k?!e[b].bEscapeRegex:e[b].bRegex,e[b].bSmart,e[b].bCaseInsensitive);Ab(a)}else f(b);a.bFiltered=!0;t(a,null,"search",[a])}function Ab(a){for(var b=n.ext.search,c=a.aiDisplay,d,e,f=0,g=b.length;f<
g;f++){for(var j=[],i=0,m=c.length;i<m;i++)e=c[i],d=a.aoData[e],b[f](a,d._aFilterData,e,d._aData,i)&&j.push(e);c.length=0;h.merge(c,j)}}function zb(a,b,c,d,e,f){if(""!==b){for(var g=[],j=a.aiDisplay,d=Ra(b,d,e,f),e=0;e<j.length;e++)b=a.aoData[j[e]]._aFilterData[c],d.test(b)&&g.push(j[e]);a.aiDisplay=g}}function yb(a,b,c,d,e,f){var e=Ra(b,d,e,f),g=a.oPreviousSearch.sSearch,j=a.aiDisplayMaster,i,f=[];0!==n.ext.search.length&&(c=!0);i=Bb(a);if(0>=b.length)a.aiDisplay=j.slice();else{if(i||c||d||g.length>
b.length||0!==b.indexOf(g)||a.bSorted)a.aiDisplay=j.slice();b=a.aiDisplay;for(c=0;c<b.length;c++)e.test(a.aoData[b[c]]._sFilterRow)&&f.push(b[c]);a.aiDisplay=f}}function Ra(a,b,c,d){a=b?a:Sa(a);c&&(a="^(?=.*?"+h.map(a.match(/"[^"]+"|[^ ]+/g)||[""],function(a){if('"'===a.charAt(0))var b=a.match(/^"(.*)"$/),a=b?b[1]:a;return a.replace('"',"")}).join(")(?=.*?")+").*$");return RegExp(a,d?"i":"")}function Bb(a){var b=a.aoColumns,c,d,e,f,g,j,i,h,l=n.ext.type.search;c=!1;d=0;for(f=a.aoData.length;d<f;d++)if(h=
a.aoData[d],!h._aFilterData){j=[];e=0;for(g=b.length;e<g;e++)c=b[e],c.bSearchable?(i=B(a,d,e,"filter"),l[c.sType]&&(i=l[c.sType](i)),null===i&&(i=""),"string"!==typeof i&&i.toString&&(i=i.toString())):i="",i.indexOf&&-1!==i.indexOf("&")&&(wa.innerHTML=i,i=Zb?wa.textContent:wa.innerText),i.replace&&(i=i.replace(/[\r\n\u2028]/g,"")),j.push(i);h._aFilterData=j;h._sFilterRow=j.join(" ");c=!0}return c}function Cb(a){return{search:a.sSearch,smart:a.bSmart,regex:a.bRegex,caseInsensitive:a.bCaseInsensitive}}
function Db(a){return{sSearch:a.search,bSmart:a.smart,bRegex:a.regex,bCaseInsensitive:a.caseInsensitive}}function ub(a){var b=a.sTableId,c=a.aanFeatures.i,d=h("<div/>",{"class":a.oClasses.sInfo,id:!c?b+"_info":null});c||(a.aoDrawCallback.push({fn:Eb,sName:"information"}),d.attr("role","status").attr("aria-live","polite"),h(a.nTable).attr("aria-describedby",b+"_info"));return d[0]}function Eb(a){var b=a.aanFeatures.i;if(0!==b.length){var c=a.oLanguage,d=a._iDisplayStart+1,e=a.fnDisplayEnd(),f=a.fnRecordsTotal(),
g=a.fnRecordsDisplay(),j=g?c.sInfo:c.sInfoEmpty;g!==f&&(j+=" "+c.sInfoFiltered);j+=c.sInfoPostFix;j=Fb(a,j);c=c.fnInfoCallback;null!==c&&(j=c.call(a.oInstance,a,d,e,f,g,j));h(b).html(j)}}function Fb(a,b){var c=a.fnFormatNumber,d=a._iDisplayStart+1,e=a._iDisplayLength,f=a.fnRecordsDisplay(),g=-1===e;return b.replace(/_START_/g,c.call(a,d)).replace(/_END_/g,c.call(a,a.fnDisplayEnd())).replace(/_MAX_/g,c.call(a,a.fnRecordsTotal())).replace(/_TOTAL_/g,c.call(a,f)).replace(/_PAGE_/g,c.call(a,g?1:Math.ceil(d/
e))).replace(/_PAGES_/g,c.call(a,g?1:Math.ceil(f/e)))}function ia(a){var b,c,d=a.iInitDisplayStart,e=a.aoColumns,f;c=a.oFeatures;var g=a.bDeferLoading;if(a.bInitialised){pb(a);mb(a);ga(a,a.aoHeader);ga(a,a.aoFooter);D(a,!0);c.bAutoWidth&&Ha(a);b=0;for(c=e.length;b<c;b++)f=e[b],f.sWidth&&(f.nTh.style.width=w(f.sWidth));t(a,null,"preInit",[a]);T(a);e=y(a);if("ssp"!=e||g)"ajax"==e?ta(a,[],function(c){var f=ua(a,c);for(b=0;b<f.length;b++)O(a,f[b]);a.iInitDisplayStart=d;T(a);D(a,!1);va(a,c)},a):(D(a,!1),
va(a))}else setTimeout(function(){ia(a)},200)}function va(a,b){a._bInitComplete=!0;(b||a.oInit.aaData)&&aa(a);t(a,null,"plugin-init",[a,b]);t(a,"aoInitComplete","init",[a,b])}function Ta(a,b){var c=parseInt(b,10);a._iDisplayLength=c;Ua(a);t(a,null,"length",[a,c])}function qb(a){for(var b=a.oClasses,c=a.sTableId,d=a.aLengthMenu,e=Array.isArray(d[0]),f=e?d[0]:d,d=e?d[1]:d,e=h("<select/>",{name:c+"_length","aria-controls":c,"class":b.sLengthSelect}),g=0,j=f.length;g<j;g++)e[0][g]=new Option("number"===
typeof d[g]?a.fnFormatNumber(d[g]):d[g],f[g]);var i=h("<div><label/></div>").addClass(b.sLength);a.aanFeatures.l||(i[0].id=c+"_length");i.children().append(a.oLanguage.sLengthMenu.replace("_MENU_",e[0].outerHTML));h("select",i).val(a._iDisplayLength).on("change.DT",function(){Ta(a,h(this).val());P(a)});h(a.nTable).on("length.dt.DT",function(b,c,d){a===c&&h("select",i).val(d)});return i[0]}function vb(a){var b=a.sPaginationType,c=n.ext.pager[b],d="function"===typeof c,e=function(a){P(a)},b=h("<div/>").addClass(a.oClasses.sPaging+
b)[0],f=a.aanFeatures;d||c.fnInit(a,b,e);f.p||(b.id=a.sTableId+"_paginate",a.aoDrawCallback.push({fn:function(a){if(d){var b=a._iDisplayStart,i=a._iDisplayLength,h=a.fnRecordsDisplay(),l=-1===i,b=l?0:Math.ceil(b/i),i=l?1:Math.ceil(h/i),h=c(b,i),k,l=0;for(k=f.p.length;l<k;l++)Pa(a,"pageButton")(a,f.p[l],l,h,b,i)}else c.fnUpdate(a,e)},sName:"pagination"}));return b}function Va(a,b,c){var d=a._iDisplayStart,e=a._iDisplayLength,f=a.fnRecordsDisplay();0===f||-1===e?d=0:"number"===typeof b?(d=b*e,d>f&&
(d=0)):"first"==b?d=0:"previous"==b?(d=0<=e?d-e:0,0>d&&(d=0)):"next"==b?d+e<f&&(d+=e):"last"==b?d=Math.floor((f-1)/e)*e:K(a,0,"Unknown paging action: "+b,5);b=a._iDisplayStart!==d;a._iDisplayStart=d;b&&(t(a,null,"page",[a]),c&&P(a));return b}function sb(a){return h("<div/>",{id:!a.aanFeatures.r?a.sTableId+"_processing":null,"class":a.oClasses.sProcessing}).html(a.oLanguage.sProcessing).insertBefore(a.nTable)[0]}function D(a,b){a.oFeatures.bProcessing&&h(a.aanFeatures.r).css("display",b?"block":"none");
t(a,null,"processing",[a,b])}function tb(a){var b=h(a.nTable);b.attr("role","grid");var c=a.oScroll;if(""===c.sX&&""===c.sY)return a.nTable;var d=c.sX,e=c.sY,f=a.oClasses,g=b.children("caption"),j=g.length?g[0]._captionSide:null,i=h(b[0].cloneNode(!1)),m=h(b[0].cloneNode(!1)),l=b.children("tfoot");l.length||(l=null);i=h("<div/>",{"class":f.sScrollWrapper}).append(h("<div/>",{"class":f.sScrollHead}).css({overflow:"hidden",position:"relative",border:0,width:d?!d?null:w(d):"100%"}).append(h("<div/>",
{"class":f.sScrollHeadInner}).css({"box-sizing":"content-box",width:c.sXInner||"100%"}).append(i.removeAttr("id").css("margin-left",0).append("top"===j?g:null).append(b.children("thead"))))).append(h("<div/>",{"class":f.sScrollBody}).css({position:"relative",overflow:"auto",width:!d?null:w(d)}).append(b));l&&i.append(h("<div/>",{"class":f.sScrollFoot}).css({overflow:"hidden",border:0,width:d?!d?null:w(d):"100%"}).append(h("<div/>",{"class":f.sScrollFootInner}).append(m.removeAttr("id").css("margin-left",
0).append("bottom"===j?g:null).append(b.children("tfoot")))));var b=i.children(),k=b[0],f=b[1],u=l?b[2]:null;if(d)h(f).on("scroll.DT",function(){var a=this.scrollLeft;k.scrollLeft=a;l&&(u.scrollLeft=a)});h(f).css("max-height",e);c.bCollapse||h(f).css("height",e);a.nScrollHead=k;a.nScrollBody=f;a.nScrollFoot=u;a.aoDrawCallback.push({fn:ma,sName:"scrolling"});return i[0]}function ma(a){var b=a.oScroll,c=b.sX,d=b.sXInner,e=b.sY,b=b.iBarWidth,f=h(a.nScrollHead),g=f[0].style,j=f.children("div"),i=j[0].style,
m=j.children("table"),j=a.nScrollBody,l=h(j),q=j.style,u=h(a.nScrollFoot).children("div"),n=u.children("table"),o=h(a.nTHead),p=h(a.nTable),r=p[0],t=r.style,s=a.nTFoot?h(a.nTFoot):null,U=a.oBrowser,V=U.bScrollOversize,$b=C(a.aoColumns,"nTh"),Q,L,R,xa,v=[],x=[],y=[],z=[],A,B=function(a){a=a.style;a.paddingTop="0";a.paddingBottom="0";a.borderTopWidth="0";a.borderBottomWidth="0";a.height=0};L=j.scrollHeight>j.clientHeight;if(a.scrollBarVis!==L&&a.scrollBarVis!==k)a.scrollBarVis=L,aa(a);else{a.scrollBarVis=
L;p.children("thead, tfoot").remove();s&&(R=s.clone().prependTo(p),Q=s.find("tr"),R=R.find("tr"));xa=o.clone().prependTo(p);o=o.find("tr");L=xa.find("tr");xa.find("th, td").removeAttr("tabindex");c||(q.width="100%",f[0].style.width="100%");h.each(sa(a,xa),function(b,c){A=ba(a,b);c.style.width=a.aoColumns[A].sWidth});s&&I(function(a){a.style.width=""},R);f=p.outerWidth();if(""===c){t.width="100%";if(V&&(p.find("tbody").height()>j.offsetHeight||"scroll"==l.css("overflow-y")))t.width=w(p.outerWidth()-
b);f=p.outerWidth()}else""!==d&&(t.width=w(d),f=p.outerWidth());I(B,L);I(function(a){y.push(a.innerHTML);v.push(w(h(a).css("width")))},L);I(function(a,b){if(h.inArray(a,$b)!==-1)a.style.width=v[b]},o);h(L).height(0);s&&(I(B,R),I(function(a){z.push(a.innerHTML);x.push(w(h(a).css("width")))},R),I(function(a,b){a.style.width=x[b]},Q),h(R).height(0));I(function(a,b){a.innerHTML='<div class="dataTables_sizing">'+y[b]+"</div>";a.childNodes[0].style.height="0";a.childNodes[0].style.overflow="hidden";a.style.width=
v[b]},L);s&&I(function(a,b){a.innerHTML='<div class="dataTables_sizing">'+z[b]+"</div>";a.childNodes[0].style.height="0";a.childNodes[0].style.overflow="hidden";a.style.width=x[b]},R);if(p.outerWidth()<f){Q=j.scrollHeight>j.offsetHeight||"scroll"==l.css("overflow-y")?f+b:f;if(V&&(j.scrollHeight>j.offsetHeight||"scroll"==l.css("overflow-y")))t.width=w(Q-b);(""===c||""!==d)&&K(a,1,"Possible column misalignment",6)}else Q="100%";q.width=w(Q);g.width=w(Q);s&&(a.nScrollFoot.style.width=w(Q));!e&&V&&(q.height=
w(r.offsetHeight+b));c=p.outerWidth();m[0].style.width=w(c);i.width=w(c);d=p.height()>j.clientHeight||"scroll"==l.css("overflow-y");e="padding"+(U.bScrollbarLeft?"Left":"Right");i[e]=d?b+"px":"0px";s&&(n[0].style.width=w(c),u[0].style.width=w(c),u[0].style[e]=d?b+"px":"0px");p.children("colgroup").insertBefore(p.children("thead"));l.trigger("scroll");if((a.bSorted||a.bFiltered)&&!a._drawHold)j.scrollTop=0}}function I(a,b,c){for(var d=0,e=0,f=b.length,g,j;e<f;){g=b[e].firstChild;for(j=c?c[e].firstChild:
null;g;)1===g.nodeType&&(c?a(g,j,d):a(g,d),d++),g=g.nextSibling,j=c?j.nextSibling:null;e++}}function Ha(a){var b=a.nTable,c=a.aoColumns,d=a.oScroll,e=d.sY,f=d.sX,g=d.sXInner,j=c.length,i=na(a,"bVisible"),m=h("th",a.nTHead),l=b.getAttribute("width"),k=b.parentNode,u=!1,n,o,p=a.oBrowser,d=p.bScrollOversize;(n=b.style.width)&&-1!==n.indexOf("%")&&(l=n);for(n=0;n<i.length;n++)o=c[i[n]],null!==o.sWidth&&(o.sWidth=Gb(o.sWidthOrig,k),u=!0);if(d||!u&&!f&&!e&&j==W(a)&&j==m.length)for(n=0;n<j;n++)i=ba(a,n),
null!==i&&(c[i].sWidth=w(m.eq(n).width()));else{j=h(b).clone().css("visibility","hidden").removeAttr("id");j.find("tbody tr").remove();var r=h("<tr/>").appendTo(j.find("tbody"));j.find("thead, tfoot").remove();j.append(h(a.nTHead).clone()).append(h(a.nTFoot).clone());j.find("tfoot th, tfoot td").css("width","");m=sa(a,j.find("thead")[0]);for(n=0;n<i.length;n++)o=c[i[n]],m[n].style.width=null!==o.sWidthOrig&&""!==o.sWidthOrig?w(o.sWidthOrig):"",o.sWidthOrig&&f&&h(m[n]).append(h("<div/>").css({width:o.sWidthOrig,
margin:0,padding:0,border:0,height:1}));if(a.aoData.length)for(n=0;n<i.length;n++)u=i[n],o=c[u],h(Hb(a,u)).clone(!1).append(o.sContentPadding).appendTo(r);h("[name]",j).removeAttr("name");o=h("<div/>").css(f||e?{position:"absolute",top:0,left:0,height:1,right:0,overflow:"hidden"}:{}).append(j).appendTo(k);f&&g?j.width(g):f?(j.css("width","auto"),j.removeAttr("width"),j.width()<k.clientWidth&&l&&j.width(k.clientWidth)):e?j.width(k.clientWidth):l&&j.width(l);for(n=e=0;n<i.length;n++)k=h(m[n]),g=k.outerWidth()-
k.width(),k=p.bBounding?Math.ceil(m[n].getBoundingClientRect().width):k.outerWidth(),e+=k,c[i[n]].sWidth=w(k-g);b.style.width=w(e);o.remove()}l&&(b.style.width=w(l));if((l||f)&&!a._reszEvt)b=function(){h(E).on("resize.DT-"+a.sInstance,Qa(function(){aa(a)}))},d?setTimeout(b,1E3):b(),a._reszEvt=!0}function Gb(a,b){if(!a)return 0;var c=h("<div/>").css("width",w(a)).appendTo(b||H.body),d=c[0].offsetWidth;c.remove();return d}function Hb(a,b){var c=Ib(a,b);if(0>c)return null;var d=a.aoData[c];return!d.nTr?
h("<td/>").html(B(a,c,b,"display"))[0]:d.anCells[b]}function Ib(a,b){for(var c,d=-1,e=-1,f=0,g=a.aoData.length;f<g;f++)c=B(a,f,b,"display")+"",c=c.replace(ac,""),c=c.replace(/&nbsp;/g," "),c.length>d&&(d=c.length,e=f);return e}function w(a){return null===a?"0px":"number"==typeof a?0>a?"0px":a+"px":a.match(/\d$/)?a+"px":a}function Y(a){var b,c,d=[],e=a.aoColumns,f,g,j,i;b=a.aaSortingFixed;c=h.isPlainObject(b);var m=[];f=function(a){a.length&&!Array.isArray(a[0])?m.push(a):h.merge(m,a)};Array.isArray(b)&&
f(b);c&&b.pre&&f(b.pre);f(a.aaSorting);c&&b.post&&f(b.post);for(a=0;a<m.length;a++){i=m[a][0];f=e[i].aDataSort;b=0;for(c=f.length;b<c;b++)g=f[b],j=e[g].sType||"string",m[a]._idx===k&&(m[a]._idx=h.inArray(m[a][1],e[g].asSorting)),d.push({src:i,col:g,dir:m[a][1],index:m[a]._idx,type:j,formatter:n.ext.type.order[j+"-pre"]})}return d}function ob(a){var b,c,d=[],e=n.ext.type.order,f=a.aoData,g=0,j,i=a.aiDisplayMaster,h;Ia(a);h=Y(a);b=0;for(c=h.length;b<c;b++)j=h[b],j.formatter&&g++,Jb(a,j.col);if("ssp"!=
y(a)&&0!==h.length){b=0;for(c=i.length;b<c;b++)d[i[b]]=b;g===h.length?i.sort(function(a,b){var c,e,g,j,i=h.length,k=f[a]._aSortData,n=f[b]._aSortData;for(g=0;g<i;g++)if(j=h[g],c=k[j.col],e=n[j.col],c=c<e?-1:c>e?1:0,0!==c)return"asc"===j.dir?c:-c;c=d[a];e=d[b];return c<e?-1:c>e?1:0}):i.sort(function(a,b){var c,g,j,i,k=h.length,n=f[a]._aSortData,o=f[b]._aSortData;for(j=0;j<k;j++)if(i=h[j],c=n[i.col],g=o[i.col],i=e[i.type+"-"+i.dir]||e["string-"+i.dir],c=i(c,g),0!==c)return c;c=d[a];g=d[b];return c<
g?-1:c>g?1:0})}a.bSorted=!0}function Kb(a){for(var b,c,d=a.aoColumns,e=Y(a),a=a.oLanguage.oAria,f=0,g=d.length;f<g;f++){c=d[f];var j=c.asSorting;b=c.sTitle.replace(/<.*?>/g,"");var i=c.nTh;i.removeAttribute("aria-sort");c.bSortable&&(0<e.length&&e[0].col==f?(i.setAttribute("aria-sort","asc"==e[0].dir?"ascending":"descending"),c=j[e[0].index+1]||j[0]):c=j[0],b+="asc"===c?a.sSortAscending:a.sSortDescending);i.setAttribute("aria-label",b)}}function Wa(a,b,c,d){var e=a.aaSorting,f=a.aoColumns[b].asSorting,
g=function(a,b){var c=a._idx;c===k&&(c=h.inArray(a[1],f));return c+1<f.length?c+1:b?null:0};"number"===typeof e[0]&&(e=a.aaSorting=[e]);c&&a.oFeatures.bSortMulti?(c=h.inArray(b,C(e,"0")),-1!==c?(b=g(e[c],!0),null===b&&1===e.length&&(b=0),null===b?e.splice(c,1):(e[c][1]=f[b],e[c]._idx=b)):(e.push([b,f[0],0]),e[e.length-1]._idx=0)):e.length&&e[0][0]==b?(b=g(e[0]),e.length=1,e[0][1]=f[b],e[0]._idx=b):(e.length=0,e.push([b,f[0]]),e[0]._idx=0);T(a);"function"==typeof d&&d(a)}function Oa(a,b,c,d){var e=
a.aoColumns[c];Xa(b,{},function(b){!1!==e.bSortable&&(a.oFeatures.bProcessing?(D(a,!0),setTimeout(function(){Wa(a,c,b.shiftKey,d);"ssp"!==y(a)&&D(a,!1)},0)):Wa(a,c,b.shiftKey,d))})}function ya(a){var b=a.aLastSort,c=a.oClasses.sSortColumn,d=Y(a),e=a.oFeatures,f,g;if(e.bSort&&e.bSortClasses){e=0;for(f=b.length;e<f;e++)g=b[e].src,h(C(a.aoData,"anCells",g)).removeClass(c+(2>e?e+1:3));e=0;for(f=d.length;e<f;e++)g=d[e].src,h(C(a.aoData,"anCells",g)).addClass(c+(2>e?e+1:3))}a.aLastSort=d}function Jb(a,
b){var c=a.aoColumns[b],d=n.ext.order[c.sSortDataType],e;d&&(e=d.call(a.oInstance,a,b,ca(a,b)));for(var f,g=n.ext.type.order[c.sType+"-pre"],j=0,i=a.aoData.length;j<i;j++)if(c=a.aoData[j],c._aSortData||(c._aSortData=[]),!c._aSortData[b]||d)f=d?e[j]:B(a,j,b,"sort"),c._aSortData[b]=g?g(f):f}function za(a){if(a.oFeatures.bStateSave&&!a.bDestroying){var b={time:+new Date,start:a._iDisplayStart,length:a._iDisplayLength,order:h.extend(!0,[],a.aaSorting),search:Cb(a.oPreviousSearch),columns:h.map(a.aoColumns,
function(b,d){return{visible:b.bVisible,search:Cb(a.aoPreSearchCols[d])}})};t(a,"aoStateSaveParams","stateSaveParams",[a,b]);a.oSavedState=b;a.fnStateSaveCallback.call(a.oInstance,a,b)}}function Lb(a,b,c){var d,e,f=a.aoColumns,b=function(b){if(b&&b.time){var g=t(a,"aoStateLoadParams","stateLoadParams",[a,b]);if(-1===h.inArray(!1,g)&&(g=a.iStateDuration,!(0<g&&b.time<+new Date-1E3*g)&&!(b.columns&&f.length!==b.columns.length))){a.oLoadedState=h.extend(!0,{},b);b.start!==k&&(a._iDisplayStart=b.start,
a.iInitDisplayStart=b.start);b.length!==k&&(a._iDisplayLength=b.length);b.order!==k&&(a.aaSorting=[],h.each(b.order,function(b,c){a.aaSorting.push(c[0]>=f.length?[0,c[1]]:c)}));b.search!==k&&h.extend(a.oPreviousSearch,Db(b.search));if(b.columns){d=0;for(e=b.columns.length;d<e;d++)g=b.columns[d],g.visible!==k&&(f[d].bVisible=g.visible),g.search!==k&&h.extend(a.aoPreSearchCols[d],Db(g.search))}t(a,"aoStateLoaded","stateLoaded",[a,b])}}c()};if(a.oFeatures.bStateSave){var g=a.fnStateLoadCallback.call(a.oInstance,
a,b);g!==k&&b(g)}else c()}function Aa(a){var b=n.settings,a=h.inArray(a,C(b,"nTable"));return-1!==a?b[a]:null}function K(a,b,c,d){c="DataTables warning: "+(a?"table id="+a.sTableId+" - ":"")+c;d&&(c+=". For more information about this error, please see http://datatables.net/tn/"+d);if(b)E.console&&console.log&&console.log(c);else if(b=n.ext,b=b.sErrMode||b.errMode,a&&t(a,null,"error",[a,d,c]),"alert"==b)alert(c);else{if("throw"==b)throw Error(c);"function"==typeof b&&b(a,d,c)}}function F(a,b,c,d){Array.isArray(c)?
h.each(c,function(c,d){Array.isArray(d)?F(a,b,d[0],d[1]):F(a,b,d)}):(d===k&&(d=c),b[c]!==k&&(a[d]=b[c]))}function Ya(a,b,c){var d,e;for(e in b)b.hasOwnProperty(e)&&(d=b[e],h.isPlainObject(d)?(h.isPlainObject(a[e])||(a[e]={}),h.extend(!0,a[e],d)):a[e]=c&&"data"!==e&&"aaData"!==e&&Array.isArray(d)?d.slice():d);return a}function Xa(a,b,c){h(a).on("click.DT",b,function(b){h(a).trigger("blur");c(b)}).on("keypress.DT",b,function(a){13===a.which&&(a.preventDefault(),c(a))}).on("selectstart.DT",function(){return!1})}
function z(a,b,c,d){c&&a[b].push({fn:c,sName:d})}function t(a,b,c,d){var e=[];b&&(e=h.map(a[b].slice().reverse(),function(b){return b.fn.apply(a.oInstance,d)}));null!==c&&(b=h.Event(c+".dt"),h(a.nTable).trigger(b,d),e.push(b.result));return e}function Ua(a){var b=a._iDisplayStart,c=a.fnDisplayEnd(),d=a._iDisplayLength;b>=c&&(b=c-d);b-=b%d;if(-1===d||0>b)b=0;a._iDisplayStart=b}function Pa(a,b){var c=a.renderer,d=n.ext.renderer[b];return h.isPlainObject(c)&&c[b]?d[c[b]]||d._:"string"===typeof c?d[c]||
d._:d._}function y(a){return a.oFeatures.bServerSide?"ssp":a.ajax||a.sAjaxSource?"ajax":"dom"}function ja(a,b){var c=[],c=Mb.numbers_length,d=Math.floor(c/2);b<=c?c=Z(0,b):a<=d?(c=Z(0,c-2),c.push("ellipsis"),c.push(b-1)):(a>=b-1-d?c=Z(b-(c-2),b):(c=Z(a-d+2,a+d-1),c.push("ellipsis"),c.push(b-1)),c.splice(0,0,"ellipsis"),c.splice(0,0,0));c.DT_el="span";return c}function Fa(a){h.each({num:function(b){return Ba(b,a)},"num-fmt":function(b){return Ba(b,a,Za)},"html-num":function(b){return Ba(b,a,Ca)},"html-num-fmt":function(b){return Ba(b,
a,Ca,Za)}},function(b,c){v.type.order[b+a+"-pre"]=c;b.match(/^html\-/)&&(v.type.search[b+a]=v.type.search.html)})}function Nb(a){return function(){var b=[Aa(this[n.ext.iApiIndex])].concat(Array.prototype.slice.call(arguments));return n.ext.internal[a].apply(this,b)}}var n=function(a){this.$=function(a,b){return this.api(!0).$(a,b)};this._=function(a,b){return this.api(!0).rows(a,b).data()};this.api=function(a){return a?new r(Aa(this[v.iApiIndex])):new r(this)};this.fnAddData=function(a,b){var c=this.api(!0),
d=Array.isArray(a)&&(Array.isArray(a[0])||h.isPlainObject(a[0]))?c.rows.add(a):c.row.add(a);(b===k||b)&&c.draw();return d.flatten().toArray()};this.fnAdjustColumnSizing=function(a){var b=this.api(!0).columns.adjust(),c=b.settings()[0],d=c.oScroll;a===k||a?b.draw(!1):(""!==d.sX||""!==d.sY)&&ma(c)};this.fnClearTable=function(a){var b=this.api(!0).clear();(a===k||a)&&b.draw()};this.fnClose=function(a){this.api(!0).row(a).child.hide()};this.fnDeleteRow=function(a,b,c){var d=this.api(!0),a=d.rows(a),e=
a.settings()[0],h=e.aoData[a[0][0]];a.remove();b&&b.call(this,e,h);(c===k||c)&&d.draw();return h};this.fnDestroy=function(a){this.api(!0).destroy(a)};this.fnDraw=function(a){this.api(!0).draw(a)};this.fnFilter=function(a,b,c,d,e,h){e=this.api(!0);null===b||b===k?e.search(a,c,d,h):e.column(b).search(a,c,d,h);e.draw()};this.fnGetData=function(a,b){var c=this.api(!0);if(a!==k){var d=a.nodeName?a.nodeName.toLowerCase():"";return b!==k||"td"==d||"th"==d?c.cell(a,b).data():c.row(a).data()||null}return c.data().toArray()};
this.fnGetNodes=function(a){var b=this.api(!0);return a!==k?b.row(a).node():b.rows().nodes().flatten().toArray()};this.fnGetPosition=function(a){var b=this.api(!0),c=a.nodeName.toUpperCase();return"TR"==c?b.row(a).index():"TD"==c||"TH"==c?(a=b.cell(a).index(),[a.row,a.columnVisible,a.column]):null};this.fnIsOpen=function(a){return this.api(!0).row(a).child.isShown()};this.fnOpen=function(a,b,c){return this.api(!0).row(a).child(b,c).show().child()[0]};this.fnPageChange=function(a,b){var c=this.api(!0).page(a);
(b===k||b)&&c.draw(!1)};this.fnSetColumnVis=function(a,b,c){a=this.api(!0).column(a).visible(b);(c===k||c)&&a.columns.adjust().draw()};this.fnSettings=function(){return Aa(this[v.iApiIndex])};this.fnSort=function(a){this.api(!0).order(a).draw()};this.fnSortListener=function(a,b,c){this.api(!0).order.listener(a,b,c)};this.fnUpdate=function(a,b,c,d,e){var h=this.api(!0);c===k||null===c?h.row(b).data(a):h.cell(b,c).data(a);(e===k||e)&&h.columns.adjust();(d===k||d)&&h.draw();return 0};this.fnVersionCheck=
v.fnVersionCheck;var b=this,c=a===k,d=this.length;c&&(a={});this.oApi=this.internal=v.internal;for(var e in n.ext.internal)e&&(this[e]=Nb(e));this.each(function(){var e={},g=1<d?Ya(e,a,!0):a,j=0,i,e=this.getAttribute("id"),m=!1,l=n.defaults,q=h(this);if("table"!=this.nodeName.toLowerCase())K(null,0,"Non-table node initialisation ("+this.nodeName+")",2);else{gb(l);hb(l.column);J(l,l,!0);J(l.column,l.column,!0);J(l,h.extend(g,q.data()),!0);var u=n.settings,j=0;for(i=u.length;j<i;j++){var o=u[j];if(o.nTable==
this||o.nTHead&&o.nTHead.parentNode==this||o.nTFoot&&o.nTFoot.parentNode==this){var r=g.bRetrieve!==k?g.bRetrieve:l.bRetrieve;if(c||r)return o.oInstance;if(g.bDestroy!==k?g.bDestroy:l.bDestroy){o.oInstance.fnDestroy();break}else{K(o,0,"Cannot reinitialise DataTable",3);return}}if(o.sTableId==this.id){u.splice(j,1);break}}if(null===e||""===e)this.id=e="DataTables_Table_"+n.ext._unique++;var p=h.extend(!0,{},n.models.oSettings,{sDestroyWidth:q[0].style.width,sInstance:e,sTableId:e});p.nTable=this;p.oApi=
b.internal;p.oInit=g;u.push(p);p.oInstance=1===b.length?b:q.dataTable();gb(g);Ea(g.oLanguage);g.aLengthMenu&&!g.iDisplayLength&&(g.iDisplayLength=Array.isArray(g.aLengthMenu[0])?g.aLengthMenu[0][0]:g.aLengthMenu[0]);g=Ya(h.extend(!0,{},l),g);F(p.oFeatures,g,"bPaginate bLengthChange bFilter bSort bSortMulti bInfo bProcessing bAutoWidth bSortClasses bServerSide bDeferRender".split(" "));F(p,g,["asStripeClasses","ajax","fnServerData","fnFormatNumber","sServerMethod","aaSorting","aaSortingFixed","aLengthMenu",
"sPaginationType","sAjaxSource","sAjaxDataProp","iStateDuration","sDom","bSortCellsTop","iTabIndex","fnStateLoadCallback","fnStateSaveCallback","renderer","searchDelay","rowId",["iCookieDuration","iStateDuration"],["oSearch","oPreviousSearch"],["aoSearchCols","aoPreSearchCols"],["iDisplayLength","_iDisplayLength"]]);F(p.oScroll,g,[["sScrollX","sX"],["sScrollXInner","sXInner"],["sScrollY","sY"],["bScrollCollapse","bCollapse"]]);F(p.oLanguage,g,"fnInfoCallback");z(p,"aoDrawCallback",g.fnDrawCallback,
"user");z(p,"aoServerParams",g.fnServerParams,"user");z(p,"aoStateSaveParams",g.fnStateSaveParams,"user");z(p,"aoStateLoadParams",g.fnStateLoadParams,"user");z(p,"aoStateLoaded",g.fnStateLoaded,"user");z(p,"aoRowCallback",g.fnRowCallback,"user");z(p,"aoRowCreatedCallback",g.fnCreatedRow,"user");z(p,"aoHeaderCallback",g.fnHeaderCallback,"user");z(p,"aoFooterCallback",g.fnFooterCallback,"user");z(p,"aoInitComplete",g.fnInitComplete,"user");z(p,"aoPreDrawCallback",g.fnPreDrawCallback,"user");p.rowIdFn=
S(g.rowId);ib(p);var s=p.oClasses;h.extend(s,n.ext.classes,g.oClasses);q.addClass(s.sTable);p.iInitDisplayStart===k&&(p.iInitDisplayStart=g.iDisplayStart,p._iDisplayStart=g.iDisplayStart);null!==g.iDeferLoading&&(p.bDeferLoading=!0,e=Array.isArray(g.iDeferLoading),p._iRecordsDisplay=e?g.iDeferLoading[0]:g.iDeferLoading,p._iRecordsTotal=e?g.iDeferLoading[1]:g.iDeferLoading);var w=p.oLanguage;h.extend(!0,w,g.oLanguage);w.sUrl&&(h.ajax({dataType:"json",url:w.sUrl,success:function(a){Ea(a);J(l.oLanguage,
a);h.extend(true,w,a);ia(p)},error:function(){ia(p)}}),m=!0);null===g.asStripeClasses&&(p.asStripeClasses=[s.sStripeOdd,s.sStripeEven]);var e=p.asStripeClasses,v=q.children("tbody").find("tr").eq(0);-1!==h.inArray(!0,h.map(e,function(a){return v.hasClass(a)}))&&(h("tbody tr",this).removeClass(e.join(" ")),p.asDestroyStripes=e.slice());e=[];u=this.getElementsByTagName("thead");0!==u.length&&(fa(p.aoHeader,u[0]),e=sa(p));if(null===g.aoColumns){u=[];j=0;for(i=e.length;j<i;j++)u.push(null)}else u=g.aoColumns;
j=0;for(i=u.length;j<i;j++)Ga(p,e?e[j]:null);kb(p,g.aoColumnDefs,u,function(a,b){la(p,a,b)});if(v.length){var U=function(a,b){return a.getAttribute("data-"+b)!==null?b:null};h(v[0]).children("th, td").each(function(a,b){var c=p.aoColumns[a];if(c.mData===a){var d=U(b,"sort")||U(b,"order"),e=U(b,"filter")||U(b,"search");if(d!==null||e!==null){c.mData={_:a+".display",sort:d!==null?a+".@data-"+d:k,type:d!==null?a+".@data-"+d:k,filter:e!==null?a+".@data-"+e:k};la(p,a)}}})}var V=p.oFeatures,e=function(){if(g.aaSorting===
k){var a=p.aaSorting;j=0;for(i=a.length;j<i;j++)a[j][1]=p.aoColumns[j].asSorting[0]}ya(p);V.bSort&&z(p,"aoDrawCallback",function(){if(p.bSorted){var a=Y(p),b={};h.each(a,function(a,c){b[c.src]=c.dir});t(p,null,"order",[p,a,b]);Kb(p)}});z(p,"aoDrawCallback",function(){(p.bSorted||y(p)==="ssp"||V.bDeferRender)&&ya(p)},"sc");var a=q.children("caption").each(function(){this._captionSide=h(this).css("caption-side")}),b=q.children("thead");b.length===0&&(b=h("<thead/>").appendTo(q));p.nTHead=b[0];b=q.children("tbody");
b.length===0&&(b=h("<tbody/>").appendTo(q));p.nTBody=b[0];b=q.children("tfoot");if(b.length===0&&a.length>0&&(p.oScroll.sX!==""||p.oScroll.sY!==""))b=h("<tfoot/>").appendTo(q);if(b.length===0||b.children().length===0)q.addClass(s.sNoFooter);else if(b.length>0){p.nTFoot=b[0];fa(p.aoFooter,p.nTFoot)}if(g.aaData)for(j=0;j<g.aaData.length;j++)O(p,g.aaData[j]);else(p.bDeferLoading||y(p)=="dom")&&oa(p,h(p.nTBody).children("tr"));p.aiDisplay=p.aiDisplayMaster.slice();p.bInitialised=true;m===false&&ia(p)};
g.bStateSave?(V.bStateSave=!0,z(p,"aoDrawCallback",za,"state_save"),Lb(p,g,e)):e()}});b=null;return this},v,r,o,s,$a={},Ob=/[\r\n\u2028]/g,Ca=/<.*?>/g,bc=/^\d{2,4}[\.\/\-]\d{1,2}[\.\/\-]\d{1,2}([T ]{1}\d{1,2}[:\.]\d{2}([\.:]\d{2})?)?$/,cc=RegExp("(\\/|\\.|\\*|\\+|\\?|\\||\\(|\\)|\\[|\\]|\\{|\\}|\\\\|\\$|\\^|\\-)","g"),Za=/['\u00A0,$£€¥%\u2009\u202F\u20BD\u20a9\u20BArfkɃΞ]/gi,M=function(a){return!a||!0===a||"-"===a?!0:!1},Pb=function(a){var b=parseInt(a,10);return!isNaN(b)&&isFinite(a)?b:null},Qb=
function(a,b){$a[b]||($a[b]=RegExp(Sa(b),"g"));return"string"===typeof a&&"."!==b?a.replace(/\./g,"").replace($a[b],"."):a},ab=function(a,b,c){var d="string"===typeof a;if(M(a))return!0;b&&d&&(a=Qb(a,b));c&&d&&(a=a.replace(Za,""));return!isNaN(parseFloat(a))&&isFinite(a)},Rb=function(a,b,c){return M(a)?!0:!(M(a)||"string"===typeof a)?null:ab(a.replace(Ca,""),b,c)?!0:null},C=function(a,b,c){var d=[],e=0,f=a.length;if(c!==k)for(;e<f;e++)a[e]&&a[e][b]&&d.push(a[e][b][c]);else for(;e<f;e++)a[e]&&d.push(a[e][b]);
return d},ka=function(a,b,c,d){var e=[],f=0,g=b.length;if(d!==k)for(;f<g;f++)a[b[f]][c]&&e.push(a[b[f]][c][d]);else for(;f<g;f++)e.push(a[b[f]][c]);return e},Z=function(a,b){var c=[],d;b===k?(b=0,d=a):(d=b,b=a);for(var e=b;e<d;e++)c.push(e);return c},Sb=function(a){for(var b=[],c=0,d=a.length;c<d;c++)a[c]&&b.push(a[c]);return b},ra=function(a){var b;a:{if(!(2>a.length)){b=a.slice().sort();for(var c=b[0],d=1,e=b.length;d<e;d++){if(b[d]===c){b=!1;break a}c=b[d]}}b=!0}if(b)return a.slice();b=[];var e=
a.length,f,g=0,d=0;a:for(;d<e;d++){c=a[d];for(f=0;f<g;f++)if(b[f]===c)continue a;b.push(c);g++}return b},Tb=function(a,b){if(Array.isArray(b))for(var c=0;c<b.length;c++)Tb(a,b[c]);else a.push(b);return a};Array.isArray||(Array.isArray=function(a){return"[object Array]"===Object.prototype.toString.call(a)});String.prototype.trim||(String.prototype.trim=function(){return this.replace(/^[\s\uFEFF\xA0]+|[\s\uFEFF\xA0]+$/g,"")});n.util={throttle:function(a,b){var c=b!==k?b:200,d,e;return function(){var b=
this,g=+new Date,j=arguments;if(d&&g<d+c){clearTimeout(e);e=setTimeout(function(){d=k;a.apply(b,j)},c)}else{d=g;a.apply(b,j)}}},escapeRegex:function(a){return a.replace(cc,"\\$1")}};var A=function(a,b,c){a[b]!==k&&(a[c]=a[b])},da=/\[.*?\]$/,X=/\(\)$/,Sa=n.util.escapeRegex,wa=h("<div>")[0],Zb=wa.textContent!==k,ac=/<.*?>/g,Qa=n.util.throttle,Ub=[],x=Array.prototype,dc=function(a){var b,c,d=n.settings,e=h.map(d,function(a){return a.nTable});if(a){if(a.nTable&&a.oApi)return[a];if(a.nodeName&&a.nodeName.toLowerCase()===
"table"){b=h.inArray(a,e);return b!==-1?[d[b]]:null}if(a&&typeof a.settings==="function")return a.settings().toArray();typeof a==="string"?c=h(a):a instanceof h&&(c=a)}else return[];if(c)return c.map(function(){b=h.inArray(this,e);return b!==-1?d[b]:null}).toArray()};r=function(a,b){if(!(this instanceof r))return new r(a,b);var c=[],d=function(a){(a=dc(a))&&c.push.apply(c,a)};if(Array.isArray(a))for(var e=0,f=a.length;e<f;e++)d(a[e]);else d(a);this.context=ra(c);b&&h.merge(this,b);this.selector={rows:null,
cols:null,opts:null};r.extend(this,this,Ub)};n.Api=r;h.extend(r.prototype,{any:function(){return this.count()!==0},concat:x.concat,context:[],count:function(){return this.flatten().length},each:function(a){for(var b=0,c=this.length;b<c;b++)a.call(this,this[b],b,this);return this},eq:function(a){var b=this.context;return b.length>a?new r(b[a],this[a]):null},filter:function(a){var b=[];if(x.filter)b=x.filter.call(this,a,this);else for(var c=0,d=this.length;c<d;c++)a.call(this,this[c],c,this)&&b.push(this[c]);
return new r(this.context,b)},flatten:function(){var a=[];return new r(this.context,a.concat.apply(a,this.toArray()))},join:x.join,indexOf:x.indexOf||function(a,b){for(var c=b||0,d=this.length;c<d;c++)if(this[c]===a)return c;return-1},iterator:function(a,b,c,d){var e=[],f,g,j,i,h,l=this.context,n,o,s=this.selector;if(typeof a==="string"){d=c;c=b;b=a;a=false}g=0;for(j=l.length;g<j;g++){var t=new r(l[g]);if(b==="table"){f=c.call(t,l[g],g);f!==k&&e.push(f)}else if(b==="columns"||b==="rows"){f=c.call(t,
l[g],this[g],g);f!==k&&e.push(f)}else if(b==="column"||b==="column-rows"||b==="row"||b==="cell"){o=this[g];b==="column-rows"&&(n=Da(l[g],s.opts));i=0;for(h=o.length;i<h;i++){f=o[i];f=b==="cell"?c.call(t,l[g],f.row,f.column,g,i):c.call(t,l[g],f,g,i,n);f!==k&&e.push(f)}}}if(e.length||d){a=new r(l,a?e.concat.apply([],e):e);b=a.selector;b.rows=s.rows;b.cols=s.cols;b.opts=s.opts;return a}return this},lastIndexOf:x.lastIndexOf||function(a,b){return this.indexOf.apply(this.toArray.reverse(),arguments)},
length:0,map:function(a){var b=[];if(x.map)b=x.map.call(this,a,this);else for(var c=0,d=this.length;c<d;c++)b.push(a.call(this,this[c],c));return new r(this.context,b)},pluck:function(a){return this.map(function(b){return b[a]})},pop:x.pop,push:x.push,reduce:x.reduce||function(a,b){return jb(this,a,b,0,this.length,1)},reduceRight:x.reduceRight||function(a,b){return jb(this,a,b,this.length-1,-1,-1)},reverse:x.reverse,selector:null,shift:x.shift,slice:function(){return new r(this.context,this)},sort:x.sort,
splice:x.splice,toArray:function(){return x.slice.call(this)},to$:function(){return h(this)},toJQuery:function(){return h(this)},unique:function(){return new r(this.context,ra(this))},unshift:x.unshift});r.extend=function(a,b,c){if(c.length&&b&&(b instanceof r||b.__dt_wrapper)){var d,e,f,g=function(a,b,c){return function(){var d=b.apply(a,arguments);r.extend(d,d,c.methodExt);return d}};d=0;for(e=c.length;d<e;d++){f=c[d];b[f.name]=f.type==="function"?g(a,f.val,f):f.type==="object"?{}:f.val;b[f.name].__dt_wrapper=
true;r.extend(a,b[f.name],f.propExt)}}};r.register=o=function(a,b){if(Array.isArray(a))for(var c=0,d=a.length;c<d;c++)r.register(a[c],b);else for(var e=a.split("."),f=Ub,g,j,c=0,d=e.length;c<d;c++){g=(j=e[c].indexOf("()")!==-1)?e[c].replace("()",""):e[c];var i;a:{i=0;for(var k=f.length;i<k;i++)if(f[i].name===g){i=f[i];break a}i=null}if(!i){i={name:g,val:{},methodExt:[],propExt:[],type:"object"};f.push(i)}if(c===d-1){i.val=b;i.type=typeof b==="function"?"function":h.isPlainObject(b)?"object":"other"}else f=
j?i.methodExt:i.propExt}};r.registerPlural=s=function(a,b,c){r.register(a,c);r.register(b,function(){var a=c.apply(this,arguments);return a===this?this:a instanceof r?a.length?Array.isArray(a[0])?new r(a.context,a[0]):a[0]:k:a})};var Vb=function(a,b){if(Array.isArray(a))return h.map(a,function(a){return Vb(a,b)});if(typeof a==="number")return[b[a]];var c=h.map(b,function(a){return a.nTable});return h(c).filter(a).map(function(){var a=h.inArray(this,c);return b[a]}).toArray()};o("tables()",function(a){return a!==
k&&a!==null?new r(Vb(a,this.context)):this});o("table()",function(a){var a=this.tables(a),b=a.context;return b.length?new r(b[0]):a});s("tables().nodes()","table().node()",function(){return this.iterator("table",function(a){return a.nTable},1)});s("tables().body()","table().body()",function(){return this.iterator("table",function(a){return a.nTBody},1)});s("tables().header()","table().header()",function(){return this.iterator("table",function(a){return a.nTHead},1)});s("tables().footer()","table().footer()",
function(){return this.iterator("table",function(a){return a.nTFoot},1)});s("tables().containers()","table().container()",function(){return this.iterator("table",function(a){return a.nTableWrapper},1)});o("draw()",function(a){return this.iterator("table",function(b){if(a==="page")P(b);else{typeof a==="string"&&(a=a==="full-hold"?false:true);T(b,a===false)}})});o("page()",function(a){return a===k?this.page.info().page:this.iterator("table",function(b){Va(b,a)})});o("page.info()",function(){if(this.context.length===
0)return k;var a=this.context[0],b=a._iDisplayStart,c=a.oFeatures.bPaginate?a._iDisplayLength:-1,d=a.fnRecordsDisplay(),e=c===-1;return{page:e?0:Math.floor(b/c),pages:e?1:Math.ceil(d/c),start:b,end:a.fnDisplayEnd(),length:c,recordsTotal:a.fnRecordsTotal(),recordsDisplay:d,serverSide:y(a)==="ssp"}});o("page.len()",function(a){return a===k?this.context.length!==0?this.context[0]._iDisplayLength:k:this.iterator("table",function(b){Ta(b,a)})});var Wb=function(a,b,c){if(c){var d=new r(a);d.one("draw",
function(){c(d.ajax.json())})}if(y(a)=="ssp")T(a,b);else{D(a,true);var e=a.jqXHR;e&&e.readyState!==4&&e.abort();ta(a,[],function(c){pa(a);for(var c=ua(a,c),d=0,e=c.length;d<e;d++)O(a,c[d]);T(a,b);D(a,false)})}};o("ajax.json()",function(){var a=this.context;if(a.length>0)return a[0].json});o("ajax.params()",function(){var a=this.context;if(a.length>0)return a[0].oAjaxData});o("ajax.reload()",function(a,b){return this.iterator("table",function(c){Wb(c,b===false,a)})});o("ajax.url()",function(a){var b=
this.context;if(a===k){if(b.length===0)return k;b=b[0];return b.ajax?h.isPlainObject(b.ajax)?b.ajax.url:b.ajax:b.sAjaxSource}return this.iterator("table",function(b){h.isPlainObject(b.ajax)?b.ajax.url=a:b.ajax=a})});o("ajax.url().load()",function(a,b){return this.iterator("table",function(c){Wb(c,b===false,a)})});var bb=function(a,b,c,d,e){var f=[],g,j,h,m,l,n;h=typeof b;if(!b||h==="string"||h==="function"||b.length===k)b=[b];h=0;for(m=b.length;h<m;h++){j=b[h]&&b[h].split&&!b[h].match(/[\[\(:]/)?
b[h].split(","):[b[h]];l=0;for(n=j.length;l<n;l++)(g=c(typeof j[l]==="string"?j[l].trim():j[l]))&&g.length&&(f=f.concat(g))}a=v.selector[a];if(a.length){h=0;for(m=a.length;h<m;h++)f=a[h](d,e,f)}return ra(f)},cb=function(a){a||(a={});if(a.filter&&a.search===k)a.search=a.filter;return h.extend({search:"none",order:"current",page:"all"},a)},db=function(a){for(var b=0,c=a.length;b<c;b++)if(a[b].length>0){a[0]=a[b];a[0].length=1;a.length=1;a.context=[a.context[b]];return a}a.length=0;return a},Da=function(a,
b){var c,d,e,f=[],g=a.aiDisplay;e=a.aiDisplayMaster;var j=b.search;c=b.order;d=b.page;if(y(a)=="ssp")return j==="removed"?[]:Z(0,e.length);if(d=="current"){c=a._iDisplayStart;for(d=a.fnDisplayEnd();c<d;c++)f.push(g[c])}else if(c=="current"||c=="applied")if(j=="none")f=e.slice();else if(j=="applied")f=g.slice();else{if(j=="removed"){var i={};c=0;for(d=g.length;c<d;c++)i[g[c]]=null;f=h.map(e,function(a){return!i.hasOwnProperty(a)?a:null})}}else if(c=="index"||c=="original"){c=0;for(d=a.aoData.length;c<
d;c++)if(j=="none")f.push(c);else{e=h.inArray(c,g);(e===-1&&j=="removed"||e>=0&&j=="applied")&&f.push(c)}}return f};o("rows()",function(a,b){if(a===k)a="";else if(h.isPlainObject(a)){b=a;a=""}var b=cb(b),c=this.iterator("table",function(c){var e=b,f;return bb("row",a,function(a){var b=Pb(a),i=c.aoData;if(b!==null&&!e)return[b];f||(f=Da(c,e));if(b!==null&&h.inArray(b,f)!==-1)return[b];if(a===null||a===k||a==="")return f;if(typeof a==="function")return h.map(f,function(b){var c=i[b];return a(b,c._aData,
c.nTr)?b:null});if(a.nodeName){var b=a._DT_RowIndex,m=a._DT_CellIndex;if(b!==k)return i[b]&&i[b].nTr===a?[b]:[];if(m)return i[m.row]&&i[m.row].nTr===a.parentNode?[m.row]:[];b=h(a).closest("*[data-dt-row]");return b.length?[b.data("dt-row")]:[]}if(typeof a==="string"&&a.charAt(0)==="#"){b=c.aIds[a.replace(/^#/,"")];if(b!==k)return[b.idx]}b=Sb(ka(c.aoData,f,"nTr"));return h(b).filter(a).map(function(){return this._DT_RowIndex}).toArray()},c,e)},1);c.selector.rows=a;c.selector.opts=b;return c});o("rows().nodes()",
function(){return this.iterator("row",function(a,b){return a.aoData[b].nTr||k},1)});o("rows().data()",function(){return this.iterator(true,"rows",function(a,b){return ka(a.aoData,b,"_aData")},1)});s("rows().cache()","row().cache()",function(a){return this.iterator("row",function(b,c){var d=b.aoData[c];return a==="search"?d._aFilterData:d._aSortData},1)});s("rows().invalidate()","row().invalidate()",function(a){return this.iterator("row",function(b,c){ea(b,c,a)})});s("rows().indexes()","row().index()",
function(){return this.iterator("row",function(a,b){return b},1)});s("rows().ids()","row().id()",function(a){for(var b=[],c=this.context,d=0,e=c.length;d<e;d++)for(var f=0,g=this[d].length;f<g;f++){var h=c[d].rowIdFn(c[d].aoData[this[d][f]]._aData);b.push((a===true?"#":"")+h)}return new r(c,b)});s("rows().remove()","row().remove()",function(){var a=this;this.iterator("row",function(b,c,d){var e=b.aoData,f=e[c],g,h,i,m,l;e.splice(c,1);g=0;for(h=e.length;g<h;g++){i=e[g];l=i.anCells;if(i.nTr!==null)i.nTr._DT_RowIndex=
g;if(l!==null){i=0;for(m=l.length;i<m;i++)l[i]._DT_CellIndex.row=g}}qa(b.aiDisplayMaster,c);qa(b.aiDisplay,c);qa(a[d],c,false);b._iRecordsDisplay>0&&b._iRecordsDisplay--;Ua(b);c=b.rowIdFn(f._aData);c!==k&&delete b.aIds[c]});this.iterator("table",function(a){for(var c=0,d=a.aoData.length;c<d;c++)a.aoData[c].idx=c});return this});o("rows.add()",function(a){var b=this.iterator("table",function(b){var c,f,g,h=[];f=0;for(g=a.length;f<g;f++){c=a[f];c.nodeName&&c.nodeName.toUpperCase()==="TR"?h.push(oa(b,
c)[0]):h.push(O(b,c))}return h},1),c=this.rows(-1);c.pop();h.merge(c,b);return c});o("row()",function(a,b){return db(this.rows(a,b))});o("row().data()",function(a){var b=this.context;if(a===k)return b.length&&this.length?b[0].aoData[this[0]]._aData:k;var c=b[0].aoData[this[0]];c._aData=a;Array.isArray(a)&&(c.nTr&&c.nTr.id)&&N(b[0].rowId)(a,c.nTr.id);ea(b[0],this[0],"data");return this});o("row().node()",function(){var a=this.context;return a.length&&this.length?a[0].aoData[this[0]].nTr||null:null});
o("row.add()",function(a){a instanceof h&&a.length&&(a=a[0]);var b=this.iterator("table",function(b){return a.nodeName&&a.nodeName.toUpperCase()==="TR"?oa(b,a)[0]:O(b,a)});return this.row(b[0])});var eb=function(a,b){var c=a.context;if(c.length)if((c=c[0].aoData[b!==k?b:a[0]])&&c._details){c._details.remove();c._detailsShow=k;c._details=k}},Xb=function(a,b){var c=a.context;if(c.length&&a.length){var d=c[0].aoData[a[0]];if(d._details){(d._detailsShow=b)?d._details.insertAfter(d.nTr):d._details.detach();
var e=c[0],f=new r(e),g=e.aoData;f.off("draw.dt.DT_details column-visibility.dt.DT_details destroy.dt.DT_details");if(C(g,"_details").length>0){f.on("draw.dt.DT_details",function(a,b){e===b&&f.rows({page:"current"}).eq(0).each(function(a){a=g[a];a._detailsShow&&a._details.insertAfter(a.nTr)})});f.on("column-visibility.dt.DT_details",function(a,b){if(e===b)for(var c,d=W(b),f=0,h=g.length;f<h;f++){c=g[f];c._details&&c._details.children("td[colspan]").attr("colspan",d)}});f.on("destroy.dt.DT_details",
function(a,b){if(e===b)for(var c=0,d=g.length;c<d;c++)g[c]._details&&eb(f,c)})}}}};o("row().child()",function(a,b){var c=this.context;if(a===k)return c.length&&this.length?c[0].aoData[this[0]]._details:k;if(a===true)this.child.show();else if(a===false)eb(this);else if(c.length&&this.length){var d=c[0],c=c[0].aoData[this[0]],e=[],f=function(a,b){if(Array.isArray(a)||a instanceof h)for(var c=0,k=a.length;c<k;c++)f(a[c],b);else if(a.nodeName&&a.nodeName.toLowerCase()==="tr")e.push(a);else{c=h("<tr><td></td></tr>").addClass(b);
h("td",c).addClass(b).html(a)[0].colSpan=W(d);e.push(c[0])}};f(a,b);c._details&&c._details.detach();c._details=h(e);c._detailsShow&&c._details.insertAfter(c.nTr)}return this});o(["row().child.show()","row().child().show()"],function(){Xb(this,true);return this});o(["row().child.hide()","row().child().hide()"],function(){Xb(this,false);return this});o(["row().child.remove()","row().child().remove()"],function(){eb(this);return this});o("row().child.isShown()",function(){var a=this.context;return a.length&&
this.length?a[0].aoData[this[0]]._detailsShow||false:false});var ec=/^([^:]+):(name|visIdx|visible)$/,Yb=function(a,b,c,d,e){for(var c=[],d=0,f=e.length;d<f;d++)c.push(B(a,e[d],b));return c};o("columns()",function(a,b){if(a===k)a="";else if(h.isPlainObject(a)){b=a;a=""}var b=cb(b),c=this.iterator("table",function(c){var e=a,f=b,g=c.aoColumns,j=C(g,"sName"),i=C(g,"nTh");return bb("column",e,function(a){var b=Pb(a);if(a==="")return Z(g.length);if(b!==null)return[b>=0?b:g.length+b];if(typeof a==="function"){var e=
Da(c,f);return h.map(g,function(b,f){return a(f,Yb(c,f,0,0,e),i[f])?f:null})}var k=typeof a==="string"?a.match(ec):"";if(k)switch(k[2]){case "visIdx":case "visible":b=parseInt(k[1],10);if(b<0){var n=h.map(g,function(a,b){return a.bVisible?b:null});return[n[n.length+b]]}return[ba(c,b)];case "name":return h.map(j,function(a,b){return a===k[1]?b:null});default:return[]}if(a.nodeName&&a._DT_CellIndex)return[a._DT_CellIndex.column];b=h(i).filter(a).map(function(){return h.inArray(this,i)}).toArray();if(b.length||
!a.nodeName)return b;b=h(a).closest("*[data-dt-column]");return b.length?[b.data("dt-column")]:[]},c,f)},1);c.selector.cols=a;c.selector.opts=b;return c});s("columns().header()","column().header()",function(){return this.iterator("column",function(a,b){return a.aoColumns[b].nTh},1)});s("columns().footer()","column().footer()",function(){return this.iterator("column",function(a,b){return a.aoColumns[b].nTf},1)});s("columns().data()","column().data()",function(){return this.iterator("column-rows",Yb,
1)});s("columns().dataSrc()","column().dataSrc()",function(){return this.iterator("column",function(a,b){return a.aoColumns[b].mData},1)});s("columns().cache()","column().cache()",function(a){return this.iterator("column-rows",function(b,c,d,e,f){return ka(b.aoData,f,a==="search"?"_aFilterData":"_aSortData",c)},1)});s("columns().nodes()","column().nodes()",function(){return this.iterator("column-rows",function(a,b,c,d,e){return ka(a.aoData,e,"anCells",b)},1)});s("columns().visible()","column().visible()",
function(a,b){var c=this,d=this.iterator("column",function(b,c){if(a===k)return b.aoColumns[c].bVisible;var d=b.aoColumns,j=d[c],i=b.aoData,m,l,n;if(a!==k&&j.bVisible!==a){if(a){var o=h.inArray(true,C(d,"bVisible"),c+1);m=0;for(l=i.length;m<l;m++){n=i[m].nTr;d=i[m].anCells;n&&n.insertBefore(d[c],d[o]||null)}}else h(C(b.aoData,"anCells",c)).detach();j.bVisible=a}});a!==k&&this.iterator("table",function(d){ga(d,d.aoHeader);ga(d,d.aoFooter);d.aiDisplay.length||h(d.nTBody).find("td[colspan]").attr("colspan",
W(d));za(d);c.iterator("column",function(c,d){t(c,null,"column-visibility",[c,d,a,b])});(b===k||b)&&c.columns.adjust()});return d});s("columns().indexes()","column().index()",function(a){return this.iterator("column",function(b,c){return a==="visible"?ca(b,c):c},1)});o("columns.adjust()",function(){return this.iterator("table",function(a){aa(a)},1)});o("column.index()",function(a,b){if(this.context.length!==0){var c=this.context[0];if(a==="fromVisible"||a==="toData")return ba(c,b);if(a==="fromData"||
a==="toVisible")return ca(c,b)}});o("column()",function(a,b){return db(this.columns(a,b))});o("cells()",function(a,b,c){if(h.isPlainObject(a))if(a.row===k){c=a;a=null}else{c=b;b=null}if(h.isPlainObject(b)){c=b;b=null}if(b===null||b===k)return this.iterator("table",function(b){var d=a,e=cb(c),f=b.aoData,g=Da(b,e),j=Sb(ka(f,g,"anCells")),i=h(Tb([],j)),m,n=b.aoColumns.length,o,s,r,t,w,v;return bb("cell",d,function(a){var c=typeof a==="function";if(a===null||a===k||c){o=[];s=0;for(r=g.length;s<r;s++){m=
g[s];for(t=0;t<n;t++){w={row:m,column:t};if(c){v=f[m];a(w,B(b,m,t),v.anCells?v.anCells[t]:null)&&o.push(w)}else o.push(w)}}return o}if(h.isPlainObject(a))return a.column!==k&&a.row!==k&&h.inArray(a.row,g)!==-1?[a]:[];c=i.filter(a).map(function(a,b){return{row:b._DT_CellIndex.row,column:b._DT_CellIndex.column}}).toArray();if(c.length||!a.nodeName)return c;v=h(a).closest("*[data-dt-row]");return v.length?[{row:v.data("dt-row"),column:v.data("dt-column")}]:[]},b,e)});var d=c?{page:c.page,order:c.order,
search:c.search}:{},e=this.columns(b,d),f=this.rows(a,d),g,j,i,m,d=this.iterator("table",function(a,b){var c=[];g=0;for(j=f[b].length;g<j;g++){i=0;for(m=e[b].length;i<m;i++)c.push({row:f[b][g],column:e[b][i]})}return c},1),d=c&&c.selected?this.cells(d,c):d;h.extend(d.selector,{cols:b,rows:a,opts:c});return d});s("cells().nodes()","cell().node()",function(){return this.iterator("cell",function(a,b,c){return(a=a.aoData[b])&&a.anCells?a.anCells[c]:k},1)});o("cells().data()",function(){return this.iterator("cell",
function(a,b,c){return B(a,b,c)},1)});s("cells().cache()","cell().cache()",function(a){a=a==="search"?"_aFilterData":"_aSortData";return this.iterator("cell",function(b,c,d){return b.aoData[c][a][d]},1)});s("cells().render()","cell().render()",function(a){return this.iterator("cell",function(b,c,d){return B(b,c,d,a)},1)});s("cells().indexes()","cell().index()",function(){return this.iterator("cell",function(a,b,c){return{row:b,column:c,columnVisible:ca(a,c)}},1)});s("cells().invalidate()","cell().invalidate()",
function(a){return this.iterator("cell",function(b,c,d){ea(b,c,a,d)})});o("cell()",function(a,b,c){return db(this.cells(a,b,c))});o("cell().data()",function(a){var b=this.context,c=this[0];if(a===k)return b.length&&c.length?B(b[0],c[0].row,c[0].column):k;lb(b[0],c[0].row,c[0].column,a);ea(b[0],c[0].row,"data",c[0].column);return this});o("order()",function(a,b){var c=this.context;if(a===k)return c.length!==0?c[0].aaSorting:k;typeof a==="number"?a=[[a,b]]:a.length&&!Array.isArray(a[0])&&(a=Array.prototype.slice.call(arguments));
return this.iterator("table",function(b){b.aaSorting=a.slice()})});o("order.listener()",function(a,b,c){return this.iterator("table",function(d){Oa(d,a,b,c)})});o("order.fixed()",function(a){if(!a){var b=this.context,b=b.length?b[0].aaSortingFixed:k;return Array.isArray(b)?{pre:b}:b}return this.iterator("table",function(b){b.aaSortingFixed=h.extend(true,{},a)})});o(["columns().order()","column().order()"],function(a){var b=this;return this.iterator("table",function(c,d){var e=[];h.each(b[d],function(b,
c){e.push([c,a])});c.aaSorting=e})});o("search()",function(a,b,c,d){var e=this.context;return a===k?e.length!==0?e[0].oPreviousSearch.sSearch:k:this.iterator("table",function(e){e.oFeatures.bFilter&&ha(e,h.extend({},e.oPreviousSearch,{sSearch:a+"",bRegex:b===null?false:b,bSmart:c===null?true:c,bCaseInsensitive:d===null?true:d}),1)})});s("columns().search()","column().search()",function(a,b,c,d){return this.iterator("column",function(e,f){var g=e.aoPreSearchCols;if(a===k)return g[f].sSearch;if(e.oFeatures.bFilter){h.extend(g[f],
{sSearch:a+"",bRegex:b===null?false:b,bSmart:c===null?true:c,bCaseInsensitive:d===null?true:d});ha(e,e.oPreviousSearch,1)}})});o("state()",function(){return this.context.length?this.context[0].oSavedState:null});o("state.clear()",function(){return this.iterator("table",function(a){a.fnStateSaveCallback.call(a.oInstance,a,{})})});o("state.loaded()",function(){return this.context.length?this.context[0].oLoadedState:null});o("state.save()",function(){return this.iterator("table",function(a){za(a)})});
n.versionCheck=n.fnVersionCheck=function(a){for(var b=n.version.split("."),a=a.split("."),c,d,e=0,f=a.length;e<f;e++){c=parseInt(b[e],10)||0;d=parseInt(a[e],10)||0;if(c!==d)return c>d}return true};n.isDataTable=n.fnIsDataTable=function(a){var b=h(a).get(0),c=false;if(a instanceof n.Api)return true;h.each(n.settings,function(a,e){var f=e.nScrollHead?h("table",e.nScrollHead)[0]:null,g=e.nScrollFoot?h("table",e.nScrollFoot)[0]:null;if(e.nTable===b||f===b||g===b)c=true});return c};n.tables=n.fnTables=
function(a){var b=false;if(h.isPlainObject(a)){b=a.api;a=a.visible}var c=h.map(n.settings,function(b){if(!a||a&&h(b.nTable).is(":visible"))return b.nTable});return b?new r(c):c};n.camelToHungarian=J;o("$()",function(a,b){var c=this.rows(b).nodes(),c=h(c);return h([].concat(c.filter(a).toArray(),c.find(a).toArray()))});h.each(["on","one","off"],function(a,b){o(b+"()",function(){var a=Array.prototype.slice.call(arguments);a[0]=h.map(a[0].split(/\s/),function(a){return!a.match(/\.dt\b/)?a+".dt":a}).join(" ");
var d=h(this.tables().nodes());d[b].apply(d,a);return this})});o("clear()",function(){return this.iterator("table",function(a){pa(a)})});o("settings()",function(){return new r(this.context,this.context)});o("init()",function(){var a=this.context;return a.length?a[0].oInit:null});o("data()",function(){return this.iterator("table",function(a){return C(a.aoData,"_aData")}).flatten()});o("destroy()",function(a){a=a||false;return this.iterator("table",function(b){var c=b.nTableWrapper.parentNode,d=b.oClasses,
e=b.nTable,f=b.nTBody,g=b.nTHead,j=b.nTFoot,i=h(e),f=h(f),k=h(b.nTableWrapper),l=h.map(b.aoData,function(a){return a.nTr}),o;b.bDestroying=true;t(b,"aoDestroyCallback","destroy",[b]);a||(new r(b)).columns().visible(true);k.off(".DT").find(":not(tbody *)").off(".DT");h(E).off(".DT-"+b.sInstance);if(e!=g.parentNode){i.children("thead").detach();i.append(g)}if(j&&e!=j.parentNode){i.children("tfoot").detach();i.append(j)}b.aaSorting=[];b.aaSortingFixed=[];ya(b);h(l).removeClass(b.asStripeClasses.join(" "));
h("th, td",g).removeClass(d.sSortable+" "+d.sSortableAsc+" "+d.sSortableDesc+" "+d.sSortableNone);f.children().detach();f.append(l);g=a?"remove":"detach";i[g]();k[g]();if(!a&&c){c.insertBefore(e,b.nTableReinsertBefore);i.css("width",b.sDestroyWidth).removeClass(d.sTable);(o=b.asDestroyStripes.length)&&f.children().each(function(a){h(this).addClass(b.asDestroyStripes[a%o])})}c=h.inArray(b,n.settings);c!==-1&&n.settings.splice(c,1)})});h.each(["column","row","cell"],function(a,b){o(b+"s().every()",
function(a){var d=this.selector.opts,e=this;return this.iterator(b,function(f,g,h,i,m){a.call(e[b](g,b==="cell"?h:d,b==="cell"?d:k),g,h,i,m)})})});o("i18n()",function(a,b,c){var d=this.context[0],a=S(a)(d.oLanguage);a===k&&(a=b);c!==k&&h.isPlainObject(a)&&(a=a[c]!==k?a[c]:a._);return a.replace("%d",c)});n.version="1.10.22";n.settings=[];n.models={};n.models.oSearch={bCaseInsensitive:!0,sSearch:"",bRegex:!1,bSmart:!0};n.models.oRow={nTr:null,anCells:null,_aData:[],_aSortData:null,_aFilterData:null,
_sFilterRow:null,_sRowStripe:"",src:null,idx:-1};n.models.oColumn={idx:null,aDataSort:null,asSorting:null,bSearchable:null,bSortable:null,bVisible:null,_sManualType:null,_bAttrSrc:!1,fnCreatedCell:null,fnGetData:null,fnSetData:null,mData:null,mRender:null,nTh:null,nTf:null,sClass:null,sContentPadding:null,sDefaultContent:null,sName:null,sSortDataType:"std",sSortingClass:null,sSortingClassJUI:null,sTitle:null,sType:null,sWidth:null,sWidthOrig:null};n.defaults={aaData:null,aaSorting:[[0,"asc"]],aaSortingFixed:[],
ajax:null,aLengthMenu:[10,25,50,100],aoColumns:null,aoColumnDefs:null,aoSearchCols:[],asStripeClasses:null,bAutoWidth:!0,bDeferRender:!1,bDestroy:!1,bFilter:!0,bInfo:!0,bLengthChange:!0,bPaginate:!0,bProcessing:!1,bRetrieve:!1,bScrollCollapse:!1,bServerSide:!1,bSort:!0,bSortMulti:!0,bSortCellsTop:!1,bSortClasses:!0,bStateSave:!1,fnCreatedRow:null,fnDrawCallback:null,fnFooterCallback:null,fnFormatNumber:function(a){return a.toString().replace(/\B(?=(\d{3})+(?!\d))/g,this.oLanguage.sThousands)},fnHeaderCallback:null,
fnInfoCallback:null,fnInitComplete:null,fnPreDrawCallback:null,fnRowCallback:null,fnServerData:null,fnServerParams:null,fnStateLoadCallback:function(a){try{return JSON.parse((a.iStateDuration===-1?sessionStorage:localStorage).getItem("DataTables_"+a.sInstance+"_"+location.pathname))}catch(b){return{}}},fnStateLoadParams:null,fnStateLoaded:null,fnStateSaveCallback:function(a,b){try{(a.iStateDuration===-1?sessionStorage:localStorage).setItem("DataTables_"+a.sInstance+"_"+location.pathname,JSON.stringify(b))}catch(c){}},
fnStateSaveParams:null,iStateDuration:7200,iDeferLoading:null,iDisplayLength:10,iDisplayStart:0,iTabIndex:0,oClasses:{},oLanguage:{oAria:{sSortAscending:": activate to sort column ascending",sSortDescending:": activate to sort column descending"},oPaginate:{sFirst:"First",sLast:"Last",sNext:"Next",sPrevious:"Previous"},sEmptyTable:"No data available in table",sInfo:"Showing _START_ to _END_ of _TOTAL_ entries",sInfoEmpty:"Showing 0 to 0 of 0 entries",sInfoFiltered:"(filtered from _MAX_ total entries)",
sInfoPostFix:"",sDecimal:"",sThousands:",",sLengthMenu:"Show _MENU_ entries",sLoadingRecords:"Loading...",sProcessing:"Processing...",sSearch:"Search:",sSearchPlaceholder:"",sUrl:"",sZeroRecords:"No matching records found"},oSearch:h.extend({},n.models.oSearch),sAjaxDataProp:"data",sAjaxSource:null,sDom:"lfrtip",searchDelay:null,sPaginationType:"simple_numbers",sScrollX:"",sScrollXInner:"",sScrollY:"",sServerMethod:"GET",renderer:null,rowId:"DT_RowId"};$(n.defaults);n.defaults.column={aDataSort:null,
iDataSort:-1,asSorting:["asc","desc"],bSearchable:!0,bSortable:!0,bVisible:!0,fnCreatedCell:null,mData:null,mRender:null,sCellType:"td",sClass:"",sContentPadding:"",sDefaultContent:null,sName:"",sSortDataType:"std",sTitle:null,sType:null,sWidth:null};$(n.defaults.column);n.models.oSettings={oFeatures:{bAutoWidth:null,bDeferRender:null,bFilter:null,bInfo:null,bLengthChange:null,bPaginate:null,bProcessing:null,bServerSide:null,bSort:null,bSortMulti:null,bSortClasses:null,bStateSave:null},oScroll:{bCollapse:null,
iBarWidth:0,sX:null,sXInner:null,sY:null},oLanguage:{fnInfoCallback:null},oBrowser:{bScrollOversize:!1,bScrollbarLeft:!1,bBounding:!1,barWidth:0},ajax:null,aanFeatures:[],aoData:[],aiDisplay:[],aiDisplayMaster:[],aIds:{},aoColumns:[],aoHeader:[],aoFooter:[],oPreviousSearch:{},aoPreSearchCols:[],aaSorting:null,aaSortingFixed:[],asStripeClasses:null,asDestroyStripes:[],sDestroyWidth:0,aoRowCallback:[],aoHeaderCallback:[],aoFooterCallback:[],aoDrawCallback:[],aoRowCreatedCallback:[],aoPreDrawCallback:[],
aoInitComplete:[],aoStateSaveParams:[],aoStateLoadParams:[],aoStateLoaded:[],sTableId:"",nTable:null,nTHead:null,nTFoot:null,nTBody:null,nTableWrapper:null,bDeferLoading:!1,bInitialised:!1,aoOpenRows:[],sDom:null,searchDelay:null,sPaginationType:"two_button",iStateDuration:0,aoStateSave:[],aoStateLoad:[],oSavedState:null,oLoadedState:null,sAjaxSource:null,sAjaxDataProp:null,bAjaxDataGet:!0,jqXHR:null,json:k,oAjaxData:k,fnServerData:null,aoServerParams:[],sServerMethod:null,fnFormatNumber:null,aLengthMenu:null,
iDraw:0,bDrawing:!1,iDrawError:-1,_iDisplayLength:10,_iDisplayStart:0,_iRecordsTotal:0,_iRecordsDisplay:0,oClasses:{},bFiltered:!1,bSorted:!1,bSortCellsTop:null,oInit:null,aoDestroyCallback:[],fnRecordsTotal:function(){return y(this)=="ssp"?this._iRecordsTotal*1:this.aiDisplayMaster.length},fnRecordsDisplay:function(){return y(this)=="ssp"?this._iRecordsDisplay*1:this.aiDisplay.length},fnDisplayEnd:function(){var a=this._iDisplayLength,b=this._iDisplayStart,c=b+a,d=this.aiDisplay.length,e=this.oFeatures,
f=e.bPaginate;return e.bServerSide?f===false||a===-1?b+d:Math.min(b+a,this._iRecordsDisplay):!f||c>d||a===-1?d:c},oInstance:null,sInstance:null,iTabIndex:0,nScrollHead:null,nScrollFoot:null,aLastSort:[],oPlugins:{},rowIdFn:null,rowId:null};n.ext=v={buttons:{},classes:{},builder:"-source-",errMode:"alert",feature:[],search:[],selector:{cell:[],column:[],row:[]},internal:{},legacy:{ajax:null},pager:{},renderer:{pageButton:{},header:{}},order:{},type:{detect:[],search:{},order:{}},_unique:0,fnVersionCheck:n.fnVersionCheck,
iApiIndex:0,oJUIClasses:{},sVersion:n.version};h.extend(v,{afnFiltering:v.search,aTypes:v.type.detect,ofnSearch:v.type.search,oSort:v.type.order,afnSortData:v.order,aoFeatures:v.feature,oApi:v.internal,oStdClasses:v.classes,oPagination:v.pager});h.extend(n.ext.classes,{sTable:"dataTable",sNoFooter:"no-footer",sPageButton:"paginate_button",sPageButtonActive:"current",sPageButtonDisabled:"disabled",sStripeOdd:"odd",sStripeEven:"even",sRowEmpty:"dataTables_empty",sWrapper:"dataTables_wrapper",sFilter:"dataTables_filter",
sInfo:"dataTables_info",sPaging:"dataTables_paginate paging_",sLength:"dataTables_length",sProcessing:"dataTables_processing",sSortAsc:"sorting_asc",sSortDesc:"sorting_desc",sSortable:"sorting",sSortableAsc:"sorting_asc_disabled",sSortableDesc:"sorting_desc_disabled",sSortableNone:"sorting_disabled",sSortColumn:"sorting_",sFilterInput:"",sLengthSelect:"",sScrollWrapper:"dataTables_scroll",sScrollHead:"dataTables_scrollHead",sScrollHeadInner:"dataTables_scrollHeadInner",sScrollBody:"dataTables_scrollBody",
sScrollFoot:"dataTables_scrollFoot",sScrollFootInner:"dataTables_scrollFootInner",sHeaderTH:"",sFooterTH:"",sSortJUIAsc:"",sSortJUIDesc:"",sSortJUI:"",sSortJUIAscAllowed:"",sSortJUIDescAllowed:"",sSortJUIWrapper:"",sSortIcon:"",sJUIHeader:"",sJUIFooter:""});var Mb=n.ext.pager;h.extend(Mb,{simple:function(){return["previous","next"]},full:function(){return["first","previous","next","last"]},numbers:function(a,b){return[ja(a,b)]},simple_numbers:function(a,b){return["previous",ja(a,b),"next"]},full_numbers:function(a,
b){return["first","previous",ja(a,b),"next","last"]},first_last_numbers:function(a,b){return["first",ja(a,b),"last"]},_numbers:ja,numbers_length:7});h.extend(!0,n.ext.renderer,{pageButton:{_:function(a,b,c,d,e,f){var g=a.oClasses,j=a.oLanguage.oPaginate,i=a.oLanguage.oAria.paginate||{},m,l,n=0,o=function(b,d){var k,s,r,t,v=g.sPageButtonDisabled,w=function(b){Va(a,b.data.action,true)};k=0;for(s=d.length;k<s;k++){t=d[k];if(Array.isArray(t)){r=h("<"+(t.DT_el||"div")+"/>").appendTo(b);o(r,t)}else{m=null;
l=t;r=a.iTabIndex;switch(t){case "ellipsis":b.append('<span class="ellipsis">&#x2026;</span>');break;case "first":m=j.sFirst;if(e===0){r=-1;l=l+(" "+v)}break;case "previous":m=j.sPrevious;if(e===0){r=-1;l=l+(" "+v)}break;case "next":m=j.sNext;if(f===0||e===f-1){r=-1;l=l+(" "+v)}break;case "last":m=j.sLast;if(f===0||e===f-1){r=-1;l=l+(" "+v)}break;default:m=a.fnFormatNumber(t+1);l=e===t?g.sPageButtonActive:""}if(m!==null){r=h("<a>",{"class":g.sPageButton+" "+l,"aria-controls":a.sTableId,"aria-label":i[t],
"data-dt-idx":n,tabindex:r,id:c===0&&typeof t==="string"?a.sTableId+"_"+t:null}).html(m).appendTo(b);Xa(r,{action:t},w);n++}}}},s;try{s=h(b).find(H.activeElement).data("dt-idx")}catch(r){}o(h(b).empty(),d);s!==k&&h(b).find("[data-dt-idx="+s+"]").trigger("focus")}}});h.extend(n.ext.type.detect,[function(a,b){var c=b.oLanguage.sDecimal;return ab(a,c)?"num"+c:null},function(a){if(a&&!(a instanceof Date)&&!bc.test(a))return null;var b=Date.parse(a);return b!==null&&!isNaN(b)||M(a)?"date":null},function(a,
b){var c=b.oLanguage.sDecimal;return ab(a,c,true)?"num-fmt"+c:null},function(a,b){var c=b.oLanguage.sDecimal;return Rb(a,c)?"html-num"+c:null},function(a,b){var c=b.oLanguage.sDecimal;return Rb(a,c,true)?"html-num-fmt"+c:null},function(a){return M(a)||typeof a==="string"&&a.indexOf("<")!==-1?"html":null}]);h.extend(n.ext.type.search,{html:function(a){return M(a)?a:typeof a==="string"?a.replace(Ob," ").replace(Ca,""):""},string:function(a){return M(a)?a:typeof a==="string"?a.replace(Ob," "):a}});var Ba=
function(a,b,c,d){if(a!==0&&(!a||a==="-"))return-Infinity;b&&(a=Qb(a,b));if(a.replace){c&&(a=a.replace(c,""));d&&(a=a.replace(d,""))}return a*1};h.extend(v.type.order,{"date-pre":function(a){a=Date.parse(a);return isNaN(a)?-Infinity:a},"html-pre":function(a){return M(a)?"":a.replace?a.replace(/<.*?>/g,"").toLowerCase():a+""},"string-pre":function(a){return M(a)?"":typeof a==="string"?a.toLowerCase():!a.toString?"":a.toString()},"string-asc":function(a,b){return a<b?-1:a>b?1:0},"string-desc":function(a,
b){return a<b?1:a>b?-1:0}});Fa("");h.extend(!0,n.ext.renderer,{header:{_:function(a,b,c,d){h(a.nTable).on("order.dt.DT",function(e,f,g,h){if(a===f){e=c.idx;b.removeClass(c.sSortingClass+" "+d.sSortAsc+" "+d.sSortDesc).addClass(h[e]=="asc"?d.sSortAsc:h[e]=="desc"?d.sSortDesc:c.sSortingClass)}})},jqueryui:function(a,b,c,d){h("<div/>").addClass(d.sSortJUIWrapper).append(b.contents()).append(h("<span/>").addClass(d.sSortIcon+" "+c.sSortingClassJUI)).appendTo(b);h(a.nTable).on("order.dt.DT",function(e,
f,g,h){if(a===f){e=c.idx;b.removeClass(d.sSortAsc+" "+d.sSortDesc).addClass(h[e]=="asc"?d.sSortAsc:h[e]=="desc"?d.sSortDesc:c.sSortingClass);b.find("span."+d.sSortIcon).removeClass(d.sSortJUIAsc+" "+d.sSortJUIDesc+" "+d.sSortJUI+" "+d.sSortJUIAscAllowed+" "+d.sSortJUIDescAllowed).addClass(h[e]=="asc"?d.sSortJUIAsc:h[e]=="desc"?d.sSortJUIDesc:c.sSortingClassJUI)}})}}});var fb=function(a){return typeof a==="string"?a.replace(/&/g,"&amp;").replace(/</g,"&lt;").replace(/>/g,"&gt;").replace(/"/g,"&quot;"):
a};n.render={number:function(a,b,c,d,e){return{display:function(f){if(typeof f!=="number"&&typeof f!=="string")return f;var g=f<0?"-":"",h=parseFloat(f);if(isNaN(h))return fb(f);h=h.toFixed(c);f=Math.abs(h);h=parseInt(f,10);f=c?b+(f-h).toFixed(c).substring(2):"";return g+(d||"")+h.toString().replace(/\B(?=(\d{3})+(?!\d))/g,a)+f+(e||"")}}},text:function(){return{display:fb,filter:fb}}};h.extend(n.ext.internal,{_fnExternApiFunc:Nb,_fnBuildAjax:ta,_fnAjaxUpdate:nb,_fnAjaxParameters:wb,_fnAjaxUpdateDraw:xb,
_fnAjaxDataSrc:ua,_fnAddColumn:Ga,_fnColumnOptions:la,_fnAdjustColumnSizing:aa,_fnVisibleToColumnIndex:ba,_fnColumnIndexToVisible:ca,_fnVisbleColumns:W,_fnGetColumns:na,_fnColumnTypes:Ia,_fnApplyColumnDefs:kb,_fnHungarianMap:$,_fnCamelToHungarian:J,_fnLanguageCompat:Ea,_fnBrowserDetect:ib,_fnAddData:O,_fnAddTr:oa,_fnNodeToDataIndex:function(a,b){return b._DT_RowIndex!==k?b._DT_RowIndex:null},_fnNodeToColumnIndex:function(a,b,c){return h.inArray(c,a.aoData[b].anCells)},_fnGetCellData:B,_fnSetCellData:lb,
_fnSplitObjNotation:La,_fnGetObjectDataFn:S,_fnSetObjectDataFn:N,_fnGetDataMaster:Ma,_fnClearTable:pa,_fnDeleteIndex:qa,_fnInvalidate:ea,_fnGetRowElements:Ka,_fnCreateTr:Ja,_fnBuildHead:mb,_fnDrawHead:ga,_fnDraw:P,_fnReDraw:T,_fnAddOptionsHtml:pb,_fnDetectHeader:fa,_fnGetUniqueThs:sa,_fnFeatureHtmlFilter:rb,_fnFilterComplete:ha,_fnFilterCustom:Ab,_fnFilterColumn:zb,_fnFilter:yb,_fnFilterCreateSearch:Ra,_fnEscapeRegex:Sa,_fnFilterData:Bb,_fnFeatureHtmlInfo:ub,_fnUpdateInfo:Eb,_fnInfoMacros:Fb,_fnInitialise:ia,
_fnInitComplete:va,_fnLengthChange:Ta,_fnFeatureHtmlLength:qb,_fnFeatureHtmlPaginate:vb,_fnPageChange:Va,_fnFeatureHtmlProcessing:sb,_fnProcessingDisplay:D,_fnFeatureHtmlTable:tb,_fnScrollDraw:ma,_fnApplyToChildren:I,_fnCalculateColumnWidths:Ha,_fnThrottle:Qa,_fnConvertToWidth:Gb,_fnGetWidestNode:Hb,_fnGetMaxLenString:Ib,_fnStringToCss:w,_fnSortFlatten:Y,_fnSort:ob,_fnSortAria:Kb,_fnSortListener:Wa,_fnSortAttachListener:Oa,_fnSortingClasses:ya,_fnSortData:Jb,_fnSaveState:za,_fnLoadState:Lb,_fnSettingsFromNode:Aa,
_fnLog:K,_fnMap:F,_fnBindAction:Xa,_fnCallbackReg:z,_fnCallbackFire:t,_fnLengthOverflow:Ua,_fnRenderer:Pa,_fnDataSource:y,_fnRowAttributes:Na,_fnExtend:Ya,_fnCalculateEnd:function(){}});h.fn.dataTable=n;n.$=h;h.fn.dataTableSettings=n.settings;h.fn.dataTableExt=n.ext;h.fn.DataTable=function(a){return h(this).dataTable(a).api()};h.each(n,function(a,b){h.fn.DataTable[a]=b});return h.fn.dataTable});

View file

@ -1,59 +0,0 @@
/*
* Easing Compatibility v1 - http://gsgd.co.uk/sandbox/jquery/easing
*
* Adds compatibility for applications that use the pre 1.2 easing names
*
* Copyright (c) 2007 George Smith
* Licensed under the MIT License:
* http://www.opensource.org/licenses/mit-license.php
*/
(function($){
$.extend( $.easing,
{
easeIn: function (x, t, b, c, d) {
return $.easing.easeInQuad(x, t, b, c, d);
},
easeOut: function (x, t, b, c, d) {
return $.easing.easeOutQuad(x, t, b, c, d);
},
easeInOut: function (x, t, b, c, d) {
return $.easing.easeInOutQuad(x, t, b, c, d);
},
expoin: function(x, t, b, c, d) {
return $.easing.easeInExpo(x, t, b, c, d);
},
expoout: function(x, t, b, c, d) {
return $.easing.easeOutExpo(x, t, b, c, d);
},
expoinout: function(x, t, b, c, d) {
return $.easing.easeInOutExpo(x, t, b, c, d);
},
bouncein: function(x, t, b, c, d) {
return $.easing.easeInBounce(x, t, b, c, d);
},
bounceout: function(x, t, b, c, d) {
return $.easing.easeOutBounce(x, t, b, c, d);
},
bounceinout: function(x, t, b, c, d) {
return $.easing.easeInOutBounce(x, t, b, c, d);
},
elasin: function(x, t, b, c, d) {
return $.easing.easeInElastic(x, t, b, c, d);
},
elasout: function(x, t, b, c, d) {
return $.easing.easeOutElastic(x, t, b, c, d);
},
elasinout: function(x, t, b, c, d) {
return $.easing.easeInOutElastic(x, t, b, c, d);
},
backin: function(x, t, b, c, d) {
return $.easing.easeInBack(x, t, b, c, d);
},
backout: function(x, t, b, c, d) {
return $.easing.easeOutBack(x, t, b, c, d);
},
backinout: function(x, t, b, c, d) {
return $.easing.easeInOutBack(x, t, b, c, d);
}
});})(jQuery);

View file

@ -1,166 +0,0 @@
/*
* jQuery Easing v1.4.1 - http://gsgd.co.uk/sandbox/jquery/easing/
* Open source under the BSD License.
* Copyright © 2008 George McGinley Smith
* All rights reserved.
* https://raw.github.com/gdsmith/jquery-easing/master/LICENSE
*/
(function (factory) {
if (typeof define === "function" && define.amd) {
define(['jquery'], function ($) {
return factory($);
});
} else if (typeof module === "object" && typeof module.exports === "object") {
exports = factory(require('jquery'));
} else {
factory(jQuery);
}
})(function($){
// Preserve the original jQuery "swing" easing as "jswing"
$.easing.jswing = $.easing.swing;
var pow = Math.pow,
sqrt = Math.sqrt,
sin = Math.sin,
cos = Math.cos,
PI = Math.PI,
c1 = 1.70158,
c2 = c1 * 1.525,
c3 = c1 + 1,
c4 = ( 2 * PI ) / 3,
c5 = ( 2 * PI ) / 4.5;
// x is the fraction of animation progress, in the range 0..1
function bounceOut(x) {
var n1 = 7.5625,
d1 = 2.75;
if ( x < 1/d1 ) {
return n1*x*x;
} else if ( x < 2/d1 ) {
return n1*(x-=(1.5/d1))*x + 0.75;
} else if ( x < 2.5/d1 ) {
return n1*(x-=(2.25/d1))*x + 0.9375;
} else {
return n1*(x-=(2.625/d1))*x + 0.984375;
}
}
$.extend( $.easing,
{
def: 'easeOutQuad',
swing: function (x) {
return $.easing[$.easing.def](x);
},
easeInQuad: function (x) {
return x * x;
},
easeOutQuad: function (x) {
return 1 - ( 1 - x ) * ( 1 - x );
},
easeInOutQuad: function (x) {
return x < 0.5 ?
2 * x * x :
1 - pow( -2 * x + 2, 2 ) / 2;
},
easeInCubic: function (x) {
return x * x * x;
},
easeOutCubic: function (x) {
return 1 - pow( 1 - x, 3 );
},
easeInOutCubic: function (x) {
return x < 0.5 ?
4 * x * x * x :
1 - pow( -2 * x + 2, 3 ) / 2;
},
easeInQuart: function (x) {
return x * x * x * x;
},
easeOutQuart: function (x) {
return 1 - pow( 1 - x, 4 );
},
easeInOutQuart: function (x) {
return x < 0.5 ?
8 * x * x * x * x :
1 - pow( -2 * x + 2, 4 ) / 2;
},
easeInQuint: function (x) {
return x * x * x * x * x;
},
easeOutQuint: function (x) {
return 1 - pow( 1 - x, 5 );
},
easeInOutQuint: function (x) {
return x < 0.5 ?
16 * x * x * x * x * x :
1 - pow( -2 * x + 2, 5 ) / 2;
},
easeInSine: function (x) {
return 1 - cos( x * PI/2 );
},
easeOutSine: function (x) {
return sin( x * PI/2 );
},
easeInOutSine: function (x) {
return -( cos( PI * x ) - 1 ) / 2;
},
easeInExpo: function (x) {
return x === 0 ? 0 : pow( 2, 10 * x - 10 );
},
easeOutExpo: function (x) {
return x === 1 ? 1 : 1 - pow( 2, -10 * x );
},
easeInOutExpo: function (x) {
return x === 0 ? 0 : x === 1 ? 1 : x < 0.5 ?
pow( 2, 20 * x - 10 ) / 2 :
( 2 - pow( 2, -20 * x + 10 ) ) / 2;
},
easeInCirc: function (x) {
return 1 - sqrt( 1 - pow( x, 2 ) );
},
easeOutCirc: function (x) {
return sqrt( 1 - pow( x - 1, 2 ) );
},
easeInOutCirc: function (x) {
return x < 0.5 ?
( 1 - sqrt( 1 - pow( 2 * x, 2 ) ) ) / 2 :
( sqrt( 1 - pow( -2 * x + 2, 2 ) ) + 1 ) / 2;
},
easeInElastic: function (x) {
return x === 0 ? 0 : x === 1 ? 1 :
-pow( 2, 10 * x - 10 ) * sin( ( x * 10 - 10.75 ) * c4 );
},
easeOutElastic: function (x) {
return x === 0 ? 0 : x === 1 ? 1 :
pow( 2, -10 * x ) * sin( ( x * 10 - 0.75 ) * c4 ) + 1;
},
easeInOutElastic: function (x) {
return x === 0 ? 0 : x === 1 ? 1 : x < 0.5 ?
-( pow( 2, 20 * x - 10 ) * sin( ( 20 * x - 11.125 ) * c5 )) / 2 :
pow( 2, -20 * x + 10 ) * sin( ( 20 * x - 11.125 ) * c5 ) / 2 + 1;
},
easeInBack: function (x) {
return c3 * x * x * x - c1 * x * x;
},
easeOutBack: function (x) {
return 1 + c3 * pow( x - 1, 3 ) + c1 * pow( x - 1, 2 );
},
easeInOutBack: function (x) {
return x < 0.5 ?
( pow( 2 * x, 2 ) * ( ( c2 + 1 ) * 2 * x - c2 ) ) / 2 :
( pow( 2 * x - 2, 2 ) *( ( c2 + 1 ) * ( x * 2 - 2 ) + c2 ) + 2 ) / 2;
},
easeInBounce: function (x) {
return 1 - bounceOut( 1 - x );
},
easeOutBounce: bounceOut,
easeInOutBounce: function (x) {
return x < 0.5 ?
( 1 - bounceOut( 1 - 2 * x ) ) / 2 :
( 1 + bounceOut( 2 * x - 1 ) ) / 2;
}
});
});

View file

@ -1 +0,0 @@
(function(factory){if(typeof define==="function"&&define.amd){define(["jquery"],function($){return factory($)})}else if(typeof module==="object"&&typeof module.exports==="object"){exports=factory(require("jquery"))}else{factory(jQuery)}})(function($){$.easing.jswing=$.easing.swing;var pow=Math.pow,sqrt=Math.sqrt,sin=Math.sin,cos=Math.cos,PI=Math.PI,c1=1.70158,c2=c1*1.525,c3=c1+1,c4=2*PI/3,c5=2*PI/4.5;function bounceOut(x){var n1=7.5625,d1=2.75;if(x<1/d1){return n1*x*x}else if(x<2/d1){return n1*(x-=1.5/d1)*x+.75}else if(x<2.5/d1){return n1*(x-=2.25/d1)*x+.9375}else{return n1*(x-=2.625/d1)*x+.984375}}$.extend($.easing,{def:"easeOutQuad",swing:function(x){return $.easing[$.easing.def](x)},easeInQuad:function(x){return x*x},easeOutQuad:function(x){return 1-(1-x)*(1-x)},easeInOutQuad:function(x){return x<.5?2*x*x:1-pow(-2*x+2,2)/2},easeInCubic:function(x){return x*x*x},easeOutCubic:function(x){return 1-pow(1-x,3)},easeInOutCubic:function(x){return x<.5?4*x*x*x:1-pow(-2*x+2,3)/2},easeInQuart:function(x){return x*x*x*x},easeOutQuart:function(x){return 1-pow(1-x,4)},easeInOutQuart:function(x){return x<.5?8*x*x*x*x:1-pow(-2*x+2,4)/2},easeInQuint:function(x){return x*x*x*x*x},easeOutQuint:function(x){return 1-pow(1-x,5)},easeInOutQuint:function(x){return x<.5?16*x*x*x*x*x:1-pow(-2*x+2,5)/2},easeInSine:function(x){return 1-cos(x*PI/2)},easeOutSine:function(x){return sin(x*PI/2)},easeInOutSine:function(x){return-(cos(PI*x)-1)/2},easeInExpo:function(x){return x===0?0:pow(2,10*x-10)},easeOutExpo:function(x){return x===1?1:1-pow(2,-10*x)},easeInOutExpo:function(x){return x===0?0:x===1?1:x<.5?pow(2,20*x-10)/2:(2-pow(2,-20*x+10))/2},easeInCirc:function(x){return 1-sqrt(1-pow(x,2))},easeOutCirc:function(x){return sqrt(1-pow(x-1,2))},easeInOutCirc:function(x){return x<.5?(1-sqrt(1-pow(2*x,2)))/2:(sqrt(1-pow(-2*x+2,2))+1)/2},easeInElastic:function(x){return x===0?0:x===1?1:-pow(2,10*x-10)*sin((x*10-10.75)*c4)},easeOutElastic:function(x){return x===0?0:x===1?1:pow(2,-10*x)*sin((x*10-.75)*c4)+1},easeInOutElastic:function(x){return x===0?0:x===1?1:x<.5?-(pow(2,20*x-10)*sin((20*x-11.125)*c5))/2:pow(2,-20*x+10)*sin((20*x-11.125)*c5)/2+1},easeInBack:function(x){return c3*x*x*x-c1*x*x},easeOutBack:function(x){return 1+c3*pow(x-1,3)+c1*pow(x-1,2)},easeInOutBack:function(x){return x<.5?pow(2*x,2)*((c2+1)*2*x-c2)/2:(pow(2*x-2,2)*((c2+1)*(x*2-2)+c2)+2)/2},easeInBounce:function(x){return 1-bounceOut(1-x)},easeOutBounce:bounceOut,easeInOutBounce:function(x){return x<.5?(1-bounceOut(1-2*x))/2:(1+bounceOut(2*x-1))/2}})});

File diff suppressed because it is too large Load diff

File diff suppressed because one or more lines are too long

File diff suppressed because one or more lines are too long

File diff suppressed because it is too large Load diff

File diff suppressed because one or more lines are too long

File diff suppressed because one or more lines are too long

File diff suppressed because one or more lines are too long

File diff suppressed because one or more lines are too long

View file

@ -1,21 +0,0 @@
The MIT License (MIT)
Copyright (c) 2013-2020 Start Bootstrap LLC
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.

View file

@ -1,56 +0,0 @@
(function($) {
"use strict"; // Start of use strict
// Toggle the side navigation
$("#sidebarToggle, #sidebarToggleTop").on('click', function(e) {
$("body").toggleClass("sidebar-toggled");
$(".sidebar").toggleClass("toggled");
if ($(".sidebar").hasClass("toggled")) {
$('.sidebar .collapse').collapse('hide');
};
});
// Close any open menu accordions when window is resized below 768px
$(window).resize(function() {
if ($(window).width() < 768) {
$('.sidebar .collapse').collapse('hide');
};
// Toggle the side navigation when window is resized below 480px
if ($(window).width() < 480 && !$(".sidebar").hasClass("toggled")) {
$("body").addClass("sidebar-toggled");
$(".sidebar").addClass("toggled");
$('.sidebar .collapse').collapse('hide');
};
});
// Prevent the content wrapper from scrolling when the fixed side navigation hovered over
$('body.fixed-nav .sidebar').on('mousewheel DOMMouseScroll wheel', function(e) {
if ($(window).width() > 768) {
var e0 = e.originalEvent,
delta = e0.wheelDelta || -e0.detail;
this.scrollTop += (delta < 0 ? 1 : -1) * 30;
e.preventDefault();
}
});
// Scroll to top button appear
$(document).on('scroll', function() {
var scrollDistance = $(this).scrollTop();
if (scrollDistance > 100) {
$('.scroll-to-top').fadeIn();
} else {
$('.scroll-to-top').fadeOut();
}
});
// Smooth scrolling using jQuery easing
$(document).on('click', 'a.scroll-to-top', function(e) {
var $anchor = $(this);
$('html, body').stop().animate({
scrollTop: ($($anchor.attr('href')).offset().top)
}, 1000, 'easeInOutExpo');
e.preventDefault();
});
})(jQuery); // End of use strict

View file

@ -1,7 +0,0 @@
/*!
* Start Bootstrap - SB Admin 2 v4.1.3 (https://startbootstrap.com/theme/sb-admin-2)
* Copyright 2013-2020 Start Bootstrap
* Licensed under MIT (https://github.com/StartBootstrap/startbootstrap-sb-admin-2/blob/master/LICENSE)
*/
!function(s){"use strict";s("#sidebarToggle, #sidebarToggleTop").on("click",function(e){s("body").toggleClass("sidebar-toggled"),s(".sidebar").toggleClass("toggled"),s(".sidebar").hasClass("toggled")&&s(".sidebar .collapse").collapse("hide")}),s(window).resize(function(){s(window).width()<768&&s(".sidebar .collapse").collapse("hide"),s(window).width()<480&&!s(".sidebar").hasClass("toggled")&&(s("body").addClass("sidebar-toggled"),s(".sidebar").addClass("toggled"),s(".sidebar .collapse").collapse("hide"))}),s("body.fixed-nav .sidebar").on("mousewheel DOMMouseScroll wheel",function(e){if(768<s(window).width()){var o=e.originalEvent,l=o.wheelDelta||-o.detail;this.scrollTop+=30*(l<0?1:-1),e.preventDefault()}}),s(document).on("scroll",function(){100<s(this).scrollTop()?s(".scroll-to-top").fadeIn():s(".scroll-to-top").fadeOut()}),s(document).on("click","a.scroll-to-top",function(e){var o=s(this);s("html, body").stop().animate({scrollTop:s(o.attr("href")).offset().top},1e3,"easeInOutExpo"),e.preventDefault()})}(jQuery);

View file

@ -1,338 +0,0 @@
/*!
SerializeJSON jQuery plugin.
https://github.com/marioizquierdo/jquery.serializeJSON
version 3.2.1 (Feb, 2021)
Copyright (c) 2012-2021 Mario Izquierdo
Dual licensed under the MIT (http://www.opensource.org/licenses/mit-license.php)
and GPL (http://www.opensource.org/licenses/gpl-license.php) licenses.
*/
(function (factory) {
/* global define, require, module */
if (typeof define === "function" && define.amd) { // AMD. Register as an anonymous module.
define(["jquery"], factory);
} else if (typeof exports === "object") { // Node/CommonJS
var jQuery = require("jquery");
module.exports = factory(jQuery);
} else { // Browser globals (zepto supported)
factory(window.jQuery || window.Zepto || window.$); // Zepto supported on browsers as well
}
}(function ($) {
"use strict";
var rCRLF = /\r?\n/g;
var rsubmitterTypes = /^(?:submit|button|image|reset|file)$/i;
var rsubmittable = /^(?:input|select|textarea|keygen)/i;
var rcheckableType = /^(?:checkbox|radio)$/i;
$.fn.serializeJSON = function (options) {
var f = $.serializeJSON;
var $form = this; // NOTE: the set of matched elements is most likely a form, but it could also be a group of inputs
var opts = f.setupOpts(options); // validate options and apply defaults
var typeFunctions = $.extend({}, opts.defaultTypes, opts.customTypes);
// Make a list with {name, value, el} for each input element
var serializedArray = f.serializeArray($form, opts);
// Convert the serializedArray into a serializedObject with nested keys
var serializedObject = {};
$.each(serializedArray, function (_i, obj) {
var nameSansType = obj.name;
var type = $(obj.el).attr("data-value-type");
if (!type && !opts.disableColonTypes) { // try getting the type from the input name
var p = f.splitType(obj.name); // "foo:string" => ["foo", "string"]
nameSansType = p[0];
type = p[1];
}
if (type === "skip") {
return; // ignore fields with type skip
}
if (!type) {
type = opts.defaultType; // "string" by default
}
var typedValue = f.applyTypeFunc(obj.name, obj.value, type, obj.el, typeFunctions); // Parse type as string, number, etc.
if (!typedValue && f.shouldSkipFalsy(obj.name, nameSansType, type, obj.el, opts)) {
return; // ignore falsy inputs if specified in the options
}
var keys = f.splitInputNameIntoKeysArray(nameSansType);
f.deepSet(serializedObject, keys, typedValue, opts);
});
return serializedObject;
};
// Use $.serializeJSON as namespace for the auxiliar functions
// and to define defaults
$.serializeJSON = {
defaultOptions: {}, // reassign to override option defaults for all serializeJSON calls
defaultBaseOptions: { // do not modify, use defaultOptions instead
checkboxUncheckedValue: undefined, // to include that value for unchecked checkboxes (instead of ignoring them)
useIntKeysAsArrayIndex: false, // name="foo[2]" value="v" => {foo: [null, null, "v"]}, instead of {foo: ["2": "v"]}
skipFalsyValuesForTypes: [], // skip serialization of falsy values for listed value types
skipFalsyValuesForFields: [], // skip serialization of falsy values for listed field names
disableColonTypes: false, // do not interpret ":type" suffix as a type
customTypes: {}, // extends defaultTypes
defaultTypes: {
"string": function(str) { return String(str); },
"number": function(str) { return Number(str); },
"boolean": function(str) { var falses = ["false", "null", "undefined", "", "0"]; return falses.indexOf(str) === -1; },
"null": function(str) { var falses = ["false", "null", "undefined", "", "0"]; return falses.indexOf(str) === -1 ? str : null; },
"array": function(str) { return JSON.parse(str); },
"object": function(str) { return JSON.parse(str); },
"skip": null // skip is a special type used to ignore fields
},
defaultType: "string",
},
// Validate and set defaults
setupOpts: function(options) {
if (options == null) options = {};
var f = $.serializeJSON;
// Validate
var validOpts = [
"checkboxUncheckedValue",
"useIntKeysAsArrayIndex",
"skipFalsyValuesForTypes",
"skipFalsyValuesForFields",
"disableColonTypes",
"customTypes",
"defaultTypes",
"defaultType"
];
for (var opt in options) {
if (validOpts.indexOf(opt) === -1) {
throw new Error("serializeJSON ERROR: invalid option '" + opt + "'. Please use one of " + validOpts.join(", "));
}
}
// Helper to get options or defaults
return $.extend({}, f.defaultBaseOptions, f.defaultOptions, options);
},
// Just like jQuery's serializeArray method, returns an array of objects with name and value.
// but also includes the dom element (el) and is handles unchecked checkboxes if the option or data attribute are provided.
serializeArray: function($form, opts) {
if (opts == null) { opts = {}; }
var f = $.serializeJSON;
return $form.map(function() {
var elements = $.prop(this, "elements"); // handle propHook "elements" to filter or add form elements
return elements ? $.makeArray(elements) : this;
}).filter(function() {
var $el = $(this);
var type = this.type;
// Filter with the standard W3C rules for successful controls: http://www.w3.org/TR/html401/interact/forms.html#h-17.13.2
return this.name && // must contain a name attribute
!$el.is(":disabled") && // must not be disable (use .is(":disabled") so that fieldset[disabled] works)
rsubmittable.test(this.nodeName) && !rsubmitterTypes.test(type) && // only serialize submittable fields (and not buttons)
(this.checked || !rcheckableType.test(type) || f.getCheckboxUncheckedValue($el, opts) != null); // skip unchecked checkboxes (unless using opts)
}).map(function(_i, el) {
var $el = $(this);
var val = $el.val();
var type = this.type; // "input", "select", "textarea", "checkbox", etc.
if (val == null) {
return null;
}
if (rcheckableType.test(type) && !this.checked) {
val = f.getCheckboxUncheckedValue($el, opts);
}
if (isArray(val)) {
return $.map(val, function(val) {
return { name: el.name, value: val.replace(rCRLF, "\r\n"), el: el };
} );
}
return { name: el.name, value: val.replace(rCRLF, "\r\n"), el: el };
}).get();
},
getCheckboxUncheckedValue: function($el, opts) {
var val = $el.attr("data-unchecked-value");
if (val == null) {
val = opts.checkboxUncheckedValue;
}
return val;
},
// Parse value with type function
applyTypeFunc: function(name, strVal, type, el, typeFunctions) {
var typeFunc = typeFunctions[type];
if (!typeFunc) { // quick feedback to user if there is a typo or missconfiguration
throw new Error("serializeJSON ERROR: Invalid type " + type + " found in input name '" + name + "', please use one of " + objectKeys(typeFunctions).join(", "));
}
return typeFunc(strVal, el);
},
// Splits a field name into the name and the type. Examples:
// "foo" => ["foo", ""]
// "foo:boolean" => ["foo", "boolean"]
// "foo[bar]:null" => ["foo[bar]", "null"]
splitType : function(name) {
var parts = name.split(":");
if (parts.length > 1) {
var t = parts.pop();
return [parts.join(":"), t];
} else {
return [name, ""];
}
},
// Check if this input should be skipped when it has a falsy value,
// depending on the options to skip values by name or type, and the data-skip-falsy attribute.
shouldSkipFalsy: function(name, nameSansType, type, el, opts) {
var skipFromDataAttr = $(el).attr("data-skip-falsy");
if (skipFromDataAttr != null) {
return skipFromDataAttr !== "false"; // any value is true, except the string "false"
}
var optForFields = opts.skipFalsyValuesForFields;
if (optForFields && (optForFields.indexOf(nameSansType) !== -1 || optForFields.indexOf(name) !== -1)) {
return true;
}
var optForTypes = opts.skipFalsyValuesForTypes;
if (optForTypes && optForTypes.indexOf(type) !== -1) {
return true;
}
return false;
},
// Split the input name in programatically readable keys.
// Examples:
// "foo" => ["foo"]
// "[foo]" => ["foo"]
// "foo[inn][bar]" => ["foo", "inn", "bar"]
// "foo[inn[bar]]" => ["foo", "inn", "bar"]
// "foo[inn][arr][0]" => ["foo", "inn", "arr", "0"]
// "arr[][val]" => ["arr", "", "val"]
splitInputNameIntoKeysArray: function(nameWithNoType) {
var keys = nameWithNoType.split("["); // split string into array
keys = $.map(keys, function (key) { return key.replace(/\]/g, ""); }); // remove closing brackets
if (keys[0] === "") { keys.shift(); } // ensure no opening bracket ("[foo][inn]" should be same as "foo[inn]")
return keys;
},
// Set a value in an object or array, using multiple keys to set in a nested object or array.
// This is the main function of the script, that allows serializeJSON to use nested keys.
// Examples:
//
// deepSet(obj, ["foo"], v) // obj["foo"] = v
// deepSet(obj, ["foo", "inn"], v) // obj["foo"]["inn"] = v // Create the inner obj["foo"] object, if needed
// deepSet(obj, ["foo", "inn", "123"], v) // obj["foo"]["arr"]["123"] = v //
//
// deepSet(obj, ["0"], v) // obj["0"] = v
// deepSet(arr, ["0"], v, {useIntKeysAsArrayIndex: true}) // arr[0] = v
// deepSet(arr, [""], v) // arr.push(v)
// deepSet(obj, ["arr", ""], v) // obj["arr"].push(v)
//
// arr = [];
// deepSet(arr, ["", v] // arr => [v]
// deepSet(arr, ["", "foo"], v) // arr => [v, {foo: v}]
// deepSet(arr, ["", "bar"], v) // arr => [v, {foo: v, bar: v}]
// deepSet(arr, ["", "bar"], v) // arr => [v, {foo: v, bar: v}, {bar: v}]
//
deepSet: function (o, keys, value, opts) {
if (opts == null) { opts = {}; }
var f = $.serializeJSON;
if (isUndefined(o)) { throw new Error("ArgumentError: param 'o' expected to be an object or array, found undefined"); }
if (!keys || keys.length === 0) { throw new Error("ArgumentError: param 'keys' expected to be an array with least one element"); }
var key = keys[0];
// Only one key, then it's not a deepSet, just assign the value in the object or add it to the array.
if (keys.length === 1) {
if (key === "") { // push values into an array (o must be an array)
o.push(value);
} else {
o[key] = value; // keys can be object keys (strings) or array indexes (numbers)
}
return;
}
var nextKey = keys[1]; // nested key
var tailKeys = keys.slice(1); // list of all other nested keys (nextKey is first)
if (key === "") { // push nested objects into an array (o must be an array)
var lastIdx = o.length - 1;
var lastVal = o[lastIdx];
// if the last value is an object or array, and the new key is not set yet
if (isObject(lastVal) && isUndefined(f.deepGet(lastVal, tailKeys))) {
key = lastIdx; // then set the new value as a new attribute of the same object
} else {
key = lastIdx + 1; // otherwise, add a new element in the array
}
}
if (nextKey === "") { // "" is used to push values into the nested array "array[]"
if (isUndefined(o[key]) || !isArray(o[key])) {
o[key] = []; // define (or override) as array to push values
}
} else {
if (opts.useIntKeysAsArrayIndex && isValidArrayIndex(nextKey)) { // if 1, 2, 3 ... then use an array, where nextKey is the index
if (isUndefined(o[key]) || !isArray(o[key])) {
o[key] = []; // define (or override) as array, to insert values using int keys as array indexes
}
} else { // nextKey is going to be the nested object's attribute
if (isUndefined(o[key]) || !isObject(o[key])) {
o[key] = {}; // define (or override) as object, to set nested properties
}
}
}
// Recursively set the inner object
f.deepSet(o[key], tailKeys, value, opts);
},
deepGet: function (o, keys) {
var f = $.serializeJSON;
if (isUndefined(o) || isUndefined(keys) || keys.length === 0 || (!isObject(o) && !isArray(o))) {
return o;
}
var key = keys[0];
if (key === "") { // "" means next array index (used by deepSet)
return undefined;
}
if (keys.length === 1) {
return o[key];
}
var tailKeys = keys.slice(1);
return f.deepGet(o[key], tailKeys);
}
};
// polyfill Object.keys to get option keys in IE<9
var objectKeys = function(obj) {
if (Object.keys) {
return Object.keys(obj);
} else {
var key, keys = [];
for (key in obj) { keys.push(key); }
return keys;
}
};
var isObject = function(obj) { return obj === Object(obj); }; // true for Objects and Arrays
var isUndefined = function(obj) { return obj === void 0; }; // safe check for undefined values
var isValidArrayIndex = function(val) { return /^[0-9]+$/.test(String(val)); }; // 1,2,3,4 ... are valid array indexes
var isArray = Array.isArray || function(obj) { return Object.prototype.toString.call(obj) === "[object Array]"; };
}));

View file

@ -38,6 +38,7 @@ function configureSidebarForServers(){
function populateSidebarLinks(){
$("#clusterMembersLinkSidebar").show()
$("#clusterGroupsLinkSidebar").show()
$("#instanceSidebarLinks").show()
$("#coreSidebarLinks").show()
$("#networkSidebarLinks").show()
@ -52,25 +53,26 @@ function populateNavbarLinks(){
}
function applySidebarLinks() {
$("#containersLinkSidebar").attr("href", "containers?id=" + encodeURI(serverId) + "&project=" + encodeURI(project));
$("#virtualMachinesLinkSidebar").attr("href", "virtual-machines?id=" + encodeURI(serverId) + "&project=" + encodeURI(project));
$("#instancesLinkSidebar").attr("href", "instances?id=" + encodeURI(serverId) + "&project=" + encodeURI(project));
$("#imagesLinkSidebar").attr("href", "images?id=" + encodeURI(serverId) + "&project=" + encodeURI(project));
$("#profilesLinkSidebar").attr("href", "profiles?id=" + encodeURI(serverId) + "&project=" + encodeURI(project));
$("#networksLinkSidebar").attr("href", "networks?id=" + encodeURI(serverId) + "&project=" + encodeURI(project));
$("#storagePoolsLinkSidebar").attr("href", "storage-pools?id=" + encodeURI(serverId) + "&project=" + encodeURI(project));
$("#clusterMembersLinkSidebar").attr("href", "cluster-members?id=" + encodeURI(serverId) + "&project=" + encodeURI(project));
$("#clusterGroupsLinkSidebar").attr("href", "cluster-groups?id=" + encodeURI(serverId) + "&project=" + encodeURI(project));
$("#projectsLinkSidebar").attr("href", "projects?id=" + encodeURI(serverId) + "&project=" + encodeURI(project));
$("#networkAclsLinkSidebar").attr("href", "network-acls?id=" + encodeURI(serverId) + "&project=" + encodeURI(project));
$("#networkZonesLinkSidebar").attr("href", "network-zones?id=" + encodeURI(serverId) + "&project=" + encodeURI(project));
$("#operationsLinkSidebar").attr("href", "operations?id=" + encodeURI(serverId) + "&project=" + encodeURI(project));
$("#certificatesLinkSidebar").attr("href", "certificates?id=" + encodeURI(serverId) + "&project=" + encodeURI(project));
$("#simplestreamsLinkSidebar").attr("href", "simplestreams?id=" + encodeURI(serverId) + "&project=" + encodeURI(project));
}
function applySidebarStyles() {
if (location.pathname == "/containers" || location.pathname == "/container"){
$('#containersSpan').css('color','#fff');
$('#containersIcon').css('color','#fff');
if (location.pathname == "/instances" || location.pathname == "/instance"){
$('#instancesSpan').css('color','#fff');
$('#instancesIcon').css('color','#fff');
}
if (location.pathname == "/images"){
$('#imagesSpan').css('color','#fff');
@ -100,6 +102,10 @@ function applySidebarStyles() {
$('#networkAclsSpan').css('color','#fff');
$('#networkAclsIcon').css('color','#fff');
}
if (location.pathname == "/network-zones" || location.pathname == "/network-zone"){
$('#networkZonesSpan').css('color','#fff');
$('#networkZonesIcon').css('color','#fff');
}
if (location.pathname == "/operations"){
$('#operationsSpan').css('color','#fff');
$('#operationsIcon').css('color','#fff');

File diff suppressed because one or more lines are too long

File diff suppressed because one or more lines are too long

View file

@ -1,399 +0,0 @@
/*!
* Bootstrap Colorpicker - Bootstrap Colorpicker is a modular color picker plugin for Bootstrap 4.
* @package bootstrap-colorpicker
* @version v3.4.0
* @license MIT
* @link https://itsjavi.com/bootstrap-colorpicker/
* @link https://github.com/itsjavi/bootstrap-colorpicker.git
*/
.colorpicker {
position: relative;
display: none;
font-size: inherit;
color: inherit;
text-align: left;
list-style: none;
background-color: #ffffff;
background-clip: padding-box;
border: 1px solid rgba(0, 0, 0, 0.2);
padding: .75rem .75rem;
width: 148px;
border-radius: 4px;
-webkit-box-sizing: content-box;
box-sizing: content-box; }
.colorpicker.colorpicker-disabled,
.colorpicker.colorpicker-disabled * {
cursor: default !important; }
.colorpicker div {
position: relative; }
.colorpicker-popup {
position: absolute;
top: 100%;
left: 0;
float: left;
margin-top: 1px;
z-index: 1060; }
.colorpicker-popup.colorpicker-bs-popover-content {
position: relative;
top: auto;
left: auto;
float: none;
margin: 0;
z-index: initial;
border: none;
padding: 0.25rem 0;
border-radius: 0;
background: none;
-webkit-box-shadow: none;
box-shadow: none; }
.colorpicker:before,
.colorpicker:after {
content: "";
display: table;
clear: both;
line-height: 0; }
.colorpicker-clear {
clear: both;
display: block; }
.colorpicker:before {
content: '';
display: inline-block;
border-left: 7px solid transparent;
border-right: 7px solid transparent;
border-bottom: 7px solid #ccc;
border-bottom-color: rgba(0, 0, 0, 0.2);
position: absolute;
top: -7px;
left: auto;
right: 6px; }
.colorpicker:after {
content: '';
display: inline-block;
border-left: 6px solid transparent;
border-right: 6px solid transparent;
border-bottom: 6px solid #ffffff;
position: absolute;
top: -6px;
left: auto;
right: 7px; }
.colorpicker.colorpicker-with-alpha {
width: 170px; }
.colorpicker.colorpicker-with-alpha .colorpicker-alpha {
display: block; }
.colorpicker-saturation {
position: relative;
width: 126px;
height: 126px;
/* FF3.6+ */
/* Chrome,Safari4+ */
/* Chrome10+,Safari5.1+ */
/* Opera 11.10+ */
/* IE10+ */
background: -webkit-gradient(linear, left top, left bottom, from(transparent), to(black)), -webkit-gradient(linear, left top, right top, from(white), to(rgba(255, 255, 255, 0)));
background: linear-gradient(to bottom, transparent 0%, black 100%), linear-gradient(to right, white 0%, rgba(255, 255, 255, 0) 100%);
/* W3C */
cursor: crosshair;
float: left;
-webkit-box-shadow: 0 0 0 1px rgba(0, 0, 0, 0.2);
box-shadow: 0 0 0 1px rgba(0, 0, 0, 0.2);
margin-bottom: 6px; }
.colorpicker-saturation .colorpicker-guide {
display: block;
height: 6px;
width: 6px;
border-radius: 6px;
border: 1px solid #000;
-webkit-box-shadow: 0 0 0 1px rgba(255, 255, 255, 0.8);
box-shadow: 0 0 0 1px rgba(255, 255, 255, 0.8);
position: absolute;
top: 0;
left: 0;
margin: -3px 0 0 -3px; }
.colorpicker-hue,
.colorpicker-alpha {
position: relative;
width: 16px;
height: 126px;
float: left;
cursor: row-resize;
margin-left: 6px;
margin-bottom: 6px; }
.colorpicker-alpha-color {
position: absolute;
top: 0;
left: 0;
width: 100%;
height: 100%; }
.colorpicker-hue,
.colorpicker-alpha-color {
-webkit-box-shadow: 0 0 0 1px rgba(0, 0, 0, 0.2);
box-shadow: 0 0 0 1px rgba(0, 0, 0, 0.2); }
.colorpicker-hue .colorpicker-guide,
.colorpicker-alpha .colorpicker-guide {
display: block;
height: 4px;
background: rgba(255, 255, 255, 0.8);
border: 1px solid rgba(0, 0, 0, 0.4);
position: absolute;
top: 0;
left: 0;
margin-left: -2px;
margin-top: -2px;
right: -2px;
z-index: 1; }
.colorpicker-hue {
/* FF3.6+ */
/* Chrome,Safari4+ */
/* Chrome10+,Safari5.1+ */
/* Opera 11.10+ */
/* IE10+ */
background: -webkit-gradient(linear, left bottom, left top, from(red), color-stop(8%, #ff8000), color-stop(17%, yellow), color-stop(25%, #80ff00), color-stop(33%, lime), color-stop(42%, #00ff80), color-stop(50%, cyan), color-stop(58%, #0080ff), color-stop(67%, blue), color-stop(75%, #8000ff), color-stop(83%, magenta), color-stop(92%, #ff0080), to(red));
background: linear-gradient(to top, red 0%, #ff8000 8%, yellow 17%, #80ff00 25%, lime 33%, #00ff80 42%, cyan 50%, #0080ff 58%, blue 67%, #8000ff 75%, magenta 83%, #ff0080 92%, red 100%);
/* W3C */ }
.colorpicker-alpha {
background: linear-gradient(45deg, rgba(0, 0, 0, 0.1) 25%, transparent 25%, transparent 75%, rgba(0, 0, 0, 0.1) 75%, rgba(0, 0, 0, 0.1) 0), linear-gradient(45deg, rgba(0, 0, 0, 0.1) 25%, transparent 25%, transparent 75%, rgba(0, 0, 0, 0.1) 75%, rgba(0, 0, 0, 0.1) 0), white;
background-size: 10px 10px;
background-position: 0 0, 5px 5px;
display: none; }
.colorpicker-bar {
min-height: 16px;
margin: 6px 0 0 0;
clear: both;
text-align: center;
font-size: 10px;
line-height: normal;
max-width: 100%;
-webkit-box-shadow: 0 0 0 1px rgba(0, 0, 0, 0.2);
box-shadow: 0 0 0 1px rgba(0, 0, 0, 0.2); }
.colorpicker-bar:before {
content: "";
display: table;
clear: both; }
.colorpicker-bar.colorpicker-bar-horizontal {
height: 126px;
width: 16px;
margin: 0 0 6px 0;
float: left; }
.colorpicker-input-addon {
position: relative; }
.colorpicker-input-addon i {
display: inline-block;
cursor: pointer;
vertical-align: text-top;
height: 16px;
width: 16px;
position: relative; }
.colorpicker-input-addon:before {
content: "";
position: absolute;
width: 16px;
height: 16px;
display: inline-block;
vertical-align: text-top;
background: linear-gradient(45deg, rgba(0, 0, 0, 0.1) 25%, transparent 25%, transparent 75%, rgba(0, 0, 0, 0.1) 75%, rgba(0, 0, 0, 0.1) 0), linear-gradient(45deg, rgba(0, 0, 0, 0.1) 25%, transparent 25%, transparent 75%, rgba(0, 0, 0, 0.1) 75%, rgba(0, 0, 0, 0.1) 0), white;
background-size: 10px 10px;
background-position: 0 0, 5px 5px; }
.colorpicker.colorpicker-inline {
position: relative;
display: inline-block;
float: none;
z-index: auto;
vertical-align: text-bottom; }
.colorpicker.colorpicker-horizontal {
width: 126px;
height: auto; }
.colorpicker.colorpicker-horizontal .colorpicker-bar {
width: 126px; }
.colorpicker.colorpicker-horizontal .colorpicker-saturation {
float: none;
margin-bottom: 0; }
.colorpicker.colorpicker-horizontal .colorpicker-hue,
.colorpicker.colorpicker-horizontal .colorpicker-alpha {
float: none;
width: 126px;
height: 16px;
cursor: col-resize;
margin-left: 0;
margin-top: 6px;
margin-bottom: 0; }
.colorpicker.colorpicker-horizontal .colorpicker-hue .colorpicker-guide,
.colorpicker.colorpicker-horizontal .colorpicker-alpha .colorpicker-guide {
position: absolute;
display: block;
bottom: -2px;
left: 0;
right: auto;
height: auto;
width: 4px; }
.colorpicker.colorpicker-horizontal .colorpicker-hue {
/* FF3.6+ */
/* Chrome,Safari4+ */
/* Chrome10+,Safari5.1+ */
/* Opera 11.10+ */
/* IE10+ */
background: -webkit-gradient(linear, right top, left top, from(red), color-stop(8%, #ff8000), color-stop(17%, yellow), color-stop(25%, #80ff00), color-stop(33%, lime), color-stop(42%, #00ff80), color-stop(50%, cyan), color-stop(58%, #0080ff), color-stop(67%, blue), color-stop(75%, #8000ff), color-stop(83%, magenta), color-stop(92%, #ff0080), to(red));
background: linear-gradient(to left, red 0%, #ff8000 8%, yellow 17%, #80ff00 25%, lime 33%, #00ff80 42%, cyan 50%, #0080ff 58%, blue 67%, #8000ff 75%, magenta 83%, #ff0080 92%, red 100%);
/* W3C */ }
.colorpicker.colorpicker-horizontal .colorpicker-alpha {
background: linear-gradient(45deg, rgba(0, 0, 0, 0.1) 25%, transparent 25%, transparent 75%, rgba(0, 0, 0, 0.1) 75%, rgba(0, 0, 0, 0.1) 0), linear-gradient(45deg, rgba(0, 0, 0, 0.1) 25%, transparent 25%, transparent 75%, rgba(0, 0, 0, 0.1) 75%, rgba(0, 0, 0, 0.1) 0), white;
background-size: 10px 10px;
background-position: 0 0, 5px 5px; }
.colorpicker-inline:before,
.colorpicker-no-arrow:before,
.colorpicker-popup.colorpicker-bs-popover-content:before {
content: none;
display: none; }
.colorpicker-inline:after,
.colorpicker-no-arrow:after,
.colorpicker-popup.colorpicker-bs-popover-content:after {
content: none;
display: none; }
.colorpicker-alpha,
.colorpicker-saturation,
.colorpicker-hue {
-webkit-user-select: none;
-moz-user-select: none;
-ms-user-select: none;
user-select: none; }
.colorpicker.colorpicker-visible,
.colorpicker-alpha.colorpicker-visible,
.colorpicker-saturation.colorpicker-visible,
.colorpicker-hue.colorpicker-visible,
.colorpicker-bar.colorpicker-visible {
display: block; }
.colorpicker.colorpicker-hidden,
.colorpicker-alpha.colorpicker-hidden,
.colorpicker-saturation.colorpicker-hidden,
.colorpicker-hue.colorpicker-hidden,
.colorpicker-bar.colorpicker-hidden {
display: none; }
.colorpicker-inline.colorpicker-visible {
display: inline-block; }
.colorpicker.colorpicker-disabled:after {
border: none;
content: '';
display: block;
width: 100%;
height: 100%;
background: rgba(233, 236, 239, 0.33);
top: 0;
left: 0;
right: auto;
z-index: 2;
position: absolute; }
.colorpicker.colorpicker-disabled .colorpicker-guide {
display: none; }
/** EXTENSIONS **/
.colorpicker-preview {
background: linear-gradient(45deg, rgba(0, 0, 0, 0.1) 25%, transparent 25%, transparent 75%, rgba(0, 0, 0, 0.1) 75%, rgba(0, 0, 0, 0.1) 0), linear-gradient(45deg, rgba(0, 0, 0, 0.1) 25%, transparent 25%, transparent 75%, rgba(0, 0, 0, 0.1) 75%, rgba(0, 0, 0, 0.1) 0), white;
background-size: 10px 10px;
background-position: 0 0, 5px 5px; }
.colorpicker-preview > div {
position: absolute;
left: 0;
top: 0;
width: 100%;
height: 100%; }
.colorpicker-bar.colorpicker-swatches {
-webkit-box-shadow: none;
box-shadow: none;
height: auto; }
.colorpicker-swatches--inner {
clear: both;
margin-top: -6px; }
.colorpicker-swatch {
position: relative;
cursor: pointer;
float: left;
height: 16px;
width: 16px;
margin-right: 6px;
margin-top: 6px;
margin-left: 0;
display: block;
-webkit-box-shadow: 0 0 0 1px rgba(0, 0, 0, 0.2);
box-shadow: 0 0 0 1px rgba(0, 0, 0, 0.2);
background: linear-gradient(45deg, rgba(0, 0, 0, 0.1) 25%, transparent 25%, transparent 75%, rgba(0, 0, 0, 0.1) 75%, rgba(0, 0, 0, 0.1) 0), linear-gradient(45deg, rgba(0, 0, 0, 0.1) 25%, transparent 25%, transparent 75%, rgba(0, 0, 0, 0.1) 75%, rgba(0, 0, 0, 0.1) 0), white;
background-size: 10px 10px;
background-position: 0 0, 5px 5px; }
.colorpicker-swatch--inner {
position: absolute;
top: 0;
left: 0;
width: 100%;
height: 100%; }
.colorpicker-swatch:nth-of-type(7n+0) {
margin-right: 0; }
.colorpicker-with-alpha .colorpicker-swatch:nth-of-type(7n+0) {
margin-right: 6px; }
.colorpicker-with-alpha .colorpicker-swatch:nth-of-type(8n+0) {
margin-right: 0; }
.colorpicker-horizontal .colorpicker-swatch:nth-of-type(6n+0) {
margin-right: 0; }
.colorpicker-horizontal .colorpicker-swatch:nth-of-type(7n+0) {
margin-right: 6px; }
.colorpicker-horizontal .colorpicker-swatch:nth-of-type(8n+0) {
margin-right: 6px; }
.colorpicker-swatch:last-of-type:after {
content: "";
display: table;
clear: both; }
*[dir='rtl'] .colorpicker-element input,
.colorpicker-element[dir='rtl'] input,
.colorpicker-element input[dir='rtl'] {
direction: ltr;
text-align: right; }
/*# sourceMappingURL=bootstrap-colorpicker.css.map */

File diff suppressed because one or more lines are too long

File diff suppressed because one or more lines are too long

File diff suppressed because one or more lines are too long

File diff suppressed because it is too large Load diff

File diff suppressed because one or more lines are too long

File diff suppressed because one or more lines are too long

File diff suppressed because one or more lines are too long

File diff suppressed because it is too large Load diff

File diff suppressed because one or more lines are too long

View file

@ -1,418 +0,0 @@
/*! =======================================================
VERSION 11.0.2
========================================================= */
/*! =========================================================
* bootstrap-slider.js
*
* Maintainers:
* Kyle Kemp
* - Twitter: @seiyria
* - Github: seiyria
* Rohit Kalkur
* - Twitter: @Rovolutionary
* - Github: rovolution
*
* =========================================================
*
* bootstrap-slider is released under the MIT License
* Copyright (c) 2019 Kyle Kemp, Rohit Kalkur, and contributors
*
* 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.
*
* ========================================================= */
.slider {
display: inline-block;
vertical-align: middle;
position: relative;
}
.slider.slider-horizontal {
width: 210px;
height: 20px;
}
.slider.slider-horizontal .slider-track {
height: 10px;
width: 100%;
margin-top: -5px;
top: 50%;
left: 0;
}
.slider.slider-horizontal .slider-selection, .slider.slider-horizontal .slider-track-low, .slider.slider-horizontal .slider-track-high {
height: 100%;
top: 0;
bottom: 0;
}
.slider.slider-horizontal .slider-tick,
.slider.slider-horizontal .slider-handle {
margin-left: -10px;
}
.slider.slider-horizontal .slider-tick.triangle,
.slider.slider-horizontal .slider-handle.triangle {
position: relative;
top: 50%;
transform: translateY(-50%);
border-width: 0 10px 10px 10px;
width: 0;
height: 0;
border-bottom-color: #036fa5;
margin-top: 0;
}
.slider.slider-horizontal .slider-tick-container {
white-space: nowrap;
position: absolute;
top: 0;
left: 0;
width: 100%;
}
.slider.slider-horizontal .slider-tick-label-container {
white-space: nowrap;
margin-top: 20px;
}
.slider.slider-horizontal .slider-tick-label-container .slider-tick-label {
display: inline-block;
text-align: center;
}
.slider.slider-horizontal.slider-rtl .slider-track {
left: initial;
right: 0;
}
.slider.slider-horizontal.slider-rtl .slider-tick,
.slider.slider-horizontal.slider-rtl .slider-handle {
margin-left: initial;
margin-right: -10px;
}
.slider.slider-horizontal.slider-rtl .slider-tick-container {
left: initial;
right: 0;
}
.slider.slider-vertical {
height: 210px;
width: 20px;
}
.slider.slider-vertical .slider-track {
width: 10px;
height: 100%;
left: 25%;
top: 0;
}
.slider.slider-vertical .slider-selection {
width: 100%;
left: 0;
top: 0;
bottom: 0;
}
.slider.slider-vertical .slider-track-low, .slider.slider-vertical .slider-track-high {
width: 100%;
left: 0;
right: 0;
}
.slider.slider-vertical .slider-tick,
.slider.slider-vertical .slider-handle {
margin-top: -10px;
}
.slider.slider-vertical .slider-tick.triangle,
.slider.slider-vertical .slider-handle.triangle {
border-width: 10px 0 10px 10px;
width: 1px;
height: 1px;
border-left-color: #036fa5;
margin-left: 0;
}
.slider.slider-vertical .slider-tick-label-container {
white-space: nowrap;
}
.slider.slider-vertical .slider-tick-label-container .slider-tick-label {
padding-left: 4px;
}
.slider.slider-vertical.slider-rtl .slider-track {
left: initial;
right: 25%;
}
.slider.slider-vertical.slider-rtl .slider-selection {
left: initial;
right: 0;
}
.slider.slider-vertical.slider-rtl .slider-tick.triangle,
.slider.slider-vertical.slider-rtl .slider-handle.triangle {
border-width: 10px 10px 10px 0;
}
.slider.slider-vertical.slider-rtl .slider-tick-label-container .slider-tick-label {
padding-left: initial;
padding-right: 4px;
}
.slider.slider-disabled .slider-handle {
background-color: #cfcfcf;
background-image: -moz-linear-gradient(top, #DFDFDF, #BEBEBE);
background-image: -webkit-gradient(linear, 0 0, 0 100%, from(#DFDFDF), to(#BEBEBE));
background-image: -webkit-linear-gradient(top, #DFDFDF, #BEBEBE);
background-image: -o-linear-gradient(top, #DFDFDF, #BEBEBE);
background-image: linear-gradient(to bottom, #DFDFDF, #BEBEBE);
background-repeat: repeat-x;
filter: progid:DXImageTransform.Microsoft.gradient(startColorstr='#DFDFDF', endColorstr='#BEBEBE',GradientType=0);
}
.slider.slider-disabled .slider-track {
background-color: #e7e7e7;
background-image: -moz-linear-gradient(top, #E5E5E5, #E9E9E9);
background-image: -webkit-gradient(linear, 0 0, 0 100%, from(#E5E5E5), to(#E9E9E9));
background-image: -webkit-linear-gradient(top, #E5E5E5, #E9E9E9);
background-image: -o-linear-gradient(top, #E5E5E5, #E9E9E9);
background-image: linear-gradient(to bottom, #E5E5E5, #E9E9E9);
background-repeat: repeat-x;
filter: progid:DXImageTransform.Microsoft.gradient(startColorstr='#E5E5E5', endColorstr='#E9E9E9',GradientType=0);
cursor: not-allowed;
}
.slider input {
display: none;
}
.slider .tooltip-inner {
white-space: nowrap;
max-width: none;
}
.slider .bs-tooltip-top .tooltip-inner,
.slider .bs-tooltip-bottom .tooltip-inner {
position: relative;
left: -50%;
}
.slider.bs-tooltip-left .tooltip-inner, .slider.bs-tooltip-right .tooltip-inner {
position: relative;
top: -100%;
}
.slider .tooltip {
pointer-events: none;
}
.slider .tooltip.bs-tooltip-top .arrow, .slider .tooltip.bs-tooltip-bottom .arrow {
left: -.4rem;
}
.slider .tooltip.bs-tooltip-top {
margin-top: -44px;
}
.slider .tooltip.bs-tooltip-bottom {
margin-top: 2px;
}
.slider .tooltip.bs-tooltip-left, .slider .tooltip.bs-tooltip-right {
margin-top: -14px;
}
.slider .tooltip.bs-tooltip-left .arrow, .slider .tooltip.bs-tooltip-right .arrow {
top: 8px;
}
.slider .hide {
display: none;
}
.slider-track {
background-color: #f7f7f7;
background-image: -moz-linear-gradient(top, #F5F5F5, #F9F9F9);
background-image: -webkit-gradient(linear, 0 0, 0 100%, from(#F5F5F5), to(#F9F9F9));
background-image: -webkit-linear-gradient(top, #F5F5F5, #F9F9F9);
background-image: -o-linear-gradient(top, #F5F5F5, #F9F9F9);
background-image: linear-gradient(to bottom, #F5F5F5, #F9F9F9);
background-repeat: repeat-x;
filter: progid:DXImageTransform.Microsoft.gradient(startColorstr='#F5F5F5', endColorstr='#F9F9F9',GradientType=0);
-webkit-box-shadow: inset 0 1px 2px rgba(0, 0, 0, 0.1);
-moz-box-shadow: inset 0 1px 2px rgba(0, 0, 0, 0.1);
box-shadow: inset 0 1px 2px rgba(0, 0, 0, 0.1);
-webkit-border-radius: 4px;
-moz-border-radius: 4px;
border-radius: 4px;
position: absolute;
cursor: pointer;
}
.slider-selection {
background-color: #f7f7f7;
background-image: -moz-linear-gradient(top, #F9F9F9, #F5F5F5);
background-image: -webkit-gradient(linear, 0 0, 0 100%, from(#F9F9F9), to(#F5F5F5));
background-image: -webkit-linear-gradient(top, #F9F9F9, #F5F5F5);
background-image: -o-linear-gradient(top, #F9F9F9, #F5F5F5);
background-image: linear-gradient(to bottom, #F9F9F9, #F5F5F5);
background-repeat: repeat-x;
filter: progid:DXImageTransform.Microsoft.gradient(startColorstr='#F9F9F9', endColorstr='#F5F5F5',GradientType=0);
-webkit-box-shadow: inset 0 -1px 0 rgba(0, 0, 0, 0.15);
-moz-box-shadow: inset 0 -1px 0 rgba(0, 0, 0, 0.15);
box-shadow: inset 0 -1px 0 rgba(0, 0, 0, 0.15);
-webkit-box-sizing: border-box;
-moz-box-sizing: border-box;
box-sizing: border-box;
-webkit-border-radius: 4px;
-moz-border-radius: 4px;
border-radius: 4px;
position: absolute;
}
.slider-selection.tick-slider-selection {
background-color: #46c1fe;
background-image: -moz-linear-gradient(top, #52c5ff, #3abcfd);
background-image: -webkit-gradient(linear, 0 0, 0 100%, from(#52c5ff), to(#3abcfd));
background-image: -webkit-linear-gradient(top, #52c5ff, #3abcfd);
background-image: -o-linear-gradient(top, #52c5ff, #3abcfd);
background-image: linear-gradient(to bottom, #52c5ff, #3abcfd);
background-repeat: repeat-x;
filter: progid:DXImageTransform.Microsoft.gradient(startColorstr='#52c5ff', endColorstr='#3abcfd',GradientType=0);
}
.slider-track-low, .slider-track-high {
-webkit-box-sizing: border-box;
-moz-box-sizing: border-box;
box-sizing: border-box;
-webkit-border-radius: 4px;
-moz-border-radius: 4px;
border-radius: 4px;
position: absolute;
background: transparent;
}
.slider-handle {
background-color: #0478b2;
background-image: -moz-linear-gradient(top, #0480BE, #036fa5);
background-image: -webkit-gradient(linear, 0 0, 0 100%, from(#0480BE), to(#036fa5));
background-image: -webkit-linear-gradient(top, #0480BE, #036fa5);
background-image: -o-linear-gradient(top, #0480BE, #036fa5);
background-image: linear-gradient(to bottom, #0480BE, #036fa5);
background-repeat: repeat-x;
filter: progid:DXImageTransform.Microsoft.gradient(startColorstr='#0480BE', endColorstr='#036fa5',GradientType=0);
-webkit-box-shadow: inset 0 1px 0 rgba(255, 255, 255, 0.2), 0 1px 2px rgba(0, 0, 0, 0.05);
-moz-box-shadow: inset 0 1px 0 rgba(255, 255, 255, 0.2), 0 1px 2px rgba(0, 0, 0, 0.05);
box-shadow: inset 0 1px 0 rgba(255, 255, 255, 0.2), 0 1px 2px rgba(0, 0, 0, 0.05);
position: absolute;
top: 0;
width: 20px;
height: 20px;
background-color: #0480BE;
border: 0px solid transparent;
}
.slider-handle:hover {
cursor: pointer;
}
.slider-handle.round {
-webkit-border-radius: 20px;
-moz-border-radius: 20px;
border-radius: 20px;
}
.slider-handle.triangle {
background: transparent none;
}
.slider-handle.custom {
background: transparent none;
}
.slider-handle.custom::before {
line-height: 20px;
font-size: 20px;
content: '\2605';
color: #726204;
}
.slider-tick {
background-color: #f7f7f7;
background-image: -moz-linear-gradient(top, #F5F5F5, #F9F9F9);
background-image: -webkit-gradient(linear, 0 0, 0 100%, from(#F5F5F5), to(#F9F9F9));
background-image: -webkit-linear-gradient(top, #F5F5F5, #F9F9F9);
background-image: -o-linear-gradient(top, #F5F5F5, #F9F9F9);
background-image: linear-gradient(to bottom, #F5F5F5, #F9F9F9);
background-repeat: repeat-x;
filter: progid:DXImageTransform.Microsoft.gradient(startColorstr='#F5F5F5', endColorstr='#F9F9F9',GradientType=0);
-webkit-box-shadow: inset 0 -1px 0 rgba(0, 0, 0, 0.15);
-moz-box-shadow: inset 0 -1px 0 rgba(0, 0, 0, 0.15);
box-shadow: inset 0 -1px 0 rgba(0, 0, 0, 0.15);
-webkit-box-sizing: border-box;
-moz-box-sizing: border-box;
box-sizing: border-box;
position: absolute;
cursor: pointer;
width: 20px;
height: 20px;
filter: none;
opacity: 0.8;
border: 0px solid transparent;
}
.slider-tick.round {
border-radius: 50%;
}
.slider-tick.triangle {
background: transparent none;
}
.slider-tick.custom {
background: transparent none;
}
.slider-tick.custom::before {
line-height: 20px;
font-size: 20px;
content: '\2605';
color: #726204;
}
.slider-tick.in-selection {
background-color: #46c1fe;
background-image: -moz-linear-gradient(top, #52c5ff, #3abcfd);
background-image: -webkit-gradient(linear, 0 0, 0 100%, from(#52c5ff), to(#3abcfd));
background-image: -webkit-linear-gradient(top, #52c5ff, #3abcfd);
background-image: -o-linear-gradient(top, #52c5ff, #3abcfd);
background-image: linear-gradient(to bottom, #52c5ff, #3abcfd);
background-repeat: repeat-x;
filter: progid:DXImageTransform.Microsoft.gradient(startColorstr='#52c5ff', endColorstr='#3abcfd',GradientType=0);
opacity: 1;
}
/*# sourceMappingURL=bootstrap-slider.css.map */

File diff suppressed because one or more lines are too long

View file

@ -1,510 +0,0 @@
/**
* bootstrap-switch - Turn checkboxes and radio buttons into toggle switches.
*
* @version v3.3.4
* @homepage https://bttstrp.github.io/bootstrap-switch
* @author Mattia Larentis <mattia@larentis.eu> (http://larentis.eu)
* @license Apache-2.0
*/
.clearfix {
*zoom: 1;
}
.clearfix:before,
.clearfix:after {
display: table;
content: "";
line-height: 0;
}
.clearfix:after {
clear: both;
}
.hide-text {
font: 0/0 a;
color: transparent;
text-shadow: none;
background-color: transparent;
border: 0;
}
.input-block-level {
display: block;
width: 100%;
min-height: 30px;
-webkit-box-sizing: border-box;
-moz-box-sizing: border-box;
box-sizing: border-box;
}
.bootstrap-switch {
display: inline-block;
direction: ltr;
cursor: pointer;
-webkit-border-radius: 5px;
-moz-border-radius: 5px;
border-radius: 5px;
border: 1px solid;
border-color: rgba(0, 0, 0, 0.1) rgba(0, 0, 0, 0.1) rgba(0, 0, 0, 0.25);
position: relative;
text-align: left;
overflow: hidden;
line-height: 8px;
z-index: 0;
-webkit-user-select: none;
-moz-user-select: none;
-ms-user-select: none;
-o-user-select: none;
user-select: none;
vertical-align: middle;
-webkit-transition: border-color ease-in-out .15s, box-shadow ease-in-out .15s;
-moz-transition: border-color ease-in-out .15s, box-shadow ease-in-out .15s;
-o-transition: border-color ease-in-out .15s, box-shadow ease-in-out .15s;
transition: border-color ease-in-out .15s, box-shadow ease-in-out .15s;
}
.bootstrap-switch .bootstrap-switch-container {
display: inline-block;
top: 0;
-webkit-border-radius: 4px;
-moz-border-radius: 4px;
border-radius: 4px;
-webkit-transform: translate3d(0, 0, 0);
-moz-transform: translate3d(0, 0, 0);
-o-transform: translate3d(0, 0, 0);
transform: translate3d(0, 0, 0);
}
.bootstrap-switch .bootstrap-switch-handle-on,
.bootstrap-switch .bootstrap-switch-handle-off,
.bootstrap-switch .bootstrap-switch-label {
-webkit-box-sizing: border-box;
-moz-box-sizing: border-box;
box-sizing: border-box;
cursor: pointer;
display: inline-block !important;
padding-top: 4px;
padding-bottom: 4px;
padding-left: 8px;
padding-right: 8px;
font-size: 14px;
line-height: 20px;
}
.bootstrap-switch .bootstrap-switch-handle-on,
.bootstrap-switch .bootstrap-switch-handle-off {
text-align: center;
z-index: 1;
}
.bootstrap-switch .bootstrap-switch-handle-on.bootstrap-switch-primary,
.bootstrap-switch .bootstrap-switch-handle-off.bootstrap-switch-primary {
color: #fff;
text-shadow: 0 -1px 0 rgba(0, 0, 0, 0.25);
background-color: #005fcc;
background-image: -moz-linear-gradient(top, #0044cc, #08c);
background-image: -webkit-gradient(linear, 0 0, 0 100%, from(#0044cc), to(#08c));
background-image: -webkit-linear-gradient(top, #0044cc, #08c);
background-image: -o-linear-gradient(top, #0044cc, #08c);
background-image: linear-gradient(to bottom, #0044cc, #08c);
background-repeat: repeat-x;
filter: progid:DXImageTransform.Microsoft.gradient(startColorstr='#ff0044cc', endColorstr='#ff0088cc', GradientType=0);
border-color: #08c #08c #005580;
border-color: rgba(0, 0, 0, 0.1) rgba(0, 0, 0, 0.1) rgba(0, 0, 0, 0.25);
*background-color: #08c;
/* Darken IE7 buttons by default so they stand out more given they won't have borders */
filter: progid:DXImageTransform.Microsoft.gradient(enabled = false);
}
.bootstrap-switch .bootstrap-switch-handle-on.bootstrap-switch-primary:hover,
.bootstrap-switch .bootstrap-switch-handle-off.bootstrap-switch-primary:hover,
.bootstrap-switch .bootstrap-switch-handle-on.bootstrap-switch-primary:focus,
.bootstrap-switch .bootstrap-switch-handle-off.bootstrap-switch-primary:focus,
.bootstrap-switch .bootstrap-switch-handle-on.bootstrap-switch-primary:active,
.bootstrap-switch .bootstrap-switch-handle-off.bootstrap-switch-primary:active,
.bootstrap-switch .bootstrap-switch-handle-on.bootstrap-switch-primary.active,
.bootstrap-switch .bootstrap-switch-handle-off.bootstrap-switch-primary.active,
.bootstrap-switch .bootstrap-switch-handle-on.bootstrap-switch-primary.disabled,
.bootstrap-switch .bootstrap-switch-handle-off.bootstrap-switch-primary.disabled,
.bootstrap-switch .bootstrap-switch-handle-on.bootstrap-switch-primary[disabled],
.bootstrap-switch .bootstrap-switch-handle-off.bootstrap-switch-primary[disabled] {
color: #fff;
background-color: #08c;
*background-color: #0077b3;
}
.bootstrap-switch .bootstrap-switch-handle-on.bootstrap-switch-primary:active,
.bootstrap-switch .bootstrap-switch-handle-off.bootstrap-switch-primary:active,
.bootstrap-switch .bootstrap-switch-handle-on.bootstrap-switch-primary.active,
.bootstrap-switch .bootstrap-switch-handle-off.bootstrap-switch-primary.active {
background-color: #006699 \9;
}
.bootstrap-switch .bootstrap-switch-handle-on.bootstrap-switch-info,
.bootstrap-switch .bootstrap-switch-handle-off.bootstrap-switch-info {
color: #fff;
text-shadow: 0 -1px 0 rgba(0, 0, 0, 0.25);
background-color: #41a7c5;
background-image: -moz-linear-gradient(top, #2f96b4, #5bc0de);
background-image: -webkit-gradient(linear, 0 0, 0 100%, from(#2f96b4), to(#5bc0de));
background-image: -webkit-linear-gradient(top, #2f96b4, #5bc0de);
background-image: -o-linear-gradient(top, #2f96b4, #5bc0de);
background-image: linear-gradient(to bottom, #2f96b4, #5bc0de);
background-repeat: repeat-x;
filter: progid:DXImageTransform.Microsoft.gradient(startColorstr='#ff2f96b4', endColorstr='#ff5bc0de', GradientType=0);
border-color: #5bc0de #5bc0de #28a1c5;
border-color: rgba(0, 0, 0, 0.1) rgba(0, 0, 0, 0.1) rgba(0, 0, 0, 0.25);
*background-color: #5bc0de;
/* Darken IE7 buttons by default so they stand out more given they won't have borders */
filter: progid:DXImageTransform.Microsoft.gradient(enabled = false);
}
.bootstrap-switch .bootstrap-switch-handle-on.bootstrap-switch-info:hover,
.bootstrap-switch .bootstrap-switch-handle-off.bootstrap-switch-info:hover,
.bootstrap-switch .bootstrap-switch-handle-on.bootstrap-switch-info:focus,
.bootstrap-switch .bootstrap-switch-handle-off.bootstrap-switch-info:focus,
.bootstrap-switch .bootstrap-switch-handle-on.bootstrap-switch-info:active,
.bootstrap-switch .bootstrap-switch-handle-off.bootstrap-switch-info:active,
.bootstrap-switch .bootstrap-switch-handle-on.bootstrap-switch-info.active,
.bootstrap-switch .bootstrap-switch-handle-off.bootstrap-switch-info.active,
.bootstrap-switch .bootstrap-switch-handle-on.bootstrap-switch-info.disabled,
.bootstrap-switch .bootstrap-switch-handle-off.bootstrap-switch-info.disabled,
.bootstrap-switch .bootstrap-switch-handle-on.bootstrap-switch-info[disabled],
.bootstrap-switch .bootstrap-switch-handle-off.bootstrap-switch-info[disabled] {
color: #fff;
background-color: #5bc0de;
*background-color: #46b8da;
}
.bootstrap-switch .bootstrap-switch-handle-on.bootstrap-switch-info:active,
.bootstrap-switch .bootstrap-switch-handle-off.bootstrap-switch-info:active,
.bootstrap-switch .bootstrap-switch-handle-on.bootstrap-switch-info.active,
.bootstrap-switch .bootstrap-switch-handle-off.bootstrap-switch-info.active {
background-color: #31b0d5 \9;
}
.bootstrap-switch .bootstrap-switch-handle-on.bootstrap-switch-success,
.bootstrap-switch .bootstrap-switch-handle-off.bootstrap-switch-success {
color: #fff;
text-shadow: 0 -1px 0 rgba(0, 0, 0, 0.25);
background-color: #58b058;
background-image: -moz-linear-gradient(top, #51a351, #62c462);
background-image: -webkit-gradient(linear, 0 0, 0 100%, from(#51a351), to(#62c462));
background-image: -webkit-linear-gradient(top, #51a351, #62c462);
background-image: -o-linear-gradient(top, #51a351, #62c462);
background-image: linear-gradient(to bottom, #51a351, #62c462);
background-repeat: repeat-x;
filter: progid:DXImageTransform.Microsoft.gradient(startColorstr='#ff51a351', endColorstr='#ff62c462', GradientType=0);
border-color: #62c462 #62c462 #3b9e3b;
border-color: rgba(0, 0, 0, 0.1) rgba(0, 0, 0, 0.1) rgba(0, 0, 0, 0.25);
*background-color: #62c462;
/* Darken IE7 buttons by default so they stand out more given they won't have borders */
filter: progid:DXImageTransform.Microsoft.gradient(enabled = false);
}
.bootstrap-switch .bootstrap-switch-handle-on.bootstrap-switch-success:hover,
.bootstrap-switch .bootstrap-switch-handle-off.bootstrap-switch-success:hover,
.bootstrap-switch .bootstrap-switch-handle-on.bootstrap-switch-success:focus,
.bootstrap-switch .bootstrap-switch-handle-off.bootstrap-switch-success:focus,
.bootstrap-switch .bootstrap-switch-handle-on.bootstrap-switch-success:active,
.bootstrap-switch .bootstrap-switch-handle-off.bootstrap-switch-success:active,
.bootstrap-switch .bootstrap-switch-handle-on.bootstrap-switch-success.active,
.bootstrap-switch .bootstrap-switch-handle-off.bootstrap-switch-success.active,
.bootstrap-switch .bootstrap-switch-handle-on.bootstrap-switch-success.disabled,
.bootstrap-switch .bootstrap-switch-handle-off.bootstrap-switch-success.disabled,
.bootstrap-switch .bootstrap-switch-handle-on.bootstrap-switch-success[disabled],
.bootstrap-switch .bootstrap-switch-handle-off.bootstrap-switch-success[disabled] {
color: #fff;
background-color: #62c462;
*background-color: #4fbd4f;
}
.bootstrap-switch .bootstrap-switch-handle-on.bootstrap-switch-success:active,
.bootstrap-switch .bootstrap-switch-handle-off.bootstrap-switch-success:active,
.bootstrap-switch .bootstrap-switch-handle-on.bootstrap-switch-success.active,
.bootstrap-switch .bootstrap-switch-handle-off.bootstrap-switch-success.active {
background-color: #42b142 \9;
}
.bootstrap-switch .bootstrap-switch-handle-on.bootstrap-switch-warning,
.bootstrap-switch .bootstrap-switch-handle-off.bootstrap-switch-warning {
color: #fff;
text-shadow: 0 -1px 0 rgba(0, 0, 0, 0.25);
background-color: #f9a123;
background-image: -moz-linear-gradient(top, #f89406, #fbb450);
background-image: -webkit-gradient(linear, 0 0, 0 100%, from(#f89406), to(#fbb450));
background-image: -webkit-linear-gradient(top, #f89406, #fbb450);
background-image: -o-linear-gradient(top, #f89406, #fbb450);
background-image: linear-gradient(to bottom, #f89406, #fbb450);
background-repeat: repeat-x;
filter: progid:DXImageTransform.Microsoft.gradient(startColorstr='#fff89406', endColorstr='#fffbb450', GradientType=0);
border-color: #fbb450 #fbb450 #f89406;
border-color: rgba(0, 0, 0, 0.1) rgba(0, 0, 0, 0.1) rgba(0, 0, 0, 0.25);
*background-color: #fbb450;
/* Darken IE7 buttons by default so they stand out more given they won't have borders */
filter: progid:DXImageTransform.Microsoft.gradient(enabled = false);
}
.bootstrap-switch .bootstrap-switch-handle-on.bootstrap-switch-warning:hover,
.bootstrap-switch .bootstrap-switch-handle-off.bootstrap-switch-warning:hover,
.bootstrap-switch .bootstrap-switch-handle-on.bootstrap-switch-warning:focus,
.bootstrap-switch .bootstrap-switch-handle-off.bootstrap-switch-warning:focus,
.bootstrap-switch .bootstrap-switch-handle-on.bootstrap-switch-warning:active,
.bootstrap-switch .bootstrap-switch-handle-off.bootstrap-switch-warning:active,
.bootstrap-switch .bootstrap-switch-handle-on.bootstrap-switch-warning.active,
.bootstrap-switch .bootstrap-switch-handle-off.bootstrap-switch-warning.active,
.bootstrap-switch .bootstrap-switch-handle-on.bootstrap-switch-warning.disabled,
.bootstrap-switch .bootstrap-switch-handle-off.bootstrap-switch-warning.disabled,
.bootstrap-switch .bootstrap-switch-handle-on.bootstrap-switch-warning[disabled],
.bootstrap-switch .bootstrap-switch-handle-off.bootstrap-switch-warning[disabled] {
color: #fff;
background-color: #fbb450;
*background-color: #faa937;
}
.bootstrap-switch .bootstrap-switch-handle-on.bootstrap-switch-warning:active,
.bootstrap-switch .bootstrap-switch-handle-off.bootstrap-switch-warning:active,
.bootstrap-switch .bootstrap-switch-handle-on.bootstrap-switch-warning.active,
.bootstrap-switch .bootstrap-switch-handle-off.bootstrap-switch-warning.active {
background-color: #fa9f1e \9;
}
.bootstrap-switch .bootstrap-switch-handle-on.bootstrap-switch-danger,
.bootstrap-switch .bootstrap-switch-handle-off.bootstrap-switch-danger {
color: #fff;
text-shadow: 0 -1px 0 rgba(0, 0, 0, 0.25);
background-color: #d14641;
background-image: -moz-linear-gradient(top, #bd362f, #ee5f5b);
background-image: -webkit-gradient(linear, 0 0, 0 100%, from(#bd362f), to(#ee5f5b));
background-image: -webkit-linear-gradient(top, #bd362f, #ee5f5b);
background-image: -o-linear-gradient(top, #bd362f, #ee5f5b);
background-image: linear-gradient(to bottom, #bd362f, #ee5f5b);
background-repeat: repeat-x;
filter: progid:DXImageTransform.Microsoft.gradient(startColorstr='#ffbd362f', endColorstr='#ffee5f5b', GradientType=0);
border-color: #ee5f5b #ee5f5b #e51d18;
border-color: rgba(0, 0, 0, 0.1) rgba(0, 0, 0, 0.1) rgba(0, 0, 0, 0.25);
*background-color: #ee5f5b;
/* Darken IE7 buttons by default so they stand out more given they won't have borders */
filter: progid:DXImageTransform.Microsoft.gradient(enabled = false);
}
.bootstrap-switch .bootstrap-switch-handle-on.bootstrap-switch-danger:hover,
.bootstrap-switch .bootstrap-switch-handle-off.bootstrap-switch-danger:hover,
.bootstrap-switch .bootstrap-switch-handle-on.bootstrap-switch-danger:focus,
.bootstrap-switch .bootstrap-switch-handle-off.bootstrap-switch-danger:focus,
.bootstrap-switch .bootstrap-switch-handle-on.bootstrap-switch-danger:active,
.bootstrap-switch .bootstrap-switch-handle-off.bootstrap-switch-danger:active,
.bootstrap-switch .bootstrap-switch-handle-on.bootstrap-switch-danger.active,
.bootstrap-switch .bootstrap-switch-handle-off.bootstrap-switch-danger.active,
.bootstrap-switch .bootstrap-switch-handle-on.bootstrap-switch-danger.disabled,
.bootstrap-switch .bootstrap-switch-handle-off.bootstrap-switch-danger.disabled,
.bootstrap-switch .bootstrap-switch-handle-on.bootstrap-switch-danger[disabled],
.bootstrap-switch .bootstrap-switch-handle-off.bootstrap-switch-danger[disabled] {
color: #fff;
background-color: #ee5f5b;
*background-color: #ec4844;
}
.bootstrap-switch .bootstrap-switch-handle-on.bootstrap-switch-danger:active,
.bootstrap-switch .bootstrap-switch-handle-off.bootstrap-switch-danger:active,
.bootstrap-switch .bootstrap-switch-handle-on.bootstrap-switch-danger.active,
.bootstrap-switch .bootstrap-switch-handle-off.bootstrap-switch-danger.active {
background-color: #e9322d \9;
}
.bootstrap-switch .bootstrap-switch-handle-on.bootstrap-switch-default,
.bootstrap-switch .bootstrap-switch-handle-off.bootstrap-switch-default {
color: #333;
text-shadow: 0 1px 1px rgba(255, 255, 255, 0.75);
background-color: #f0f0f0;
background-image: -moz-linear-gradient(top, #e6e6e6, #fff);
background-image: -webkit-gradient(linear, 0 0, 0 100%, from(#e6e6e6), to(#fff));
background-image: -webkit-linear-gradient(top, #e6e6e6, #fff);
background-image: -o-linear-gradient(top, #e6e6e6, #fff);
background-image: linear-gradient(to bottom, #e6e6e6, #fff);
background-repeat: repeat-x;
filter: progid:DXImageTransform.Microsoft.gradient(startColorstr='#ffe6e6e6', endColorstr='#ffffffff', GradientType=0);
border-color: #fff #fff #d9d9d9;
border-color: rgba(0, 0, 0, 0.1) rgba(0, 0, 0, 0.1) rgba(0, 0, 0, 0.25);
*background-color: #fff;
/* Darken IE7 buttons by default so they stand out more given they won't have borders */
filter: progid:DXImageTransform.Microsoft.gradient(enabled = false);
}
.bootstrap-switch .bootstrap-switch-handle-on.bootstrap-switch-default:hover,
.bootstrap-switch .bootstrap-switch-handle-off.bootstrap-switch-default:hover,
.bootstrap-switch .bootstrap-switch-handle-on.bootstrap-switch-default:focus,
.bootstrap-switch .bootstrap-switch-handle-off.bootstrap-switch-default:focus,
.bootstrap-switch .bootstrap-switch-handle-on.bootstrap-switch-default:active,
.bootstrap-switch .bootstrap-switch-handle-off.bootstrap-switch-default:active,
.bootstrap-switch .bootstrap-switch-handle-on.bootstrap-switch-default.active,
.bootstrap-switch .bootstrap-switch-handle-off.bootstrap-switch-default.active,
.bootstrap-switch .bootstrap-switch-handle-on.bootstrap-switch-default.disabled,
.bootstrap-switch .bootstrap-switch-handle-off.bootstrap-switch-default.disabled,
.bootstrap-switch .bootstrap-switch-handle-on.bootstrap-switch-default[disabled],
.bootstrap-switch .bootstrap-switch-handle-off.bootstrap-switch-default[disabled] {
color: #333;
background-color: #fff;
*background-color: #f2f2f2;
}
.bootstrap-switch .bootstrap-switch-handle-on.bootstrap-switch-default:active,
.bootstrap-switch .bootstrap-switch-handle-off.bootstrap-switch-default:active,
.bootstrap-switch .bootstrap-switch-handle-on.bootstrap-switch-default.active,
.bootstrap-switch .bootstrap-switch-handle-off.bootstrap-switch-default.active {
background-color: #e6e6e6 \9;
}
.bootstrap-switch .bootstrap-switch-label {
text-align: center;
margin-top: -1px;
margin-bottom: -1px;
z-index: 100;
border-left: 1px solid #ccc;
border-right: 1px solid #ccc;
color: #333;
text-shadow: 0 -1px 0 rgba(0, 0, 0, 0.25);
background-color: #f5f5f5;
background-image: -moz-linear-gradient(top, #fff, #e6e6e6);
background-image: -webkit-gradient(linear, 0 0, 0 100%, from(#fff), to(#e6e6e6));
background-image: -webkit-linear-gradient(top, #fff, #e6e6e6);
background-image: -o-linear-gradient(top, #fff, #e6e6e6);
background-image: linear-gradient(to bottom, #fff, #e6e6e6);
background-repeat: repeat-x;
filter: progid:DXImageTransform.Microsoft.gradient(startColorstr='#ffffffff', endColorstr='#ffe6e6e6', GradientType=0);
border-color: #e6e6e6 #e6e6e6 #bfbfbf;
border-color: rgba(0, 0, 0, 0.1) rgba(0, 0, 0, 0.1) rgba(0, 0, 0, 0.25);
*background-color: #e6e6e6;
/* Darken IE7 buttons by default so they stand out more given they won't have borders */
filter: progid:DXImageTransform.Microsoft.gradient(enabled = false);
}
.bootstrap-switch .bootstrap-switch-label:hover,
.bootstrap-switch .bootstrap-switch-label:focus,
.bootstrap-switch .bootstrap-switch-label:active,
.bootstrap-switch .bootstrap-switch-label.active,
.bootstrap-switch .bootstrap-switch-label.disabled,
.bootstrap-switch .bootstrap-switch-label[disabled] {
color: #333;
background-color: #e6e6e6;
*background-color: #d9d9d9;
}
.bootstrap-switch .bootstrap-switch-label:active,
.bootstrap-switch .bootstrap-switch-label.active {
background-color: #cccccc \9;
}
.bootstrap-switch span::before {
content: "\200b";
}
.bootstrap-switch .bootstrap-switch-handle-on {
-webkit-border-top-left-radius: 4px;
-moz-border-radius-topleft: 4px;
border-top-left-radius: 4px;
-webkit-border-bottom-left-radius: 4px;
-moz-border-radius-bottomleft: 4px;
border-bottom-left-radius: 4px;
}
.bootstrap-switch .bootstrap-switch-handle-off {
-webkit-border-top-right-radius: 4px;
-moz-border-radius-topright: 4px;
border-top-right-radius: 4px;
-webkit-border-bottom-right-radius: 4px;
-moz-border-radius-bottomright: 4px;
border-bottom-right-radius: 4px;
}
.bootstrap-switch input[type='radio'],
.bootstrap-switch input[type='checkbox'] {
position: absolute !important;
top: 0;
left: 0;
opacity: 0;
filter: alpha(opacity=0);
z-index: -1;
visibility: hidden;
}
.bootstrap-switch input[type='radio'].form-control,
.bootstrap-switch input[type='checkbox'].form-control {
height: auto;
}
.bootstrap-switch.bootstrap-switch-mini {
min-width: 71px;
}
.bootstrap-switch.bootstrap-switch-mini .bootstrap-switch-handle-on,
.bootstrap-switch.bootstrap-switch-mini .bootstrap-switch-handle-off,
.bootstrap-switch.bootstrap-switch-mini .bootstrap-switch-label {
padding: 3px 6px;
font-size: 10px;
line-height: 9px;
}
.bootstrap-switch.bootstrap-switch-small {
min-width: 79px;
}
.bootstrap-switch.bootstrap-switch-small .bootstrap-switch-handle-on,
.bootstrap-switch.bootstrap-switch-small .bootstrap-switch-handle-off,
.bootstrap-switch.bootstrap-switch-small .bootstrap-switch-label {
padding: 3px 6px;
font-size: 12px;
line-height: 18px;
}
.bootstrap-switch.bootstrap-switch-large {
min-width: 120px;
}
.bootstrap-switch.bootstrap-switch-large .bootstrap-switch-handle-on,
.bootstrap-switch.bootstrap-switch-large .bootstrap-switch-handle-off,
.bootstrap-switch.bootstrap-switch-large .bootstrap-switch-label {
padding: 9px 12px;
font-size: 16px;
line-height: normal;
}
.bootstrap-switch.bootstrap-switch-disabled,
.bootstrap-switch.bootstrap-switch-readonly,
.bootstrap-switch.bootstrap-switch-indeterminate {
cursor: default !important;
}
.bootstrap-switch.bootstrap-switch-disabled .bootstrap-switch-handle-on,
.bootstrap-switch.bootstrap-switch-readonly .bootstrap-switch-handle-on,
.bootstrap-switch.bootstrap-switch-indeterminate .bootstrap-switch-handle-on,
.bootstrap-switch.bootstrap-switch-disabled .bootstrap-switch-handle-off,
.bootstrap-switch.bootstrap-switch-readonly .bootstrap-switch-handle-off,
.bootstrap-switch.bootstrap-switch-indeterminate .bootstrap-switch-handle-off,
.bootstrap-switch.bootstrap-switch-disabled .bootstrap-switch-label,
.bootstrap-switch.bootstrap-switch-readonly .bootstrap-switch-label,
.bootstrap-switch.bootstrap-switch-indeterminate .bootstrap-switch-label {
opacity: 0.5;
filter: alpha(opacity=50);
cursor: default !important;
}
.bootstrap-switch.bootstrap-switch-animate .bootstrap-switch-container {
-webkit-transition: margin-left 0.5s;
-moz-transition: margin-left 0.5s;
-o-transition: margin-left 0.5s;
transition: margin-left 0.5s;
}
.bootstrap-switch.bootstrap-switch-inverse .bootstrap-switch-handle-on {
-webkit-border-top-left-radius: 0;
-moz-border-radius-topleft: 0;
border-top-left-radius: 0;
-webkit-border-bottom-left-radius: 0;
-moz-border-radius-bottomleft: 0;
border-bottom-left-radius: 0;
-webkit-border-top-right-radius: 4px;
-moz-border-radius-topright: 4px;
border-top-right-radius: 4px;
-webkit-border-bottom-right-radius: 4px;
-moz-border-radius-bottomright: 4px;
border-bottom-right-radius: 4px;
}
.bootstrap-switch.bootstrap-switch-inverse .bootstrap-switch-handle-off {
-webkit-border-top-right-radius: 0;
-moz-border-radius-topright: 0;
border-top-right-radius: 0;
-webkit-border-bottom-right-radius: 0;
-moz-border-radius-bottomright: 0;
border-bottom-right-radius: 0;
-webkit-border-top-left-radius: 4px;
-moz-border-radius-topleft: 4px;
border-top-left-radius: 4px;
-webkit-border-bottom-left-radius: 4px;
-moz-border-radius-bottomleft: 4px;
border-bottom-left-radius: 4px;
}
.bootstrap-switch.bootstrap-switch-focused {
border-color: rgba(82, 168, 236, 0.8);
outline: 0;
outline: thin dotted \9;
-webkit-box-shadow: inset 0 1px 1px rgba(0,0,0,.075), 0 0 8px rgba(82, 168, 236, .6);
-moz-box-shadow: inset 0 1px 1px rgba(0,0,0,.075), 0 0 8px rgba(82, 168, 236, .6);
box-shadow: inset 0 1px 1px rgba(0,0,0,.075), 0 0 8px rgba(82, 168, 236, .6);
}
.bootstrap-switch.bootstrap-switch-on .bootstrap-switch-label,
.bootstrap-switch.bootstrap-switch-inverse.bootstrap-switch-off .bootstrap-switch-label {
-webkit-border-top-right-radius: 4px;
-moz-border-radius-topright: 4px;
border-top-right-radius: 4px;
-webkit-border-bottom-right-radius: 4px;
-moz-border-radius-bottomright: 4px;
border-bottom-right-radius: 4px;
}
.bootstrap-switch.bootstrap-switch-off .bootstrap-switch-label,
.bootstrap-switch.bootstrap-switch-inverse.bootstrap-switch-on .bootstrap-switch-label {
-webkit-border-top-left-radius: 4px;
-moz-border-radius-topleft: 4px;
border-top-left-radius: 4px;
-webkit-border-bottom-left-radius: 4px;
-moz-border-radius-bottomleft: 4px;
border-bottom-left-radius: 4px;
}

File diff suppressed because one or more lines are too long

View file

@ -1,187 +0,0 @@
/**
* bootstrap-switch - Turn checkboxes and radio buttons into toggle switches.
*
* @version v3.3.4
* @homepage https://bttstrp.github.io/bootstrap-switch
* @author Mattia Larentis <mattia@larentis.eu> (http://larentis.eu)
* @license Apache-2.0
*/
.bootstrap-switch {
display: inline-block;
direction: ltr;
cursor: pointer;
border-radius: 4px;
border: 1px solid;
border-color: #ccc;
position: relative;
text-align: left;
overflow: hidden;
line-height: 8px;
z-index: 0;
-webkit-user-select: none;
-moz-user-select: none;
-ms-user-select: none;
user-select: none;
vertical-align: middle;
-webkit-transition: border-color ease-in-out .15s, box-shadow ease-in-out .15s;
-o-transition: border-color ease-in-out .15s, box-shadow ease-in-out .15s;
transition: border-color ease-in-out .15s, box-shadow ease-in-out .15s;
}
.bootstrap-switch .bootstrap-switch-container {
display: inline-block;
top: 0;
border-radius: 4px;
-webkit-transform: translate3d(0, 0, 0);
transform: translate3d(0, 0, 0);
}
.bootstrap-switch .bootstrap-switch-handle-on,
.bootstrap-switch .bootstrap-switch-handle-off,
.bootstrap-switch .bootstrap-switch-label {
-webkit-box-sizing: border-box;
-moz-box-sizing: border-box;
box-sizing: border-box;
cursor: pointer;
display: table-cell;
vertical-align: middle;
padding: 6px 12px;
font-size: 14px;
line-height: 20px;
}
.bootstrap-switch .bootstrap-switch-handle-on,
.bootstrap-switch .bootstrap-switch-handle-off {
text-align: center;
z-index: 1;
}
.bootstrap-switch .bootstrap-switch-handle-on.bootstrap-switch-primary,
.bootstrap-switch .bootstrap-switch-handle-off.bootstrap-switch-primary {
color: #fff;
background: #337ab7;
}
.bootstrap-switch .bootstrap-switch-handle-on.bootstrap-switch-info,
.bootstrap-switch .bootstrap-switch-handle-off.bootstrap-switch-info {
color: #fff;
background: #5bc0de;
}
.bootstrap-switch .bootstrap-switch-handle-on.bootstrap-switch-success,
.bootstrap-switch .bootstrap-switch-handle-off.bootstrap-switch-success {
color: #fff;
background: #5cb85c;
}
.bootstrap-switch .bootstrap-switch-handle-on.bootstrap-switch-warning,
.bootstrap-switch .bootstrap-switch-handle-off.bootstrap-switch-warning {
background: #f0ad4e;
color: #fff;
}
.bootstrap-switch .bootstrap-switch-handle-on.bootstrap-switch-danger,
.bootstrap-switch .bootstrap-switch-handle-off.bootstrap-switch-danger {
color: #fff;
background: #d9534f;
}
.bootstrap-switch .bootstrap-switch-handle-on.bootstrap-switch-default,
.bootstrap-switch .bootstrap-switch-handle-off.bootstrap-switch-default {
color: #000;
background: #eeeeee;
}
.bootstrap-switch .bootstrap-switch-label {
text-align: center;
margin-top: -1px;
margin-bottom: -1px;
z-index: 100;
color: #333;
background: #fff;
}
.bootstrap-switch span::before {
content: "\200b";
}
.bootstrap-switch .bootstrap-switch-handle-on {
border-bottom-left-radius: 3px;
border-top-left-radius: 3px;
}
.bootstrap-switch .bootstrap-switch-handle-off {
border-bottom-right-radius: 3px;
border-top-right-radius: 3px;
}
.bootstrap-switch input[type='radio'],
.bootstrap-switch input[type='checkbox'] {
position: absolute !important;
top: 0;
left: 0;
margin: 0;
z-index: -1;
opacity: 0;
filter: alpha(opacity=0);
visibility: hidden;
}
.bootstrap-switch.bootstrap-switch-mini .bootstrap-switch-handle-on,
.bootstrap-switch.bootstrap-switch-mini .bootstrap-switch-handle-off,
.bootstrap-switch.bootstrap-switch-mini .bootstrap-switch-label {
padding: 1px 5px;
font-size: 12px;
line-height: 1.5;
}
.bootstrap-switch.bootstrap-switch-small .bootstrap-switch-handle-on,
.bootstrap-switch.bootstrap-switch-small .bootstrap-switch-handle-off,
.bootstrap-switch.bootstrap-switch-small .bootstrap-switch-label {
padding: 5px 10px;
font-size: 12px;
line-height: 1.5;
}
.bootstrap-switch.bootstrap-switch-large .bootstrap-switch-handle-on,
.bootstrap-switch.bootstrap-switch-large .bootstrap-switch-handle-off,
.bootstrap-switch.bootstrap-switch-large .bootstrap-switch-label {
padding: 6px 16px;
font-size: 18px;
line-height: 1.3333333;
}
.bootstrap-switch.bootstrap-switch-disabled,
.bootstrap-switch.bootstrap-switch-readonly,
.bootstrap-switch.bootstrap-switch-indeterminate {
cursor: default !important;
}
.bootstrap-switch.bootstrap-switch-disabled .bootstrap-switch-handle-on,
.bootstrap-switch.bootstrap-switch-readonly .bootstrap-switch-handle-on,
.bootstrap-switch.bootstrap-switch-indeterminate .bootstrap-switch-handle-on,
.bootstrap-switch.bootstrap-switch-disabled .bootstrap-switch-handle-off,
.bootstrap-switch.bootstrap-switch-readonly .bootstrap-switch-handle-off,
.bootstrap-switch.bootstrap-switch-indeterminate .bootstrap-switch-handle-off,
.bootstrap-switch.bootstrap-switch-disabled .bootstrap-switch-label,
.bootstrap-switch.bootstrap-switch-readonly .bootstrap-switch-label,
.bootstrap-switch.bootstrap-switch-indeterminate .bootstrap-switch-label {
opacity: 0.5;
filter: alpha(opacity=50);
cursor: default !important;
}
.bootstrap-switch.bootstrap-switch-animate .bootstrap-switch-container {
-webkit-transition: margin-left 0.5s;
-o-transition: margin-left 0.5s;
transition: margin-left 0.5s;
}
.bootstrap-switch.bootstrap-switch-inverse .bootstrap-switch-handle-on {
border-bottom-left-radius: 0;
border-top-left-radius: 0;
border-bottom-right-radius: 3px;
border-top-right-radius: 3px;
}
.bootstrap-switch.bootstrap-switch-inverse .bootstrap-switch-handle-off {
border-bottom-right-radius: 0;
border-top-right-radius: 0;
border-bottom-left-radius: 3px;
border-top-left-radius: 3px;
}
.bootstrap-switch.bootstrap-switch-focused {
border-color: #66afe9;
outline: 0;
-webkit-box-shadow: inset 0 1px 1px rgba(0,0,0,.075), 0 0 8px rgba(102, 175, 233, 0.6);
box-shadow: inset 0 1px 1px rgba(0,0,0,.075), 0 0 8px rgba(102, 175, 233, 0.6);
}
.bootstrap-switch.bootstrap-switch-on .bootstrap-switch-label,
.bootstrap-switch.bootstrap-switch-inverse.bootstrap-switch-off .bootstrap-switch-label {
border-bottom-right-radius: 3px;
border-top-right-radius: 3px;
}
.bootstrap-switch.bootstrap-switch-off .bootstrap-switch-label,
.bootstrap-switch.bootstrap-switch-inverse.bootstrap-switch-on .bootstrap-switch-label {
border-bottom-left-radius: 3px;
border-top-left-radius: 3px;
}

File diff suppressed because one or more lines are too long

View file

@ -1,784 +0,0 @@
/**
* bootstrap-switch - Turn checkboxes and radio buttons into toggle switches.
*
* @version v3.3.4
* @homepage https://bttstrp.github.io/bootstrap-switch
* @author Mattia Larentis <mattia@larentis.eu> (http://larentis.eu)
* @license Apache-2.0
*/
(function (global, factory) {
if (typeof define === "function" && define.amd) {
define(['jquery'], factory);
} else if (typeof exports !== "undefined") {
factory(require('jquery'));
} else {
var mod = {
exports: {}
};
factory(global.jquery);
global.bootstrapSwitch = mod.exports;
}
})(this, function (_jquery) {
'use strict';
var _jquery2 = _interopRequireDefault(_jquery);
function _interopRequireDefault(obj) {
return obj && obj.__esModule ? obj : {
default: obj
};
}
var _extends = Object.assign || function (target) {
for (var i = 1; i < arguments.length; i++) {
var source = arguments[i];
for (var key in source) {
if (Object.prototype.hasOwnProperty.call(source, key)) {
target[key] = source[key];
}
}
}
return target;
};
function _classCallCheck(instance, Constructor) {
if (!(instance instanceof Constructor)) {
throw new TypeError("Cannot call a class as a function");
}
}
var _createClass = function () {
function defineProperties(target, props) {
for (var i = 0; i < props.length; i++) {
var descriptor = props[i];
descriptor.enumerable = descriptor.enumerable || false;
descriptor.configurable = true;
if ("value" in descriptor) descriptor.writable = true;
Object.defineProperty(target, descriptor.key, descriptor);
}
}
return function (Constructor, protoProps, staticProps) {
if (protoProps) defineProperties(Constructor.prototype, protoProps);
if (staticProps) defineProperties(Constructor, staticProps);
return Constructor;
};
}();
var $ = _jquery2.default || window.jQuery || window.$;
var BootstrapSwitch = function () {
function BootstrapSwitch(element) {
var _this = this;
var options = arguments.length > 1 && arguments[1] !== undefined ? arguments[1] : {};
_classCallCheck(this, BootstrapSwitch);
this.$element = $(element);
this.options = $.extend({}, $.fn.bootstrapSwitch.defaults, this._getElementOptions(), options);
this.prevOptions = {};
this.$wrapper = $('<div>', {
class: function _class() {
var classes = [];
classes.push(_this.options.state ? 'on' : 'off');
if (_this.options.size) {
classes.push(_this.options.size);
}
if (_this.options.disabled) {
classes.push('disabled');
}
if (_this.options.readonly) {
classes.push('readonly');
}
if (_this.options.indeterminate) {
classes.push('indeterminate');
}
if (_this.options.inverse) {
classes.push('inverse');
}
if (_this.$element.attr('id')) {
classes.push('id-' + _this.$element.attr('id'));
}
return classes.map(_this._getClass.bind(_this)).concat([_this.options.baseClass], _this._getClasses(_this.options.wrapperClass)).join(' ');
}
});
this.$container = $('<div>', { class: this._getClass('container') });
this.$on = $('<span>', {
html: this.options.onText,
class: this._getClass('handle-on') + ' ' + this._getClass(this.options.onColor)
});
this.$off = $('<span>', {
html: this.options.offText,
class: this._getClass('handle-off') + ' ' + this._getClass(this.options.offColor)
});
this.$label = $('<span>', {
html: this.options.labelText,
class: this._getClass('label')
});
this.$element.on('init.bootstrapSwitch', this.options.onInit.bind(this, element));
this.$element.on('switchChange.bootstrapSwitch', function () {
for (var _len = arguments.length, args = Array(_len), _key = 0; _key < _len; _key++) {
args[_key] = arguments[_key];
}
if (_this.options.onSwitchChange.apply(element, args) === false) {
if (_this.$element.is(':radio')) {
$('[name="' + _this.$element.attr('name') + '"]').trigger('previousState.bootstrapSwitch', true);
} else {
_this.$element.trigger('previousState.bootstrapSwitch', true);
}
}
});
this.$container = this.$element.wrap(this.$container).parent();
this.$wrapper = this.$container.wrap(this.$wrapper).parent();
this.$element.before(this.options.inverse ? this.$off : this.$on).before(this.$label).before(this.options.inverse ? this.$on : this.$off);
if (this.options.indeterminate) {
this.$element.prop('indeterminate', true);
}
this._init();
this._elementHandlers();
this._handleHandlers();
this._labelHandlers();
this._formHandler();
this._externalLabelHandler();
this.$element.trigger('init.bootstrapSwitch', this.options.state);
}
_createClass(BootstrapSwitch, [{
key: 'setPrevOptions',
value: function setPrevOptions() {
this.prevOptions = _extends({}, this.options);
}
}, {
key: 'state',
value: function state(value, skip) {
if (typeof value === 'undefined') {
return this.options.state;
}
if (this.options.disabled || this.options.readonly || this.options.state && !this.options.radioAllOff && this.$element.is(':radio')) {
return this.$element;
}
if (this.$element.is(':radio')) {
$('[name="' + this.$element.attr('name') + '"]').trigger('setPreviousOptions.bootstrapSwitch');
} else {
this.$element.trigger('setPreviousOptions.bootstrapSwitch');
}
if (this.options.indeterminate) {
this.indeterminate(false);
}
this.$element.prop('checked', Boolean(value)).trigger('change.bootstrapSwitch', skip);
return this.$element;
}
}, {
key: 'toggleState',
value: function toggleState(skip) {
if (this.options.disabled || this.options.readonly) {
return this.$element;
}
if (this.options.indeterminate) {
this.indeterminate(false);
return this.state(true);
} else {
return this.$element.prop('checked', !this.options.state).trigger('change.bootstrapSwitch', skip);
}
}
}, {
key: 'size',
value: function size(value) {
if (typeof value === 'undefined') {
return this.options.size;
}
if (this.options.size != null) {
this.$wrapper.removeClass(this._getClass(this.options.size));
}
if (value) {
this.$wrapper.addClass(this._getClass(value));
}
this._width();
this._containerPosition();
this.options.size = value;
return this.$element;
}
}, {
key: 'animate',
value: function animate(value) {
if (typeof value === 'undefined') {
return this.options.animate;
}
if (this.options.animate === Boolean(value)) {
return this.$element;
}
return this.toggleAnimate();
}
}, {
key: 'toggleAnimate',
value: function toggleAnimate() {
this.options.animate = !this.options.animate;
this.$wrapper.toggleClass(this._getClass('animate'));
return this.$element;
}
}, {
key: 'disabled',
value: function disabled(value) {
if (typeof value === 'undefined') {
return this.options.disabled;
}
if (this.options.disabled === Boolean(value)) {
return this.$element;
}
return this.toggleDisabled();
}
}, {
key: 'toggleDisabled',
value: function toggleDisabled() {
this.options.disabled = !this.options.disabled;
this.$element.prop('disabled', this.options.disabled);
this.$wrapper.toggleClass(this._getClass('disabled'));
return this.$element;
}
}, {
key: 'readonly',
value: function readonly(value) {
if (typeof value === 'undefined') {
return this.options.readonly;
}
if (this.options.readonly === Boolean(value)) {
return this.$element;
}
return this.toggleReadonly();
}
}, {
key: 'toggleReadonly',
value: function toggleReadonly() {
this.options.readonly = !this.options.readonly;
this.$element.prop('readonly', this.options.readonly);
this.$wrapper.toggleClass(this._getClass('readonly'));
return this.$element;
}
}, {
key: 'indeterminate',
value: function indeterminate(value) {
if (typeof value === 'undefined') {
return this.options.indeterminate;
}
if (this.options.indeterminate === Boolean(value)) {
return this.$element;
}
return this.toggleIndeterminate();
}
}, {
key: 'toggleIndeterminate',
value: function toggleIndeterminate() {
this.options.indeterminate = !this.options.indeterminate;
this.$element.prop('indeterminate', this.options.indeterminate);
this.$wrapper.toggleClass(this._getClass('indeterminate'));
this._containerPosition();
return this.$element;
}
}, {
key: 'inverse',
value: function inverse(value) {
if (typeof value === 'undefined') {
return this.options.inverse;
}
if (this.options.inverse === Boolean(value)) {
return this.$element;
}
return this.toggleInverse();
}
}, {
key: 'toggleInverse',
value: function toggleInverse() {
this.$wrapper.toggleClass(this._getClass('inverse'));
var $on = this.$on.clone(true);
var $off = this.$off.clone(true);
this.$on.replaceWith($off);
this.$off.replaceWith($on);
this.$on = $off;
this.$off = $on;
this.options.inverse = !this.options.inverse;
return this.$element;
}
}, {
key: 'onColor',
value: function onColor(value) {
if (typeof value === 'undefined') {
return this.options.onColor;
}
if (this.options.onColor) {
this.$on.removeClass(this._getClass(this.options.onColor));
}
this.$on.addClass(this._getClass(value));
this.options.onColor = value;
return this.$element;
}
}, {
key: 'offColor',
value: function offColor(value) {
if (typeof value === 'undefined') {
return this.options.offColor;
}
if (this.options.offColor) {
this.$off.removeClass(this._getClass(this.options.offColor));
}
this.$off.addClass(this._getClass(value));
this.options.offColor = value;
return this.$element;
}
}, {
key: 'onText',
value: function onText(value) {
if (typeof value === 'undefined') {
return this.options.onText;
}
this.$on.html(value);
this._width();
this._containerPosition();
this.options.onText = value;
return this.$element;
}
}, {
key: 'offText',
value: function offText(value) {
if (typeof value === 'undefined') {
return this.options.offText;
}
this.$off.html(value);
this._width();
this._containerPosition();
this.options.offText = value;
return this.$element;
}
}, {
key: 'labelText',
value: function labelText(value) {
if (typeof value === 'undefined') {
return this.options.labelText;
}
this.$label.html(value);
this._width();
this.options.labelText = value;
return this.$element;
}
}, {
key: 'handleWidth',
value: function handleWidth(value) {
if (typeof value === 'undefined') {
return this.options.handleWidth;
}
this.options.handleWidth = value;
this._width();
this._containerPosition();
return this.$element;
}
}, {
key: 'labelWidth',
value: function labelWidth(value) {
if (typeof value === 'undefined') {
return this.options.labelWidth;
}
this.options.labelWidth = value;
this._width();
this._containerPosition();
return this.$element;
}
}, {
key: 'baseClass',
value: function baseClass(value) {
return this.options.baseClass;
}
}, {
key: 'wrapperClass',
value: function wrapperClass(value) {
if (typeof value === 'undefined') {
return this.options.wrapperClass;
}
if (!value) {
value = $.fn.bootstrapSwitch.defaults.wrapperClass;
}
this.$wrapper.removeClass(this._getClasses(this.options.wrapperClass).join(' '));
this.$wrapper.addClass(this._getClasses(value).join(' '));
this.options.wrapperClass = value;
return this.$element;
}
}, {
key: 'radioAllOff',
value: function radioAllOff(value) {
if (typeof value === 'undefined') {
return this.options.radioAllOff;
}
var val = Boolean(value);
if (this.options.radioAllOff === val) {
return this.$element;
}
this.options.radioAllOff = val;
return this.$element;
}
}, {
key: 'onInit',
value: function onInit(value) {
if (typeof value === 'undefined') {
return this.options.onInit;
}
if (!value) {
value = $.fn.bootstrapSwitch.defaults.onInit;
}
this.options.onInit = value;
return this.$element;
}
}, {
key: 'onSwitchChange',
value: function onSwitchChange(value) {
if (typeof value === 'undefined') {
return this.options.onSwitchChange;
}
if (!value) {
value = $.fn.bootstrapSwitch.defaults.onSwitchChange;
}
this.options.onSwitchChange = value;
return this.$element;
}
}, {
key: 'destroy',
value: function destroy() {
var $form = this.$element.closest('form');
if ($form.length) {
$form.off('reset.bootstrapSwitch').removeData('bootstrap-switch');
}
this.$container.children().not(this.$element).remove();
this.$element.unwrap().unwrap().off('.bootstrapSwitch').removeData('bootstrap-switch');
return this.$element;
}
}, {
key: '_getElementOptions',
value: function _getElementOptions() {
return {
state: this.$element.is(':checked'),
size: this.$element.data('size'),
animate: this.$element.data('animate'),
disabled: this.$element.is(':disabled'),
readonly: this.$element.is('[readonly]'),
indeterminate: this.$element.data('indeterminate'),
inverse: this.$element.data('inverse'),
radioAllOff: this.$element.data('radio-all-off'),
onColor: this.$element.data('on-color'),
offColor: this.$element.data('off-color'),
onText: this.$element.data('on-text'),
offText: this.$element.data('off-text'),
labelText: this.$element.data('label-text'),
handleWidth: this.$element.data('handle-width'),
labelWidth: this.$element.data('label-width'),
baseClass: this.$element.data('base-class'),
wrapperClass: this.$element.data('wrapper-class')
};
}
}, {
key: '_width',
value: function _width() {
var _this2 = this;
var $handles = this.$on.add(this.$off).add(this.$label).css('width', '');
var handleWidth = this.options.handleWidth === 'auto' ? Math.round(Math.max(this.$on.width(), this.$off.width())) : this.options.handleWidth;
$handles.width(handleWidth);
this.$label.width(function (index, width) {
if (_this2.options.labelWidth !== 'auto') {
return _this2.options.labelWidth;
}
if (width < handleWidth) {
return handleWidth;
}
return width;
});
this._handleWidth = this.$on.outerWidth();
this._labelWidth = this.$label.outerWidth();
this.$container.width(this._handleWidth * 2 + this._labelWidth);
return this.$wrapper.width(this._handleWidth + this._labelWidth);
}
}, {
key: '_containerPosition',
value: function _containerPosition() {
var _this3 = this;
var state = arguments.length > 0 && arguments[0] !== undefined ? arguments[0] : this.options.state;
var callback = arguments[1];
this.$container.css('margin-left', function () {
var values = [0, '-' + _this3._handleWidth + 'px'];
if (_this3.options.indeterminate) {
return '-' + _this3._handleWidth / 2 + 'px';
}
if (state) {
if (_this3.options.inverse) {
return values[1];
} else {
return values[0];
}
} else {
if (_this3.options.inverse) {
return values[0];
} else {
return values[1];
}
}
});
}
}, {
key: '_init',
value: function _init() {
var _this4 = this;
var init = function init() {
_this4.setPrevOptions();
_this4._width();
_this4._containerPosition();
setTimeout(function () {
if (_this4.options.animate) {
return _this4.$wrapper.addClass(_this4._getClass('animate'));
}
}, 50);
};
if (this.$wrapper.is(':visible')) {
init();
return;
}
var initInterval = window.setInterval(function () {
if (_this4.$wrapper.is(':visible')) {
init();
return window.clearInterval(initInterval);
}
}, 50);
}
}, {
key: '_elementHandlers',
value: function _elementHandlers() {
var _this5 = this;
return this.$element.on({
'setPreviousOptions.bootstrapSwitch': this.setPrevOptions.bind(this),
'previousState.bootstrapSwitch': function previousStateBootstrapSwitch() {
_this5.options = _this5.prevOptions;
if (_this5.options.indeterminate) {
_this5.$wrapper.addClass(_this5._getClass('indeterminate'));
}
_this5.$element.prop('checked', _this5.options.state).trigger('change.bootstrapSwitch', true);
},
'change.bootstrapSwitch': function changeBootstrapSwitch(event, skip) {
event.preventDefault();
event.stopImmediatePropagation();
var state = _this5.$element.is(':checked');
_this5._containerPosition(state);
if (state === _this5.options.state) {
return;
}
_this5.options.state = state;
_this5.$wrapper.toggleClass(_this5._getClass('off')).toggleClass(_this5._getClass('on'));
if (!skip) {
if (_this5.$element.is(':radio')) {
$('[name="' + _this5.$element.attr('name') + '"]').not(_this5.$element).prop('checked', false).trigger('change.bootstrapSwitch', true);
}
_this5.$element.trigger('switchChange.bootstrapSwitch', [state]);
}
},
'focus.bootstrapSwitch': function focusBootstrapSwitch(event) {
event.preventDefault();
_this5.$wrapper.addClass(_this5._getClass('focused'));
},
'blur.bootstrapSwitch': function blurBootstrapSwitch(event) {
event.preventDefault();
_this5.$wrapper.removeClass(_this5._getClass('focused'));
},
'keydown.bootstrapSwitch': function keydownBootstrapSwitch(event) {
if (!event.which || _this5.options.disabled || _this5.options.readonly) {
return;
}
if (event.which === 37 || event.which === 39) {
event.preventDefault();
event.stopImmediatePropagation();
_this5.state(event.which === 39);
}
}
});
}
}, {
key: '_handleHandlers',
value: function _handleHandlers() {
var _this6 = this;
this.$on.on('click.bootstrapSwitch', function (event) {
event.preventDefault();
event.stopPropagation();
_this6.state(false);
return _this6.$element.trigger('focus.bootstrapSwitch');
});
return this.$off.on('click.bootstrapSwitch', function (event) {
event.preventDefault();
event.stopPropagation();
_this6.state(true);
return _this6.$element.trigger('focus.bootstrapSwitch');
});
}
}, {
key: '_labelHandlers',
value: function _labelHandlers() {
var _this7 = this;
var handlers = {
click: function click(event) {
event.stopPropagation();
},
'mousedown.bootstrapSwitch touchstart.bootstrapSwitch': function mousedownBootstrapSwitchTouchstartBootstrapSwitch(event) {
if (_this7._dragStart || _this7.options.disabled || _this7.options.readonly) {
return;
}
event.preventDefault();
event.stopPropagation();
_this7._dragStart = (event.pageX || event.originalEvent.touches[0].pageX) - parseInt(_this7.$container.css('margin-left'), 10);
if (_this7.options.animate) {
_this7.$wrapper.removeClass(_this7._getClass('animate'));
}
_this7.$element.trigger('focus.bootstrapSwitch');
},
'mousemove.bootstrapSwitch touchmove.bootstrapSwitch': function mousemoveBootstrapSwitchTouchmoveBootstrapSwitch(event) {
if (_this7._dragStart == null) {
return;
}
var difference = (event.pageX || event.originalEvent.touches[0].pageX) - _this7._dragStart;
event.preventDefault();
if (difference < -_this7._handleWidth || difference > 0) {
return;
}
_this7._dragEnd = difference;
_this7.$container.css('margin-left', _this7._dragEnd + 'px');
},
'mouseup.bootstrapSwitch touchend.bootstrapSwitch': function mouseupBootstrapSwitchTouchendBootstrapSwitch(event) {
if (!_this7._dragStart) {
return;
}
event.preventDefault();
if (_this7.options.animate) {
_this7.$wrapper.addClass(_this7._getClass('animate'));
}
if (_this7._dragEnd) {
var state = _this7._dragEnd > -(_this7._handleWidth / 2);
_this7._dragEnd = false;
_this7.state(_this7.options.inverse ? !state : state);
} else {
_this7.state(!_this7.options.state);
}
_this7._dragStart = false;
},
'mouseleave.bootstrapSwitch': function mouseleaveBootstrapSwitch() {
_this7.$label.trigger('mouseup.bootstrapSwitch');
}
};
this.$label.on(handlers);
}
}, {
key: '_externalLabelHandler',
value: function _externalLabelHandler() {
var _this8 = this;
var $externalLabel = this.$element.closest('label');
$externalLabel.on('click', function (event) {
event.preventDefault();
event.stopImmediatePropagation();
if (event.target === $externalLabel[0]) {
_this8.toggleState();
}
});
}
}, {
key: '_formHandler',
value: function _formHandler() {
var $form = this.$element.closest('form');
if ($form.data('bootstrap-switch')) {
return;
}
$form.on('reset.bootstrapSwitch', function () {
window.setTimeout(function () {
$form.find('input').filter(function () {
return $(this).data('bootstrap-switch');
}).each(function () {
return $(this).bootstrapSwitch('state', this.checked);
});
}, 1);
}).data('bootstrap-switch', true);
}
}, {
key: '_getClass',
value: function _getClass(name) {
return this.options.baseClass + '-' + name;
}
}, {
key: '_getClasses',
value: function _getClasses(classes) {
if (!$.isArray(classes)) {
return [this._getClass(classes)];
}
return classes.map(this._getClass.bind(this));
}
}]);
return BootstrapSwitch;
}();
$.fn.bootstrapSwitch = function (option) {
for (var _len2 = arguments.length, args = Array(_len2 > 1 ? _len2 - 1 : 0), _key2 = 1; _key2 < _len2; _key2++) {
args[_key2 - 1] = arguments[_key2];
}
function reducer(ret, next) {
var $this = $(next);
var existingData = $this.data('bootstrap-switch');
var data = existingData || new BootstrapSwitch(next, option);
if (!existingData) {
$this.data('bootstrap-switch', data);
}
if (typeof option === 'string') {
return data[option].apply(data, args);
}
return ret;
}
return Array.prototype.reduce.call(this, reducer, this);
};
$.fn.bootstrapSwitch.Constructor = BootstrapSwitch;
$.fn.bootstrapSwitch.defaults = {
state: true,
size: null,
animate: true,
disabled: false,
readonly: false,
indeterminate: false,
inverse: false,
radioAllOff: false,
onColor: 'primary',
offColor: 'default',
onText: 'ON',
offText: 'OFF',
labelText: '&nbsp',
handleWidth: 'auto',
labelWidth: 'auto',
baseClass: 'bootstrap-switch',
wrapperClass: 'wrapper',
onInit: function onInit() {},
onSwitchChange: function onSwitchChange() {}
};
});

File diff suppressed because one or more lines are too long

File diff suppressed because it is too large Load diff

File diff suppressed because one or more lines are too long

File diff suppressed because one or more lines are too long

File diff suppressed because one or more lines are too long

File diff suppressed because it is too large Load diff

File diff suppressed because one or more lines are too long

File diff suppressed because one or more lines are too long

File diff suppressed because one or more lines are too long

View file

@ -1,87 +0,0 @@
/*
* Bootstrap Duallistbox - v4.0.2
* A responsive dual listbox widget optimized for Twitter Bootstrap. It works on all modern browsers and on touch devices.
* http://www.virtuosoft.eu/code/bootstrap-duallistbox/
*
* Made by István Ujj-Mészáros
* Under Apache License v2.0 License
*/
.bootstrap-duallistbox-container .buttons {
width: 100%;
margin-bottom: -1px;
}
.bootstrap-duallistbox-container label {
display: block;
}
.bootstrap-duallistbox-container .info {
display: inline-block;
margin-bottom: 5px;
font-size: 11px;
}
.bootstrap-duallistbox-container .clear1,
.bootstrap-duallistbox-container .clear2 {
display: none;
font-size: 10px;
}
.bootstrap-duallistbox-container .box1.filtered .clear1,
.bootstrap-duallistbox-container .box2.filtered .clear2 {
display: inline-block;
}
.bootstrap-duallistbox-container .move,
.bootstrap-duallistbox-container .remove {
width: 50%;
box-sizing: content-box;
}
.bootstrap-duallistbox-container .btn-group .btn {
border-bottom-left-radius: 0;
border-bottom-right-radius: 0;
}
.bootstrap-duallistbox-container:not(.moveonselect) select {
border-top-left-radius: 0;
border-top-right-radius: 0;
}
.bootstrap-duallistbox-container .moveall,
.bootstrap-duallistbox-container .removeall {
width: 50%;
box-sizing: content-box;
}
.bootstrap-duallistbox-container.bs2compatible .btn-group > .btn + .btn {
margin-left: 0;
}
.bootstrap-duallistbox-container select {
width: 100%;
height: 300px;
padding: 0;
}
.bootstrap-duallistbox-container .filter {
display: inline-block;
width: 100%;
height: 31px;
margin: 0 0 5px 0;
-webkit-box-sizing: border-box;
-moz-box-sizing: border-box;
box-sizing: border-box;
}
.bootstrap-duallistbox-container .filter.placeholder {
color: #aaa;
}
.bootstrap-duallistbox-container.moveonselect .move,
.bootstrap-duallistbox-container.moveonselect .remove {
display:none;
}
.bootstrap-duallistbox-container.moveonselect .moveall,
.bootstrap-duallistbox-container.moveonselect .removeall {
width: 100%;
}

View file

@ -1 +0,0 @@
.bootstrap-duallistbox-container .buttons{width:100%;margin-bottom:-1px}.bootstrap-duallistbox-container label{display:block}.bootstrap-duallistbox-container .info{display:inline-block;margin-bottom:5px;font-size:11px}.bootstrap-duallistbox-container .clear1,.bootstrap-duallistbox-container .clear2{display:none;font-size:10px}.bootstrap-duallistbox-container .box1.filtered .clear1,.bootstrap-duallistbox-container .box2.filtered .clear2{display:inline-block}.bootstrap-duallistbox-container .move,.bootstrap-duallistbox-container .remove{width:50%;box-sizing:content-box}.bootstrap-duallistbox-container .btn-group .btn{border-bottom-left-radius:0;border-bottom-right-radius:0}.bootstrap-duallistbox-container:not(.moveonselect) select{border-top-left-radius:0;border-top-right-radius:0}.bootstrap-duallistbox-container .moveall,.bootstrap-duallistbox-container .removeall{width:50%;box-sizing:content-box}.bootstrap-duallistbox-container.bs2compatible .btn-group>.btn+.btn{margin-left:0}.bootstrap-duallistbox-container select{width:100%;height:300px;padding:0}.bootstrap-duallistbox-container .filter{display:inline-block;width:100%;height:31px;margin:0 0 5px 0;-webkit-box-sizing:border-box;-moz-box-sizing:border-box;box-sizing:border-box}.bootstrap-duallistbox-container .filter.placeholder{color:#aaa}.bootstrap-duallistbox-container.moveonselect .move,.bootstrap-duallistbox-container.moveonselect .remove{display:none}.bootstrap-duallistbox-container.moveonselect .moveall,.bootstrap-duallistbox-container.moveonselect .removeall{width:100%}

View file

@ -1,893 +0,0 @@
/*
* Bootstrap Duallistbox - v4.0.2
* A responsive dual listbox widget optimized for Twitter Bootstrap. It works on all modern browsers and on touch devices.
* http://www.virtuosoft.eu/code/bootstrap-duallistbox/
*
* Made by István Ujj-Mészáros
* Under Apache License v2.0 License
*/
(function(factory) {
if (typeof define === 'function' && define.amd) {
define(['jquery'], factory);
} else if (typeof module === 'object' && module.exports) {
module.exports = function(root, jQuery) {
if (jQuery === undefined) {
if (typeof window !== 'undefined') {
jQuery = require('jquery');
}
else {
jQuery = require('jquery')(root);
}
}
factory(jQuery);
return jQuery;
};
} else {
factory(jQuery);
}
}(function($) {
// Create the defaults once
var pluginName = 'bootstrapDualListbox',
defaults = {
filterTextClear: 'show all',
filterPlaceHolder: 'Filter',
moveSelectedLabel: 'Move selected',
moveAllLabel: 'Move all',
removeSelectedLabel: 'Remove selected',
removeAllLabel: 'Remove all',
moveOnSelect: true, // true/false (forced true on androids, see the comment later)
moveOnDoubleClick: true, // true/false (forced false on androids, cause moveOnSelect is forced to true)
preserveSelectionOnMove: false, // 'all' / 'moved' / false
selectedListLabel: false, // 'string', false
nonSelectedListLabel: false, // 'string', false
helperSelectNamePostfix: '_helper', // 'string_of_postfix' / false
selectorMinimalHeight: 100,
showFilterInputs: true, // whether to show filter inputs
nonSelectedFilter: '', // string, filter the non selected options
selectedFilter: '', // string, filter the selected options
infoText: 'Showing all {0}', // text when all options are visible / false for no info text
infoTextFiltered: '<span class="badge badge-warning">Filtered</span> {0} from {1}', // when not all of the options are visible due to the filter
infoTextEmpty: 'Empty list', // when there are no options present in the list
filterOnValues: false, // filter by selector's values, boolean
sortByInputOrder: false,
eventMoveOverride: false, // boolean, allows user to unbind default event behaviour and run their own instead
eventMoveAllOverride: false, // boolean, allows user to unbind default event behaviour and run their own instead
eventRemoveOverride: false, // boolean, allows user to unbind default event behaviour and run their own instead
eventRemoveAllOverride: false, // boolean, allows user to unbind default event behaviour and run their own instead
btnClass: 'btn-outline-secondary', // sets the button style class for all the buttons
btnMoveText: '&gt;', // string, sets the text for the "Move" button
btnRemoveText: '&lt;', // string, sets the text for the "Remove" button
btnMoveAllText: '&gt;&gt;', // string, sets the text for the "Move All" button
btnRemoveAllText: '&lt;&lt;' // string, sets the text for the "Remove All" button
},
// Selections are invisible on android if the containing select is styled with CSS
// http://code.google.com/p/android/issues/detail?id=16922
isBuggyAndroid = /android/i.test(navigator.userAgent.toLowerCase());
// The actual plugin constructor
function BootstrapDualListbox(element, options) {
this.element = $(element);
// jQuery has an extend method which merges the contents of two or
// more objects, storing the result in the first object. The first object
// is generally empty as we don't want to alter the default options for
// future instances of the plugin
this.settings = $.extend({}, defaults, options);
this._defaults = defaults;
this._name = pluginName;
this.init();
}
function triggerChangeEvent(dualListbox) {
dualListbox.element.trigger('change');
}
function updateSelectionStates(dualListbox) {
dualListbox.element.find('option').each(function(index, item) {
var $item = $(item);
if (typeof($item.data('original-index')) === 'undefined') {
$item.data('original-index', dualListbox.elementCount++);
}
if (typeof($item.data('_selected')) === 'undefined') {
$item.data('_selected', false);
}
});
}
function changeSelectionState(dualListbox, original_index, selected) {
dualListbox.element.find('option').each(function(index, item) {
var $item = $(item);
if ($item.data('original-index') === original_index) {
$item.prop('selected', selected);
if(selected){
$item.attr('data-sortindex', dualListbox.sortIndex);
dualListbox.sortIndex++;
} else {
$item.removeAttr('data-sortindex');
}
}
});
}
function formatString(s, args) {
console.log(s, args);
return s.replace(/{(\d+)}/g, function(match, number) {
return typeof args[number] !== 'undefined' ? args[number] : match;
});
}
function refreshInfo(dualListbox) {
if (!dualListbox.settings.infoText) {
return;
}
var visible1 = dualListbox.elements.select1.find('option').length,
visible2 = dualListbox.elements.select2.find('option').length,
all1 = dualListbox.element.find('option').length - dualListbox.selectedElements,
all2 = dualListbox.selectedElements,
content = '';
if (all1 === 0) {
content = dualListbox.settings.infoTextEmpty;
} else if (visible1 === all1) {
content = formatString(dualListbox.settings.infoText, [visible1, all1]);
} else {
content = formatString(dualListbox.settings.infoTextFiltered, [visible1, all1]);
}
dualListbox.elements.info1.html(content);
dualListbox.elements.box1.toggleClass('filtered', !(visible1 === all1 || all1 === 0));
if (all2 === 0) {
content = dualListbox.settings.infoTextEmpty;
} else if (visible2 === all2) {
content = formatString(dualListbox.settings.infoText, [visible2, all2]);
} else {
content = formatString(dualListbox.settings.infoTextFiltered, [visible2, all2]);
}
dualListbox.elements.info2.html(content);
dualListbox.elements.box2.toggleClass('filtered', !(visible2 === all2 || all2 === 0));
}
function refreshSelects(dualListbox) {
dualListbox.selectedElements = 0;
dualListbox.elements.select1.empty();
dualListbox.elements.select2.empty();
dualListbox.element.find('option').each(function(index, item) {
var $item = $(item);
if ($item.prop('selected')) {
dualListbox.selectedElements++;
dualListbox.elements.select2.append($item.clone(true).prop('selected', $item.data('_selected')));
} else {
dualListbox.elements.select1.append($item.clone(true).prop('selected', $item.data('_selected')));
}
});
if (dualListbox.settings.showFilterInputs) {
filter(dualListbox, 1);
filter(dualListbox, 2);
}
refreshInfo(dualListbox);
}
function filter(dualListbox, selectIndex) {
if (!dualListbox.settings.showFilterInputs) {
return;
}
saveSelections(dualListbox, selectIndex);
dualListbox.elements['select'+selectIndex].empty().scrollTop(0);
var regex,
allOptions = dualListbox.element.find('option'),
options = dualListbox.element;
if (selectIndex === 1) {
options = allOptions.not(':selected');
} else {
options = options.find('option:selected');
}
try {
regex = new RegExp($.trim(dualListbox.elements['filterInput'+selectIndex].val()), 'gi');
}
catch(e) {
// a regex to match nothing
regex = new RegExp('/a^/', 'gi');
}
options.each(function(index, item) {
var $item = $(item),
isFiltered = true;
if (item.text.match(regex) || (dualListbox.settings.filterOnValues && $item.attr('value').match(regex) ) ) {
isFiltered = false;
dualListbox.elements['select'+selectIndex].append($item.clone(true).prop('selected', $item.data('_selected')));
}
allOptions.eq($item.data('original-index')).data('filtered'+selectIndex, isFiltered);
});
refreshInfo(dualListbox);
}
function saveSelections(dualListbox, selectIndex) {
var options = dualListbox.element.find('option');
dualListbox.elements['select'+selectIndex].find('option').each(function(index, item) {
var $item = $(item);
options.eq($item.data('original-index')).data('_selected', $item.prop('selected'));
});
}
function sortOptionsByInputOrder(select){
var selectopt = select.children('option');
selectopt.sort(function(a,b){
var an = parseInt(a.getAttribute('data-sortindex')),
bn = parseInt(b.getAttribute('data-sortindex'));
if(an > bn) {
return 1;
}
if(an < bn) {
return -1;
}
return 0;
});
selectopt.detach().appendTo(select);
}
function sortOptions(select, dualListbox) {
select.find('option').sort(function(a, b) {
return ($(a).data('original-index') > $(b).data('original-index')) ? 1 : -1;
}).appendTo(select);
// workaround for chromium bug: https://bugs.chromium.org/p/chromium/issues/detail?id=1072475
refreshSelects(dualListbox);
}
function clearSelections(dualListbox) {
dualListbox.elements.select1.find('option').each(function() {
dualListbox.element.find('option').data('_selected', false);
});
}
function move(dualListbox) {
if (dualListbox.settings.preserveSelectionOnMove === 'all' && !dualListbox.settings.moveOnSelect) {
saveSelections(dualListbox, 1);
saveSelections(dualListbox, 2);
} else if (dualListbox.settings.preserveSelectionOnMove === 'moved' && !dualListbox.settings.moveOnSelect) {
saveSelections(dualListbox, 1);
}
dualListbox.elements.select1.find('option:selected').each(function(index, item) {
var $item = $(item);
if (!$item.data('filtered1')) {
changeSelectionState(dualListbox, $item.data('original-index'), true);
}
});
refreshSelects(dualListbox);
triggerChangeEvent(dualListbox);
if(dualListbox.settings.sortByInputOrder){
sortOptionsByInputOrder(dualListbox.elements.select2);
} else {
sortOptions(dualListbox.elements.select2, dualListbox);
}
}
function remove(dualListbox) {
if (dualListbox.settings.preserveSelectionOnMove === 'all' && !dualListbox.settings.moveOnSelect) {
saveSelections(dualListbox, 1);
saveSelections(dualListbox, 2);
} else if (dualListbox.settings.preserveSelectionOnMove === 'moved' && !dualListbox.settings.moveOnSelect) {
saveSelections(dualListbox, 2);
}
dualListbox.elements.select2.find('option:selected').each(function(index, item) {
var $item = $(item);
if (!$item.data('filtered2')) {
changeSelectionState(dualListbox, $item.data('original-index'), false);
}
});
refreshSelects(dualListbox);
triggerChangeEvent(dualListbox);
sortOptions(dualListbox.elements.select1, dualListbox);
if(dualListbox.settings.sortByInputOrder){
sortOptionsByInputOrder(dualListbox.elements.select2);
}
}
function moveAll(dualListbox) {
if (dualListbox.settings.preserveSelectionOnMove === 'all' && !dualListbox.settings.moveOnSelect) {
saveSelections(dualListbox, 1);
saveSelections(dualListbox, 2);
} else if (dualListbox.settings.preserveSelectionOnMove === 'moved' && !dualListbox.settings.moveOnSelect) {
saveSelections(dualListbox, 1);
}
dualListbox.element.find('option').each(function(index, item) {
var $item = $(item);
if (!$item.data('filtered1')) {
$item.prop('selected', true);
$item.attr('data-sortindex', dualListbox.sortIndex);
dualListbox.sortIndex++;
}
});
refreshSelects(dualListbox);
triggerChangeEvent(dualListbox);
}
function removeAll(dualListbox) {
if (dualListbox.settings.preserveSelectionOnMove === 'all' && !dualListbox.settings.moveOnSelect) {
saveSelections(dualListbox, 1);
saveSelections(dualListbox, 2);
} else if (dualListbox.settings.preserveSelectionOnMove === 'moved' && !dualListbox.settings.moveOnSelect) {
saveSelections(dualListbox, 2);
}
dualListbox.element.find('option').each(function(index, item) {
var $item = $(item);
if (!$item.data('filtered2')) {
$item.prop('selected', false);
$item.removeAttr('data-sortindex');
}
});
refreshSelects(dualListbox);
triggerChangeEvent(dualListbox);
}
function bindEvents(dualListbox) {
dualListbox.elements.form.submit(function(e) {
if (dualListbox.elements.filterInput1.is(':focus')) {
e.preventDefault();
dualListbox.elements.filterInput1.focusout();
} else if (dualListbox.elements.filterInput2.is(':focus')) {
e.preventDefault();
dualListbox.elements.filterInput2.focusout();
}
});
dualListbox.element.on('bootstrapDualListbox.refresh', function(e, mustClearSelections){
dualListbox.refresh(mustClearSelections);
});
dualListbox.elements.filterClear1.on('click', function() {
dualListbox.setNonSelectedFilter('', true);
});
dualListbox.elements.filterClear2.on('click', function() {
dualListbox.setSelectedFilter('', true);
});
if (dualListbox.settings.eventMoveOverride === false) {
dualListbox.elements.moveButton.on('click', function() {
move(dualListbox);
});
}
if (dualListbox.settings.eventMoveAllOverride === false) {
dualListbox.elements.moveAllButton.on('click', function() {
moveAll(dualListbox);
});
}
if (dualListbox.settings.eventRemoveOverride === false) {
dualListbox.elements.removeButton.on('click', function() {
remove(dualListbox);
});
}
if (dualListbox.settings.eventRemoveAllOverride === false) {
dualListbox.elements.removeAllButton.on('click', function() {
removeAll(dualListbox);
});
}
dualListbox.elements.filterInput1.on('change keyup', function() {
filter(dualListbox, 1);
});
dualListbox.elements.filterInput2.on('change keyup', function() {
filter(dualListbox, 2);
});
}
BootstrapDualListbox.prototype = {
init: function () {
// Add the custom HTML template
this.container = $('' +
'<div class="bootstrap-duallistbox-container row">' +
' <div class="box1 col-md-6">' +
' <label></label>' +
' <span class="info-container">' +
' <span class="info"></span>' +
' <button type="button" class="btn btn-sm clear1" style="float:right!important;"></button>' +
' </span>' +
' <input class="form-control filter" type="text">' +
' <div class="btn-group buttons">' +
' <button type="button" class="btn moveall"></button>' +
' <button type="button" class="btn move"></button>' +
' </div>' +
' <select multiple="multiple"></select>' +
' </div>' +
' <div class="box2 col-md-6">' +
' <label></label>' +
' <span class="info-container">' +
' <span class="info"></span>' +
' <button type="button" class="btn btn-sm clear2" style="float:right!important;"></button>' +
' </span>' +
' <input class="form-control filter" type="text">' +
' <div class="btn-group buttons">' +
' <button type="button" class="btn remove"></button>' +
' <button type="button" class="btn removeall"></button>' +
' </div>' +
' <select multiple="multiple"></select>' +
' </div>' +
'</div>')
.insertBefore(this.element);
// Cache the inner elements
this.elements = {
originalSelect: this.element,
box1: $('.box1', this.container),
box2: $('.box2', this.container),
filterInput1: $('.box1 .filter', this.container),
filterInput2: $('.box2 .filter', this.container),
filterClear1: $('.box1 .clear1', this.container),
filterClear2: $('.box2 .clear2', this.container),
label1: $('.box1 > label', this.container),
label2: $('.box2 > label', this.container),
info1: $('.box1 .info', this.container),
info2: $('.box2 .info', this.container),
select1: $('.box1 select', this.container),
select2: $('.box2 select', this.container),
moveButton: $('.box1 .move', this.container),
removeButton: $('.box2 .remove', this.container),
moveAllButton: $('.box1 .moveall', this.container),
removeAllButton: $('.box2 .removeall', this.container),
form: $($('.box1 .filter', this.container)[0].form)
};
// Set select IDs
this.originalSelectName = this.element.attr('name') || '';
var select1Id = 'bootstrap-duallistbox-nonselected-list_' + this.originalSelectName,
select2Id = 'bootstrap-duallistbox-selected-list_' + this.originalSelectName;
this.elements.select1.attr('id', select1Id);
this.elements.select2.attr('id', select2Id);
this.elements.label1.attr('for', select1Id);
this.elements.label2.attr('for', select2Id);
// Apply all settings
this.selectedElements = 0;
this.sortIndex = 0;
this.elementCount = 0;
this.setFilterTextClear(this.settings.filterTextClear);
this.setFilterPlaceHolder(this.settings.filterPlaceHolder);
this.setMoveSelectedLabel(this.settings.moveSelectedLabel);
this.setMoveAllLabel(this.settings.moveAllLabel);
this.setRemoveSelectedLabel(this.settings.removeSelectedLabel);
this.setRemoveAllLabel(this.settings.removeAllLabel);
this.setMoveOnSelect(this.settings.moveOnSelect);
this.setMoveOnDoubleClick(this.settings.moveOnDoubleClick);
this.setPreserveSelectionOnMove(this.settings.preserveSelectionOnMove);
this.setSelectedListLabel(this.settings.selectedListLabel);
this.setNonSelectedListLabel(this.settings.nonSelectedListLabel);
this.setHelperSelectNamePostfix(this.settings.helperSelectNamePostfix);
this.setSelectOrMinimalHeight(this.settings.selectorMinimalHeight);
updateSelectionStates(this);
this.setShowFilterInputs(this.settings.showFilterInputs);
this.setNonSelectedFilter(this.settings.nonSelectedFilter);
this.setSelectedFilter(this.settings.selectedFilter);
this.setInfoText(this.settings.infoText);
this.setInfoTextFiltered(this.settings.infoTextFiltered);
this.setInfoTextEmpty(this.settings.infoTextEmpty);
this.setFilterOnValues(this.settings.filterOnValues);
this.setSortByInputOrder(this.settings.sortByInputOrder);
this.setEventMoveOverride(this.settings.eventMoveOverride);
this.setEventMoveAllOverride(this.settings.eventMoveAllOverride);
this.setEventRemoveOverride(this.settings.eventRemoveOverride);
this.setEventRemoveAllOverride(this.settings.eventRemoveAllOverride);
this.setBtnClass(this.settings.btnClass);
this.setBtnMoveText(this.settings.btnMoveText);
this.setBtnRemoveText(this.settings.btnRemoveText);
this.setBtnMoveAllText(this.settings.btnMoveAllText);
this.setBtnRemoveAllText(this.settings.btnRemoveAllText);
// Hide the original select
this.element.hide();
bindEvents(this);
refreshSelects(this);
return this.element;
},
setFilterTextClear: function(value, refresh) {
this.settings.filterTextClear = value;
this.elements.filterClear1.html(value);
this.elements.filterClear2.html(value);
if (refresh) {
refreshSelects(this);
}
return this.element;
},
setFilterPlaceHolder: function(value, refresh) {
this.settings.filterPlaceHolder = value;
this.elements.filterInput1.attr('placeholder', value);
this.elements.filterInput2.attr('placeholder', value);
if (refresh) {
refreshSelects(this);
}
return this.element;
},
setMoveSelectedLabel: function(value, refresh) {
this.settings.moveSelectedLabel = value;
this.elements.moveButton.attr('title', value);
if (refresh) {
refreshSelects(this);
}
return this.element;
},
setMoveAllLabel: function(value, refresh) {
this.settings.moveAllLabel = value;
this.elements.moveAllButton.attr('title', value);
if (refresh) {
refreshSelects(this);
}
return this.element;
},
setRemoveSelectedLabel: function(value, refresh) {
this.settings.removeSelectedLabel = value;
this.elements.removeButton.attr('title', value);
if (refresh) {
refreshSelects(this);
}
return this.element;
},
setRemoveAllLabel: function(value, refresh) {
this.settings.removeAllLabel = value;
this.elements.removeAllButton.attr('title', value);
if (refresh) {
refreshSelects(this);
}
return this.element;
},
setMoveOnSelect: function(value, refresh) {
if (isBuggyAndroid) {
value = true;
}
this.settings.moveOnSelect = value;
if (this.settings.moveOnSelect) {
this.container.addClass('moveonselect');
var self = this;
this.elements.select1.on('change', function() {
move(self);
});
this.elements.select2.on('change', function() {
remove(self);
});
this.elements.moveButton.detach();
this.elements.removeButton.detach();
} else {
this.container.removeClass('moveonselect');
this.elements.select1.off('change');
this.elements.select2.off('change');
this.elements.moveButton.insertAfter(this.elements.moveAllButton);
this.elements.removeButton.insertBefore(this.elements.removeAllButton);
}
if (refresh) {
refreshSelects(this);
}
return this.element;
},
setMoveOnDoubleClick: function(value, refresh) {
if (isBuggyAndroid) {
value = false;
}
this.settings.moveOnDoubleClick = value;
if (this.settings.moveOnDoubleClick) {
this.container.addClass('moveondoubleclick');
var self = this;
this.elements.select1.on('dblclick', function() {
move(self);
});
this.elements.select2.on('dblclick', function() {
remove(self);
});
} else {
this.container.removeClass('moveondoubleclick');
this.elements.select1.off('dblclick');
this.elements.select2.off('dblclick');
}
if (refresh) {
refreshSelects(this);
}
return this.element;
},
setPreserveSelectionOnMove: function(value, refresh) {
// We are forcing to move on select and disabling preserveSelectionOnMove on Android
if (isBuggyAndroid) {
value = false;
}
this.settings.preserveSelectionOnMove = value;
if (refresh) {
refreshSelects(this);
}
return this.element;
},
setSelectedListLabel: function(value, refresh) {
this.settings.selectedListLabel = value;
if (value) {
this.elements.label2.show().html(value);
} else {
this.elements.label2.hide().html(value);
}
if (refresh) {
refreshSelects(this);
}
return this.element;
},
setNonSelectedListLabel: function(value, refresh) {
this.settings.nonSelectedListLabel = value;
if (value) {
this.elements.label1.show().html(value);
} else {
this.elements.label1.hide().html(value);
}
if (refresh) {
refreshSelects(this);
}
return this.element;
},
setHelperSelectNamePostfix: function(value, refresh) {
this.settings.helperSelectNamePostfix = value;
if (value) {
this.elements.select1.attr('name', this.originalSelectName + value + '1');
this.elements.select2.attr('name', this.originalSelectName + value + '2');
} else {
this.elements.select1.removeAttr('name');
this.elements.select2.removeAttr('name');
}
if (refresh) {
refreshSelects(this);
}
return this.element;
},
setSelectOrMinimalHeight: function(value, refresh) {
this.settings.selectorMinimalHeight = value;
var height = this.element.height();
if (this.element.height() < value) {
height = value;
}
this.elements.select1.height(height);
this.elements.select2.height(height);
if (refresh) {
refreshSelects(this);
}
return this.element;
},
setShowFilterInputs: function(value, refresh) {
if (!value) {
this.setNonSelectedFilter('');
this.setSelectedFilter('');
refreshSelects(this);
this.elements.filterInput1.hide();
this.elements.filterInput2.hide();
} else {
this.elements.filterInput1.show();
this.elements.filterInput2.show();
}
this.settings.showFilterInputs = value;
if (refresh) {
refreshSelects(this);
}
return this.element;
},
setNonSelectedFilter: function(value, refresh) {
if (this.settings.showFilterInputs) {
this.settings.nonSelectedFilter = value;
this.elements.filterInput1.val(value);
if (refresh) {
refreshSelects(this);
}
return this.element;
}
},
setSelectedFilter: function(value, refresh) {
if (this.settings.showFilterInputs) {
this.settings.selectedFilter = value;
this.elements.filterInput2.val(value);
if (refresh) {
refreshSelects(this);
}
return this.element;
}
},
setInfoText: function(value, refresh) {
this.settings.infoText = value;
if (value) {
this.elements.info1.show();
this.elements.info2.show();
} else {
this.elements.info1.hide();
this.elements.info2.hide();
}
if (refresh) {
refreshSelects(this);
}
return this.element;
},
setInfoTextFiltered: function(value, refresh) {
this.settings.infoTextFiltered = value;
if (refresh) {
refreshSelects(this);
}
return this.element;
},
setInfoTextEmpty: function(value, refresh) {
this.settings.infoTextEmpty = value;
if (refresh) {
refreshSelects(this);
}
return this.element;
},
setFilterOnValues: function(value, refresh) {
this.settings.filterOnValues = value;
if (refresh) {
refreshSelects(this);
}
return this.element;
},
setSortByInputOrder: function(value, refresh){
this.settings.sortByInputOrder = value;
if (refresh) {
refreshSelects(this);
}
return this.element;
},
setEventMoveOverride: function(value, refresh) {
this.settings.eventMoveOverride = value;
if (refresh) {
refreshSelects(this);
}
return this.element;
},
setEventMoveAllOverride: function(value, refresh) {
this.settings.eventMoveAllOverride = value;
if (refresh) {
refreshSelects(this);
}
return this.element;
},
setEventRemoveOverride: function(value, refresh) {
this.settings.eventRemoveOverride = value;
if (refresh) {
refreshSelects(this);
}
return this.element;
},
setEventRemoveAllOverride: function(value, refresh) {
this.settings.eventRemoveAllOverride = value;
if (refresh) {
refreshSelects(this);
}
return this.element;
},
setBtnClass: function(value, refresh) {
this.settings.btnClass = value;
this.elements.moveButton.attr('class', 'btn move').addClass(value);
this.elements.removeButton.attr('class', 'btn remove').addClass(value);
this.elements.moveAllButton.attr('class', 'btn moveall').addClass(value);
this.elements.removeAllButton.attr('class', 'btn removeall').addClass(value);
if (refresh) {
refreshSelects(this);
}
return this.element;
},
setBtnMoveText: function(value, refresh) {
this.settings.btnMoveText = value;
this.elements.moveButton.html(value);
if (refresh) {
refreshSelects(this);
}
return this.element;
},
setBtnRemoveText: function(value, refresh) {
this.settings.btnMoveText = value;
this.elements.removeButton.html(value);
if (refresh) {
refreshSelects(this);
}
return this.element;
},
setBtnMoveAllText: function(value, refresh) {
this.settings.btnMoveText = value;
this.elements.moveAllButton.html(value);
if (refresh) {
refreshSelects(this);
}
return this.element;
},
setBtnRemoveAllText: function(value, refresh) {
this.settings.btnMoveText = value;
this.elements.removeAllButton.html(value);
if (refresh) {
refreshSelects(this);
}
return this.element;
},
getContainer: function() {
return this.container;
},
refresh: function(mustClearSelections) {
updateSelectionStates(this);
if (!mustClearSelections) {
saveSelections(this, 1);
saveSelections(this, 2);
} else {
clearSelections(this);
}
refreshSelects(this);
},
destroy: function() {
this.container.remove();
this.element.show();
$.data(this, 'plugin_' + pluginName, null);
return this.element;
}
};
// A really lightweight plugin wrapper around the constructor,
// preventing against multiple instantiations
$.fn[ pluginName ] = function (options) {
var args = arguments;
// Is the first parameter an object (options), or was omitted, instantiate a new instance of the plugin.
if (options === undefined || typeof options === 'object') {
return this.each(function () {
// If this is not a select
if (!$(this).is('select')) {
$(this).find('select').each(function(index, item) {
// For each nested select, instantiate the Dual List Box
$(item).bootstrapDualListbox(options);
});
} else if (!$.data(this, 'plugin_' + pluginName)) {
// Only allow the plugin to be instantiated once so we check that the element has no plugin instantiation yet
// if it has no instance, create a new one, pass options to our plugin constructor,
// and store the plugin instance in the elements jQuery data object.
$.data(this, 'plugin_' + pluginName, new BootstrapDualListbox(this, options));
}
});
// If the first parameter is a string and it doesn't start with an underscore or "contains" the `init`-function,
// treat this as a call to a public method.
} else if (typeof options === 'string' && options[0] !== '_' && options !== 'init') {
// Cache the method call to make it possible to return a value
var returns;
this.each(function () {
var instance = $.data(this, 'plugin_' + pluginName);
// Tests that there's already a plugin-instance and checks that the requested public method exists
if (instance instanceof BootstrapDualListbox && typeof instance[options] === 'function') {
// Call the method of our plugin instance, and pass it the supplied arguments.
returns = instance[options].apply(instance, Array.prototype.slice.call(args, 1));
}
});
// If the earlier cached method gives a value back return the value,
// otherwise return this to preserve chainability.
return returns !== undefined ? returns : this;
}
};
}));

File diff suppressed because one or more lines are too long

View file

@ -1,167 +0,0 @@
/*!
* bsCustomFileInput v1.3.4 (https://github.com/Johann-S/bs-custom-file-input)
* Copyright 2018 - 2020 Johann-S <johann.servoire@gmail.com>
* Licensed under MIT (https://github.com/Johann-S/bs-custom-file-input/blob/master/LICENSE)
*/
(function (global, factory) {
typeof exports === 'object' && typeof module !== 'undefined' ? module.exports = factory() :
typeof define === 'function' && define.amd ? define(factory) :
(global = global || self, global.bsCustomFileInput = factory());
}(this, (function () { 'use strict';
var Selector = {
CUSTOMFILE: '.custom-file input[type="file"]',
CUSTOMFILELABEL: '.custom-file-label',
FORM: 'form',
INPUT: 'input'
};
var textNodeType = 3;
var getDefaultText = function getDefaultText(input) {
var defaultText = '';
var label = input.parentNode.querySelector(Selector.CUSTOMFILELABEL);
if (label) {
defaultText = label.textContent;
}
return defaultText;
};
var findFirstChildNode = function findFirstChildNode(element) {
if (element.childNodes.length > 0) {
var childNodes = [].slice.call(element.childNodes);
for (var i = 0; i < childNodes.length; i++) {
var node = childNodes[i];
if (node.nodeType !== textNodeType) {
return node;
}
}
}
return element;
};
var restoreDefaultText = function restoreDefaultText(input) {
var defaultText = input.bsCustomFileInput.defaultText;
var label = input.parentNode.querySelector(Selector.CUSTOMFILELABEL);
if (label) {
var element = findFirstChildNode(label);
element.textContent = defaultText;
}
};
var fileApi = !!window.File;
var FAKE_PATH = 'fakepath';
var FAKE_PATH_SEPARATOR = '\\';
var getSelectedFiles = function getSelectedFiles(input) {
if (input.hasAttribute('multiple') && fileApi) {
return [].slice.call(input.files).map(function (file) {
return file.name;
}).join(', ');
}
if (input.value.indexOf(FAKE_PATH) !== -1) {
var splittedValue = input.value.split(FAKE_PATH_SEPARATOR);
return splittedValue[splittedValue.length - 1];
}
return input.value;
};
function handleInputChange() {
var label = this.parentNode.querySelector(Selector.CUSTOMFILELABEL);
if (label) {
var element = findFirstChildNode(label);
var inputValue = getSelectedFiles(this);
if (inputValue.length) {
element.textContent = inputValue;
} else {
restoreDefaultText(this);
}
}
}
function handleFormReset() {
var customFileList = [].slice.call(this.querySelectorAll(Selector.INPUT)).filter(function (input) {
return !!input.bsCustomFileInput;
});
for (var i = 0, len = customFileList.length; i < len; i++) {
restoreDefaultText(customFileList[i]);
}
}
var customProperty = 'bsCustomFileInput';
var Event = {
FORMRESET: 'reset',
INPUTCHANGE: 'change'
};
var bsCustomFileInput = {
init: function init(inputSelector, formSelector) {
if (inputSelector === void 0) {
inputSelector = Selector.CUSTOMFILE;
}
if (formSelector === void 0) {
formSelector = Selector.FORM;
}
var customFileInputList = [].slice.call(document.querySelectorAll(inputSelector));
var formList = [].slice.call(document.querySelectorAll(formSelector));
for (var i = 0, len = customFileInputList.length; i < len; i++) {
var input = customFileInputList[i];
Object.defineProperty(input, customProperty, {
value: {
defaultText: getDefaultText(input)
},
writable: true
});
handleInputChange.call(input);
input.addEventListener(Event.INPUTCHANGE, handleInputChange);
}
for (var _i = 0, _len = formList.length; _i < _len; _i++) {
formList[_i].addEventListener(Event.FORMRESET, handleFormReset);
Object.defineProperty(formList[_i], customProperty, {
value: true,
writable: true
});
}
},
destroy: function destroy() {
var formList = [].slice.call(document.querySelectorAll(Selector.FORM)).filter(function (form) {
return !!form.bsCustomFileInput;
});
var customFileInputList = [].slice.call(document.querySelectorAll(Selector.INPUT)).filter(function (input) {
return !!input.bsCustomFileInput;
});
for (var i = 0, len = customFileInputList.length; i < len; i++) {
var input = customFileInputList[i];
restoreDefaultText(input);
input[customProperty] = undefined;
input.removeEventListener(Event.INPUTCHANGE, handleInputChange);
}
for (var _i2 = 0, _len2 = formList.length; _i2 < _len2; _i2++) {
formList[_i2].removeEventListener(Event.FORMRESET, handleFormReset);
formList[_i2][customProperty] = undefined;
}
}
};
return bsCustomFileInput;
})));
//# sourceMappingURL=bs-custom-file-input.js.map

File diff suppressed because one or more lines are too long

View file

@ -1,7 +0,0 @@
/*!
* bsCustomFileInput v1.3.4 (https://github.com/Johann-S/bs-custom-file-input)
* Copyright 2018 - 2020 Johann-S <johann.servoire@gmail.com>
* Licensed under MIT (https://github.com/Johann-S/bs-custom-file-input/blob/master/LICENSE)
*/
!function(e,t){"object"==typeof exports&&"undefined"!=typeof module?module.exports=t():"function"==typeof define&&define.amd?define(t):(e=e||self).bsCustomFileInput=t()}(this,function(){"use strict";var s={CUSTOMFILE:'.custom-file input[type="file"]',CUSTOMFILELABEL:".custom-file-label",FORM:"form",INPUT:"input"},l=function(e){if(0<e.childNodes.length)for(var t=[].slice.call(e.childNodes),n=0;n<t.length;n++){var l=t[n];if(3!==l.nodeType)return l}return e},u=function(e){var t=e.bsCustomFileInput.defaultText,n=e.parentNode.querySelector(s.CUSTOMFILELABEL);n&&(l(n).textContent=t)},n=!!window.File,r=function(e){if(e.hasAttribute("multiple")&&n)return[].slice.call(e.files).map(function(e){return e.name}).join(", ");if(-1===e.value.indexOf("fakepath"))return e.value;var t=e.value.split("\\");return t[t.length-1]};function d(){var e=this.parentNode.querySelector(s.CUSTOMFILELABEL);if(e){var t=l(e),n=r(this);n.length?t.textContent=n:u(this)}}function v(){for(var e=[].slice.call(this.querySelectorAll(s.INPUT)).filter(function(e){return!!e.bsCustomFileInput}),t=0,n=e.length;t<n;t++)u(e[t])}var p="bsCustomFileInput",m="reset",h="change";return{init:function(e,t){void 0===e&&(e=s.CUSTOMFILE),void 0===t&&(t=s.FORM);for(var n,l,r=[].slice.call(document.querySelectorAll(e)),i=[].slice.call(document.querySelectorAll(t)),o=0,u=r.length;o<u;o++){var c=r[o];Object.defineProperty(c,p,{value:{defaultText:(n=void 0,n="",(l=c.parentNode.querySelector(s.CUSTOMFILELABEL))&&(n=l.textContent),n)},writable:!0}),d.call(c),c.addEventListener(h,d)}for(var f=0,a=i.length;f<a;f++)i[f].addEventListener(m,v),Object.defineProperty(i[f],p,{value:!0,writable:!0})},destroy:function(){for(var e=[].slice.call(document.querySelectorAll(s.FORM)).filter(function(e){return!!e.bsCustomFileInput}),t=[].slice.call(document.querySelectorAll(s.INPUT)).filter(function(e){return!!e.bsCustomFileInput}),n=0,l=t.length;n<l;n++){var r=t[n];u(r),r[p]=void 0,r.removeEventListener(h,d)}for(var i=0,o=e.length;i<o;i++)e[i].removeEventListener(m,v),e[i][p]=void 0}}});
//# sourceMappingURL=bs-custom-file-input.min.js.map

File diff suppressed because one or more lines are too long

View file

@ -1,194 +0,0 @@
/*!
* bsStepper v1.7.0 (https://github.com/Johann-S/bs-stepper)
* Copyright 2018 - 2019 Johann-S <johann.servoire@gmail.com>
* Licensed under MIT (https://github.com/Johann-S/bs-stepper/blob/master/LICENSE)
*/
.bs-stepper .step-trigger {
display: -ms-inline-flexbox;
display: inline-flex;
-ms-flex-wrap: wrap;
flex-wrap: wrap;
-ms-flex-align: center;
align-items: center;
-ms-flex-pack: center;
justify-content: center;
padding: 20px;
font-size: 1rem;
font-weight: 700;
line-height: 1.5;
color: #6c757d;
text-align: center;
text-decoration: none;
white-space: nowrap;
vertical-align: middle;
-webkit-user-select: none;
-moz-user-select: none;
-ms-user-select: none;
user-select: none;
background-color: transparent;
border: none;
border-radius: .25rem;
transition: background-color .15s ease-out, color .15s ease-out;
}
.bs-stepper .step-trigger:not(:disabled):not(.disabled) {
cursor: pointer;
}
.bs-stepper .step-trigger:disabled,
.bs-stepper .step-trigger.disabled {
pointer-events: none;
opacity: .65;
}
.bs-stepper .step-trigger:focus {
color: #007bff;
outline: none;
}
.bs-stepper .step-trigger:hover {
text-decoration: none;
background-color: rgba(0, 0, 0, .06);
}
@media (max-width: 520px) {
.bs-stepper .step-trigger {
-ms-flex-direction: column;
flex-direction: column;
padding: 10px;
}
}
.bs-stepper-label {
display: inline-block;
margin: .25rem;
}
.bs-stepper-header {
display: -ms-flexbox;
display: flex;
-ms-flex-align: center;
align-items: center;
}
@media (max-width: 520px) {
.bs-stepper-header {
margin: 0 -10px;
text-align: center;
}
}
.bs-stepper-line,
.bs-stepper .line {
-ms-flex: 1 0 32px;
flex: 1 0 32px;
min-width: 1px;
min-height: 1px;
margin: auto;
background-color: rgba(0, 0, 0, .12);
}
@media (max-width: 400px) {
.bs-stepper-line,
.bs-stepper .line {
-ms-flex-preferred-size: 20px;
flex-basis: 20px;
}
}
.bs-stepper-circle {
display: -ms-inline-flexbox;
display: inline-flex;
-ms-flex-line-pack: center;
align-content: center;
-ms-flex-pack: center;
justify-content: center;
width: 2em;
height: 2em;
padding: .5em 0;
margin: .25rem;
line-height: 1em;
color: #fff;
background-color: #6c757d;
border-radius: 1em;
}
.active .bs-stepper-circle {
background-color: #007bff;
}
.bs-stepper-content {
padding: 0 20px 20px;
}
@media (max-width: 520px) {
.bs-stepper-content {
padding: 0;
}
}
.bs-stepper.vertical {
display: -ms-flexbox;
display: flex;
}
.bs-stepper.vertical .bs-stepper-header {
-ms-flex-direction: column;
flex-direction: column;
-ms-flex-align: stretch;
align-items: stretch;
margin: 0;
}
.bs-stepper.vertical .bs-stepper-pane,
.bs-stepper.vertical .content {
display: block;
}
.bs-stepper.vertical .bs-stepper-pane:not(.fade),
.bs-stepper.vertical .content:not(.fade) {
display: block;
visibility: hidden;
}
.bs-stepper-pane:not(.fade),
.bs-stepper .content:not(.fade) {
display: none;
}
.bs-stepper .content.fade,
.bs-stepper-pane.fade {
visibility: hidden;
transition-duration: .3s;
transition-property: opacity;
}
.bs-stepper-pane.fade.active,
.bs-stepper .content.fade.active {
visibility: visible;
opacity: 1;
}
.bs-stepper-pane.active:not(.fade),
.bs-stepper .content.active:not(.fade) {
display: block;
visibility: visible;
}
.bs-stepper-pane.dstepper-block,
.bs-stepper .content.dstepper-block {
display: block;
}
.bs-stepper:not(.vertical) .bs-stepper-pane.dstepper-none,
.bs-stepper:not(.vertical) .content.dstepper-none {
display: none;
}
.vertical .bs-stepper-pane.fade.dstepper-none,
.vertical .content.fade.dstepper-none {
visibility: hidden;
}
/*# sourceMappingURL=bs-stepper.css.map */

File diff suppressed because one or more lines are too long

View file

@ -1,6 +0,0 @@
/*!
* bsStepper v1.7.0 (https://github.com/Johann-S/bs-stepper)
* Copyright 2018 - 2019 Johann-S <johann.servoire@gmail.com>
* Licensed under MIT (https://github.com/Johann-S/bs-stepper/blob/master/LICENSE)
*/.bs-stepper .step-trigger{display:-ms-inline-flexbox;display:inline-flex;-ms-flex-wrap:wrap;flex-wrap:wrap;-ms-flex-align:center;align-items:center;-ms-flex-pack:center;justify-content:center;padding:20px;font-size:1rem;font-weight:700;line-height:1.5;color:#6c757d;text-align:center;text-decoration:none;white-space:nowrap;vertical-align:middle;-webkit-user-select:none;-moz-user-select:none;-ms-user-select:none;user-select:none;background-color:transparent;border:none;border-radius:.25rem;transition:background-color .15s ease-out,color .15s ease-out}.bs-stepper .step-trigger:not(:disabled):not(.disabled){cursor:pointer}.bs-stepper .step-trigger.disabled,.bs-stepper .step-trigger:disabled{pointer-events:none;opacity:.65}.bs-stepper .step-trigger:focus{color:#007bff;outline:0}.bs-stepper .step-trigger:hover{text-decoration:none;background-color:rgba(0,0,0,.06)}@media (max-width:520px){.bs-stepper .step-trigger{-ms-flex-direction:column;flex-direction:column;padding:10px}}.bs-stepper-label{display:inline-block;margin:.25rem}.bs-stepper-header{display:-ms-flexbox;display:flex;-ms-flex-align:center;align-items:center}@media (max-width:520px){.bs-stepper-header{margin:0 -10px;text-align:center}}.bs-stepper .line,.bs-stepper-line{-ms-flex:1 0 32px;flex:1 0 32px;min-width:1px;min-height:1px;margin:auto;background-color:rgba(0,0,0,.12)}@media (max-width:400px){.bs-stepper .line,.bs-stepper-line{-ms-flex-preferred-size:20px;flex-basis:20px}}.bs-stepper-circle{display:-ms-inline-flexbox;display:inline-flex;-ms-flex-line-pack:center;align-content:center;-ms-flex-pack:center;justify-content:center;width:2em;height:2em;padding:.5em 0;margin:.25rem;line-height:1em;color:#fff;background-color:#6c757d;border-radius:1em}.active .bs-stepper-circle{background-color:#007bff}.bs-stepper-content{padding:0 20px 20px}@media (max-width:520px){.bs-stepper-content{padding:0}}.bs-stepper.vertical{display:-ms-flexbox;display:flex}.bs-stepper.vertical .bs-stepper-header{-ms-flex-direction:column;flex-direction:column;-ms-flex-align:stretch;align-items:stretch;margin:0}.bs-stepper.vertical .bs-stepper-pane,.bs-stepper.vertical .content{display:block}.bs-stepper.vertical .bs-stepper-pane:not(.fade),.bs-stepper.vertical .content:not(.fade){display:block;visibility:hidden}.bs-stepper .content:not(.fade),.bs-stepper-pane:not(.fade){display:none}.bs-stepper .content.fade,.bs-stepper-pane.fade{visibility:hidden;transition-duration:.3s;transition-property:opacity}.bs-stepper .content.fade.active,.bs-stepper-pane.fade.active{visibility:visible;opacity:1}.bs-stepper .content.active:not(.fade),.bs-stepper-pane.active:not(.fade){display:block;visibility:visible}.bs-stepper .content.dstepper-block,.bs-stepper-pane.dstepper-block{display:block}.bs-stepper:not(.vertical) .bs-stepper-pane.dstepper-none,.bs-stepper:not(.vertical) .content.dstepper-none{display:none}.vertical .bs-stepper-pane.fade.dstepper-none,.vertical .content.fade.dstepper-none{visibility:hidden}
/*# sourceMappingURL=bs-stepper.min.css.map */

File diff suppressed because one or more lines are too long

View file

@ -1,428 +0,0 @@
/*!
* bsStepper v1.7.0 (https://github.com/Johann-S/bs-stepper)
* Copyright 2018 - 2019 Johann-S <johann.servoire@gmail.com>
* Licensed under MIT (https://github.com/Johann-S/bs-stepper/blob/master/LICENSE)
*/
(function (global, factory) {
typeof exports === 'object' && typeof module !== 'undefined' ? module.exports = factory() :
typeof define === 'function' && define.amd ? define(factory) :
(global = global || self, global.Stepper = factory());
}(this, function () { 'use strict';
function _extends() {
_extends = Object.assign || function (target) {
for (var i = 1; i < arguments.length; i++) {
var source = arguments[i];
for (var key in source) {
if (Object.prototype.hasOwnProperty.call(source, key)) {
target[key] = source[key];
}
}
}
return target;
};
return _extends.apply(this, arguments);
}
var matches = window.Element.prototype.matches;
var closest = function closest(element, selector) {
return element.closest(selector);
};
var WinEvent = function WinEvent(inType, params) {
return new window.Event(inType, params);
};
var createCustomEvent = function createCustomEvent(eventName, params) {
var cEvent = new window.CustomEvent(eventName, params);
return cEvent;
};
/* istanbul ignore next */
function polyfill() {
if (!window.Element.prototype.matches) {
matches = window.Element.prototype.msMatchesSelector || window.Element.prototype.webkitMatchesSelector;
}
if (!window.Element.prototype.closest) {
closest = function closest(element, selector) {
if (!document.documentElement.contains(element)) {
return null;
}
do {
if (matches.call(element, selector)) {
return element;
}
element = element.parentElement || element.parentNode;
} while (element !== null && element.nodeType === 1);
return null;
};
}
if (!window.Event || typeof window.Event !== 'function') {
WinEvent = function WinEvent(inType, params) {
params = params || {};
var e = document.createEvent('Event');
e.initEvent(inType, Boolean(params.bubbles), Boolean(params.cancelable));
return e;
};
}
if (typeof window.CustomEvent !== 'function') {
var originPreventDefault = window.Event.prototype.preventDefault;
createCustomEvent = function createCustomEvent(eventName, params) {
var evt = document.createEvent('CustomEvent');
params = params || {
bubbles: false,
cancelable: false,
detail: null
};
evt.initCustomEvent(eventName, params.bubbles, params.cancelable, params.detail);
evt.preventDefault = function () {
if (!this.cancelable) {
return;
}
originPreventDefault.call(this);
Object.defineProperty(this, 'defaultPrevented', {
get: function get() {
return true;
}
});
};
return evt;
};
}
}
polyfill();
var MILLISECONDS_MULTIPLIER = 1000;
var ClassName = {
ACTIVE: 'active',
LINEAR: 'linear',
BLOCK: 'dstepper-block',
NONE: 'dstepper-none',
FADE: 'fade',
VERTICAL: 'vertical'
};
var transitionEndEvent = 'transitionend';
var customProperty = 'bsStepper';
var show = function show(stepperNode, indexStep, options, done) {
var stepper = stepperNode[customProperty];
if (stepper._steps[indexStep].classList.contains(ClassName.ACTIVE) || stepper._stepsContents[indexStep].classList.contains(ClassName.ACTIVE)) {
return;
}
var showEvent = createCustomEvent('show.bs-stepper', {
cancelable: true,
detail: {
from: stepper._currentIndex,
to: indexStep,
indexStep: indexStep
}
});
stepperNode.dispatchEvent(showEvent);
var activeStep = stepper._steps.filter(function (step) {
return step.classList.contains(ClassName.ACTIVE);
});
var activeContent = stepper._stepsContents.filter(function (content) {
return content.classList.contains(ClassName.ACTIVE);
});
if (showEvent.defaultPrevented) {
return;
}
if (activeStep.length) {
activeStep[0].classList.remove(ClassName.ACTIVE);
}
if (activeContent.length) {
activeContent[0].classList.remove(ClassName.ACTIVE);
if (!stepperNode.classList.contains(ClassName.VERTICAL) && !stepper.options.animation) {
activeContent[0].classList.remove(ClassName.BLOCK);
}
}
showStep(stepperNode, stepper._steps[indexStep], stepper._steps, options);
showContent(stepperNode, stepper._stepsContents[indexStep], stepper._stepsContents, activeContent, done);
};
var showStep = function showStep(stepperNode, step, stepList, options) {
stepList.forEach(function (step) {
var trigger = step.querySelector(options.selectors.trigger);
trigger.setAttribute('aria-selected', 'false'); // if stepper is in linear mode, set disabled attribute on the trigger
if (stepperNode.classList.contains(ClassName.LINEAR)) {
trigger.setAttribute('disabled', 'disabled');
}
});
step.classList.add(ClassName.ACTIVE);
var currentTrigger = step.querySelector(options.selectors.trigger);
currentTrigger.setAttribute('aria-selected', 'true'); // if stepper is in linear mode, remove disabled attribute on current
if (stepperNode.classList.contains(ClassName.LINEAR)) {
currentTrigger.removeAttribute('disabled');
}
};
var showContent = function showContent(stepperNode, content, contentList, activeContent, done) {
var stepper = stepperNode[customProperty];
var toIndex = contentList.indexOf(content);
var shownEvent = createCustomEvent('shown.bs-stepper', {
cancelable: true,
detail: {
from: stepper._currentIndex,
to: toIndex,
indexStep: toIndex
}
});
function complete() {
content.classList.add(ClassName.BLOCK);
content.removeEventListener(transitionEndEvent, complete);
stepperNode.dispatchEvent(shownEvent);
done();
}
if (content.classList.contains(ClassName.FADE)) {
content.classList.remove(ClassName.NONE);
var duration = getTransitionDurationFromElement(content);
content.addEventListener(transitionEndEvent, complete);
if (activeContent.length) {
activeContent[0].classList.add(ClassName.NONE);
}
content.classList.add(ClassName.ACTIVE);
emulateTransitionEnd(content, duration);
} else {
content.classList.add(ClassName.ACTIVE);
content.classList.add(ClassName.BLOCK);
stepperNode.dispatchEvent(shownEvent);
done();
}
};
var getTransitionDurationFromElement = function getTransitionDurationFromElement(element) {
if (!element) {
return 0;
} // Get transition-duration of the element
var transitionDuration = window.getComputedStyle(element).transitionDuration;
var floatTransitionDuration = parseFloat(transitionDuration); // Return 0 if element or transition duration is not found
if (!floatTransitionDuration) {
return 0;
} // If multiple durations are defined, take the first
transitionDuration = transitionDuration.split(',')[0];
return parseFloat(transitionDuration) * MILLISECONDS_MULTIPLIER;
};
var emulateTransitionEnd = function emulateTransitionEnd(element, duration) {
var called = false;
var durationPadding = 5;
var emulatedDuration = duration + durationPadding;
function listener() {
called = true;
element.removeEventListener(transitionEndEvent, listener);
}
element.addEventListener(transitionEndEvent, listener);
window.setTimeout(function () {
if (!called) {
element.dispatchEvent(WinEvent(transitionEndEvent));
}
element.removeEventListener(transitionEndEvent, listener);
}, emulatedDuration);
};
var detectAnimation = function detectAnimation(contentList, options) {
if (options.animation) {
contentList.forEach(function (content) {
content.classList.add(ClassName.FADE);
content.classList.add(ClassName.NONE);
});
}
};
var buildClickStepLinearListener = function buildClickStepLinearListener() {
return function clickStepLinearListener(event) {
event.preventDefault();
};
};
var buildClickStepNonLinearListener = function buildClickStepNonLinearListener(options) {
return function clickStepNonLinearListener(event) {
event.preventDefault();
var step = closest(event.target, options.selectors.steps);
var stepperNode = closest(step, options.selectors.stepper);
var stepper = stepperNode[customProperty];
var stepIndex = stepper._steps.indexOf(step);
show(stepperNode, stepIndex, options, function () {
stepper._currentIndex = stepIndex;
});
};
};
var DEFAULT_OPTIONS = {
linear: true,
animation: false,
selectors: {
steps: '.step',
trigger: '.step-trigger',
stepper: '.bs-stepper'
}
};
var Stepper =
/*#__PURE__*/
function () {
function Stepper(element, _options) {
var _this = this;
if (_options === void 0) {
_options = {};
}
this._element = element;
this._currentIndex = 0;
this._stepsContents = [];
this.options = _extends({}, DEFAULT_OPTIONS, {}, _options);
this.options.selectors = _extends({}, DEFAULT_OPTIONS.selectors, {}, this.options.selectors);
if (this.options.linear) {
this._element.classList.add(ClassName.LINEAR);
}
this._steps = [].slice.call(this._element.querySelectorAll(this.options.selectors.steps));
this._steps.filter(function (step) {
return step.hasAttribute('data-target');
}).forEach(function (step) {
_this._stepsContents.push(_this._element.querySelector(step.getAttribute('data-target')));
});
detectAnimation(this._stepsContents, this.options);
this._setLinkListeners();
Object.defineProperty(this._element, customProperty, {
value: this,
writable: true
});
if (this._steps.length) {
show(this._element, this._currentIndex, this.options, function () {});
}
} // Private
var _proto = Stepper.prototype;
_proto._setLinkListeners = function _setLinkListeners() {
var _this2 = this;
this._steps.forEach(function (step) {
var trigger = step.querySelector(_this2.options.selectors.trigger);
if (_this2.options.linear) {
_this2._clickStepLinearListener = buildClickStepLinearListener(_this2.options);
trigger.addEventListener('click', _this2._clickStepLinearListener);
} else {
_this2._clickStepNonLinearListener = buildClickStepNonLinearListener(_this2.options);
trigger.addEventListener('click', _this2._clickStepNonLinearListener);
}
});
} // Public
;
_proto.next = function next() {
var _this3 = this;
var nextStep = this._currentIndex + 1 <= this._steps.length - 1 ? this._currentIndex + 1 : this._steps.length - 1;
show(this._element, nextStep, this.options, function () {
_this3._currentIndex = nextStep;
});
};
_proto.previous = function previous() {
var _this4 = this;
var previousStep = this._currentIndex - 1 >= 0 ? this._currentIndex - 1 : 0;
show(this._element, previousStep, this.options, function () {
_this4._currentIndex = previousStep;
});
};
_proto.to = function to(stepNumber) {
var _this5 = this;
var tempIndex = stepNumber - 1;
var nextStep = tempIndex >= 0 && tempIndex < this._steps.length ? tempIndex : 0;
show(this._element, nextStep, this.options, function () {
_this5._currentIndex = nextStep;
});
};
_proto.reset = function reset() {
var _this6 = this;
show(this._element, 0, this.options, function () {
_this6._currentIndex = 0;
});
};
_proto.destroy = function destroy() {
var _this7 = this;
this._steps.forEach(function (step) {
var trigger = step.querySelector(_this7.options.selectors.trigger);
if (_this7.options.linear) {
trigger.removeEventListener('click', _this7._clickStepLinearListener);
} else {
trigger.removeEventListener('click', _this7._clickStepNonLinearListener);
}
});
this._element[customProperty] = undefined;
this._element = undefined;
this._currentIndex = undefined;
this._steps = undefined;
this._stepsContents = undefined;
this._clickStepLinearListener = undefined;
this._clickStepNonLinearListener = undefined;
};
return Stepper;
}();
return Stepper;
}));
//# sourceMappingURL=bs-stepper.js.map

File diff suppressed because one or more lines are too long

File diff suppressed because one or more lines are too long

File diff suppressed because one or more lines are too long

File diff suppressed because it is too large Load diff

File diff suppressed because one or more lines are too long

View file

@ -1,47 +0,0 @@
/*
* DOM element rendering detection
* https://davidwalsh.name/detect-node-insertion
*/
@keyframes chartjs-render-animation {
from { opacity: 0.99; }
to { opacity: 1; }
}
.chartjs-render-monitor {
animation: chartjs-render-animation 0.001s;
}
/*
* DOM element resizing detection
* https://github.com/marcj/css-element-queries
*/
.chartjs-size-monitor,
.chartjs-size-monitor-expand,
.chartjs-size-monitor-shrink {
position: absolute;
direction: ltr;
left: 0;
top: 0;
right: 0;
bottom: 0;
overflow: hidden;
pointer-events: none;
visibility: hidden;
z-index: -1;
}
.chartjs-size-monitor-expand > div {
position: absolute;
width: 1000000px;
height: 1000000px;
left: 0;
top: 0;
}
.chartjs-size-monitor-shrink > div {
position: absolute;
width: 200%;
height: 200%;
left: 0;
top: 0;
}

File diff suppressed because it is too large Load diff

View file

@ -1 +0,0 @@
@keyframes chartjs-render-animation{from{opacity:.99}to{opacity:1}}.chartjs-render-monitor{animation:chartjs-render-animation 1ms}.chartjs-size-monitor,.chartjs-size-monitor-expand,.chartjs-size-monitor-shrink{position:absolute;direction:ltr;left:0;top:0;right:0;bottom:0;overflow:hidden;pointer-events:none;visibility:hidden;z-index:-1}.chartjs-size-monitor-expand>div{position:absolute;width:1000000px;height:1000000px;left:0;top:0}.chartjs-size-monitor-shrink>div{position:absolute;width:200%;height:200%;left:0;top:0}

File diff suppressed because one or more lines are too long

Some files were not shown because too many files have changed in this diff Show more