Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
5 changes: 2 additions & 3 deletions deploy/README.md
Original file line number Diff line number Diff line change
Expand Up @@ -87,9 +87,8 @@ What `/run` and `/versions` do, and who may run them:
/opt/session-ops/.venv/bin/session-ops discord-register
```

6. The commands start hidden from everyone but server administrators. In Server
Settings → Integrations, allow them for the role or channel that runs jobs. Seeing
them is not running them: the relay's allowlist still decides.
6. Every member sees the commands. In Server Settings → Integrations, limit them to the
channels that run jobs. Seeing them is not running them: the relay's allowlist decides.

Register again after changing which jobs have `discord = true`.

Expand Down
8 changes: 4 additions & 4 deletions docs/jobs/session-ops-discord.md
Original file line number Diff line number Diff line change
Expand Up @@ -20,10 +20,10 @@ options chosen.
A request is refused unless Discord signed it in the last five minutes, it comes from
`DISCORD_GUILD_ID` and, when `ALLOWED_CHANNEL_IDS` is set, one of its channels, and its
author is in `ALLOWED_USER_IDS` or holds a role in `ALLOWED_ROLE_IDS`. Both lists empty
refuses everybody. `/run` is registered hidden from everyone but server administrators,
and the server's Integrations settings show it to the right role; that only hides it, and
these checks are what refuse everyone else, administrators included. `/versions` only reads, so it is shown to
everyone and skips the author check.
refuses everybody, administrators included. Both commands are shown to every member, since
Discord lets only someone who can use a command change who sees it; the server's
Integrations settings can narrow the channels. `/versions` only reads, so it skips the
author check.

The relay runs as `opsbot`, which can start no unit itself. It can write only to
`/run/session-ops/requests`, where `session-ops units` writes a `PathChanged=` watch for
Expand Down
11 changes: 5 additions & 6 deletions src/session_ops/ops/discord_commands.py
Original file line number Diff line number Diff line change
Expand Up @@ -3,10 +3,10 @@
session-ops discord-register # with discord.env's variables in the environment

Registered on one guild rather than globally: a guild's commands update at once, and
nobody outside that server can see or run them. /run starts hidden from every member but
server administrators; the server's Integrations settings grant it to a role or channel.
That only hides it, and the relay's allowlist is what refuses everyone else,
administrators included. /versions only reads, so everyone sees it.
nobody outside that server can see or run them. Both are shown to every member, since
Discord lets only someone who can use a command change who sees it; the relay's
allowlist is what refuses /run to everyone else. The server's Integrations settings can
still narrow where they show.
"""
import os
import sys
Expand All @@ -28,8 +28,7 @@
def commands(jobs):
choices = [{"name": discord.clip(f"{job.name}: {job.description}", MAX_CHOICE_NAME),
"value": job.name} for job in jobs if job.discord]
hidden = {"type": CHAT_INPUT, "default_member_permissions": "0"}
found = [{**hidden, "name": RUN, "description": "Start a session-ops job now",
found = [{"type": CHAT_INPUT, "name": RUN, "description": "Start a session-ops job now",
"options": [{"type": OPTION_STRING, "name": "job", "required": True,
"description": "The job to start", "choices": choices}]}]
if any(job.name == STORE_VERSIONS_JOB for job in jobs):
Expand Down
4 changes: 2 additions & 2 deletions tests/ops/test_discord_relay.py
Original file line number Diff line number Diff line change
Expand Up @@ -327,13 +327,13 @@ def test_anyone_in_the_server_can_ask_but_not_from_elsewhere(self):


class TestCommands(unittest.TestCase):
def test_run_offers_the_discord_jobs_and_starts_hidden(self):
def test_run_offers_the_discord_jobs_to_every_member(self):
jobs = registry.load()
run, versions = discord_commands.commands(jobs)
offered = [choice["value"] for choice in run["options"][0]["choices"]]
self.assertEqual(offered, [job.name for job in jobs if job.discord])
self.assertIn("crowdin-sync", offered)
self.assertEqual(run["default_member_permissions"], "0")
self.assertNotIn("default_member_permissions", run)
for choice in run["options"][0]["choices"]:
self.assertLessEqual(len(choice["name"]), discord_commands.MAX_CHOICE_NAME)
self.assertEqual(versions["name"], discord_commands.VERSIONS)
Expand Down
Loading