mirror of
https://github.com/aclist/dztui.git
synced 2026-10-26 12:42:34 +01:00
Compare commits
12
Commits
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
1752018331 | ||
|
|
01be1247b4 | ||
|
|
27d5c4b4b2 | ||
|
|
045e47037e | ||
|
|
3bc2a54ee4 | ||
|
|
4e22b82703 | ||
|
|
492ed221c4 | ||
|
|
71a61a9201 | ||
|
|
516735defa | ||
|
|
9a3df70914 | ||
|
|
c41e47859f | ||
|
|
11bbe15ecb |
No files matched your search
@@ -6,6 +6,7 @@ import subprocess
|
|||||||
import vdf # type: ignore
|
import vdf # type: ignore
|
||||||
|
|
||||||
from pathlib import Path
|
from pathlib import Path
|
||||||
|
from requests.exceptions import HTTPError
|
||||||
from typing import Any, Union
|
from typing import Any, Union
|
||||||
from warnings import deprecated
|
from warnings import deprecated
|
||||||
|
|
||||||
@@ -32,6 +33,7 @@ from dzgui.const.endpoints import (
|
|||||||
UNSUB_ENDPOINT,
|
UNSUB_ENDPOINT,
|
||||||
)
|
)
|
||||||
from dzgui.strings import wizard
|
from dzgui.strings import wizard
|
||||||
|
from dzgui.strings.errors import api_validation_error, workshop_endpoint_error
|
||||||
from dzgui.util.bash import concat_bash_args
|
from dzgui.util.bash import concat_bash_args
|
||||||
|
|
||||||
logger = logging.getLogger(APP_NAME)
|
logger = logging.getLogger(APP_NAME)
|
||||||
@@ -262,6 +264,16 @@ def find_user_id_32(path: Path) -> int:
|
|||||||
return int(uid) & 0xFFFFFFFF
|
return int(uid) & 0xFFFFFFFF
|
||||||
|
|
||||||
|
|
||||||
|
class SteamAPIKeyError(Exception):
|
||||||
|
def __init__(self, msg=None):
|
||||||
|
super().__init__(msg or api_validation_error)
|
||||||
|
|
||||||
|
|
||||||
|
class SteamWorkshopEndpointError(Exception):
|
||||||
|
def __init__(self, msg=None):
|
||||||
|
super().__init__(msg or workshop_endpoint_error)
|
||||||
|
|
||||||
|
|
||||||
def update_workshop(key: str, mod: int, endpoint: str) -> None:
|
def update_workshop(key: str, mod: int, endpoint: str) -> None:
|
||||||
payload: dict[str, Union[int, str]] = {
|
payload: dict[str, Union[int, str]] = {
|
||||||
"publishedfileid": mod,
|
"publishedfileid": mod,
|
||||||
@@ -273,8 +285,19 @@ def update_workshop(key: str, mod: int, endpoint: str) -> None:
|
|||||||
try:
|
try:
|
||||||
res = requests.post(endpoint, params=payload, timeout=REQUEST_TIMEOUT)
|
res = requests.post(endpoint, params=payload, timeout=REQUEST_TIMEOUT)
|
||||||
res.raise_for_status()
|
res.raise_for_status()
|
||||||
|
except HTTPError as e:
|
||||||
|
logger.critical(e)
|
||||||
|
match res.status_code:
|
||||||
|
case 403:
|
||||||
|
raise SteamAPIKeyError()
|
||||||
|
case 404:
|
||||||
|
raise SteamWorkshopEndpointError()
|
||||||
|
case _:
|
||||||
|
# TODO: apply redaction filter
|
||||||
|
raise e
|
||||||
except Exception as e:
|
except Exception as e:
|
||||||
logger.critical(e)
|
logger.critical(e)
|
||||||
|
raise e
|
||||||
|
|
||||||
|
|
||||||
def subscribe(key: str, mod: int) -> None:
|
def subscribe(key: str, mod: int) -> None:
|
||||||
|
|||||||
@@ -36,7 +36,7 @@ HEX_GREEN = "#32CD32"
|
|||||||
HEX_RED = "#FF0000"
|
HEX_RED = "#FF0000"
|
||||||
HEX_ORANGE = "#FFAC1C"
|
HEX_ORANGE = "#FFAC1C"
|
||||||
|
|
||||||
# FIXME: normalize icon names
|
# TODO: normalize icon names
|
||||||
CALCULATOR = "accessories-calculator-symbolic"
|
CALCULATOR = "accessories-calculator-symbolic"
|
||||||
CARET_DOWN = "go-down-symbolic"
|
CARET_DOWN = "go-down-symbolic"
|
||||||
CARET_UP = "go-up-symbolic"
|
CARET_UP = "go-up-symbolic"
|
||||||
|
|||||||
+9
-2
@@ -4,17 +4,24 @@ from pathlib import Path
|
|||||||
|
|
||||||
from dzgui.api.steam import get_app_path
|
from dzgui.api.steam import get_app_path
|
||||||
from dzgui.config.query import lookup
|
from dzgui.config.query import lookup
|
||||||
from dzgui.const.constants import APPID_DAYZ, APP_NAME
|
from dzgui.const.constants import APPID_DAYZ, APP_NAME, APPNAME_DAYZ
|
||||||
from dzgui.const.enum import Preferences
|
from dzgui.const.enum import Preferences
|
||||||
|
|
||||||
|
from dzgui.strings.preconnect import resync
|
||||||
|
|
||||||
|
|
||||||
logger = logging.getLogger(APP_NAME)
|
logger = logging.getLogger(APP_NAME)
|
||||||
|
|
||||||
|
|
||||||
|
class VDFSyncError(Exception):
|
||||||
|
pass
|
||||||
|
|
||||||
|
|
||||||
def is_dayz_installed(config: Path) -> None:
|
def is_dayz_installed(config: Path) -> None:
|
||||||
try:
|
try:
|
||||||
path = lookup(config, Preferences.DEFAULT)
|
path = lookup(config, Preferences.DEFAULT)
|
||||||
get_app_path(Path(path), APPID_DAYZ)
|
get_app_path(Path(path), APPID_DAYZ)
|
||||||
except Exception as e:
|
except Exception as e:
|
||||||
logger.critical(e)
|
logger.critical(e)
|
||||||
raise e
|
msg = resync.format(APPNAME_DAYZ)
|
||||||
|
raise VDFSyncError(msg)
|
||||||
@@ -48,7 +48,7 @@ from dzgui.strings.dialogs import (
|
|||||||
)
|
)
|
||||||
from dzgui.strings import kb
|
from dzgui.strings import kb
|
||||||
from dzgui.strings.server_mods import checkmark, resync
|
from dzgui.strings.server_mods import checkmark, resync
|
||||||
from dzgui.util.format import format_mib
|
from dzgui.util.format import format_exception, format_mib
|
||||||
from dzgui.util.strings import dialog, server_timeout
|
from dzgui.util.strings import dialog, server_timeout
|
||||||
from dzgui.util.symlink import rebuild_symlinks
|
from dzgui.util.symlink import rebuild_symlinks
|
||||||
from dzgui.views.dialogs.generic import ExceptionDialog
|
from dzgui.views.dialogs.generic import ExceptionDialog
|
||||||
@@ -300,6 +300,11 @@ class ConnectionManager:
|
|||||||
dialog = ServerDetailsDialog(self.controller, details)
|
dialog = ServerDetailsDialog(self.controller, details)
|
||||||
dialog.run()
|
dialog.run()
|
||||||
|
|
||||||
|
def _workshop_timeout(self, msg: str) -> None:
|
||||||
|
dialog = ExceptionDialog(self.controller, msg)
|
||||||
|
dialog.show_all()
|
||||||
|
dialog.run()
|
||||||
|
|
||||||
def _server_timeout(self) -> None:
|
def _server_timeout(self) -> None:
|
||||||
dialog = ExceptionDialog(self.controller, server_timeout)
|
dialog = ExceptionDialog(self.controller, server_timeout)
|
||||||
dialog.set_details_buffer(kb.DZG_006)
|
dialog.set_details_buffer(kb.DZG_006)
|
||||||
@@ -351,8 +356,14 @@ class ConnectionManager:
|
|||||||
for title, mod, stamp, size in self.missing_mods:
|
for title, mod, stamp, size in self.missing_mods:
|
||||||
if self.controller.is_cancel_pending():
|
if self.controller.is_cancel_pending():
|
||||||
return
|
return
|
||||||
subscribe(key, int(mod))
|
try:
|
||||||
time.sleep(API_RATE_LIMIT)
|
subscribe(key, int(mod))
|
||||||
|
time.sleep(API_RATE_LIMIT)
|
||||||
|
except Exception as e:
|
||||||
|
msg = format_exception(e)
|
||||||
|
func = StoredFunc(self._workshop_timeout, msg)
|
||||||
|
self.thread_man.set_cleanup_func(func, destroy_first=True)
|
||||||
|
return
|
||||||
|
|
||||||
self.thread_man.update_dialog(waiting_for_directories)
|
self.thread_man.update_dialog(waiting_for_directories)
|
||||||
for title, mod, stamp, size in self.missing_mods:
|
for title, mod, stamp, size in self.missing_mods:
|
||||||
|
|||||||
@@ -122,7 +122,11 @@ class ModManager:
|
|||||||
def unsub_atomic_mod(self, mod: str) -> None:
|
def unsub_atomic_mod(self, mod: str) -> None:
|
||||||
config_man = self.controller.get_config_man()
|
config_man = self.controller.get_config_man()
|
||||||
key = config_man.lookup(Preferences.STEAM)
|
key = config_man.lookup(Preferences.STEAM)
|
||||||
unsubscribe(key, int(mod))
|
try:
|
||||||
|
unsubscribe(key, int(mod))
|
||||||
|
except Exception as e:
|
||||||
|
logger.critical(e)
|
||||||
|
return
|
||||||
|
|
||||||
steam_path = Path(self.path)
|
steam_path = Path(self.path)
|
||||||
app_path = PeFile.get_nested_app_path(steam_path, APPID_DAYZ)
|
app_path = PeFile.get_nested_app_path(steam_path, APPID_DAYZ)
|
||||||
|
|||||||
@@ -1,20 +1,22 @@
|
|||||||
add_button="Add"
|
from dzgui.const.constants import UDP_PORT
|
||||||
add_con_heading="Add/connect"
|
|
||||||
|
add_button = "Add"
|
||||||
|
add_con_heading = "Add/connect"
|
||||||
add_popover = "This address is already in your Saved Servers"
|
add_popover = "This address is already in your Saved Servers"
|
||||||
add_tooltip="Add to Saved Servers"
|
add_tooltip = "Add to Saved Servers"
|
||||||
connect_button="Connect"
|
connect_button = "Connect"
|
||||||
connect_tooltip="Connect to this server"
|
connect_tooltip = "Connect to this server"
|
||||||
connect_entry_placeholder="Enter IP:Query port (e.g., 192.168.1.1:27016)"
|
connect_entry_placeholder = f"Enter IP:Query port (e.g., 192.168.1.1:{UDP_PORT})"
|
||||||
|
|
||||||
fav_heading="Favorite server"
|
fav_heading = "Favorite server"
|
||||||
favs_empty="None set. Right click a server and select 'Set favorite' to set."
|
favs_empty = "None set. Right click a server and select 'Set favorite' to set."
|
||||||
|
|
||||||
lan_heading="LAN query port"
|
lan_heading = "LAN query port"
|
||||||
lan_default_button="Default port (27016)"
|
lan_default_button = f"Default port ({UDP_PORT})"
|
||||||
lan_custom_button="Custom port"
|
lan_custom_button = "Custom port"
|
||||||
lan_scan_button="Scan"
|
lan_scan_button = "Scan"
|
||||||
lan_abort_tooltip = "Unless you have multiple DayZ servers on your LAN,\nleave this checked to get results faster"
|
lan_abort_tooltip = "Unless you have multiple DayZ servers on your LAN,\nleave this checked to get results faster"
|
||||||
lan_checkbox = "Stop scanning on first hit"
|
lan_checkbox = "Stop scanning on first hit"
|
||||||
lan_entry_placeholder="Enter the query port (1-65535)"
|
lan_entry_placeholder = "Enter the query port (1-65535)"
|
||||||
lan_entry_tooltip="Specify the port to search for DayZ servers on the local network"
|
lan_entry_tooltip = "Specify the port to search for DayZ servers on the local network"
|
||||||
lan_scan_tooltip="Scan for servers"
|
lan_scan_tooltip = "Scan for servers"
|
||||||
@@ -4,3 +4,4 @@ api_validation_error = (
|
|||||||
|
|
||||||
api_popover = "API key validation failed."
|
api_popover = "API key validation failed."
|
||||||
dayz_not_found = "Could not find a valid DayZ installation."
|
dayz_not_found = "Could not find a valid DayZ installation."
|
||||||
|
workshop_endpoint_error = "Steam Workshop service unavailable, try again later."
|
||||||
@@ -11,8 +11,6 @@ mods = "Mods"
|
|||||||
total_mods = "Total mods: "
|
total_mods = "Total mods: "
|
||||||
up_to_date = "All mods are up to date."
|
up_to_date = "All mods are up to date."
|
||||||
all_updated = "All mods updated."
|
all_updated = "All mods updated."
|
||||||
"If you recently installed {build} or moved it to a different drive, "
|
|
||||||
"restart Steam to allow these changes to synchronize, then try again."
|
|
||||||
required_space = " Need to download {0} MiB of mod updates."
|
required_space = " Need to download {0} MiB of mod updates."
|
||||||
|
|
||||||
placeholder_no_mods = "This server has no mods."
|
placeholder_no_mods = "This server has no mods."
|
||||||
@@ -36,6 +34,7 @@ steam_not_running = "'{0}' is set as the default Steam client, but it is either
|
|||||||
use_desktop_mode = "Use Desktop Mode to download mods on Steam Deck."
|
use_desktop_mode = "Use Desktop Mode to download mods on Steam Deck."
|
||||||
version_mismatch = "Local client version '{0}' does not match remote version '{1}'."
|
version_mismatch = "Local client version '{0}' does not match remote version '{1}'."
|
||||||
version_missing = "Remote server is running the build '{0}', but it is not installed."
|
version_missing = "Remote server is running the build '{0}', but it is not installed."
|
||||||
|
no_errors = "No errors."
|
||||||
|
|
||||||
|
|
||||||
# Warnings
|
# Warnings
|
||||||
|
|||||||
@@ -30,7 +30,8 @@ path_remove_prefix = "The following path will be removed:"
|
|||||||
not_installed = "It looks like DZGUI was not previously set up; nothing to uninstall."
|
not_installed = "It looks like DZGUI was not previously set up; nothing to uninstall."
|
||||||
standalone_uninstall = (
|
standalone_uninstall = (
|
||||||
"It looks like you are running the standalone version of DZGUI.\n"
|
"It looks like you are running the standalone version of DZGUI.\n"
|
||||||
"To finalize the uninstall process, you can remove the 'dzgui' file."
|
"To finalize the uninstall process, invoke './dzgui self remove',\n"
|
||||||
|
"then remove the 'dzgui' file."
|
||||||
)
|
)
|
||||||
system_uninstall = (
|
system_uninstall = (
|
||||||
"It looks like DZGUI was installed via your system package manager or directly from source code.\n"
|
"It looks like DZGUI was installed via your system package manager or directly from source code.\n"
|
||||||
|
|||||||
+10
-5
@@ -2,7 +2,12 @@ import logging
|
|||||||
from pathlib import Path
|
from pathlib import Path
|
||||||
|
|
||||||
from dzgui.api.mods import get_local_mod_path, get_local_mod_ids, _hash
|
from dzgui.api.mods import get_local_mod_path, get_local_mod_ids, _hash
|
||||||
from dzgui.const.constants import APPID_DAYZ, APPID_DAYZ_EXP, APP_NAME, DAYZ_COMMUNITY_ROOT
|
from dzgui.const.constants import (
|
||||||
|
APPID_DAYZ,
|
||||||
|
APPID_DAYZ_EXP,
|
||||||
|
APP_NAME,
|
||||||
|
DAYZ_COMMUNITY_ROOT,
|
||||||
|
)
|
||||||
from dzgui.const.enum import Preferences
|
from dzgui.const.enum import Preferences
|
||||||
from dzgui.config.query import lookup
|
from dzgui.config.query import lookup
|
||||||
|
|
||||||
@@ -20,6 +25,7 @@ def expunge_link(file: Path) -> None:
|
|||||||
if str(file.stem)[:2] == "@C":
|
if str(file.stem)[:2] == "@C":
|
||||||
file.unlink()
|
file.unlink()
|
||||||
|
|
||||||
|
|
||||||
def rebuild_symlinks(config: Path) -> None:
|
def rebuild_symlinks(config: Path) -> None:
|
||||||
# TODO: pass direct path as argument
|
# TODO: pass direct path as argument
|
||||||
path = lookup(config, Preferences.DEFAULT)
|
path = lookup(config, Preferences.DEFAULT)
|
||||||
@@ -63,10 +69,9 @@ def symlink_mission(steam_path: Path, target: str) -> str:
|
|||||||
stem = path.name
|
stem = path.name
|
||||||
parent = path.parent
|
parent = path.parent
|
||||||
source = dayz_path.joinpath(DAYZ_COMMUNITY_ROOT)
|
source = dayz_path.joinpath(DAYZ_COMMUNITY_ROOT)
|
||||||
try:
|
if source.exists():
|
||||||
source.symlink_to(parent)
|
source.unlink()
|
||||||
except Exception:
|
source.symlink_to(parent)
|
||||||
return ""
|
|
||||||
return f"{DAYZ_COMMUNITY_ROOT}/{stem}"
|
return f"{DAYZ_COMMUNITY_ROOT}/{stem}"
|
||||||
|
|
||||||
|
|
||||||
|
|||||||
@@ -102,7 +102,7 @@ class BootDialog(ColorAwareApp, Gtk.Dialog): # type: ignore
|
|||||||
margin_top=30,
|
margin_top=30,
|
||||||
margin_bottom=30,
|
margin_bottom=30,
|
||||||
)
|
)
|
||||||
self.error_label = Gtk.Label()
|
self.error_label = Gtk.Label(margin_start=15, margin_end=15)
|
||||||
|
|
||||||
# TODO: abstract class
|
# TODO: abstract class
|
||||||
self.copy_button = ClipboardButton(None, lambda: self.error_label.get_text())
|
self.copy_button = ClipboardButton(None, lambda: self.error_label.get_text())
|
||||||
|
|||||||
@@ -176,8 +176,7 @@ class PreConnectionAssistant(Gtk.Box):
|
|||||||
|
|
||||||
self.error_box = Gtk.Box(orientation=Gtk.Orientation.VERTICAL)
|
self.error_box = Gtk.Box(orientation=Gtk.Orientation.VERTICAL)
|
||||||
self.error_tree = MaskedTree(ERROR)
|
self.error_tree = MaskedTree(ERROR)
|
||||||
# TODO: strings
|
self.error_placeholder = Placeholder(preconnect.no_errors)
|
||||||
self.error_placeholder = Placeholder("No errors.")
|
|
||||||
self.error_box.add(self.error_tree)
|
self.error_box.add(self.error_tree)
|
||||||
self.error_box.add(self.error_placeholder)
|
self.error_box.add(self.error_placeholder)
|
||||||
self.error_frame = HeadingFrame.new_with_widget_and_label(
|
self.error_frame = HeadingFrame.new_with_widget_and_label(
|
||||||
|
|||||||
@@ -252,7 +252,6 @@ class ServerTreeView(ContextMixin, TreeView): # type: ignore
|
|||||||
case Gdk.KEY_c:
|
case Gdk.KEY_c:
|
||||||
self.controller.menu_action(ContextMenu.COPY_SERVER_IP, self)
|
self.controller.menu_action(ContextMenu.COPY_SERVER_IP, self)
|
||||||
case Gdk.KEY_r:
|
case Gdk.KEY_r:
|
||||||
# TODO: unimplemented, needs threading
|
|
||||||
self.controller.menu_action(ContextMenu.REFRESH_PLAYERS, self)
|
self.controller.menu_action(ContextMenu.REFRESH_PLAYERS, self)
|
||||||
else:
|
else:
|
||||||
match event.keyval:
|
match event.keyval:
|
||||||
|
|||||||
+1
-1
@@ -4,7 +4,7 @@ description = "DayZ server browser and mod manager for Linux"
|
|||||||
authors = [
|
authors = [
|
||||||
{name = "aclist"}
|
{name = "aclist"}
|
||||||
]
|
]
|
||||||
version = "7.0.0b24"
|
version = "7.0.0b25"
|
||||||
license = "GPL-3.0-or-later"
|
license = "GPL-3.0-or-later"
|
||||||
license-files = ["LICENSE"]
|
license-files = ["LICENSE"]
|
||||||
readme = "README.md"
|
readme = "README.md"
|
||||||
|
|||||||
Reference in new issue
Block a user