Skip to content

Commit 7e95ab9

Browse files
authored
Merge pull request #5 from khakers/feature/forced-plugins
2 parents 37d911f + 767345e commit 7e95ab9

File tree

2 files changed

+56
-23
lines changed

2 files changed

+56
-23
lines changed

CHANGELOG.md

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -18,7 +18,7 @@ however, insignificant breaking changes do not guarantee a major version bump, s
1818
### Added
1919
- Added `content_type` to attachments stored in the database.
2020
- `?log key <key>` to retrieve the log link and view a preview using a log key. ([PR #3196](https://github.com/modmail-dev/Modmail/pull/3196))
21-
21+
- Add Forced plugins. Allows auto installing un-removable plugins via `FORCED_PLUGINS` environment variable contain a comma separate list of plugins. (GH#5)
2222

2323
### Changed
2424
- Changing a threads title or NSFW status immediately updates the status in the database.

cogs/plugins.py

Lines changed: 55 additions & 22 deletions
Original file line numberDiff line numberDiff line change
@@ -117,6 +117,7 @@ class Plugins(commands.Cog):
117117
"""
118118

119119
def __init__(self, bot):
120+
self.forced_plugins: list[str] = []
120121
self.bot = bot
121122
self.registry = {}
122123
self.loaded_plugins = set()
@@ -134,33 +135,56 @@ async def populate_registry(self):
134135
async with self.bot.session.get(url) as resp:
135136
self.registry = json.loads(await resp.text())
136137

137-
async def initial_load_plugins(self):
138-
for plugin_name in list(self.bot.config["plugins"]):
138+
def _get_forced_plugins(self) -> list[str]:
139+
env_list = os.getenv("FORCED_PLUGINS")
140+
if env_list is None:
141+
return []
142+
plugins = env_list.split(",")
143+
return plugins
144+
145+
async def _init_load_plugin(self, plugin_name: str):
146+
try:
147+
# Strict seems to only affect whether specifying the branch is required
148+
plugin = Plugin.from_string(plugin_name, strict=False)
149+
except InvalidPluginError:
150+
self.bot.config["plugins"].remove(plugin_name)
139151
try:
140-
plugin = Plugin.from_string(plugin_name, strict=True)
152+
# For backwards compat
153+
plugin = Plugin.from_string(plugin_name)
141154
except InvalidPluginError:
142-
self.bot.config["plugins"].remove(plugin_name)
143-
try:
144-
# For backwards compat
145-
plugin = Plugin.from_string(plugin_name)
146-
except InvalidPluginError:
147-
logger.error("Failed to parse plugin name: %s.", plugin_name, exc_info=True)
148-
continue
155+
logger.error("Failed to parse plugin name: %s.", plugin_name, exc_info=True)
156+
return
149157

150-
logger.info("Migrated legacy plugin name: %s, now %s.", plugin_name, str(plugin))
151-
self.bot.config["plugins"].append(str(plugin))
158+
logger.info("Migrated legacy plugin name: %s, now %s.", plugin_name, str(plugin))
159+
self.bot.config["plugins"].append(str(plugin))
152160

153-
try:
154-
await self.download_plugin(plugin)
155-
await self.load_plugin(plugin)
156-
except Exception:
157-
self.bot.config["plugins"].remove(plugin_name)
158-
logger.error(
159-
"Error when loading plugin %s. Plugin removed from config.",
160-
plugin,
161-
exc_info=True,
162-
)
161+
try:
162+
await self.download_plugin(plugin)
163+
await self.load_plugin(plugin)
164+
except Exception:
165+
self.bot.config["plugins"].remove(plugin_name)
166+
logger.error(
167+
"Error when loading plugin %s. Plugin removed from config.",
168+
plugin,
169+
exc_info=True,
170+
)
171+
172+
async def initial_load_plugins(self):
173+
self.forced_plugins = self._get_forced_plugins()
174+
logger.debug(f"loading {len(self.forced_plugins)} forced plugins")
175+
for plugin_name in self.forced_plugins:
176+
logger.debug(f"loading forced plugin {plugin_name}")
177+
await self._init_load_plugin(plugin_name)
178+
179+
user_plugins = list(self.bot.config["plugins"])
180+
logger.debug(f"loading {len(user_plugins)} config plugins")
181+
182+
for plugin_name in user_plugins:
183+
# Skip loading this plugin if it is in the force load list and thus already loaded
184+
if plugin_name in self.forced_plugins:
185+
logger.debug(f"Skipped loading user plugin {plugin_name} because it is forced installed.")
163186
continue
187+
await self._init_load_plugin(plugin_name)
164188

165189
logger.debug("Finished loading all plugins.")
166190

@@ -440,6 +464,15 @@ async def plugins_remove(self, ctx, *, plugin_name: str):
440464
if plugin is None:
441465
return
442466

467+
if str(plugin) in self.forced_plugins:
468+
await ctx.send(
469+
embed=discord.Embed(
470+
description="This plugin cannot be removed. Contact your admin for more information.",
471+
color=self.bot.error_color,
472+
)
473+
)
474+
return
475+
443476
if str(plugin) not in self.bot.config["plugins"]:
444477
embed = discord.Embed(description="Plugin is not installed.", color=self.bot.error_color)
445478
return await ctx.send(embed=embed)

0 commit comments

Comments
 (0)