Discord Bot 构建套件 🤖

本插件的用途

本插件可执行多项功能:

  1. 允许您利用 Discourse 服务器为 Discord 机器人提供动力,以执行链接这两个系统的操作。请 Fork 此仓库,并使用简单的 Ruby 代码扩展它,以创建各种机器人功能。

  2. 现有功能可作为示例和实用工具:

  • 提供满足特定条件的双向自动内容发布。
  • 命令可临时将消息复制到 Discourse。
  • 命令可将 Discord 服务器的角色成员资格与 Discourse 实例的群组成员资格进行同步。

本插件提供了一个可扩展的骨架,您可以在其基础上构建更多功能。欢迎提交具有普遍实用性的功能改进的 PR。


这些并非两个同步命令,仅用于说明机器人交互的可能性。截图中的第二个命令在开发过程中已被弃用 :wink:

设置过程必然较为复杂,但对于两个系统的粉丝来说,如果您愿意花时间从功能和概念层面理解每个系统的工作原理,这将非常有益。要充分发挥本插件的作用,您需要了解 Discourse 和 Discord 用户管理的基本原理。

机器人命令

共有四个命令:

  1. Ping!
  2. !disckick
  3. !discsync
  4. !disccopy

Ping!

要检查机器人是否有响应,只需输入 “Ping!”,机器人应回复 “:robot: : Pong!” - 太棒了,对吧?:D(顺便提一下,这是一个梗!)

!disckick <min_trust_level: 默认 2>

输入此命令将踢出任何存在于 Discourse 中但信任级别低于您提供值的用户。如果您不提供值,默认值为 2。

例如:

!discsync <clean up: 默认 false, min_visibility: 默认 0, include automated groups: 默认 false>

此命令将尝试将所有符合提供条件(或默认条件)的群组复制到 Discord 的角色中。随后,它将尝试根据 Discourse 上的群组成员资格来填充这些角色。这仅是单向同步。Discourse 中的数据永远不会被更改。

!disccopy <number_of_messages> <optional_target_category_name> <optional_target_topic_name>

允许您从 Discord 聊天内部将 Discord 消息历史记录复制到 Discourse 实例。此功能可一次性处理数千条消息(但处理该数量级需要时间)。

双向通信

以下是相关设置:

  • 您可以在插件设置中指定 Discord 的公告频道。
  • 现在,您可以在指定的 Discord 公告频道中输入内容,这会将您的消息发布到插件设置中指定的 Discourse 主题。
  • 您可以设置 Discourse 中的类别列表,以便当有人在相应类别中发帖或添加新主题时(两者皆可),将内容发布到您的 Discord 公告频道。
  • 按频道到 Discourse 上名称完全相同的类别的自动化逐条消息聊天复制:如果频道名称与类别名称匹配,消息将被复制到 Discourse。

image

此外,我添加了一个新文件来管理由 discordrb API 支持的 Discord 事件,公告逻辑是第一个示例(如果您认为新开发的功能对社区有普遍用处,欢迎开发并提交 PR)。

注意:对于任何从 Discord 复制到 Discourse 的消息,如果该用户通过 Discord 登录(即使用 Discord 登录)登录过 Discourse,用户将正确显示(这样 Discord 机器人才能匹配用户)。

本插件的状态

这是一个设置复杂的插件。这在很大程度上是不可避免的。

然而,一旦设置完成并运行起来,使用起来就非常简单了。

请将代码视为目前的Beta版本。它已经过测试,甚至在生产环境中使用过,但可能仍包含错误。我建议您首先在全新的 Discord 服务器上进行测试,然后再将其应用于您的“生产”主 Discord 服务器,除非您刚开始使用。

任何错误更有可能影响您的 Discord 实例,而不是 Discourse 实例,因为不会对 Discourse 进行任何更改。不过,我的编写方式使得大多数问题都是可恢复的,通常只需重复操作即可修复问题。Discourse 被用作成员资格和群组信息的主数据源,这些数据用于更新您 Discord 服务器上的成员资格和角色。

设置说明

先决条件

  1. 一个您拥有管理员权限的 Discord 服务器
  2. 一个 Discord 应用(见下文)
  3. 一个 Discord 机器人(见下文)
  4. 对您 Discourse 服务器的 ssh root 访问权限
  5. 更新 app.yml 以安装插件
  6. 您的 Discourse 所有用户都需要使用插件安装后出现在登录页面上的 Discord OAuth 登录方式登录。

Discord 应用

前往此处并创建一个应用:

点击“新建应用”

您需要创建一个机器人,它看起来应该像这样(请保持其为非“公开”):

您需要在浏览器中授权机器人,参见 OAuth2 - Documentation - Discord

机器人设置好后,复制令牌(Token)。稍后您需要将其输入到 Discourse 中。

app.yml 更改

插件

现在您只需要一个插件,因为 Discord 社交登录现已成为 Discourse 核心的原生功能(太棒了 :tada:

然后在提示符下输入 ./launcher rebuild app,如常操作。

这应该能正常工作,没问题。

您可能会在首次构建时看到一些控制台和日志错误,提示机器人失败,因为您尚未在 Discourse 设置的前端输入机器人的凭据。(更优雅地处理这一点是待办事项,完成后我会删除这部分)。但这不会造成任何损害,Discourse 本身将正常工作。

进入您的 Discourse 管理区域后,前往插件设置并填写以下内容:

ID 将从 Discord 界面获取。您需要激活开发者模式以允许您复制这些 ID。在 Discord 中,前往您的设置 → 外观 → 高级,并启用开发者模式:

然后您可以从界面获取 ID,例如:

您还需要填写 Discord OAuth 设置。客户端 ID 和密钥来自您同一个 Discord 应用。

设置完成后,返回 Linux 的根提示符并输入:

./launcher restart app

如果您正确设置了 Discord 和 Discourse 服务器,您应该能看到机器人加入服务器。

如果机器人出现故障(它将离线),您需要再次执行相同的操作以使其恢复。提高机器人与 Discourse 核心服务器的独立性是待办事项。话虽如此,我已在生产环境中运行该机器人很长一段时间,它尚未出现故障。

未来的命令?

如果您有关于另一个命令的想法,该命令利用 Discourse 和 Discord 之间的链接,且您认为这对更广泛的社区有用,请在回复中告诉我,我们可以探讨实施该功能的可能性。注意:此机器人不旨在执行 Discourse 范围之外的任务。

限制

本插件的主要目标是允许用户在 Discord 上创建一个由其 Discourse 服务器提供动力的机器人,并能够执行一些基本的成员管理功能。它还为未来两个系统之间的任何额外类机器人交互提供了基础。使用机器人的一部分动机仅仅是因为它们非常有趣

机器人命令本质上是临时的。

已知问题

  • 如果您在服务器上的 rails 控制台会话中进入,机器人将启动自身的实例。这将导致机器人看似响应两次(但实际上现在有两个机器人)。在 rails 控制台中,只需输入 ::DiscordBot::Bot.discord_bot.stop 即可停止额外的机器人 现在这应该不再必要了!

  • 在 Discourse 的“在线”升级期间,机器人会稍微有些话痨,因为它在升级过程中会不断被重新激活。这回到了如何在一个独立的、受管理的进程中运行机器人,而不是从 Web 服务器分叉出的线程的问题上。我相信这都是无害的,而且如果机器人的输出仅到您的 Discord 管理频道,您真的会在意吗? 这现在应该几乎解决了,机器人在重建期间仅宣布自己两次。

致谢

本插件的完成离不开多位支持者的帮助,这花费了我很长时间,包括 @Wedgebert, @FoohonPie。感谢 Jeff 的慷慨贡献。感谢 @angus 给予的所有鼓励并处理财务支持。

本插件的灵感来自 @Watercolor_Games 在早期阶段所做的工作,并依赖于 @featheredtoast 构建的 Discord OAuth 插件。

本插件依赖于 半官方的 Discord 支持的 discordrb Ruby 库 以及 Discord 团队为使他们的系统易于访问所做的出色工作。感谢 @Falco 以极快的响应速度帮助我解决了一个依赖问题。

此外,当然,如果没有 Discourse 惊人的插件生态系统(太棒了!),这也是不可能的。

本说明的状态

这些说明将随着时间的推移得到改进,我欢迎反馈。有些部分肯定还不清楚。

47 个赞
Discord<-> Discourse Selective Group Sync
Discord login and obtain discord roles in discourse
Discord and Discourse - Better Together | Blog
Convert Existing Plugin to do Discord to Discourse role/group sync
Slack Bot Construction Kit :robot:
2019: The Year in Review
Creat a user automatically when granted a Discord Role?
Discord Sync: sync a Discourse forum with a Discord server
Creating bot on discourse
Using "custom" ruby gems
Discourse Trust Levels for Discord
Discord is taking aim at Discourse. How does Discourse remain unique and stand out from the crowd?
Discord is taking aim at Discourse. How does Discourse remain unique and stand out from the crowd?
Copy + Pasting text from Discord into Discourse mangles paragraph breaks
Discord Role Badge Sync
Discord Bot: Topics not Posts
How do I go about making a very customized theme?
API feature request for additonal info about external accounts
Can anyone help me to add chat option of discord on forum?
How to Integrate/Sync Discord User MEE6 Points with Discourse Leaderboard?
LF Developer, Theme Creator, and Discord/Discourse Hero
Discord Sync: sync a Discourse forum with a Discord server
[PAID] Discourse/Discord integration needed (roles/user groups)
Can anyone help me to add chat option of discord on forum?
Discord and Discourse - Better Together | Blog
How to easily make Discourse bots?
Discourse to Discord bot possible?
Migrating from Discord to Discourse
Convert Existing Plugin to do Discord to Discourse role/group sync
Is migration from other chat apps supported?
Partially enable login option
Introducing Discourse Chat (BETA)
Which instant messenger do you use with Discourse?
Request widgetbot.io
Discord Sync: sync a Discourse forum with a Discord server

Hey I’m super interested in this.

Would the opposite be possible? I’d love a way to be able to create a Discourse setup for my Discord server. I’m not sure if there’s a Discord API event for roles being given but you could probably check when someone logs in with Discord or with CRON.

2 个赞

Yes, absolutely.

You could either build that as a bot command for ad hoc application, but with a repeat feature that reran the command after a period (nice but not very transparent and no way to individually manage these recurrences)

OR

As I alluded to above, have it scheduled as a job in Discourse as a sidekiq job. That might be a separate plugin (I actually started on the skeleton of that approach before moving to a bot only solution mainly because the ‘bot’ approach was kind of the Discord ‘thing’, fun and offered a unique approach and result), but if I can get Discourse to fire off bot commands then that’s moot (not yet had the chance to test that), and then we can write stuff once and have it work either way (nice!).

Both these solutions would rely on the same OAuth login though.

Whilst this is an excellent idea, it can’t be a priority for me at present because I have a lot of other client work at the moment I need to deliver, but if you wish to support such an extension, we can discuss offline on a PM and schedule it in.

4 个赞

It might be interesting to play around with, but I have nowhere near the skill level required to volunteer to develop/maintain an addon like this. I might make a messy fork at some time but I certainly don’t want my name on anything official. :slight_smile:

3 个赞

Absolutely get messy. It’s the only way to learn. :).

4 个赞

Minor bug fix deployed:

Got this during rebuild:

Bot is still offline. Triple checked everything and it’s all set up correctly. Not sure how to proceed now… Maybe I need to open a port on my server instance?

2 个赞

Thanks for testing this out and so soon after the update. Let me try to reproduce and I will revert. I did not change anything wrt to the port config.

2 个赞

No issues rebuilding here, Bot comes up fine … have you changed anything in your server config in between?

Your 400 Bad Request sounds like your server sent a corrupt or bad request to the Discord server and this was the response. This suggests it received it fine and was not blocked.

You can get this for:

  • malformed requests
  • lack of authorisation
  • exceeding rate limits

Unfortunately the error message doesn’t appear to help us determine which of these was the particular issue.

Presumably your Discourse is up? Check all the plugin settings are populated correctly.

Just to rule out a temporary gremlin run ./launcher restart app when you get chance … this will take your site down for a few seconds only (sorry about that!).

I see it runs the bot in the after_initialize block, so it will prevent migrations (and rebuilds) if the bot is misconfigured, or if Discord is down.

Maybe try to handle this exception and just log it?

5 个赞

It runs on a separate thread? So I expect that not to be an issue?

However this callback seems to run several times in a rebuild, so the main issue will be that a misconfigured bot could actually breach rate limits if authorisation fails too many times in quick succession. If that happens the account, in worse case, could be blocked for some time.

In any case, I’ll do a quick patch to do that with the current implementation to lessen the impact. Thanks for the suggestion.

UPDATE: @falco, this is done, e.g.:

image

3 个赞

First I want to say thank you for making this, once I can get it working its going to be a huge help for us managing our discourse and discord for a volunteer community.
I am running into a 400 error when trying to run this bot. Prior to this plugin being added we have been successfully using the official discord auth plugin and webhooks via the chat integration plugin. I’ve validated that those are both still working appropriately.

I created the bot within the same discord app I’d previously created authorized the bot within the discord server, it shows up in the member list as offline. Your documentation didn’t say what permission value to apply, but given most bots I’ve encountered for discord asked for it I went ahead and set it up with a permissions value of 8 for Administrator.

Within the discord server I then copied the ID of the Role it created, which was named after my app, and the id of the channel for admin text.I added the app Role to that channel with full rights, just to be sure, then added the IDs to discourse and restarted.

Unfortunately no matter what I try I’m getting a 400, I even tried a rebuild just to be sure.

3 个赞

Thank you, kind words. It was also enabled by the generosity of funders.

Yes, that’s great. It should have Admin.

This is the second report of this issue.

If you intentially remove the last char of the token in settings (remember what this is) do you get a 401 instead?

Let’s move this to PM because it might get messy :wink: (we can always post the solution here).

4 个赞

Just to post an update in case anyone else sees this, we’re actively looking into the issue but haven’t yet narrowed down the cause. I’d say if anyone else is running into this issue please say so would help to have others testing.

1 个赞

This is now fixed. It was a weird one to track down.

Thanks to @ransim for raising and working with me to get to the bottom of it.

Huge thanks to the #ruby_discordrb gang on Discord API for their patient and instant help!

@neemiasvf

5 个赞

@merefield no problem,Your plugin is great.But I have encountered some problems now.
such this:

Discourse Sync:  Starting.  Please be patient, I'm rate limited to respect Discord services.
Discourse Sync:  Checking if there are any eligible groups for sync ...
Discourse Sync: 1 eligible group(s) were found
Discourse Sync:  Preparing list of users who also have a registered account on Discord ...
Discourse Sync:  Preparing list of groups that users who have a registered account on Discord belong to on Discourse ...
Discourse Sync: 0 eligible group(s) were found with Discord users
Discourse Sync:  No users were found in elibigle groups for sync using provided or default criteria!

my commond is : !discsync 4

and commond changed: !discsync false 5 false

Discourse Sync:  Starting.  Please be patient, I'm rate limited to respect Discord services.
Discourse Sync:  Checking if there are any eligible groups for sync ...
Discourse Sync: 10 eligible group(s) were found
Discourse Sync:  Preparing list of users who also have a registered account on Discord ...
Discourse Sync:  Preparing list of groups that users who have a registered account on Discord belong to on Discourse ...
1 个赞

Hey @p0nda, sorry for slow reply.

If you include any parameters, you need to include all of them. It might be interpreting things strangely.

3 个赞

Unable to get the extended bot settings to show up? I have the changes to the app.yml and plugins installed. I have the OAuth setup working, but not the bot settings. Any ideas?

1 个赞

The OAuth setting are there but no bot settings

1 个赞

image
These

2 个赞