mirror of
https://github.com/WGDashboard/WGDashboard-PRW.git
synced 2026-08-03 22:42:57 +00:00
chore: make the config lowercase and add new routes
This commit is contained in:
+23
-23
@@ -1,4 +1,4 @@
|
||||
[Peers]
|
||||
[peers]
|
||||
remote_endpoint = 89.20.90.254
|
||||
peer_global_dns = 9.9.9.9
|
||||
peer_endpoint_allowed_ip = 0.0.0.0/0
|
||||
@@ -6,7 +6,7 @@ peer_display_mode = grid
|
||||
peer_mtu = 1420
|
||||
peer_keep_alive = 21
|
||||
|
||||
[Server]
|
||||
[server]
|
||||
hostname = 0.0.0.0
|
||||
port = 10086
|
||||
debug_enabled = True
|
||||
@@ -19,46 +19,46 @@ wgdashboard_refresh_interval = 60000
|
||||
wgdashboard_peer_list_display = grid
|
||||
wgdashboard_sort = status
|
||||
wgdashboard_theme = dark
|
||||
wgdashboard_apikey = true
|
||||
#wgdashboard_language = nl-NL
|
||||
wgdashboard_apikey = True
|
||||
wgdashboard_language = en-US
|
||||
log_level = DEBUG
|
||||
|
||||
[Account]
|
||||
username = admin
|
||||
password = $2b$12$1VN62Q7CS/BJcAahHAWsA.3CD6zPqWTmE/HN/AJqwP0zds2l25Fqe
|
||||
enable_totp = false
|
||||
totp_verified = false
|
||||
totp_key = ZSI2Z4QHSGVAK6TFVMZXORFDWKHDN4TQ
|
||||
[account]
|
||||
username = dselen
|
||||
password = $2b$12$bUcVL2v0OoJnraXtx.mHsOKFRnKEf/kmewqKXHOebitDZcJviPusm
|
||||
enable_totp = False
|
||||
totp_verified = False
|
||||
totp_key = CEBHHGL4HLYUDYXKTLIL34SVLXYPVHIO
|
||||
|
||||
[Other]
|
||||
welcome_session = false
|
||||
[other]
|
||||
welcome_session = False
|
||||
|
||||
[Database]
|
||||
[database]
|
||||
type = sqlite
|
||||
host =
|
||||
port =
|
||||
username =
|
||||
password =
|
||||
|
||||
[Email]
|
||||
[email]
|
||||
server =
|
||||
port =
|
||||
encryption =
|
||||
username =
|
||||
email_password =
|
||||
authentication_required = true
|
||||
authentication_required = True
|
||||
send_from =
|
||||
email_template =
|
||||
|
||||
[OIDC]
|
||||
admin_enable = false
|
||||
client_enable = false
|
||||
[oidc]
|
||||
admin_enable = False
|
||||
client_enable = False
|
||||
|
||||
[Clients]
|
||||
enable = true
|
||||
sign_up = true
|
||||
[clients]
|
||||
enable = True
|
||||
sign_up = True
|
||||
|
||||
[WireGuardConfiguration]
|
||||
[wireguardconfiguration]
|
||||
autostart =
|
||||
peer_tracking = false
|
||||
peer_tracking = False
|
||||
|
||||
|
||||
+7
-5
@@ -15,20 +15,21 @@ from modules.utilities.utilities import utilities as util
|
||||
from modules.utilities.logger import setup_logger
|
||||
|
||||
from modules.routes.routes import routes
|
||||
from modules.routes.routes_welcome import routes_welcome
|
||||
|
||||
if __name__ == '__main__':
|
||||
# Read the config file (ini)
|
||||
ok, config_contents = config.read()
|
||||
ok, config_data = config.read()
|
||||
if not ok:
|
||||
exit(1)
|
||||
found, config_server = config.filter(config_contents, 'SERVER')
|
||||
found, config_server = config.filter(config_data, 'SERVER')
|
||||
|
||||
# Configure the loglevel of WGDashboard
|
||||
wanted_loglevel = config_server.get('log_level', 'DEBUG').upper()
|
||||
setup_logger(wanted_loglevel)
|
||||
|
||||
# Get the database configuration from thee config
|
||||
found, config_database = config.filter(config_contents, 'DATABASE')
|
||||
found, config_database = config.filter(config_data, 'DATABASE')
|
||||
if not found:
|
||||
exit(1)
|
||||
|
||||
@@ -40,13 +41,14 @@ if __name__ == '__main__':
|
||||
|
||||
# Configure the Flask app
|
||||
app = flask.Flask("WGDashboard",
|
||||
static_url_path="",
|
||||
static_url_path=prefix,
|
||||
template_folder=os.path.abspath("./static/dist/WGDashboardAdmin"),
|
||||
static_folder=os.path.abspath("./static/dist/WGDashboardAdmin")
|
||||
)
|
||||
app.register_blueprint(routes, url_prefix=prefix)
|
||||
app.register_blueprint(routes_welcome, url_prefix=prefix)
|
||||
|
||||
app.wgd_config = config_contents
|
||||
app.wgd_config = config_data
|
||||
app.locale_path = './static/locales/'
|
||||
|
||||
app.secret_key = secrets.token_urlsafe(64)
|
||||
|
||||
@@ -1,19 +1,24 @@
|
||||
#!/bin/env python3
|
||||
|
||||
import logging as log
|
||||
import flask
|
||||
|
||||
from .utilities import config_utilities
|
||||
from .config_utils import config_utils
|
||||
|
||||
class config():
|
||||
@staticmethod
|
||||
def filter(config_contents: dict, filter_keyword: str) -> tuple[bool, dict]:
|
||||
def filter(config_data: dict, filter_keyword: str) -> tuple[bool, dict]:
|
||||
'''
|
||||
Helper function to grab a specific part of the config
|
||||
'''
|
||||
for section_name, section_values in config_contents.items():
|
||||
if str(section_name).lower() == filter_keyword.lower():
|
||||
lower_filter_keyword = filter_keyword.lower()
|
||||
|
||||
for section_name, section_values in config_data.items():
|
||||
if str(section_name).lower() == lower_filter_keyword:
|
||||
if isinstance(section_values, dict):
|
||||
return True, dict(section_values)
|
||||
|
||||
log.error("failed to properly filter the config")
|
||||
return False, {}
|
||||
|
||||
@staticmethod
|
||||
@@ -22,17 +27,37 @@ class config():
|
||||
check some basic things and then return the dict containing the config data
|
||||
'''
|
||||
|
||||
ok, candidate_path = config_utilities.search_known_paths()
|
||||
ok, candidate_path = config_utils.search_known_paths()
|
||||
if not ok:
|
||||
log.error("failed to retrieve a valid path for the config")
|
||||
return False, {}
|
||||
ok, config_contents = config_utilities.verify_contents(candidate_path)
|
||||
|
||||
ok, config_data = config_utils.read_data(candidate_path)
|
||||
if not ok:
|
||||
return False, {}
|
||||
|
||||
return True, config_contents
|
||||
return True, config_data
|
||||
|
||||
@staticmethod
|
||||
def update(section: str, key: str, value: str) -> bool:
|
||||
print(config_utilities.search_known_paths())
|
||||
print(section, key, value)
|
||||
def update(target_section: str, target_key: str, new_value) -> bool:
|
||||
lower_target_section = target_section.lower()
|
||||
lower_target_key = target_key.lower()
|
||||
|
||||
ok, config_data = config.read()
|
||||
if not ok:
|
||||
log.error("failed to read the config succesfully")
|
||||
return False
|
||||
|
||||
if not config_utils.find_section(config_data, lower_target_section):
|
||||
log.error("failed to find the given section")
|
||||
return False
|
||||
if not config_utils.find_key(config_data, lower_target_section, lower_target_key):
|
||||
log.error("failed to find the given key in the given section")
|
||||
return False
|
||||
|
||||
ok = config_utils.write_key(config_data, lower_target_section, lower_target_key, new_value)
|
||||
if not ok:
|
||||
log.error("failed to write the key to the file")
|
||||
return False
|
||||
|
||||
return True
|
||||
@@ -1,69 +0,0 @@
|
||||
#!/bin/env python3
|
||||
|
||||
import logging as log
|
||||
|
||||
import configparser as cp
|
||||
import os
|
||||
|
||||
class config_utilities():
|
||||
@staticmethod
|
||||
def search_known_paths() -> tuple[bool, str]:
|
||||
'''
|
||||
Look at predefined paths on the filesystem for a config file
|
||||
'''
|
||||
|
||||
possible_config_locations = [
|
||||
"./config.ini",
|
||||
f"{os.getenv('HOME')}/.config/wgdashboard/config.ini",
|
||||
"/etc/wgdashboard/config.ini",
|
||||
]
|
||||
|
||||
try:
|
||||
for path in possible_config_locations:
|
||||
if os.path.exists(path):
|
||||
return True, path
|
||||
else:
|
||||
continue
|
||||
return False, ''
|
||||
|
||||
except Exception as err:
|
||||
return False, ''
|
||||
|
||||
@staticmethod
|
||||
def verify_contents(config_path: str) -> tuple[bool, dict]:
|
||||
'''
|
||||
Check the existing config file for contents
|
||||
'''
|
||||
config = cp.ConfigParser()
|
||||
|
||||
try:
|
||||
config.read(config_path)
|
||||
|
||||
if len(config.sections()) == 0:
|
||||
return False, {}
|
||||
|
||||
for section in config.sections():
|
||||
if len(config.items(section)) == 0:
|
||||
config.remove_section(section)
|
||||
|
||||
config_dict = {}
|
||||
for section in config.sections():
|
||||
items = dict(config.items(section))
|
||||
|
||||
for key, value in items.items():
|
||||
if value.strip().lower() == 'true':
|
||||
items[key] = True
|
||||
elif value.strip().lower() == 'false':
|
||||
items[key] = False
|
||||
else:
|
||||
items[key] = value
|
||||
|
||||
config_dict[section] = items
|
||||
|
||||
return True, config_dict
|
||||
|
||||
except cp.ParsingError as err:
|
||||
return False, {}
|
||||
|
||||
except Exception as err:
|
||||
return False, {}
|
||||
@@ -6,12 +6,12 @@ import sqlalchemy
|
||||
import sqlalchemy.orm
|
||||
|
||||
from .schema import Base
|
||||
from .utilities import checks
|
||||
from .database_utils import database_utils
|
||||
|
||||
class database():
|
||||
@staticmethod
|
||||
def create_session(database_config: dict) -> tuple[bool, sqlalchemy.engine.Engine | None, sqlalchemy.orm.Session | None]:
|
||||
ok, connection_string = checks.generate_connection_string(database_config)
|
||||
ok, connection_string = database_utils.generate_connection_string(database_config)
|
||||
if not ok:
|
||||
return False, None, None
|
||||
|
||||
|
||||
@@ -6,7 +6,7 @@ import sqlalchemy.orm
|
||||
import json
|
||||
|
||||
from .schema import Base
|
||||
from .schema import Apikeys
|
||||
from .schema import Apikeys, User
|
||||
|
||||
class functions():
|
||||
@staticmethod
|
||||
@@ -63,5 +63,8 @@ class functions():
|
||||
return valid_keys, expired_keys
|
||||
|
||||
@staticmethod
|
||||
def retrieve_users(session: sqlalchemy.orm.Session):
|
||||
print("Wanting to check users")
|
||||
def retrieve_user_objects(session: sqlalchemy.orm.Session) -> list[dict]:
|
||||
stored_users = session.query(User).all()
|
||||
|
||||
for user in stored_users:
|
||||
print(user)
|
||||
@@ -17,7 +17,7 @@ class User(Base):
|
||||
|
||||
totp_enabled = sqlalchemy.Column(sqlalchemy.Boolean, default=False)
|
||||
totp_verified = sqlalchemy.Column(sqlalchemy.Boolean, default=False)
|
||||
totp_key = sqlalchemy.Column(sqlalchemy.String)
|
||||
totp_secret = sqlalchemy.Column(sqlalchemy.String)
|
||||
|
||||
email = sqlalchemy.Column(sqlalchemy.String)
|
||||
|
||||
|
||||
@@ -1,45 +0,0 @@
|
||||
#!/bin/env python3
|
||||
|
||||
import logging as log
|
||||
|
||||
import os
|
||||
from urllib.parse import quote_plus
|
||||
|
||||
from modules.utilities.utilities import utilities as util
|
||||
|
||||
class checks():
|
||||
'''
|
||||
This class functions as a collection of function to prepare a connection to a database.
|
||||
'''
|
||||
|
||||
@staticmethod
|
||||
def generate_connection_string(database_config: dict) -> tuple[bool, str]:
|
||||
if not 'type' in database_config:
|
||||
return False, ''
|
||||
|
||||
username = quote_plus(database_config.get('username', ''))
|
||||
password = quote_plus(database_config.get('password', ''))
|
||||
|
||||
match database_config['type']:
|
||||
case 'sqlite':
|
||||
local_database_path = os.path.abspath("./database")
|
||||
|
||||
exists = util.ensure_directory(local_database_path)
|
||||
if exists:
|
||||
connection_string = f'sqlite:///{local_database_path}/wgdashboard.db'
|
||||
else:
|
||||
return False, ''
|
||||
|
||||
case 'postgresql' | 'postgres':
|
||||
connection_string = f'postgresql+psycopg://{username}:{password}@{database_config.get('host', 'localhost')}:{database_config.get('port', '5432')}'
|
||||
|
||||
case 'mariadb':
|
||||
connection_string = f'mariadb+mariadbconnector://{username}:{password}@{database_config.get('host', 'localhost')}:{database_config.get('port', '3306')}'
|
||||
|
||||
case 'mysql':
|
||||
connection_string = f'mysql+pymysql://{username}:{password}@{database_config.get('host', 'localhost')}:{database_config.get('port', '3306')}'
|
||||
|
||||
case _:
|
||||
return False, ''
|
||||
|
||||
return True, connection_string
|
||||
@@ -11,7 +11,7 @@ import werkzeug
|
||||
from datetime import datetime
|
||||
|
||||
from .response import make_resp_obj
|
||||
from .utilities import helpers
|
||||
from .routes_utils import routes_utils
|
||||
from .locale import localeman
|
||||
|
||||
from ..database.functions import functions
|
||||
@@ -20,19 +20,10 @@ from ..config.config import config
|
||||
routes = flask.Blueprint("routes", __name__)
|
||||
|
||||
white_list = [
|
||||
"/", # we need to whitelist /
|
||||
"/client",
|
||||
"/static/",
|
||||
"/fileDownload",
|
||||
"/api/authenticate",
|
||||
"/api/locale",
|
||||
"getDashboardConfiguration",
|
||||
"getDashboardTheme",
|
||||
"getDashboardVersion",
|
||||
"sharePeer/get",
|
||||
"isTotpEnabled",
|
||||
"validateAuthentication",
|
||||
"favicon.ico",
|
||||
"/", "/client", "/static/", "/fileDownload",
|
||||
"/api/authenticate", "/api/locale", "getDashboardConfiguration",
|
||||
"getDashboardTheme", "getDashboardVersion", "sharePeer/get",
|
||||
"isTotpEnabled", "validateAuthentication", "favicon.ico",
|
||||
]
|
||||
|
||||
@routes.before_request
|
||||
@@ -42,6 +33,7 @@ def authentication_required():
|
||||
|
||||
ok, config_server = config.filter(flask.current_app.wgd_config, 'SERVER')
|
||||
if not ok:
|
||||
log.error("failed to filter the config in-memory")
|
||||
return make_resp_obj(False, "Internal error", {}, 500)
|
||||
|
||||
auth_required_flag = config_server.get('auth_req', True)
|
||||
@@ -54,7 +46,7 @@ def authentication_required():
|
||||
api_key = flask.request.headers.get("wgdashboard-apikey")
|
||||
|
||||
if api_key and api_key_enabled:
|
||||
if helpers.is_valid_api_key(api_key):
|
||||
if routes_utils.is_valid_api_key(api_key):
|
||||
return
|
||||
else:
|
||||
return make_resp_obj(False, "WGDashboard API-key does not exist or is invalid/expired", {}, 401)
|
||||
@@ -62,7 +54,7 @@ def authentication_required():
|
||||
if flask.session.get("role") == "admin":
|
||||
return
|
||||
|
||||
if helpers.is_path_allowed(path, white_list, flask.session):
|
||||
if routes_utils.is_path_allowed(path, white_list, flask.session):
|
||||
return
|
||||
|
||||
return make_resp_obj(False, "Unauthorized access", {}, 401)
|
||||
@@ -71,6 +63,7 @@ def authentication_required():
|
||||
def api_authenticate():
|
||||
ok, config_server = config.filter(flask.current_app.wgd_config, 'SERVER')
|
||||
if not ok:
|
||||
log.error("failed to filter the config in-memory")
|
||||
return make_resp_obj(False, "Internal error", {}, 500)
|
||||
|
||||
auth_required_flag = config_server.get('authentication_required', True)
|
||||
@@ -79,23 +72,25 @@ def api_authenticate():
|
||||
if not auth_required_flag:
|
||||
ok, config_other = config.filter(flask.current_app.wgd_config, 'OTHER')
|
||||
if not ok:
|
||||
log.error("failed to filter the config in-memory")
|
||||
return make_resp_obj(False, "Internal error", {}, 500)
|
||||
|
||||
return make_resp_obj(True, "Login successful, no authentication required", {"welcome_session": config_other.get("welcome_session", False)}, 200)
|
||||
welcome_session_enabled = config_other.get("welcome_session", False)
|
||||
return make_resp_obj(True, "Login successful, no authentication required", {"welcome_session": welcome_session_enabled}, 200)
|
||||
|
||||
# API key authentication
|
||||
api_key = flask.request.headers.get("wgdashboard-apikey")
|
||||
given_api_key = flask.request.headers.get("wgdashboard-apikey")
|
||||
api_key_enabled = config_server.get("wgdashboard_apikey", False)
|
||||
|
||||
if api_key and api_key_enabled:
|
||||
if helpers.is_valid_api_key(api_key):
|
||||
auth_token = hashlib.sha256(f"{api_key}{datetime.now()}".encode()).hexdigest()
|
||||
if given_api_key and api_key_enabled:
|
||||
if routes_utils.is_valid_api_key(given_api_key):
|
||||
authentication_token = hashlib.sha256(f"{given_api_key}{datetime.now()}".encode()).hexdigest()
|
||||
|
||||
flask.session['role'] = 'admin'
|
||||
flask.session['username'] = auth_token
|
||||
flask.session['username'] = authentication_token
|
||||
|
||||
resp = make_resp_obj(True,"Login successful", {}, 200)
|
||||
resp.set_cookie("authToken", auth_token)
|
||||
resp.set_cookie("authToken", authentication_token)
|
||||
flask.session.permanent = True
|
||||
return resp
|
||||
else:
|
||||
@@ -104,15 +99,19 @@ def api_authenticate():
|
||||
# Load account config
|
||||
ok, config_account = config.filter(flask.current_app.wgd_config, 'ACCOUNT')
|
||||
if not ok:
|
||||
log.error("failed to filter the config in-memory")
|
||||
return make_resp_obj(False, "Internal error", {}, 500)
|
||||
|
||||
data = flask.request.get_json()
|
||||
if not data:
|
||||
req_data = flask.request.get_json()
|
||||
if not req_data:
|
||||
return make_resp_obj(False, "Invalid request body", {}, 400)
|
||||
|
||||
username = data.get("username")
|
||||
password = data.get("password")
|
||||
totp_code = data.get("totp")
|
||||
username = req_data.get("username")
|
||||
password = req_data.get("password")
|
||||
totp_code = req_data.get("totp")
|
||||
|
||||
#stored_user_objects = functions.retrieve_user_objects(flask.current_app.db_session)
|
||||
#print(stored_user_objects)
|
||||
|
||||
stored_username = config_account.get("username")
|
||||
stored_password = config_account.get("password")
|
||||
@@ -136,10 +135,10 @@ def api_authenticate():
|
||||
and ((totp_enabled and totp_valid) or not totp_enabled)
|
||||
):
|
||||
# Generate a session token
|
||||
auth_token = hashlib.sha256(f"{username}{datetime.now()}".encode()).hexdigest()
|
||||
authentication_token = hashlib.sha256(f"{username}{datetime.now()}".encode()).hexdigest()
|
||||
|
||||
flask.session['role'] = 'admin'
|
||||
flask.session['username'] = auth_token
|
||||
flask.session['username'] = authentication_token
|
||||
flask.session.permanent = True
|
||||
|
||||
# Log success via your helper if available
|
||||
@@ -149,7 +148,7 @@ def api_authenticate():
|
||||
welcome_msg = config_other.get("welcome_session", "Welcome back!") if ok else "Welcome!"
|
||||
|
||||
resp = make_resp_obj(True, {"status": True}, 200)
|
||||
resp.set_cookie("authToken", auth_token, httponly=True, samesite='Lax')
|
||||
resp.set_cookie("authToken", authentication_token, httponly=True, samesite='Lax')
|
||||
return resp
|
||||
|
||||
# Log failure
|
||||
@@ -188,6 +187,7 @@ def api_locale_handler():
|
||||
def api_validate_auth():
|
||||
ok, config_server = config.filter(flask.current_app.wgd_config, 'SERVER')
|
||||
if not ok:
|
||||
log.error("failed to filter the config in-memory")
|
||||
return make_resp_obj(False, 'Internal error', {}, 500)
|
||||
|
||||
auth_required_flag = config_server.get('auth_req', True)
|
||||
@@ -202,6 +202,7 @@ def api_validate_auth():
|
||||
def api_retrieve_dashboard_version():
|
||||
ok, config_server = config.filter(flask.current_app.wgd_config, 'SERVER')
|
||||
if not ok:
|
||||
log.error("failed to filter the config in-memory")
|
||||
return make_resp_obj(False, 'Internal error', {}, 500)
|
||||
|
||||
return make_resp_obj(True, "", config_server.get("version"))
|
||||
@@ -210,6 +211,7 @@ def api_retrieve_dashboard_version():
|
||||
def api_retrieve_dashboard_theme():
|
||||
ok, config_server = config.filter(flask.current_app.wgd_config, 'SERVER')
|
||||
if not ok:
|
||||
log.error("failed to filter the config in-memory")
|
||||
return make_resp_obj(False, 'Internal error', {}, 500)
|
||||
|
||||
return make_resp_obj(True, "", config_server.get("wgdashboard_theme"), 200)
|
||||
@@ -222,6 +224,7 @@ def api_retrieve_dashboard_config():
|
||||
def api_totp_status():
|
||||
ok, config_account = config.filter(flask.current_app.wgd_config, 'ACCOUNT')
|
||||
if not ok:
|
||||
log.error("failed to filter the config in-memory")
|
||||
return make_resp_obj(False, 'Internal error', {}, 500)
|
||||
|
||||
data = config_account.get('enable_totp') and config_account.get('totp_verified')
|
||||
|
||||
@@ -1,27 +0,0 @@
|
||||
#!/bin/env python3
|
||||
|
||||
import flask
|
||||
|
||||
from ..database.functions import functions
|
||||
|
||||
class helpers():
|
||||
@staticmethod
|
||||
def is_valid_api_key(api_key: str) -> bool:
|
||||
valid_keys, _ = functions.retrieve_api_keys(flask.current_app.db_session)
|
||||
valid_key_strings = []
|
||||
|
||||
for key in valid_keys:
|
||||
valid_key_strings.append(key["key"])
|
||||
|
||||
return api_key in valid_key_strings
|
||||
|
||||
@staticmethod
|
||||
def is_path_allowed(path: str, white_list: list[str], session_data: dict) -> bool:
|
||||
# Allow if session has admin role
|
||||
if session_data.get("role") == "admin" and "username" in session_data:
|
||||
return True
|
||||
# Check white list
|
||||
for p in white_list:
|
||||
if p in path:
|
||||
return True
|
||||
return False
|
||||
@@ -1,2 +0,0 @@
|
||||
#!/bin/env python3
|
||||
|
||||
@@ -4,3 +4,4 @@ gunicorn==25.1.0
|
||||
sqlalchemy==2.0.48
|
||||
Flask==3.1.3
|
||||
Werkzeug==3.1.6
|
||||
pyotp==2.9.0
|
||||
@@ -29,7 +29,7 @@ const route = useRoute()
|
||||
</script>
|
||||
|
||||
<template>
|
||||
<div class="h-100 bg-body" :data-bs-theme="store.Configuration?.Server.wgdashboard_theme">
|
||||
<div class="h-100 bg-body" :data-bs-theme="store.Configuration?.server?.wgdashboard_theme ?? 'light'">
|
||||
<div style="z-index: 9999; height: 5px" class="position-absolute loadingBar top-0 start-0"></div>
|
||||
<nav class="navbar bg-dark sticky-top" data-bs-theme="dark" v-if="!route.meta.hideTopNav">
|
||||
<div class="container-fluid d-flex text-body align-items-center">
|
||||
|
||||
@@ -8,7 +8,7 @@ import { DashboardConfigurationStore } from "@/stores/DashboardConfigurationStor
|
||||
const dashboardConfigurationStore = DashboardConfigurationStore()
|
||||
const loading = ref(false)
|
||||
const values = reactive({
|
||||
enableClients: dashboardConfigurationStore.Configuration.Clients.enable
|
||||
enableClients: dashboardConfigurationStore.Configuration.clients.enable
|
||||
})
|
||||
|
||||
const toggling = ref(false)
|
||||
@@ -17,7 +17,7 @@ const updateSettings = async (key: string) => {
|
||||
await fetchPost("/api/updateDashboardConfigurationItem", {
|
||||
section: "Clients",
|
||||
key: key,
|
||||
value: dashboardConfigurationStore.Configuration.Clients[key]
|
||||
value: dashboardConfigurationStore.Configuration.clients[key]
|
||||
}, async (res) => {
|
||||
await dashboardConfigurationStore.getConfiguration()
|
||||
toggling.value = false
|
||||
@@ -41,11 +41,11 @@ const updateSettings = async (key: string) => {
|
||||
</h6>
|
||||
<div class="form-check form-switch ms-auto">
|
||||
<label class="form-check-label" for="oidc_switch">
|
||||
<LocaleText :t="dashboardConfigurationStore.Configuration.Clients.enable ? 'Enabled':'Disabled'"></LocaleText>
|
||||
<LocaleText :t="dashboardConfigurationStore.Configuration.clients.enable ? 'Enabled':'Disabled'"></LocaleText>
|
||||
</label>
|
||||
<input
|
||||
:disabled="toggling"
|
||||
v-model="dashboardConfigurationStore.Configuration.Clients.enable"
|
||||
v-model="dashboardConfigurationStore.Configuration.clients.enable"
|
||||
@change="updateSettings('enable')"
|
||||
class="form-check-input" type="checkbox" role="switch" id="oidc_switch">
|
||||
</div>
|
||||
@@ -58,11 +58,11 @@ const updateSettings = async (key: string) => {
|
||||
</h6>
|
||||
<div class="form-check form-switch ms-auto">
|
||||
<label class="form-check-label" for="sign_up_switch">
|
||||
<LocaleText :t="dashboardConfigurationStore.Configuration.Clients.sign_up ? 'Enabled':'Disabled'"></LocaleText>
|
||||
<LocaleText :t="dashboardConfigurationStore.Configuration.clients.sign_up ? 'Enabled':'Disabled'"></LocaleText>
|
||||
</label>
|
||||
<input
|
||||
:disabled="toggling"
|
||||
v-model="dashboardConfigurationStore.Configuration.Clients.sign_up"
|
||||
v-model="dashboardConfigurationStore.Configuration.clients.sign_up"
|
||||
@change="updateSettings('sign_up')"
|
||||
class="form-check-input" type="checkbox" role="switch" id="sign_up_switch">
|
||||
</div>
|
||||
|
||||
+1
-1
@@ -70,7 +70,7 @@ const saveRaw = async () => {
|
||||
:disabled="true"
|
||||
:read-only="saving"
|
||||
v-model="content"
|
||||
:theme="dashboardStore.Configuration.Server.wgdashboard_theme === 'dark' ? 'github-dark':'github'"
|
||||
:theme="dashboardStore.Configuration.server.wgdashboard_theme === 'dark' ? 'github-dark':'github'"
|
||||
:languages="[['ini', path]]"
|
||||
width="100%" height="600px">
|
||||
</CodeEditor>
|
||||
|
||||
@@ -50,7 +50,7 @@ export default {
|
||||
<div
|
||||
style="font-size: 0.8rem; color: #28a745"
|
||||
class="d-flex align-items-center"
|
||||
v-if="dashboardStore.Configuration.Server.wgdashboard_peer_list_display === 'list' && Peer.status === 'running'">
|
||||
v-if="dashboardStore.Configuration.server.wgdashboard_peer_list_display === 'list' && Peer.status === 'running'">
|
||||
<i class="bi bi-box-arrow-in-right me-2"></i>
|
||||
<span>
|
||||
{{ Peer.endpoint }}
|
||||
@@ -84,8 +84,8 @@ export default {
|
||||
{{Peer.name ? Peer.name : GetLocale('Untitled Peer')}}
|
||||
</h6>
|
||||
<div class="d-flex"
|
||||
:class="[dashboardStore.Configuration.Server.wgdashboard_peer_list_display === 'grid' ? 'gap-1 flex-column' : 'flex-row gap-3']">
|
||||
<div :class="{'d-flex gap-2 align-items-center' : dashboardStore.Configuration.Server.wgdashboard_peer_list_display === 'list'}">
|
||||
:class="[dashboardStore.Configuration.server.wgdashboard_peer_list_display === 'grid' ? 'gap-1 flex-column' : 'flex-row gap-3']">
|
||||
<div :class="{'d-flex gap-2 align-items-center' : dashboardStore.Configuration.server.wgdashboard_peer_list_display === 'list'}">
|
||||
<small class="text-muted">
|
||||
<LocaleText t="Public Key"></LocaleText>
|
||||
</small>
|
||||
@@ -93,7 +93,7 @@ export default {
|
||||
<samp>{{Peer.id}}</samp>
|
||||
</small>
|
||||
</div>
|
||||
<div :class="{'d-flex gap-2 align-items-center' : dashboardStore.Configuration.Server.wgdashboard_peer_list_display === 'list'}">
|
||||
<div :class="{'d-flex gap-2 align-items-center' : dashboardStore.Configuration.server.wgdashboard_peer_list_display === 'list'}">
|
||||
<small class="text-muted">
|
||||
<LocaleText t="Allowed IPs"></LocaleText>
|
||||
</small>
|
||||
@@ -102,7 +102,7 @@ export default {
|
||||
</small>
|
||||
</div>
|
||||
<div class="d-flex align-items-center gap-1"
|
||||
:class="{'ms-auto': dashboardStore.Configuration.Server.wgdashboard_peer_list_display === 'list'}"
|
||||
:class="{'ms-auto': dashboardStore.Configuration.server.wgdashboard_peer_list_display === 'list'}"
|
||||
>
|
||||
<PeerTagBadge :BackgroundColor="group.BackgroundColor" :GroupName="group.GroupName" :Icon="'bi-' + group.Icon"
|
||||
v-for="group in Object.values(ConfigurationInfo.Info.PeerGroups).filter(x => x.Peers.includes(Peer.id))"
|
||||
|
||||
@@ -26,11 +26,11 @@ const peerData = ref({
|
||||
allowed_ips: [],
|
||||
private_key: "",
|
||||
public_key: "",
|
||||
DNS: dashboardStore.Configuration.Peers.peer_global_dns,
|
||||
endpoint_allowed_ip: dashboardStore.Configuration.Peers.peer_endpoint_allowed_ip,
|
||||
DNS: dashboardStore.Configuration.peers.peer_global_dns,
|
||||
endpoint_allowed_ip: dashboardStore.Configuration.peers.peer_endpoint_allowed_ip,
|
||||
notes: "",
|
||||
keepalive: parseInt(dashboardStore.Configuration.Peers.peer_keep_alive),
|
||||
mtu: parseInt(dashboardStore.Configuration.Peers.peer_mtu),
|
||||
keepalive: parseInt(dashboardStore.Configuration.peers.peer_keep_alive),
|
||||
mtu: parseInt(dashboardStore.Configuration.peers.peer_mtu),
|
||||
preshared_key: "",
|
||||
preshared_key_bulkAdd: false,
|
||||
allowed_ips_validation: true,
|
||||
|
||||
@@ -31,10 +31,10 @@ export default {
|
||||
allowed_ips: [],
|
||||
private_key: "",
|
||||
public_key: "",
|
||||
DNS: this.dashboardStore.Configuration.Peers.peer_global_dns,
|
||||
endpoint_allowed_ip: this.dashboardStore.Configuration.Peers.peer_endpoint_allowed_ip,
|
||||
keepalive: parseInt(this.dashboardStore.Configuration.Peers.peer_keep_alive),
|
||||
mtu: parseInt(this.dashboardStore.Configuration.Peers.peer_mtu),
|
||||
DNS: this.dashboardStore.Configuration.peers.peer_global_dns,
|
||||
endpoint_allowed_ip: this.dashboardStore.Configuration.peers.peer_endpoint_allowed_ip,
|
||||
keepalive: parseInt(this.dashboardStore.Configuration.peers.peer_keep_alive),
|
||||
mtu: parseInt(this.dashboardStore.Configuration.peers.peer_mtu),
|
||||
preshared_key: "",
|
||||
preshared_key_bulkAdd: false,
|
||||
},
|
||||
|
||||
@@ -186,7 +186,7 @@ export default {
|
||||
}
|
||||
}
|
||||
},
|
||||
'dashboardConfigurationStore.Configuration.Server.wgdashboard_refresh_interval'(){
|
||||
'dashboardConfigurationStore.Configuration.server.wgdashboard_refresh_interval'(){
|
||||
clearInterval(this.dashboardConfigurationStore.Peers.RefreshInterval);
|
||||
this.setPeerInterval();
|
||||
}
|
||||
@@ -282,7 +282,7 @@ export default {
|
||||
setPeerInterval(){
|
||||
this.dashboardConfigurationStore.Peers.RefreshInterval = setInterval(() => {
|
||||
this.getPeers()
|
||||
}, parseInt(this.dashboardConfigurationStore.Configuration.Server.wgdashboard_refresh_interval))
|
||||
}, parseInt(this.dashboardConfigurationStore.Configuration.server.wgdashboard_refresh_interval))
|
||||
},
|
||||
},
|
||||
computed: {
|
||||
@@ -405,14 +405,14 @@ export default {
|
||||
x.allowed_ip.includes(this.wireguardConfigurationStore.searchString)
|
||||
}) : this.configurationPeers;
|
||||
|
||||
if (this.dashboardConfigurationStore.Configuration.Server.wgdashboard_sort === "restricted"){
|
||||
if (this.dashboardConfigurationStore.Configuration.server.wgdashboard_sort === "restricted"){
|
||||
return result.sort((a, b) => {
|
||||
if ( a[this.dashboardConfigurationStore.Configuration.Server.wgdashboard_sort]
|
||||
< b[this.dashboardConfigurationStore.Configuration.Server.wgdashboard_sort] ){
|
||||
if ( a[this.dashboardConfigurationStore.Configuration.server.wgdashboard_sort]
|
||||
< b[this.dashboardConfigurationStore.Configuration.server.wgdashboard_sort] ){
|
||||
return 1;
|
||||
}
|
||||
if ( a[this.dashboardConfigurationStore.Configuration.Server.wgdashboard_sort]
|
||||
> b[this.dashboardConfigurationStore.Configuration.Server.wgdashboard_sort]){
|
||||
if ( a[this.dashboardConfigurationStore.Configuration.server.wgdashboard_sort]
|
||||
> b[this.dashboardConfigurationStore.Configuration.server.wgdashboard_sort]){
|
||||
return -1;
|
||||
}
|
||||
return 0;
|
||||
@@ -420,12 +420,12 @@ export default {
|
||||
}
|
||||
|
||||
return result.sort((a, b) => {
|
||||
if ( a[this.dashboardConfigurationStore.Configuration.Server.wgdashboard_sort]
|
||||
< b[this.dashboardConfigurationStore.Configuration.Server.wgdashboard_sort] ){
|
||||
if ( a[this.dashboardConfigurationStore.Configuration.server.wgdashboard_sort]
|
||||
< b[this.dashboardConfigurationStore.Configuration.server.wgdashboard_sort] ){
|
||||
return -1;
|
||||
}
|
||||
if ( a[this.dashboardConfigurationStore.Configuration.Server.wgdashboard_sort]
|
||||
> b[this.dashboardConfigurationStore.Configuration.Server.wgdashboard_sort]){
|
||||
if ( a[this.dashboardConfigurationStore.Configuration.server.wgdashboard_sort]
|
||||
> b[this.dashboardConfigurationStore.Configuration.server.wgdashboard_sort]){
|
||||
return 1;
|
||||
}
|
||||
return 0;
|
||||
|
||||
@@ -108,7 +108,7 @@ const setFetchPeerListInterval = () => {
|
||||
clearInterval(fetchPeerListInterval.value)
|
||||
fetchPeerListInterval.value = setInterval(async () => {
|
||||
await fetchPeerList()
|
||||
}, parseInt(dashboardStore.Configuration.Server.wgdashboard_refresh_interval))
|
||||
}, parseInt(dashboardStore.Configuration.server.wgdashboard_refresh_interval))
|
||||
}
|
||||
setFetchPeerListInterval()
|
||||
onBeforeUnmount(() => {
|
||||
@@ -118,7 +118,7 @@ onBeforeUnmount(() => {
|
||||
})
|
||||
|
||||
watch(() => {
|
||||
return dashboardStore.Configuration.Server.wgdashboard_refresh_interval
|
||||
return dashboardStore.Configuration.server.wgdashboard_refresh_interval
|
||||
}, () => {
|
||||
setFetchPeerListInterval()
|
||||
})
|
||||
@@ -191,14 +191,14 @@ const searchPeers = computed(() => {
|
||||
wireguardConfigurationStore.Filter.ShowAllPeersWhenHiddenTags || (!wireguardConfigurationStore.Filter.ShowAllPeersWhenHiddenTags && taggedPeers.value.includes(x.id))
|
||||
));
|
||||
|
||||
if (dashboardStore.Configuration.Server.wgdashboard_sort === "restricted"){
|
||||
if (dashboardStore.Configuration.server.wgdashboard_sort === "restricted"){
|
||||
return result.sort((a, b) => {
|
||||
if ( a[dashboardStore.Configuration.Server.wgdashboard_sort]
|
||||
< b[dashboardStore.Configuration.Server.wgdashboard_sort] ){
|
||||
if ( a[dashboardStore.Configuration.server.wgdashboard_sort]
|
||||
< b[dashboardStore.Configuration.server.wgdashboard_sort] ){
|
||||
return 1;
|
||||
}
|
||||
if ( a[dashboardStore.Configuration.Server.wgdashboard_sort]
|
||||
> b[dashboardStore.Configuration.Server.wgdashboard_sort]){
|
||||
if ( a[dashboardStore.Configuration.server.wgdashboard_sort]
|
||||
> b[dashboardStore.Configuration.server.wgdashboard_sort]){
|
||||
return -1;
|
||||
}
|
||||
return 0;
|
||||
@@ -207,26 +207,26 @@ const searchPeers = computed(() => {
|
||||
|
||||
let re = []
|
||||
|
||||
if (dashboardStore.Configuration.Server.wgdashboard_sort === 'allowed_ip'){
|
||||
if (dashboardStore.Configuration.server.wgdashboard_sort === 'allowed_ip'){
|
||||
re = result.sort((a, b) => {
|
||||
if ( firstAllowedIPCount(a[dashboardStore.Configuration.Server.wgdashboard_sort])
|
||||
< firstAllowedIPCount(b[dashboardStore.Configuration.Server.wgdashboard_sort]) ){
|
||||
if ( firstAllowedIPCount(a[dashboardStore.Configuration.server.wgdashboard_sort])
|
||||
< firstAllowedIPCount(b[dashboardStore.Configuration.server.wgdashboard_sort]) ){
|
||||
return -1;
|
||||
}
|
||||
if ( firstAllowedIPCount(a[dashboardStore.Configuration.Server.wgdashboard_sort])
|
||||
> firstAllowedIPCount(b[dashboardStore.Configuration.Server.wgdashboard_sort])){
|
||||
if ( firstAllowedIPCount(a[dashboardStore.Configuration.server.wgdashboard_sort])
|
||||
> firstAllowedIPCount(b[dashboardStore.Configuration.server.wgdashboard_sort])){
|
||||
return 1;
|
||||
}
|
||||
return 0;
|
||||
}).slice(0, showPeersCount.value)
|
||||
}else{
|
||||
re = result.sort((a, b) => {
|
||||
if ( a[dashboardStore.Configuration.Server.wgdashboard_sort]
|
||||
< b[dashboardStore.Configuration.Server.wgdashboard_sort] ){
|
||||
if ( a[dashboardStore.Configuration.server.wgdashboard_sort]
|
||||
< b[dashboardStore.Configuration.server.wgdashboard_sort] ){
|
||||
return -1;
|
||||
}
|
||||
if ( a[dashboardStore.Configuration.Server.wgdashboard_sort]
|
||||
> b[dashboardStore.Configuration.Server.wgdashboard_sort]){
|
||||
if ( a[dashboardStore.Configuration.server.wgdashboard_sort]
|
||||
> b[dashboardStore.Configuration.server.wgdashboard_sort]){
|
||||
return 1;
|
||||
}
|
||||
return 0;
|
||||
@@ -411,7 +411,7 @@ watch(() => route.query.id, (newValue) => {
|
||||
</PeerSearch>
|
||||
<TransitionGroup name="peerList" tag="div" class="row gx-2 gy-2 z-0 position-relative">
|
||||
<div class="col-12"
|
||||
:class="{'col-lg-6 col-xl-4': dashboardStore.Configuration.Server.wgdashboard_peer_list_display === 'grid'}"
|
||||
:class="{'col-lg-6 col-xl-4': dashboardStore.Configuration.server.wgdashboard_peer_list_display === 'grid'}"
|
||||
:key="peer.id"
|
||||
v-for="(peer, order) in searchPeers">
|
||||
<Peer :Peer="peer"
|
||||
|
||||
+2
-2
@@ -80,7 +80,7 @@ const toggleFetchRealtimeTraffic = () => {
|
||||
if (props.configurationInfo.Status){
|
||||
fetchRealtimeTrafficInterval.value = setInterval(() => {
|
||||
fetchRealtimeTraffic()
|
||||
}, parseInt(dashboardStore.Configuration.Server.wgdashboard_refresh_interval))
|
||||
}, parseInt(dashboardStore.Configuration.server.wgdashboard_refresh_interval))
|
||||
}
|
||||
}
|
||||
|
||||
@@ -92,7 +92,7 @@ watch(() => props.configurationInfo.Status, () => {
|
||||
toggleFetchRealtimeTraffic()
|
||||
})
|
||||
|
||||
watch(() => dashboardStore.Configuration.Server.wgdashboard_refresh_interval, () => {
|
||||
watch(() => dashboardStore.Configuration.server.wgdashboard_refresh_interval, () => {
|
||||
toggleFetchRealtimeTraffic()
|
||||
})
|
||||
|
||||
|
||||
@@ -40,7 +40,7 @@ export default {
|
||||
],
|
||||
defaultContainer: "amnezia-awg",
|
||||
description: this.selectedPeer.name,
|
||||
hostName: this.dashboardStore.Configuration.Peers.remote_endpoint
|
||||
hostName: this.dashboardStore.Configuration.peers.remote_endpoint
|
||||
}
|
||||
QRCode.toCanvas(
|
||||
document.querySelector("#awg_vpn_qrcode"), btoa(JSON.stringify(awgQRCodeObject)), (error) => {
|
||||
|
||||
+1
-1
@@ -151,7 +151,7 @@ export default {
|
||||
:clearable="false"
|
||||
:disabled="!edit"
|
||||
v-if="this.job.Field === 'date'"
|
||||
:dark="this.store.Configuration.Server.wgdashboard_theme === 'dark'"
|
||||
:dark="this.store.Configuration.server.wgdashboard_theme === 'dark'"
|
||||
/>
|
||||
|
||||
<input class="form-control form-control-sm form-control-dark rounded-3 flex-grow-1"
|
||||
|
||||
@@ -98,7 +98,7 @@ export default {
|
||||
class="btn w-100 btn-sm text-primary-emphasis bg-primary-subtle rounded-3 border-1 border-primary-subtle position-relative">
|
||||
<i class="bi bi-sort-up me-2"></i>
|
||||
<LocaleText t="Sort By"></LocaleText>
|
||||
<span class="badge text-bg-primary ms-2">{{this.sort[store.Configuration.Server.wgdashboard_sort]}}</span>
|
||||
<span class="badge text-bg-primary ms-2">{{this.sort[store.Configuration.server.wgdashboard_sort]}}</span>
|
||||
</button>
|
||||
<ul class="dropdown-menu rounded-3">
|
||||
<li v-for="(value, key) in this.sort" >
|
||||
@@ -108,7 +108,7 @@ export default {
|
||||
</small>
|
||||
<small class="ms-auto">
|
||||
<i class="bi bi-check-circle-fill"
|
||||
v-if="store.Configuration.Server.wgdashboard_sort === key"></i>
|
||||
v-if="store.Configuration.server.wgdashboard_sort === key"></i>
|
||||
</small>
|
||||
</button>
|
||||
</li>
|
||||
@@ -120,7 +120,7 @@ export default {
|
||||
class="btn btn-sm w-100 text-primary-emphasis bg-primary-subtle rounded-3 border-1 border-primary-subtle position-relative">
|
||||
<i class="bi bi-arrow-repeat me-2"></i>
|
||||
<LocaleText t="Refresh Interval"></LocaleText>
|
||||
<span class="badge text-bg-primary ms-2">{{this.interval[store.Configuration.Server.wgdashboard_refresh_interval]}}</span>
|
||||
<span class="badge text-bg-primary ms-2">{{this.interval[store.Configuration.server.wgdashboard_refresh_interval]}}</span>
|
||||
</button>
|
||||
<ul class="dropdown-menu rounded-3">
|
||||
<li v-for="(value, key) in this.interval" >
|
||||
@@ -130,7 +130,7 @@ export default {
|
||||
</small>
|
||||
<small class="ms-auto">
|
||||
<i class="bi bi-check-circle-fill"
|
||||
v-if="store.Configuration.Server.wgdashboard_refresh_interval === key"></i>
|
||||
v-if="store.Configuration.server.wgdashboard_refresh_interval === key"></i>
|
||||
</small>
|
||||
</button>
|
||||
</li>
|
||||
@@ -140,9 +140,9 @@ export default {
|
||||
<button
|
||||
data-bs-toggle="dropdown"
|
||||
class="btn btn-sm w-100 text-primary-emphasis bg-primary-subtle rounded-3 border-1 border-primary-subtle position-relative">
|
||||
<i class="bi me-2" :class="'bi-' + store.Configuration.Server.wgdashboard_peer_list_display"></i>
|
||||
<i class="bi me-2" :class="'bi-' + store.Configuration.server.wgdashboard_peer_list_display"></i>
|
||||
<LocaleText t="Display"></LocaleText>
|
||||
<span class="badge text-bg-primary ms-2">{{this.display[store.Configuration.Server.wgdashboard_peer_list_display]}}</span>
|
||||
<span class="badge text-bg-primary ms-2">{{this.display[store.Configuration.server.wgdashboard_peer_list_display]}}</span>
|
||||
</button>
|
||||
<ul class="dropdown-menu rounded-3">
|
||||
<li v-for="(value, key) in this.display" >
|
||||
@@ -152,7 +152,7 @@ export default {
|
||||
</small>
|
||||
<small class="ms-auto">
|
||||
<i class="bi bi-check-circle-fill"
|
||||
v-if="store.Configuration.Server.wgdashboard_peer_list_display === key"></i>
|
||||
v-if="store.Configuration.server.wgdashboard_peer_list_display === key"></i>
|
||||
</small>
|
||||
</button>
|
||||
</li>
|
||||
|
||||
+1
-1
@@ -14,7 +14,7 @@ await fetchGet("/api/email/ready", {}, (res) => {
|
||||
const store = DashboardConfigurationStore()
|
||||
const email = reactive({
|
||||
Receiver: "",
|
||||
Body: store.Configuration.Email.email_template,
|
||||
Body: store.Configuration.email.email_template,
|
||||
Subject: "",
|
||||
IncludeAttachment: false,
|
||||
ConfigurationName: props.selectedPeer.configuration.Name,
|
||||
|
||||
@@ -155,7 +155,7 @@ export default {
|
||||
format="yyyy-MM-dd HH:mm:ss"
|
||||
preview-format="yyyy-MM-dd HH:mm:ss"
|
||||
|
||||
:dark="this.store.Configuration.Server.wgdashboard_theme === 'dark'"
|
||||
:dark="this.store.Configuration.server.wgdashboard_theme === 'dark'"
|
||||
/>
|
||||
</div>
|
||||
<div class="d-flex gap-2 flex-column flex-sm-row">
|
||||
|
||||
@@ -27,7 +27,7 @@ export default {
|
||||
computed: {
|
||||
getActiveCrossServer(){
|
||||
if (this.dashboardConfigurationStore.ActiveServerConfiguration){
|
||||
return new URL(this.dashboardConfigurationStore.CrossServerConfiguration.ServerList
|
||||
return new URL(this.dashboardConfigurationStore.CrossServerConfiguration.serverList
|
||||
[this.dashboardConfigurationStore.ActiveServerConfiguration].host)
|
||||
}
|
||||
return undefined
|
||||
@@ -57,7 +57,7 @@ export default {
|
||||
<template>
|
||||
<div class="col-md-3 col-lg-2 d-md-block p-2 navbar-container bg-transparent"
|
||||
:class="{active: this.dashboardConfigurationStore.ShowNavBar}"
|
||||
:data-bs-theme="dashboardConfigurationStore.Configuration.Server.wgdashboard_theme"
|
||||
:data-bs-theme="dashboardConfigurationStore.Configuration.server.wgdashboard_theme"
|
||||
>
|
||||
<nav id="sidebarMenu" class=" bg-body-tertiary sidebar border h-100 rounded-3 shadow overflow-y-scroll" >
|
||||
<div class="sidebar-sticky ">
|
||||
@@ -152,12 +152,12 @@ export default {
|
||||
<a :href="this.updateUrl" v-if="this.updateAvailable" class="text-decoration-none rounded-3" target="_blank">
|
||||
<small class="nav-link text-muted rounded-3" >
|
||||
<LocaleText :t="this.updateMessage"></LocaleText>
|
||||
(<LocaleText t="Current Version:"></LocaleText> {{ dashboardConfigurationStore.Configuration.Server.version }})
|
||||
(<LocaleText t="Current Version:"></LocaleText> {{ dashboardConfigurationStore.Configuration.server.version }})
|
||||
</small>
|
||||
</a>
|
||||
<small class="nav-link text-muted rounded-3" v-else>
|
||||
<LocaleText :t="this.updateMessage"></LocaleText>
|
||||
({{ dashboardConfigurationStore.Configuration.Server.version }})
|
||||
({{ dashboardConfigurationStore.Configuration.server.version }})
|
||||
</small>
|
||||
</li>
|
||||
</ul>
|
||||
|
||||
@@ -112,7 +112,7 @@ const uploadReady = computed(() => {
|
||||
:read-only="true"
|
||||
:display-language="true"
|
||||
v-model="uploadFiles[t].content"
|
||||
:theme="dashboardStore.Configuration.Server.wgdashboard_theme === 'dark' ? 'github-dark':'github'"
|
||||
:theme="dashboardStore.Configuration.server.wgdashboard_theme === 'dark' ? 'github-dark':'github'"
|
||||
:languages="[[t, uploadFiles[t].filename]]"
|
||||
width="100%" height="500px">
|
||||
</CodeEditor>
|
||||
|
||||
@@ -42,7 +42,7 @@ export default {
|
||||
if (res.status){
|
||||
this.isValid = true;
|
||||
this.showInvalidFeedback = false;
|
||||
this.store.Configuration.Account[this.targetData] = this.value
|
||||
this.store.Configuration.account[this.targetData] = this.value
|
||||
clearTimeout(this.timeout)
|
||||
this.timeout = setTimeout(() => {
|
||||
this.isValid = false;
|
||||
|
||||
@@ -28,7 +28,7 @@ export default {
|
||||
}
|
||||
},
|
||||
mounted() {
|
||||
this.value = this.store.Configuration.Account[this.targetData];
|
||||
this.value = this.store.Configuration.account[this.targetData];
|
||||
},
|
||||
methods:{
|
||||
async useValidation(e){
|
||||
@@ -43,7 +43,7 @@ export default {
|
||||
if (res.status){
|
||||
this.isValid = true;
|
||||
this.showInvalidFeedback = false;
|
||||
this.store.Configuration.Account[this.targetData] = this.value
|
||||
this.store.Configuration.account[this.targetData] = this.value
|
||||
clearTimeout(this.timeout)
|
||||
this.timeout = setTimeout(() => this.isValid = false, 5000);
|
||||
}else{
|
||||
|
||||
@@ -18,7 +18,7 @@ export default {
|
||||
}
|
||||
},
|
||||
mounted() {
|
||||
this.status = this.store.Configuration.Account["enable_totp"]
|
||||
this.status = this.store.Configuration.account["enable_totp"]
|
||||
},
|
||||
methods: {
|
||||
async resetMFA(){
|
||||
@@ -59,7 +59,7 @@ export default {
|
||||
<button class="btn bg-warning-subtle text-warning-emphasis border-1 border-warning-subtle ms-auto rounded-3 shadow-sm"
|
||||
v-if="this.status" @click="this.resetMFA()">
|
||||
<i class="bi bi-shield-lock-fill me-2"></i>
|
||||
<LocaleText t="Reset" v-if='this.store.Configuration.Account["totp_verified"]'></LocaleText>
|
||||
<LocaleText t="Reset" v-if='this.store.Configuration.account["totp_verified"]'></LocaleText>
|
||||
<LocaleText t="Setup" v-else></LocaleText>
|
||||
MFA
|
||||
</button>
|
||||
|
||||
@@ -15,7 +15,7 @@ export default {
|
||||
},
|
||||
data(){
|
||||
return {
|
||||
value: this.store.Configuration.Server.wgdashboard_apikey,
|
||||
value: this.store.Configuration.server.wgdashboard_apikey,
|
||||
apiKeys: [],
|
||||
newDashboardAPIKey: false
|
||||
}
|
||||
@@ -28,11 +28,11 @@ export default {
|
||||
value: this.value
|
||||
}, (res) => {
|
||||
if (res.status){
|
||||
this.store.Configuration.Peers[this.targetData] = this.value;
|
||||
this.store.Configuration.peers[this.targetData] = this.value;
|
||||
this.store.newMessage("Server",
|
||||
`API Keys function is successfully ${this.value ? 'enabled':'disabled'}`, "success")
|
||||
}else{
|
||||
this.value = this.store.Configuration.Peers[this.targetData];
|
||||
this.value = this.store.Configuration.peers[this.targetData];
|
||||
this.store.newMessage("Server",
|
||||
`API Keys function is failed to ${this.value ? 'enabled':'disabled'}`, "danger")
|
||||
}
|
||||
|
||||
+1
-1
@@ -79,7 +79,7 @@ export default {
|
||||
preview-format="yyyy-MM-dd HH:mm:ss"
|
||||
:clearable="false"
|
||||
:disabled="this.newKeyData.NeverExpire || this.submitting"
|
||||
:dark="this.store.Configuration.Server.wgdashboard_theme === 'dark'"
|
||||
:dark="this.store.Configuration.server.wgdashboard_theme === 'dark'"
|
||||
/>
|
||||
</div>
|
||||
<div class="form-check">
|
||||
|
||||
@@ -13,7 +13,7 @@ onMounted(() => {
|
||||
await fetchPost("/api/updateDashboardConfigurationItem", {
|
||||
section: "Email",
|
||||
key: id,
|
||||
value: store.Configuration.Email[id]
|
||||
value: store.Configuration.email[id]
|
||||
}, (res) => {
|
||||
if (res.status){
|
||||
x.classList.remove('is-invalid')
|
||||
@@ -74,7 +74,7 @@ const sendTestEmail = async () => {
|
||||
<div class="col-12">
|
||||
<div class="form-check mb-2 form-switch">
|
||||
<input class="form-check-input" type="checkbox" role="switch"
|
||||
v-model="store.Configuration.Email.authentication_required"
|
||||
v-model="store.Configuration.email.authentication_required"
|
||||
id="authentication_required">
|
||||
<label class="form-check-label" for="authentication_required">
|
||||
<LocaleText t="Require SMTP Authentication"></LocaleText>
|
||||
@@ -89,7 +89,7 @@ const sendTestEmail = async () => {
|
||||
</small></strong>
|
||||
</label>
|
||||
<input id="server"
|
||||
v-model="store.Configuration.Email.server"
|
||||
v-model="store.Configuration.email.server"
|
||||
type="text" class="form-control rounded-3">
|
||||
</div>
|
||||
</div>
|
||||
@@ -101,7 +101,7 @@ const sendTestEmail = async () => {
|
||||
</small></strong>
|
||||
</label>
|
||||
<input id="port"
|
||||
v-model="store.Configuration.Email.port"
|
||||
v-model="store.Configuration.email.port"
|
||||
type="text" class="form-control rounded-3">
|
||||
</div>
|
||||
</div>
|
||||
@@ -113,7 +113,7 @@ const sendTestEmail = async () => {
|
||||
</small></strong>
|
||||
</label>
|
||||
<select class="form-select rounded-3"
|
||||
v-model="store.Configuration.Email.encryption"
|
||||
v-model="store.Configuration.email.encryption"
|
||||
id="encryption">
|
||||
<option value="IMPLICITTLS">
|
||||
IMPLICIT TLS
|
||||
@@ -127,7 +127,7 @@ const sendTestEmail = async () => {
|
||||
</select>
|
||||
</div>
|
||||
</div>
|
||||
<div class="col-12 col-lg-4" v-if="store.Configuration.Email.authentication_required">
|
||||
<div class="col-12 col-lg-4" v-if="store.Configuration.email.authentication_required">
|
||||
<div class="form-group">
|
||||
<label for="username" class="text-muted mb-1">
|
||||
<strong><small>
|
||||
@@ -135,11 +135,11 @@ const sendTestEmail = async () => {
|
||||
</small></strong>
|
||||
</label>
|
||||
<input id="username"
|
||||
v-model="store.Configuration.Email.username"
|
||||
v-model="store.Configuration.email.username"
|
||||
type="text" class="form-control rounded-3">
|
||||
</div>
|
||||
</div>
|
||||
<div class="col-12 col-lg-4" v-if="store.Configuration.Email.authentication_required">
|
||||
<div class="col-12 col-lg-4" v-if="store.Configuration.email.authentication_required">
|
||||
<div class="form-group">
|
||||
<label for="email_password" class="text-muted mb-1">
|
||||
<strong><small>
|
||||
@@ -147,7 +147,7 @@ const sendTestEmail = async () => {
|
||||
</small></strong>
|
||||
</label>
|
||||
<input id="email_password"
|
||||
v-model="store.Configuration.Email.email_password"
|
||||
v-model="store.Configuration.email.email_password"
|
||||
type="password" class="form-control rounded-3">
|
||||
</div>
|
||||
</div>
|
||||
@@ -160,7 +160,7 @@ const sendTestEmail = async () => {
|
||||
</small></strong>
|
||||
</label>
|
||||
<input id="send_from"
|
||||
v-model="store.Configuration.Email.send_from"
|
||||
v-model="store.Configuration.email.send_from"
|
||||
type="text" class="form-control rounded-3">
|
||||
</div>
|
||||
</div>
|
||||
@@ -201,7 +201,7 @@ const sendTestEmail = async () => {
|
||||
</small>
|
||||
</label>
|
||||
<textarea class="form-control rounded-3 font-monospace"
|
||||
v-model="store.Configuration.Email.email_template"
|
||||
v-model="store.Configuration.email.email_template"
|
||||
id="email_template"
|
||||
style="min-height: 400px"></textarea>
|
||||
</div>
|
||||
|
||||
@@ -23,8 +23,8 @@ export default {
|
||||
}
|
||||
},
|
||||
mounted() {
|
||||
this.ipAddress = this.store.Configuration.Server.app_ip
|
||||
this.port = this.store.Configuration.Server.app_port
|
||||
this.ipAddress = this.store.Configuration.server.app_ip
|
||||
this.port = this.store.Configuration.server.app_port
|
||||
},
|
||||
methods: {
|
||||
async useValidation(e, targetData, value){
|
||||
@@ -38,7 +38,7 @@ export default {
|
||||
if (res.status){
|
||||
e.target.classList.add("is-valid")
|
||||
this.showInvalidFeedback = false;
|
||||
this.store.Configuration.Server[targetData] = value
|
||||
this.store.Configuration.server[targetData] = value
|
||||
clearTimeout(this.timeout)
|
||||
this.timeout = setTimeout(() => {
|
||||
e.target.classList.remove("is-valid")
|
||||
|
||||
@@ -26,7 +26,7 @@ export default {
|
||||
lang_id: lang_id
|
||||
}, (res) => {
|
||||
if (res.status){
|
||||
this.store.Configuration.Server.wgdashboard_language = lang_id;
|
||||
this.store.Configuration.server.wgdashboard_language = lang_id;
|
||||
this.store.Locale = res.data
|
||||
}else{
|
||||
this.store.newMessage("Server", "WGDashboard language update failed", "danger")
|
||||
@@ -36,7 +36,7 @@ export default {
|
||||
},
|
||||
computed:{
|
||||
currentLanguage(){
|
||||
let lang = this.store.Configuration.Server.wgdashboard_language;
|
||||
let lang = this.store.Configuration.server.wgdashboard_language;
|
||||
return this.languages.find(x => x.lang_id === lang)
|
||||
}
|
||||
}
|
||||
|
||||
+3
-3
@@ -29,8 +29,8 @@ export default {
|
||||
}
|
||||
},
|
||||
mounted() {
|
||||
this.app_ip = this.store.Configuration.Server.app_ip;
|
||||
this.app_port = this.store.Configuration.Server.app_port;
|
||||
this.app_ip = this.store.Configuration.server.app_ip;
|
||||
this.app_port = this.store.Configuration.server.app_port;
|
||||
},
|
||||
methods:{
|
||||
async useValidation(){
|
||||
@@ -43,7 +43,7 @@ export default {
|
||||
if (res.status){
|
||||
this.isValid = true;
|
||||
this.showInvalidFeedback = false;
|
||||
this.store.Configuration.Account[this.targetData] = this.value
|
||||
this.store.Configuration.account[this.targetData] = this.value
|
||||
clearTimeout(this.timeout)
|
||||
this.timeout = setTimeout(() => this.isValid = false, 5000);
|
||||
}else{
|
||||
|
||||
+2
-2
@@ -32,7 +32,7 @@ export default {
|
||||
}
|
||||
},
|
||||
mounted() {
|
||||
this.value = this.store.Configuration.Server[this.targetData];
|
||||
this.value = this.store.Configuration.server[this.targetData];
|
||||
},
|
||||
methods:{
|
||||
async useValidation(){
|
||||
@@ -46,7 +46,7 @@ export default {
|
||||
if (res.status){
|
||||
this.isValid = true;
|
||||
this.showInvalidFeedback = false;
|
||||
this.store.Configuration.Account[this.targetData] = this.value
|
||||
this.store.Configuration.account[this.targetData] = this.value
|
||||
clearTimeout(this.timeout)
|
||||
this.timeout = setTimeout(() => this.isValid = false, 5000);
|
||||
this.WireguardConfigurationStore.getConfigurations()
|
||||
|
||||
+1
-1
@@ -6,7 +6,7 @@ import {WireguardConfigurationsStore} from "@/stores/WireguardConfigurationsStor
|
||||
import {fetchPost} from "@/utilities/fetch.js";
|
||||
const store = DashboardConfigurationStore()
|
||||
const wireguardConfigurationStore = WireguardConfigurationsStore()
|
||||
const data = ref(store.Configuration.WireGuardConfiguration.autostart)
|
||||
const data = ref(store.Configuration.wireguardconfiguration.autostart)
|
||||
|
||||
const configurations = computed(() => {
|
||||
return wireguardConfigurationStore.Configurations.map(x => x.Name)
|
||||
|
||||
@@ -18,7 +18,7 @@ export default {
|
||||
value: value
|
||||
}, (res) => {
|
||||
if (res.status){
|
||||
this.dashboardConfigurationStore.Configuration.Server.wgdashboard_theme = value;
|
||||
this.dashboardConfigurationStore.Configuration.server.wgdashboard_theme = value;
|
||||
}
|
||||
});
|
||||
}
|
||||
@@ -36,13 +36,13 @@ export default {
|
||||
<div class="d-flex gap-1">
|
||||
<button class="btn bg-primary-subtle text-primary-emphasis flex-grow-1"
|
||||
@click="this.switchTheme('light')"
|
||||
:class="{active: this.dashboardConfigurationStore.Configuration.Server.wgdashboard_theme === 'light'}">
|
||||
:class="{active: this.dashboardConfigurationStore.Configuration.server.wgdashboard_theme === 'light'}">
|
||||
<i class="bi bi-sun-fill me-2"></i>
|
||||
<LocaleText t="Light"></LocaleText>
|
||||
</button>
|
||||
<button class="btn bg-primary-subtle text-primary-emphasis flex-grow-1"
|
||||
@click="this.switchTheme('dark')"
|
||||
:class="{active: this.dashboardConfigurationStore.Configuration.Server.wgdashboard_theme === 'dark'}">
|
||||
:class="{active: this.dashboardConfigurationStore.Configuration.server.wgdashboard_theme === 'dark'}">
|
||||
<i class="bi bi-moon-fill me-2"></i>
|
||||
<LocaleText t="Dark"></LocaleText>
|
||||
</button>
|
||||
|
||||
+1
-1
@@ -10,7 +10,7 @@ import {DashboardConfigurationStore} from "@/stores/DashboardConfigurationStore.
|
||||
|
||||
const store = WireguardConfigurationsStore()
|
||||
const dashboardStore = DashboardConfigurationStore()
|
||||
const peerTrackingStatus = ref(dashboardStore.Configuration.WireGuardConfiguration.peer_tracking)
|
||||
const peerTrackingStatus = ref(dashboardStore.Configuration.wireguardconfiguration.peer_tracking)
|
||||
const loaded = ref(false)
|
||||
const trackingData = ref({})
|
||||
onMounted(async () => {
|
||||
|
||||
@@ -29,7 +29,7 @@ export default {
|
||||
}
|
||||
},
|
||||
mounted() {
|
||||
this.value = this.store.Configuration.Peers[this.targetData];
|
||||
this.value = this.store.Configuration.peers[this.targetData];
|
||||
},
|
||||
methods:{
|
||||
async useValidation(){
|
||||
@@ -42,7 +42,7 @@ export default {
|
||||
if (res.status){
|
||||
this.isValid = true;
|
||||
this.showInvalidFeedback = false;
|
||||
this.store.Configuration.Peers[this.targetData] = this.value
|
||||
this.store.Configuration.peers[this.targetData] = this.value
|
||||
clearTimeout(this.timeout)
|
||||
this.timeout = setTimeout(() => this.isValid = false, 5000);
|
||||
|
||||
|
||||
@@ -63,7 +63,7 @@ export default {
|
||||
|
||||
<template>
|
||||
<div class="container-fluid login-container-fluid d-flex main pt-5 overflow-scroll"
|
||||
:data-bs-theme="this.store.Configuration.Server.wgdashboard_theme">
|
||||
:data-bs-theme="this.store.Configuration.server.wgdashboard_theme">
|
||||
<div class="m-auto text-body" style="width: 500px">
|
||||
<div class="d-flex flex-column">
|
||||
<div>
|
||||
|
||||
@@ -28,12 +28,12 @@ export default {
|
||||
</div>
|
||||
<div class="w-100 d-flex gap-3 flex-column p-3 border border-1 border-secondary-subtle rounded-3"
|
||||
style="height: 400px; overflow-y: scroll">
|
||||
<RemoteServer v-for="(server, key) in this.store.CrossServerConfiguration.ServerList"
|
||||
<RemoteServer v-for="(server, key) in this.store.CrossServerConfiguration.serverList"
|
||||
@setActiveServer="this.store.setActiveCrossServer(key)"
|
||||
@delete="this.store.deleteCrossServerConfiguration(key)"
|
||||
:key="key"
|
||||
:server="server"></RemoteServer>
|
||||
<h6 class="text-muted m-auto" v-if="Object.keys(this.store.CrossServerConfiguration.ServerList).length === 0">
|
||||
<h6 class="text-muted m-auto" v-if="Object.keys(this.store.CrossServerConfiguration.serverList).length === 0">
|
||||
<LocaleText t="Click"></LocaleText>
|
||||
<i class="bi bi-plus-circle-fill mx-1"></i>
|
||||
<LocaleText t="to add your server"></LocaleText>
|
||||
|
||||
@@ -41,19 +41,19 @@ export const DashboardConfigurationStore = defineStore('DashboardConfigurationSt
|
||||
window.localStorage.setItem('CrossServerConfiguration', JSON.stringify(this.CrossServerConfiguration))
|
||||
},
|
||||
addCrossServerConfiguration(){
|
||||
this.CrossServerConfiguration.ServerList[v4().toString()] = {
|
||||
this.CrossServerConfiguration.serverList[v4().toString()] = {
|
||||
host: "",
|
||||
apiKey: "",
|
||||
active: false
|
||||
}
|
||||
},
|
||||
deleteCrossServerConfiguration(key){
|
||||
delete this.CrossServerConfiguration.ServerList[key];
|
||||
delete this.CrossServerConfiguration.serverList[key];
|
||||
},
|
||||
getActiveCrossServer(){
|
||||
const key = localStorage.getItem('ActiveCrossServerConfiguration');
|
||||
if (key !== null){
|
||||
return this.CrossServerConfiguration.ServerList[key]
|
||||
return this.CrossServerConfiguration.serverList[key]
|
||||
}
|
||||
return undefined
|
||||
},
|
||||
|
||||
@@ -19,7 +19,7 @@ export default {
|
||||
</script>
|
||||
|
||||
<template>
|
||||
<div class="container-fluid flex-grow-1 main" :data-bs-theme="this.dashboardConfigurationStore.Configuration.Server.wgdashboard_theme">
|
||||
<div class="container-fluid flex-grow-1 main" :data-bs-theme="this.dashboardConfigurationStore.Configuration.server.wgdashboard_theme">
|
||||
<div class="row h-100">
|
||||
<Navbar></Navbar>
|
||||
<main class="col-md-9 col-lg-10 overflow-y-scroll mb-0 pt-2">
|
||||
|
||||
@@ -56,7 +56,7 @@ export default {
|
||||
|
||||
<template>
|
||||
<div class="container-fluid login-container-fluid d-flex main pt-5 overflow-scroll"
|
||||
:data-bs-theme="this.store.Configuration.Server.wgdashboard_theme">
|
||||
:data-bs-theme="this.store.Configuration.server.wgdashboard_theme">
|
||||
<div class="m-auto text-body" style="width: 500px">
|
||||
<span class="dashboardLogo display-4">
|
||||
<LocaleText t="Nice to meet you!"></LocaleText>
|
||||
|
||||
Reference in New Issue
Block a user