improve docs and reconnection handling
This commit is contained in:
parent
e5cd059313
commit
c7146ce7df
|
@ -103,6 +103,7 @@ object EventHandler {
|
|||
@SubscribeEvent
|
||||
@JvmStatic
|
||||
fun serverTickEvent(e: TickEvent.ServerTickEvent) {
|
||||
TickHandler.handleTick()
|
||||
if(e.phase == TickEvent.Phase.END)
|
||||
TickHandler.handleTick()
|
||||
}
|
||||
}
|
|
@ -104,6 +104,7 @@ object EventHandler {
|
|||
@SubscribeEvent
|
||||
@JvmStatic
|
||||
fun serverTickEvent(e: TickEvent.ServerTickEvent) {
|
||||
TickHandler.handleTick()
|
||||
if(e.phase == TickEvent.Phase.END)
|
||||
TickHandler.handleTick()
|
||||
}
|
||||
}
|
|
@ -96,6 +96,7 @@ object EventHandler {
|
|||
@SubscribeEvent
|
||||
@JvmStatic
|
||||
fun serverTickEvent(e: TickEvent.ServerTickEvent) {
|
||||
TickHandler.handleTick()
|
||||
if(e.phase == TickEvent.Phase.END)
|
||||
TickHandler.handleTick()
|
||||
}
|
||||
}
|
|
@ -96,6 +96,7 @@ object EventHandler {
|
|||
//FORGE-DEPENDENT
|
||||
@SubscribeEvent
|
||||
fun serverTickEvent(e: TickEvent.ServerTickEvent) {
|
||||
TickHandler.handleTick()
|
||||
if(e.phase == TickEvent.Phase.END)
|
||||
TickHandler.handleTick()
|
||||
}
|
||||
}
|
85
README.md
85
README.md
|
@ -5,59 +5,68 @@ A MatterBridge endpoint for MC servers!
|
|||
THIS MOD REQUIRES YOU TO ALSO RUN A MATTERBRIDGE RELAY
|
||||
https://github.com/42wim/matterbridge
|
||||
|
||||
requires api section to be setup along these lines
|
||||
Chat with us on IRC: [#matterbridge @ irc.esper.net](irc://irc.esper.net/matterbridge)
|
||||
|
||||
Requires the matterbridge config api section to be setup along these lines:
|
||||
|
||||
```
|
||||
[api]
|
||||
[api.local]
|
||||
BindAddress="0.0.0.0:4242" # or listen only to localhost: 127.0.0.1:4242
|
||||
|
||||
#Bearer token used for authentication
|
||||
#curl -H "Authorization: Bearer testtoken" http://localhost:4343/api/messages
|
||||
|
||||
#OPTIONAL (no authorization if token is empty)
|
||||
Token="mytoken"
|
||||
|
||||
Buffer=1000
|
||||
|
||||
RemoteNickFormat="{NICK}"
|
||||
|
||||
ShowJoinPart = true
|
||||
```
|
||||
|
||||
## Features
|
||||
|
||||
* Individually configurable relaying of player deaths, achievements/advancements, server join, and server leave
|
||||
* Configurable bridge commands sent from chat to MC:
|
||||
* Custom bridge commands, including passthrough to MC!
|
||||
Default commands: `help, tps, list, seed, uptime`
|
||||
|
||||
Commands are specified in JSON format as follows:
|
||||
Passthrough command (executes the configured command as if from the MC server console)
|
||||
```json
|
||||
{
|
||||
"alias": "tps",
|
||||
"type": "PASSTHROUGH",
|
||||
"execute": "forge tps",
|
||||
"permLevel": 0,
|
||||
"help": "Print server tps",
|
||||
"allowArgs": false
|
||||
}
|
||||
```
|
||||
help: Lists all commands with no arguments,
|
||||
or displays help for a command
|
||||
players: Lists online players
|
||||
uptime: Print server uptime
|
||||
Response command
|
||||
```json
|
||||
{
|
||||
"alias": "uptime",
|
||||
"type": "RESPONSE",
|
||||
"response": "{uptime}",
|
||||
"permLevel": 1,
|
||||
"help": "Print server uptime",
|
||||
"allowArgs": false
|
||||
}
|
||||
```
|
||||
* Command permissions!
|
||||
Higher numbers mean more permissions. Configured on a network-by-network basis.
|
||||
For IRC, this is your hostmask.
|
||||
For Discord, this is your userid (NOT the four-digit number.)
|
||||
```json
|
||||
{
|
||||
"irc.esper": {
|
||||
"~DaMachina@hostname.com":1000
|
||||
}
|
||||
}
|
||||
```
|
||||
* Edit and reload the config file without restarting the server!
|
||||
```
|
||||
/config <connect|disconnect|reload>
|
||||
Connect or disconnect the bridge,
|
||||
or cycle the connection and reload the config file
|
||||
connect: Connects the MC chat to the MatterBridge server
|
||||
disconnect: Disconnects the chat from the MatterBridge server
|
||||
reload: Disconnects, reloads the config and custom command files,
|
||||
then reconnects.
|
||||
```
|
||||
* Pass through commands to MineCraft! Fully configurable.
|
||||
```
|
||||
# MC commands that can be executed through the bridge
|
||||
# Separate bridge command and MC command with '=',
|
||||
# separate multiple values with spaces
|
||||
# [default: [tps=forge tps]]
|
||||
S:commandMapping <
|
||||
tps=forge tps
|
||||
>
|
||||
```
|
||||
This default example allows you to run `/forge tps` on the server by typing `$tps` in the chat
|
||||
(replace $ with whatever you've configured as the command prefix).
|
||||
|
||||
**WARNING: There is *NO* permissions checking of any kind for command passthrough!
|
||||
Do not configure passthrough for any commands you would not be comfortable
|
||||
with anyone on your IRC/Discord/etc. executing!**
|
||||
|
||||
|
||||
## Downloads
|
||||
|
||||
|
@ -65,22 +74,26 @@ https://github.com/elytra/MatterLink/releases
|
|||
|
||||
https://ci.elytradev.com/job/elytra/job/MatterLink/job/master/lastSuccessfulBuild/ - may be unstable
|
||||
|
||||
https://minecraft.curseforge.com/projects/matterlink
|
||||
|
||||
## Dependencies
|
||||
|
||||
- forgelin: https://minecraft.curseforge.com/projects/shadowfacts-forgelin
|
||||
|
||||
## Setup
|
||||
Now you just need to run MatterBridge on the server, the default configuration works with the provided sample.
|
||||
|
||||
Install matterbridge and try out the basic sample:
|
||||
|
||||
```
|
||||
go get github.com/42wim/matterbridge
|
||||
mv matterbridge-sample.toml matterbridge.tom
|
||||
mv matterbridge-sample.toml matterbridge.toml
|
||||
matterbridge
|
||||
```
|
||||
|
||||
Now you just need to run MatterBridge on the server, the default configuration works with the provided sample.
|
||||
now start the server with matterlink (and forgelin )in the mods folder
|
||||
|
||||
and then [RTFM!!!](https://github.com/42wim/matterbridge#configuration)
|
||||
|
||||
and then [RTFM!!!](https://github.com/42wim/matterbridge#configuration) and configure all your needed gateways, endpoints etc
|
||||
|
||||
powered by wishful thinking
|
|
@ -49,8 +49,10 @@ class HttpStreamConnection(private val rcvQueue: ConcurrentLinkedQueue<ApiMessag
|
|||
if (success) {
|
||||
instance.info("connected successfully")
|
||||
messageHandler.connectErrors = 0
|
||||
messageHandler.reconnectCoodown = 0
|
||||
connected = true
|
||||
} else {
|
||||
messageHandler.reconnectCoodown = messageHandler.connectErrors
|
||||
messageHandler.connectErrors++
|
||||
connected = false
|
||||
instance.warn("connectErrors: ${messageHandler.connectErrors}")
|
||||
|
@ -76,6 +78,8 @@ class HttpStreamConnection(private val rcvQueue: ConcurrentLinkedQueue<ApiMessag
|
|||
r.entity.content.bufferedReader().forEachLine {
|
||||
instance.debug("skipping $it")
|
||||
}
|
||||
//connection was not refused, url and token should be correct
|
||||
setSuccess(true)
|
||||
}
|
||||
val response = client.execute(get)
|
||||
if (response.statusLine.statusCode != 200) {
|
||||
|
|
|
@ -13,6 +13,7 @@ object MessageHandler {
|
|||
var enabled: Boolean = false
|
||||
private var sendErrors = 0
|
||||
var connectErrors = 0
|
||||
var reconnectCoodown = 0
|
||||
private var streamConnection: HttpStreamConnection
|
||||
var rcvQueue = ConcurrentLinkedQueue<ApiMessage>()
|
||||
private set
|
||||
|
@ -103,14 +104,18 @@ object MessageHandler {
|
|||
fun checkConnection() {
|
||||
if (enabled && !streamConnection.connected && !streamConnection.connecting) {
|
||||
|
||||
if (connectErrors > 5) {
|
||||
if (connectErrors >= 10) {
|
||||
instance.fatal("Caught too many errors, closing bridge")
|
||||
stop("Interrupting connection to matterbridge API due to accumulated connection errors")
|
||||
return
|
||||
}
|
||||
|
||||
instance.info("Trying to reconnect")
|
||||
MessageHandler.start(clear = false, message = "Reconnecting to matterbridge API after connection error")
|
||||
if (reconnectCoodown <= 0) {
|
||||
instance.info("Trying to reconnect")
|
||||
MessageHandler.start(clear = false, message = "Reconnecting to matterbridge API after connection error")
|
||||
} else {
|
||||
reconnectCoodown--
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
@ -35,10 +35,10 @@ object CommandConfig {
|
|||
),
|
||||
CustomCommand(
|
||||
alias = "uptime",
|
||||
type = CommandType.PASSTHROUGH,
|
||||
type = CommandType.RESPONSE,
|
||||
permLevel = 1,
|
||||
response = "{uptime}",
|
||||
help = "Print server world seed",
|
||||
help = "Print server uptime",
|
||||
allowArgs = false
|
||||
)
|
||||
)
|
||||
|
|
|
@ -12,16 +12,15 @@ import matterlink.update.UpdateChecker
|
|||
object TickHandler {
|
||||
private var totalTicks = 0
|
||||
private var accumulator = 0
|
||||
private const val updateInterval = 12 * 60 * 20
|
||||
private const val updateInterval = 12 * 60 * 60 * 20
|
||||
fun handleTick() {
|
||||
totalTicks++
|
||||
if (totalTicks % 20 == 0) {
|
||||
if (totalTicks % 100 == 0) {
|
||||
MessageHandler.checkConnection()
|
||||
}
|
||||
|
||||
ServerChatHandler.writeIncomingToChat()
|
||||
|
||||
|
||||
if(accumulator++ > updateInterval) {
|
||||
accumulator -= updateInterval
|
||||
UpdateChecker.run()
|
||||
|
|
|
@ -9,7 +9,7 @@
|
|||
#You can configure multiple servers "[irc.name]" or "[irc.name2]"
|
||||
#In this example we use [irc.freenode]
|
||||
#REQUIRED
|
||||
[irc.freenode]
|
||||
[irc.esper]
|
||||
#irc server to connect to.
|
||||
#REQUIRED
|
||||
Server="irc.esper.net:6697"
|
||||
|
@ -117,6 +117,10 @@ ReplaceMessages=[ ["cat","dog"] ]
|
|||
#optional (default empty)
|
||||
ReplaceNicks=[ ["user--","user"] ]
|
||||
|
||||
#extra label that can be used in the RemoteNickFormat
|
||||
#optional (default empty)
|
||||
Label=""
|
||||
|
||||
#RemoteNickFormat defines how remote users appear on this bridge
|
||||
#The string "{NICK}" (case sensitive) will be replaced by the actual nick / username.
|
||||
#The string "{BRIDGE}" (case sensitive) will be replaced by the sending bridge
|
||||
|
@ -161,6 +165,10 @@ Buffer=1000
|
|||
#OPTIONAL (no authorization if token is empty)
|
||||
Token=""
|
||||
|
||||
#extra label that can be used in the RemoteNickFormat
|
||||
#optional (default empty)
|
||||
Label="minecraft"
|
||||
|
||||
#RemoteNickFormat defines how remote users appear on this bridge
|
||||
#The string "{NICK}" (case sensitive) will be replaced by the actual nick / username.
|
||||
#The string "{BRIDGE}" (case sensitive) will be replaced by the sending bridge
|
||||
|
@ -168,8 +176,6 @@ Token=""
|
|||
#OPTIONAL (default empty)
|
||||
RemoteNickFormat="{NICK}"
|
||||
|
||||
|
||||
|
||||
###################################################################
|
||||
#General configuration
|
||||
###################################################################
|
||||
|
@ -232,56 +238,11 @@ name="minecraft"
|
|||
##OPTIONAL (default false)
|
||||
enable=true
|
||||
|
||||
#API example
|
||||
# API
|
||||
[[gateway.inout]]
|
||||
account="api.minecraft"
|
||||
channel="api"
|
||||
#To send data to the api:
|
||||
#curl -XPOST -H 'Content-Type: application/json' -d '{"text":"test","username":"randomuser","gateway":"gateway1"}' http://localhost:4242/api/message
|
||||
#To read from the api:
|
||||
#curl http://localhost:4242/api/messages
|
||||
|
||||
|
||||
#[[gateway.in]] specifies the account and channels we will receive messages from.
|
||||
#The following example bridges between mattermost and irc
|
||||
[[gateway.inout]]
|
||||
account="irc.freenode"
|
||||
channel="#matterlink"
|
||||
|
||||
# #OPTIONAL - only used for IRC protocol at the moment
|
||||
# [gateway.in.options]
|
||||
# #OPTIONAL - your irc channel key
|
||||
# key="yourkey"
|
||||
|
||||
|
||||
# #[[gateway.inout]] can be used when then channel will be used to receive from
|
||||
# #and send messages to
|
||||
# [[gateway.inout]]
|
||||
# account="irc.freenode"
|
||||
# channel="#matterlink-testing"
|
||||
|
||||
# #OPTIONAL - only used for IRC protocol at the moment
|
||||
# [gateway.out.options]
|
||||
# #OPTIONAL - your irc channel key
|
||||
# key="yourkey"
|
||||
|
||||
# [[gateway.inout]]
|
||||
# account="discord.game"
|
||||
# channel="mygreatgame"
|
||||
#
|
||||
# #OPTIONAL - webhookurl only works for discord (it needs a different URL for each cahnnel)
|
||||
# [gateway.inout.options]
|
||||
# webhookurl=""https://discordapp.com/api/webhooks/123456789123456789/C9WPqExYWONPDZabcdef-def1434FGFjstasJX9pYht73y"
|
||||
|
||||
|
||||
|
||||
##If you want to do a 1:1 mapping between protocols where the channelnames are the same
|
||||
##e.g. slack and mattermost you can use the samechannelgateway configuration
|
||||
##the example configuration below send messages from channel testing on mattermost to
|
||||
##channel testing on slack and vice versa. (and for the channel testing2 and testing3)
|
||||
#
|
||||
#[[samechannelgateway]]
|
||||
# name="samechannel1"
|
||||
# enable = false
|
||||
# accounts = [ "mattermost.work","slack.hobby" ]
|
||||
# channels = [ "testing","testing2","testing3"]
|
||||
channel="#matterlink"
|
Loading…
Reference in New Issue