Skip to content

Commit cb97b4f

Browse files
committed
Merge branch 'development'
2 parents 7e73909 + cacaf7a commit cb97b4f

9 files changed

Lines changed: 68 additions & 31 deletions

File tree

extensions/lotatc/extension.py

Lines changed: 6 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -96,7 +96,11 @@ def load_config(self) -> dict:
9696
if not os.path.exists(config_path):
9797
major_version, _ = self.get_inst_version()
9898
from_path = os.path.join(self.get_inst_path(), 'server', major_version)
99-
shutil.copy2(os.path.join(from_path, 'config.lua'), config_path)
99+
origin = os.path.join(from_path, 'config.lua')
100+
if not os.path.exists(origin):
101+
self.log.error(f"{self.name}: Installation Error - Missing config.lua in {from_path}!")
102+
return cfg
103+
shutil.copy2(origin, config_path)
100104
for path in [os.path.join(self.home, 'config.lua'), os.path.join(self.home, 'config.custom.lua')]:
101105
try:
102106
with open(path, mode='r', encoding='utf-8') as file:
@@ -106,7 +110,7 @@ def load_config(self) -> dict:
106110
except FileNotFoundError:
107111
pass
108112
except Exception:
109-
self.log.error(f"Error while parsing {path}!", exc_info=True)
113+
self.log.error(f"{self.name}: Error while parsing {path}!", exc_info=True)
110114
return cfg
111115

112116
def get_inst_path(self) -> str:

extensions/mizedit/extension.py

Lines changed: 9 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -78,7 +78,10 @@ async def get_presets(self, config: dict) -> list[dict]:
7878
return []
7979

8080
now = datetime.now()
81-
presets = config['settings']
81+
presets = config.get('settings')
82+
if not presets:
83+
return []
84+
8285
if isinstance(presets, dict):
8386
tz: str | None = config.get('timezone')
8487
tzinfo = ZoneInfo(tz) if tz else None
@@ -162,8 +165,11 @@ def _filter(self, filename: str) -> bool:
162165
async def beforeMissionLoad(self, filename: str) -> tuple[str, bool]:
163166
if 'filter' in self.config and not self._filter(filename):
164167
return filename, False
165-
await self.apply_presets(self.server, filename, await self.get_presets(self.config),
166-
debug=self.config.get('debug', False))
168+
presets = await self.get_presets(self.config)
169+
if not presets:
170+
self.log.error("MizEdit: No presets defined!")
171+
return filename, False
172+
await self.apply_presets(self.server, filename, presets, debug=self.config.get('debug', False))
167173
return filename, True
168174

169175
@override

plugins/cloud/commands.py

Lines changed: 5 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -150,7 +150,7 @@ async def cog_unload(self) -> None:
150150
if self.config.get('upload_errors', True):
151151
for handler in self.log.root.handlers:
152152
if isinstance(handler, CloudLoggingHandler):
153-
await asyncio.to_thread(handler.close)
153+
handler.close()
154154
self.log.root.removeHandler(handler)
155155
if self.config.get('register', True):
156156
tasks.append(utils.safe_cancel(self.register))
@@ -208,10 +208,10 @@ async def _request_with_retry(self, method: str, url: str, *, retries: int = 1,
208208

209209
last_error = ex
210210

211-
# Reset broken/stale sessions before retrying
212-
if self._session and not self._session.closed:
213-
await self._session.close()
214-
self._session = None
211+
if isinstance(ex, (aiohttp.ClientConnectorError, aiohttp.ServerDisconnectedError)):
212+
if self._session and not self._session.closed:
213+
await self._session.close()
214+
self._session = None
215215

216216
if attempt >= retries:
217217
self.log.warning("Cloud service unavailable.")

plugins/cloud/logger.py

Lines changed: 11 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -101,9 +101,15 @@ def close(self):
101101
except Exception:
102102
pass
103103
if self._session and not self._session.closed:
104-
loop = asyncio.get_event_loop()
105-
if loop.is_running():
106-
loop.create_task(self._session.close())
107-
else:
108-
loop.run_until_complete(self._session.close())
104+
try:
105+
loop = asyncio.get_event_loop()
106+
if loop.is_running():
107+
loop.create_task(self._session.close())
108+
else:
109+
loop.run_until_complete(self._session.close())
110+
except RuntimeError:
111+
# Fallback for threads without a loop
112+
new_loop = asyncio.new_event_loop()
113+
new_loop.run_until_complete(self._session.close())
114+
new_loop.close()
109115
super().close()

plugins/discord/commands.py

Lines changed: 4 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,6 @@
11
import discord
22

3+
from contextlib import suppress
34
from core import Plugin, command, utils, get_translation, Group
45
from datetime import timedelta
56
from discord import app_commands, Permissions
@@ -73,7 +74,9 @@ async def clear(self, interaction: discord.Interaction, channel: discord.TextCha
7374
await purge_channel(node=self.node, channel=channel.id, older_than=older_than,
7475
ignore=ignore.id if ignore else None, after_id=int(after_id) if after_id else None,
7576
before_id=int(before_id) if before_id else None)
76-
await msg.edit(content=_("All messages deleted."))
77+
with suppress(discord.NotFound):
78+
await msg.delete()
79+
await interaction.followup.send(_("All messages deleted."))
7780

7881
@command(name='addrole', description=_('Adds a role to a member'))
7982
@app_commands.guild_only()

plugins/mission/commands.py

Lines changed: 6 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -596,12 +596,16 @@ async def delete(self, interaction: discord.Interaction,
596596
await server.node.remove_file(secondary + '.orig')
597597
await interaction.followup.send(_('Mission "{}" deleted.').format(mission_name),
598598
ephemeral=ephemeral)
599+
await self.bot.audit(_("deleted mission {}").format(os.path.basename(filename[:-4])),
600+
user=interaction.user)
601+
except PermissionError:
602+
await interaction.followup.send(
603+
_('Permission denied while deleting mission "{}".').format(mission_name),
604+
ephemeral=ephemeral)
599605
except FileNotFoundError:
600606
await interaction.followup.send(
601607
_('Mission "{}" was already deleted.').format(mission_name),
602608
ephemeral=ephemeral)
603-
await self.bot.audit(_("deleted mission {}").format(os.path.basename(filename[:-4])),
604-
user=interaction.user)
605609
except (TimeoutError, asyncio.TimeoutError):
606610
await interaction.followup.send(_("Timeout while deleting mission.\n"
607611
"Please reconfirm that the deletion was successful."),

plugins/music/listener.py

Lines changed: 4 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,6 @@
11
import asyncio
22

3-
from core import EventListener, Server, event
3+
from core import EventListener, Server, event, PluginInstallationError
44
from typing import TYPE_CHECKING
55

66
if TYPE_CHECKING:
@@ -14,6 +14,9 @@ async def _init_radios(self, server: Server, data: dict) -> None:
1414
await self.plugin.service.init_radios(server)
1515
except (TimeoutError, asyncio.TimeoutError):
1616
return
17+
except PluginInstallationError as ex:
18+
self.log.error(ex)
19+
return
1720
# if we've just started, we need to start the radios
1821
if data['channel'].startswith('sync-') and data.get('players'):
1922
await self.plugin.service.start_radios(server)

plugins/restapi/commands.py

Lines changed: 16 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -13,6 +13,7 @@
1313
from fastapi.security import APIKeyHeader
1414
from plugins.creditsystem.squadron import Squadron
1515
from plugins.userstats.filter import StatisticsFilter, PeriodFilter
16+
from psycopg.errors import UndefinedTable
1617
from psycopg.rows import dict_row
1718
from services.bot import DCSServerBot
1819
from services.servicebus import ServiceBus
@@ -1947,18 +1948,21 @@ async def traps(self, nick: str = Form(None), date: str | None = Form(None),
19471948
else:
19481949
join = ""
19491950
where = "WHERE t.player_ucid = %(ucid)s"
1950-
async with self.apool.connection() as conn:
1951-
async with conn.cursor(row_factory=dict_row) as cursor:
1952-
ucid = await self.get_ucid(nick, date)
1953-
await cursor.execute(f"""
1954-
SELECT t.id, t.unit_type, t.grade, t.comment, t.place, t.trapcase, t.wire, t.night, t.points, t.time
1955-
FROM traps t
1956-
{join}
1957-
{where}
1958-
ORDER BY time DESC
1959-
LIMIT {limit} OFFSET {offset}
1960-
""", {"ucid": ucid, "server_name": resolved_server_name})
1961-
return [TrapEntry.model_validate(result) for result in await cursor.fetchall()]
1951+
try:
1952+
async with self.apool.connection() as conn:
1953+
async with conn.cursor(row_factory=dict_row) as cursor:
1954+
ucid = await self.get_ucid(nick, date)
1955+
await cursor.execute(f"""
1956+
SELECT t.id, t.unit_type, t.grade, t.comment, t.place, t.trapcase, t.wire, t.night, t.points, t.time
1957+
FROM traps t
1958+
{join}
1959+
{where}
1960+
ORDER BY time DESC
1961+
LIMIT {limit} OFFSET {offset}
1962+
""", {"ucid": ucid, "server_name": resolved_server_name})
1963+
return [TrapEntry.model_validate(result) for result in await cursor.fetchall()]
1964+
except UndefinedTable:
1965+
raise HTTPException(status_code=500, detail="Greenieboard is not active on this server")
19621966

19631967
async def traps_image(self, trap_id: int = Query(...)):
19641968
self.log.debug(f'Calling /traps_image with trap_id="{trap_id}"')

plugins/scheduler/commands.py

Lines changed: 7 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -484,6 +484,13 @@ async def run_action(self, server: Server, rconf: dict):
484484
new_mission = rconf.get('mission_id')
485485
if isinstance(new_mission, list):
486486
new_mission = random.choice(new_mission)
487+
elif isinstance(new_mission, (int, str)):
488+
new_mission = int(new_mission)
489+
if new_mission > len(mission_list):
490+
self.log.warning(f"{self.__cog_name__}: "
491+
f"Mission ID {new_mission} exceeds mission list length on server {server.name}, "
492+
f"resetting to 1")
493+
new_mission = 1
487494
elif not new_mission:
488495
new_mission = await self.get_mission_from_list(server, rconf.get('mission_file'))
489496
if not new_mission:

0 commit comments

Comments
 (0)