Merge branch 'dev' into feature/bedrock-creation

This commit is contained in:
Zedifus 2022-09-04 21:12:47 +01:00
commit 7f95f7085d
9 changed files with 145 additions and 78 deletions

View File

@ -30,6 +30,11 @@ win-dev-build:
--collect-all tzdata
--collect-all pytz
--collect-all six
- |
echo "Retrieving 'latest' updater from crafty-controller/crafty-4-windows-updater"
$src = 'https://gitlab.com/crafty-controller/crafty-4-windows-updater/-/jobs/artifacts/dev/raw/crafty_updater.exe?job=win-dev-build'
$dest = 'crafty_updater.exe'
Invoke-WebRequest -Uri $src -OutFile $dest
# Download latest:
# | https://gitlab.com/crafty-controller/crafty-4/-/jobs/artifacts/dev/download?job=win-dev-build
@ -38,6 +43,7 @@ win-dev-build:
paths:
- app\
- .\crafty.exe
- .\crafty_updater.exe
exclude:
- app\classes\**\*
@ -72,6 +78,11 @@ win-prod-build:
--collect-all tzdata
--collect-all pytz
--collect-all six
- |
echo "Retrieving 'latest' updater from crafty-controller/crafty-4-windows-updater"
$src = 'https://gitlab.com/crafty-controller/crafty-4-windows-updater/-/jobs/artifacts/master/raw/crafty_updater.exe?job=win-prod-build'
$dest = 'crafty_updater.exe'
Invoke-WebRequest -Uri $src -OutFile $dest
after_script:
- Add-Content -Path job.env -Value "JOB_ID=$CI_JOB_ID"
@ -82,6 +93,7 @@ win-prod-build:
paths:
- app\
- .\crafty.exe
- .\crafty_updater.exe
expire_in: never
exclude:
- app\classes\**\*

View File

@ -1,9 +1,11 @@
# Changelog
## --- [4.0.12] - 2022/TBD
## --- [4.0.12] - 2022/09/04
### New features
TBD
- Win Portable Updater will now be included in Windows Package ([Merge Request](https://gitlab.com/crafty-controller/crafty-4/-/merge_requests/446))
### Bug fixes
TBD
- Fix performance issues on server metrics panels (Temporarily setting to 24hr query) ([Merge Request](https://gitlab.com/crafty-controller/crafty-4/-/merge_requests/440))
- Fix no id on import3 servers ([Merge Request](https://gitlab.com/crafty-controller/crafty-4/-/merge_requests/442))
- Fix functionality of bedrock update ([Merge Request](https://gitlab.com/crafty-controller/crafty-4/-/merge_requests/441))
### Tweaks
TBD
### Lang

View File

@ -106,11 +106,9 @@ class ServersController(metaclass=Singleton):
return ret
def get_history_stats(self, server_id):
max_age = self.helper.get_setting("history_max_age")
now = datetime.datetime.now()
minimum_to_exist = now - datetime.timedelta(days=max_age)
srv = ServersController().get_server_instance_by_id(server_id)
return srv.stats_helper.get_history_stats(server_id, minimum_to_exist)
return srv.stats_helper.get_history_stats(server_id)
@staticmethod
def update_unloaded_server(server_obj):

View File

@ -1,6 +1,7 @@
import os
import logging
import datetime
from datetime import timedelta
from app.classes.models.servers import Servers, HelperServers
from app.classes.shared.helpers import Helpers
@ -137,7 +138,8 @@ class HelperServerStats:
)
return server_data
def get_history_stats(self, server_id, max_age):
def get_history_stats(self, server_id):
max_age = datetime.datetime.now() - timedelta(days=1)
return (
ServerStats.select()
.where(ServerStats.created > max_age)

View File

@ -74,6 +74,7 @@ class Import3:
min_mem=(int(server["memory_min"]) / 1000),
max_mem=(int(server["memory_max"]) / 1000),
port=server["server_port"],
user_id=HelperUsers.get_user_id_by_name("system"),
)
Console.info(
f"Imported server {server['server_name']}[{server['id']}] "
@ -91,6 +92,7 @@ class Import3:
min_mem=(int(json_data["memory_min"]) / 1000),
max_mem=(int(json_data["memory_max"]) / 1000),
port=json_data["server_port"],
user_id=HelperUsers.get_user_id_by_name("system"),
)
Console.info(
f"Imported server {json_data['server_name']}[{json_data['id']}] "

View File

@ -1108,6 +1108,22 @@ class ServerInstance:
except FileNotFoundError:
logger.error("Could not create backup of jarfile. File not found.")
# wait for backup
while self.is_backingup:
time.sleep(10)
# check if backup was successful
if self.last_backup_failed:
server_users = PermissionsServers.get_server_user_list(self.server_id)
for user in server_users:
self.helper.websocket_helper.broadcast_user(
user,
"notification",
"Backup failed for " + self.name + ". canceling update.",
)
return False
# lets download the files
if HelperServers.get_server_type_by_id(self.server_id) != "minecraft-bedrock":
# boolean returns true for false for success
downloaded = Helpers.download_file(
@ -1115,55 +1131,39 @@ class ServerInstance:
)
else:
# downloads zip from remote url
bedrock_url = Helpers.get_latest_bedrock_url()
if bedrock_url.lower().startswith("https"):
urllib.request.urlretrieve(
bedrock_url,
os.path.join(self.settings["path"], "bedrock_server.zip"),
try:
bedrock_url = Helpers.get_latest_bedrock_url()
if bedrock_url.lower().startswith("https"):
urllib.request.urlretrieve(
bedrock_url,
os.path.join(self.settings["path"], "bedrock_server.zip"),
)
unzip_path = os.path.join(self.settings["path"], "bedrock_server.zip")
unzip_path = self.helper.wtol_path(unzip_path)
# unzips archive that was downloaded.
FileHelpers.unzip_file(unzip_path)
# adjusts permissions for execution if os is not windows
if not self.helper.is_os_windows():
os.chmod(
os.path.join(self.settings["path"], "bedrock_server"), 0o0744
)
# we'll delete the zip we downloaded now
os.remove(os.path.join(self.settings["path"], "bedrock_server.zip"))
downloaded = True
except Exception as e:
logger.critical(
f"Failed to download bedrock executable for update \n{e}"
)
unzip_path = os.path.join(self.settings["path"], "bedrock_server.zip")
unzip_path = self.helper.wtol_path(unzip_path)
# unzips archive that was downloaded.
FileHelpers.unzip_file(unzip_path)
# adjusts permissions for execution if os is not windows
if not self.helper.is_os_windows():
os.chmod(os.path.join(self.settings["path"], "bedrock_server"), 0o0744)
if downloaded:
logger.info("Executable updated successfully. Starting Server")
# we'll delete the zip we downloaded now
os.remove(os.path.join(self.settings["path"], "bedrock_server.zip"))
downloaded = True
while self.stats_helper.get_server_stats()["updating"]:
if downloaded and not self.is_backingup:
logger.info("Executable updated successfully. Starting Server")
self.stats_helper.set_update(False)
if len(self.helper.websocket_helper.clients) > 0:
# There are clients
self.check_update()
server_users = PermissionsServers.get_server_user_list(
self.server_id
)
for user in server_users:
self.helper.websocket_helper.broadcast_user(
user,
"notification",
"Executable update finished for " + self.name,
)
time.sleep(3)
self.helper.websocket_helper.broadcast_page(
"/panel/server_detail",
"update_button_status",
{
"isUpdating": self.check_update(),
"server_id": self.server_id,
"wasRunning": was_started,
},
)
self.helper.websocket_helper.broadcast_page(
"/panel/dashboard", "send_start_reload", {}
)
self.stats_helper.set_update(False)
if len(self.helper.websocket_helper.clients) > 0:
# There are clients
self.check_update()
server_users = PermissionsServers.get_server_user_list(self.server_id)
for user in server_users:
self.helper.websocket_helper.broadcast_user(
@ -1171,29 +1171,52 @@ class ServerInstance:
"notification",
"Executable update finished for " + self.name,
)
self.management_helper.add_to_audit_log_raw(
"Alert",
"-1",
self.server_id,
"Executable update finished for " + self.name,
self.settings["server_ip"],
# sleep so first notif can completely run
time.sleep(3)
self.helper.websocket_helper.broadcast_page(
"/panel/server_detail",
"update_button_status",
{
"isUpdating": self.check_update(),
"server_id": self.server_id,
"wasRunning": was_started,
},
)
if was_started:
self.start_server()
elif not downloaded and not self.is_backingup:
time.sleep(5)
server_users = PermissionsServers.get_server_user_list(self.server_id)
for user in server_users:
self.helper.websocket_helper.broadcast_user(
user,
"notification",
"Executable update failed for "
+ self.name
+ ". Check log file for details.",
)
logger.error("Executable download failed.")
self.stats_helper.set_update(False)
self.helper.websocket_helper.broadcast_page(
"/panel/dashboard", "send_start_reload", {}
)
self.helper.websocket_helper.broadcast_page(
"/panel/server_detail", "remove_spinner", {}
)
server_users = PermissionsServers.get_server_user_list(self.server_id)
for user in server_users:
self.helper.websocket_helper.broadcast_user(
user,
"notification",
"Executable update finished for " + self.name,
)
self.management_helper.add_to_audit_log_raw(
"Alert",
"-1",
self.server_id,
"Executable update finished for " + self.name,
self.settings["server_ip"],
)
if was_started:
self.start_server()
else:
server_users = PermissionsServers.get_server_user_list(self.server_id)
for user in server_users:
self.helper.websocket_helper.broadcast_user(
user,
"notification",
"Executable update failed for "
+ self.name
+ ". Check log file for details.",
)
logger.error("Executable download failed.")
self.stats_helper.set_update(False)
# **********************************************************************************
# Minecraft Servers Statistics

View File

@ -186,7 +186,8 @@
{% elif server['stats']['updating']%}
<!-- WHAT HAPPENED HERE -->
<a data-id="{{server['server_data']['server_id']}}" class="">{{ translate('serverTerm', 'updating',
<a data-id="{{server['server_data']['server_id']}}" class=""><i
class="fa fa-spinner fa-spin"></i>&nbsp;{{ translate('serverTerm', 'updating',
data['lang']) }}</i></a>
{% elif server['stats']['waiting_start']%}
<!-- WHAT HAPPENED HERE -->

View File

@ -253,14 +253,31 @@
<button onclick="send_command(serverId, 'update_executable');" id="update_executable"
style="max-width: 7rem;" class="btn btn-warning m-1 flex-grow-1 disabled">{{ translate('serverConfig',
'update', data['lang']) }}</button>
{% if data['server_stats']['updating'] %}
<button onclick="send_command(serverId, 'update_executable');" id="update_executable"
style="max-width: 7rem;" class="btn btn-warning m-1 flex-grow-1 disabled">{{ translate('serverConfig',
'update', data['lang']) }}&nbsp;<i id="update-spinner" class="fa fa-spinner fa-spin"></i></button>
{% else %}
<button onclick="send_command(serverId, 'update_executable');" id="update_executable"
style="max-width: 7rem;" class="btn btn-warning m-1 flex-grow-1 disabled">{{ translate('serverConfig',
'update', data['lang']) }}&nbsp;<i style="visibility: hidden;" id="update-spinner"
class="fa fa-spinner fa-spin"></i></button>
{% end %}
<a class="btn btn-sm btn-danger disabled">{{ translate('serverConfig', 'deleteServer', data['lang'])
}}</a><br />
<small>{{ translate('serverConfig', 'stopBeforeDeleting', data['lang']) }}</small>
{% else %}
{% if not data['failed'] %}
{% if data['server_stats']['updating'] %}
<button onclick="send_command(serverId, 'update_executable');" id="update_executable"
style="max-width: 7rem;" class="btn btn-warning m-1 flex-grow-1">{{ translate('serverConfig',
'update', data['lang']) }}</button>
'update', data['lang']) }}&nbsp;<i id="update-spinner" class="fa fa-spinner fa-spin"></i></button>
{% else %}
<button onclick="send_command(serverId, 'update_executable');" id="update_executable"
style="max-width: 7rem;" class="btn btn-warning m-1 flex-grow-1">{{ translate('serverConfig',
'update', data['lang']) }}&nbsp;<i style="visibility: hidden;" id="update-spinner"
class="fa fa-spinner fa-spin"></i></button>
{% end %}
{% end %}
{% if not data['failed'] %}
<button onclick="deleteConfirm()" class="btn btn-sm btn-danger">{{ translate('serverConfig',
@ -356,6 +373,9 @@
function send_command(serverId, command) {
//<!-- this getCookie function is in base.html-->
var token = getCookie("_xsrf");
if (command == "update_executable") {
document.getElementById("update-spinner").style.visibility = "visible";
}
$.ajax({
type: "POST",
@ -508,6 +528,12 @@
});
}
$(document).ready(function () {
webSocket.on('remove_spinner', function () {
document.getElementById("update-spinner").style.visibility = "hidden";
});
});
</script>
{% end %}

View File

@ -55,7 +55,8 @@
{% if data['permissions']['Commands'] in data['user_permissions'] %}
{% if data['server_stats']['updating']%}
<div id="update_control_buttons" class="mt-4 flex-wrap d-flex justify-content-between justify-content-md-center align-items-center px-5 px-md-0" style="visibility: visible">
<button onclick="" id="start-btn" style="max-width: 7rem;" class="btn btn-warning m-1 flex-grow-1 disabled">{{ translate('serverTerm', 'updating', data['lang']) }}</button>
<button onclick="" id="start-btn" style="max-width: 7rem;" class="btn btn-warning m-1 flex-grow-1 disabled"><i
class="fa fa-spinner fa-spin"></i>&nbsp;{{ translate('serverTerm', 'updating', data['lang']) }}</button>
<button onclick="" id="restart-btn" style="max-width: 7rem;" class="btn btn-outline-primary m-1 flex-grow-1 disabled">{% raw translate('serverTerm', 'restart', data['lang']) %}</button>
<button onclick="" id="stop-btn" style="max-width: 7rem;" class="btn btn-danger m-1 flex-grow-1 disabled">{{ translate('serverTerm', 'stop', data['lang']) }}</button>
</div>