Skip to content

A simple yet powerful framework to develop, configure and run Discord bots based on Discord4J.

License

Notifications You must be signed in to change notification settings

Alex1304/botrino

Folders and files

NameName
Last commit message
Last commit date

Latest commit

 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 

Repository files navigation

Botrino

A simple yet powerful framework to develop, configure and run Discord bots based on Discord4J.

GitHub release (latest SemVer) Maven Central License javadoc

What is Botrino?

Botrino is a Java framework that provides guidelines and a set of tools to build Discord bots in a more convenient way. Pretty much in the same spirit as Spring Boot, it allows to easily setup standalone bot applications that are ready to run, embedding a few third-party libraries such as Jackson for JSON-based configuration, RDI for a reactive IoC container, and Discord4J for the interface with the Discord Bot API.

Motivations

Starting the development of a Discord bot follows most of the time the same pattern: you create a project, import your favorite Discord client library, export a configuration file or an environment variable with the bot token, and design a whole structure for your commands and your logic, before you can actually start to implement them. When working with Java, this structure is even more important otherwise you may adopt bad practices and end up with a bot that is difficult to maintain.

This is how came the idea of this project: have something that can handle for you all the initial workflow of setting up a project with a solid structure, at the only cost of letting the framework choose some libraries for you, so that you can focus on what matters. Botrino is born.

It also aims at providing a library for Discord's Interaction API that integrates well with the structure of Botrino, while still being decoupled from it.

Overview

Botrino utilizes Java modules, introduced in the JDK 9 and released in the JDK 17 as a LTS version. The classes of your application will reside in one or more modules with the following module-info.java structure:

import botrino.api.annotation.BotModule;

@BotModule
open module com.example.myproject {

    requires botrino.api;
}

The annotation as well as the open modifier will allow Botrino to automatically scan through all the classes present in the module, in order to automatically register configuration entries, commands, services, etc.

Inside your module, you can create services using RDI annotations that are automatically loaded on startup:

package com.example.myproject;

import com.github.alex1304.rdi.finder.annotation.RdiFactory;
import com.github.alex1304.rdi.finder.annotation.RdiService;
import discord4j.core.GatewayDiscordClient;
import discord4j.core.event.domain.lifecycle.ReadyEvent;
import reactor.core.publisher.Mono;
import reactor.util.Logger;
import reactor.util.Loggers;

@RdiService
public final class SampleService {

    private static final Logger LOGGER = Loggers.getLogger(SampleService.class);

    // We can inject other services, here we are injecting
    // the GatewayDiscordClient provided by Botrino
    @RdiFactory
    public SampleService(GatewayDiscordClient gateway) {
        gateway.on(ReadyEvent.class, ready -> Mono.fromRunnable(
                        () -> LOGGER.info("Logged in as "
                                + ready.getSelf().getTag())))
                .subscribe();
    }
}

The bot is configured via a JSON configuration file with contents similar to this:

{
    "bot": {
        "token": "yourTokenHere",
        "presence": {
            "status": "online",
            "activity_type": "playing",
            "activity_text": "Hello world!"
        },
        "enabled_intents": 32509
    }
}

Botrino Interaction

Botrino comes with a library that allows to easily create application commands and listeners for Discord interactions. Discord recently added Application Commands as a native way to implement commands within Discord, as well as Message Components to allow for more specific and intuitive interactions with the bot.

Maven Central javadoc

Preamble

Although it is designed to be an extension of the Botrino framework, this library is completely decoupled from the framework itself. As such, it is possible to add this library to your project even if you aren't using the framework. The only difference is that you won't benefit from the automatic registration of commands, but you will be able to use all features.

Features

  • Straightforward annotation-based command declaration, with full support for slash commands with subcommands/subcommand groups and context menu commands
  • Automatic deployment of commands into the Discord application, with ability to choose whether to deploy them globally or in a specific guild during development
  • Inject command options into fields using annotations to conveniently access the values
  • Handle component interactions either by treating them as regular commands or by awaiting them in order to continue the execution of a parent command
  • Automatic ACK of interaction events, configurable on a per-command basis
  • Define privileges for each command with your own rules
  • Cooldown per user
  • Centralized error handling
  • Pre-process interaction events by filtering them or adapting the locale to the target user
  • Utilities such as pagination system using buttons

A basic ping command

package testbot1;

import botrino.interaction.annotation.ChatInputCommand;
import botrino.interaction.listener.ChatInputInteractionListener;
import botrino.interaction.context.ChatInputInteractionContext;
import org.reactivestreams.Publisher;

@ChatInputCommand(name = "ping", description = "Pings the bot to check if it is alive.")
public final class PingCommand implements ChatInputInteractionListener {

    @Override
    public Publisher<?> run(ChatInputInteractionContext ctx) {
        return ctx.event().createFollowup("Pong !");
    }
}

More examples can be found at https://botrino.alex1304.com/docs/interaction-library/overview

Getting Started

Prerequisites

  • JDK >= 17. You can download the OpenJDK here
  • Apache Maven >= 3.8.5, preferably the latest version available here.

From the Maven Archetype

The recommended way to start a project with Botrino is to use the Maven archetype (replace [VERSION] with the latest version available): Maven Central

mvn archetype:generate -DarchetypeGroupId=com.alex1304.botrino -DarchetypeArtifactId=botrino-archetype -DarchetypeVersion=[VERSION]

You will be asked to enter the groupId, the artifactId, the version and the package of your project.

From a blank project

You may as well start from a blank project and import Botrino yourself. Be aware that it will require a bit more effort to set up than using the archetype.

Import the following dependency:

Maven:

<dependency>
    <groupId>com.alex1304.botrino</groupId>
    <artifactId>botrino-api</artifactId>
    <version>[VERSION]</version>
</dependency>

Gradle:

repositories {
    mavenCentral()
}

dependencies {
    implementation 'com.alex1304.botrino:botrino-api:[VERSION]'
}

Create a module-info.java annotated with @BotModule, with the open modifier and that requires the botrino.api module:

import botrino.api.annotation.BotModule;

@BotModule
open module com.example.myproject {

    requires botrino.api;
}

The module transitively requires all libraries necessary to work, including Discord4J, Reactor, Netty, RDI and Jackson, so you don't need to put requires for those libraries. If you get compilation errors, remember to configure your project to use JDK 17 or above.

Finally, add a class with a main method:

package com.example.myproject;

import botrino.api.Botrino;

public final class Main {

    public static void main(String[] args) {
        Botrino.run(args);
    }
}

If you want to include the interaction library in your project, refer to this page.

A more complete guide to get started and to run the bot can be found on the documentation website.

Botrino semver policy and interoperability with Discord4J/Reactor

The semver policy of Botrino is the following:

  • The major version of Botrino will be bumped if:
    • The minor or major version of Discord4J or Reactor is bumped,
    • Major breaking changes (API or behavior) are introduced.
  • The minor version of Botrino will be bumped if:
    • The patch version of Discord4J or Reactor is bumped,
    • If the minimum JDK version is bumped,
    • Minor breaking changes (API or behavior) are introduced.
  • The patch version of Botrino is bumped for other non-breaking changes and bugfixes.

Find the table below for reference regarding version dependencies:

Botrino version JDK Discord4J version Reactor version RDI version
v1.1.0 17 v3.2.6 3.4.28 -
v1.0.5 - v3.2.3 - -
v1.0.4 - v3.2.2 v3.4.13 -
v1.0.3 - v3.2.1 - -
v1.0.2 - - - v1.1.3
v1.0.1 - - - -
v1.0.0 - v3.2.0 v3.4.10 -
v1.0.0-RC1 - - - v1.1.2
v1.0.0-M3 - v3.2.0-M3 v3.4.4 -
v1.0.0-M2 - - - v1.1.1
v1.0.0-M1 11 v3.2.0-M1 v3.4.1 v1.1.0

Useful links

License

This project is licensed under the MIT license.

Contributions

Have a feature to suggest or a bug to report ? Issues and pull requests are more than welcome! Make sure to follow the template and share your ideas.

Contact

If you wish to contact me directly, you can DM me on Discord (Alex1304#9704) or send an email to [email protected]. Depending on how this project turns out, a community Discord server can be considered for the future.

About

A simple yet powerful framework to develop, configure and run Discord bots based on Discord4J.

Resources

License

Stars

Watchers

Forks

Packages

No packages published