Unstable Feature
Gameyfin's plugin API is currently in an unstable state.
Expect breaking changes until the release of 2.0.0
(probably even after that).
How to create a Plugin
The plugin system is based on PF4J which allows you to create plugins in Java or Kotlin.
Depending on the type of plugin you want to create, you will need to implement the appropriate interfaces.
The Gameyfin Plugin API is published as a Maven artifact on Maven Central, so you can easily include it in your project.
For a quick start, you can follow the tutorial.
Structure of a Plugin
A Gameyfin plugin typically consists of the following components:
Plugin Manifest
The plugin manifest is a Manifest file that contains metadata about the plugin.
It should be located in the META-INF/MANIFEST.MF
file of your plugin JAR file.
Field | Description |
---|---|
Plugin-Version | Version of the plugin in SemVer format |
Plugin-Class | Fully qualified class name of your plugin wrapper class |
Plugin-Id | Unique ID for your plugin. It is recommended to either use a unique reverse-DNS identifier or a UUID. |
Plugin-Name | Name of your plugin |
Plugin-Description | Description of the functionality of your plugin in Markdown format. Use <br> for line breaks and start suceeding lines with one space. |
Plugin-Author | Name(s) of the plugin authors (if the plugin has multiple authors, use a comma-separated string) |
Plugin-Short-Description1 | Shorter description of your plugin (not in Markdown). Used primarily for display in various smaller UI elements (falls back to "Plugin-Description" if empty). |
Plugin-Url1 | URL to the website of your plugin (e.g. the GitHub repository containing the plugin source code) |
Plugin-License1 | Name of the license for the plugin (e.g. "MIT", "AGLPv3", ...) |
Source Code
Gameyfin plugins are written in Java or Kotlin (although any language that compiles to JVM bytecode can be used in theory). The source code of the plugin should be organized in a way that follows the standard Java/Kotlin project structure.
Plugin Wrapper Class
The plugin wrapper class is the main class of your plugin that extends either GameyfinPlugin
or ConfigurableGameyfinPlugin
(depending on whether your plugin requires configuration).
Your wrapper class should contain one or more inner classes that implement the necessary interfaces for your plugin type.
These inner classes will be used by Gameyfin to interact with your plugin and should be annotated with @Extension
.
Depending on the type of plugin, you will need to implement specific methods that Gameyfin will call to interact with your plugin.
Configurable Plugins
If your plugin requires configuration, you should extend ConfigurableGameyfinPlugin
instead of GameyfinPlugin
.
This also means that your plugin will have a configuration page in the Admin UI.
In order for Gameyfin to be able to display the configuration page, your plugin needs to implement two things:
- A
configMetadata
property of typeConfigMetadata
that contains the metadata of your plugin configuration. - The
validateConfig
method that validates the configuration and returns aPluginConfigValidationResult
.
For an example of how to implement plugin configuration, take a look at the tutorial.