Add a MessageClipped option to set your own clipped message. Closes #1359 (#1487)

This commit is contained in:
Wim 2021-05-27 21:45:23 +02:00 committed by GitHub
parent efec01a92f
commit c86137449e
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
8 changed files with 124 additions and 105 deletions

View File

@ -283,7 +283,7 @@ func (b *Bdiscord) handleEventBotUser(msg *config.Message, channelID string) (st
// Upload a file if it exists // Upload a file if it exists
if msg.Extra != nil { if msg.Extra != nil {
for _, rmsg := range helper.HandleExtra(msg, b.General) { for _, rmsg := range helper.HandleExtra(msg, b.General) {
rmsg.Text = helper.ClipMessage(rmsg.Text, MessageLength) rmsg.Text = helper.ClipMessage(rmsg.Text, MessageLength, b.GetString("MessageClipped"))
if _, err := b.c.ChannelMessageSend(channelID, rmsg.Username+rmsg.Text); err != nil { if _, err := b.c.ChannelMessageSend(channelID, rmsg.Username+rmsg.Text); err != nil {
b.Log.Errorf("Could not send message %#v: %s", rmsg, err) b.Log.Errorf("Could not send message %#v: %s", rmsg, err)
} }
@ -294,7 +294,7 @@ func (b *Bdiscord) handleEventBotUser(msg *config.Message, channelID string) (st
} }
} }
msg.Text = helper.ClipMessage(msg.Text, MessageLength) msg.Text = helper.ClipMessage(msg.Text, MessageLength, b.GetString("MessageClipped"))
msg.Text = b.replaceUserMentions(msg.Text) msg.Text = b.replaceUserMentions(msg.Text)
// Edit message // Edit message

View File

@ -116,7 +116,7 @@ func (b *Bdiscord) handleEventWebhook(msg *config.Message, channelID string) (st
return "", nil return "", nil
} }
msg.Text = helper.ClipMessage(msg.Text, MessageLength) msg.Text = helper.ClipMessage(msg.Text, MessageLength, b.GetString("MessageClipped"))
msg.Text = b.replaceUserMentions(msg.Text) msg.Text = b.replaceUserMentions(msg.Text)
// discord username must be [0..32] max // discord username must be [0..32] max
if len(msg.Username) > 32 { if len(msg.Username) > 32 {

View File

@ -82,8 +82,10 @@ func DownloadFileAuthRocket(url, token, userID string) (*[]byte, error) {
// TODO: The current implementation has the inconvenient that it disregards // TODO: The current implementation has the inconvenient that it disregards
// word boundaries when splitting but this is hard to solve without potentially // word boundaries when splitting but this is hard to solve without potentially
// breaking formatting and other stylistic effects. // breaking formatting and other stylistic effects.
func GetSubLines(message string, maxLineLength int) []string { func GetSubLines(message string, maxLineLength int, clippingMessage string) []string {
const clippingMessage = " <clipped message>" if clippingMessage == "" {
clippingMessage = " <clipped message>"
}
var lines []string var lines []string
for _, line := range strings.Split(strings.TrimSpace(message), "\n") { for _, line := range strings.Split(strings.TrimSpace(message), "\n") {
@ -193,8 +195,11 @@ func RemoveEmptyNewLines(msg string) string {
// ClipMessage trims a message to the specified length if it exceeds it and adds a warning // ClipMessage trims a message to the specified length if it exceeds it and adds a warning
// to the message in case it does so. // to the message in case it does so.
func ClipMessage(text string, length int) string { func ClipMessage(text string, length int, clippingMessage string) string {
const clippingMessage = " <clipped message>" if clippingMessage == "" {
clippingMessage = " <clipped message>"
}
if len(text) > length { if len(text) > length {
text = text[:length-len(clippingMessage)] text = text[:length-len(clippingMessage)]
if r, size := utf8.DecodeLastRuneInString(text); r == utf8.RuneError { if r, size := utf8.DecodeLastRuneInString(text); r == utf8.RuneError {

View File

@ -10,12 +10,11 @@ import (
const testLineLength = 64 const testLineLength = 64
var ( var lineSplittingTestCases = map[string]struct {
lineSplittingTestCases = map[string]struct {
input string input string
splitOutput []string splitOutput []string
nonSplitOutput []string nonSplitOutput []string
}{ }{
"Short single-line message": { "Short single-line message": {
input: "short", input: "short",
splitOutput: []string{"short"}, splitOutput: []string{"short"},
@ -89,19 +88,18 @@ var (
}, },
nonSplitOutput: []string{"不布人個我此而及單石業喜資富下我河下日沒一我臺空達的常景便物沒為……子大我別名解成?生賣的全直黑,我自我結毛分洲了世當,是政福那是東;斯說"}, nonSplitOutput: []string{"不布人個我此而及單石業喜資富下我河下日沒一我臺空達的常景便物沒為……子大我別名解成?生賣的全直黑,我自我結毛分洲了世當,是政福那是東;斯說"},
}, },
} }
)
func TestGetSubLines(t *testing.T) { func TestGetSubLines(t *testing.T) {
for testname, testcase := range lineSplittingTestCases { for testname, testcase := range lineSplittingTestCases {
splitLines := GetSubLines(testcase.input, testLineLength) splitLines := GetSubLines(testcase.input, testLineLength, "")
assert.Equalf(t, testcase.splitOutput, splitLines, "'%s' testcase should give expected lines with splitting.", testname) assert.Equalf(t, testcase.splitOutput, splitLines, "'%s' testcase should give expected lines with splitting.", testname)
for _, splitLine := range splitLines { for _, splitLine := range splitLines {
byteLength := len([]byte(splitLine)) byteLength := len([]byte(splitLine))
assert.True(t, byteLength <= testLineLength, "Splitted line '%s' of testcase '%s' should not exceed the maximum byte-length (%d vs. %d).", splitLine, testcase, byteLength, testLineLength) assert.True(t, byteLength <= testLineLength, "Splitted line '%s' of testcase '%s' should not exceed the maximum byte-length (%d vs. %d).", splitLine, testcase, byteLength, testLineLength)
} }
nonSplitLines := GetSubLines(testcase.input, 0) nonSplitLines := GetSubLines(testcase.input, 0, "")
assert.Equalf(t, testcase.nonSplitOutput, nonSplitLines, "'%s' testcase should give expected lines without splitting.", testname) assert.Equalf(t, testcase.nonSplitOutput, nonSplitLines, "'%s' testcase should give expected lines without splitting.", testname)
} }
} }
@ -110,16 +108,19 @@ func TestConvertWebPToPNG(t *testing.T) {
if os.Getenv("LOCAL_TEST") == "" { if os.Getenv("LOCAL_TEST") == "" {
t.Skip() t.Skip()
} }
input, err := ioutil.ReadFile("test.webp") input, err := ioutil.ReadFile("test.webp")
if err != nil { if err != nil {
t.Fail() t.Fail()
} }
d := &input d := &input
err = ConvertWebPToPNG(d) err = ConvertWebPToPNG(d)
if err != nil { if err != nil {
t.Fail() t.Fail()
} }
err = ioutil.WriteFile("test.png", *d, 0644)
err = ioutil.WriteFile("test.png", *d, 0o644) // nolint:gosec
if err != nil { if err != nil {
t.Fail() t.Fail()
} }

View File

@ -167,9 +167,9 @@ func (b *Birc) Send(msg config.Message) (string, error) {
} }
if b.GetBool("MessageSplit") { if b.GetBool("MessageSplit") {
msgLines = helper.GetSubLines(msg.Text, b.MessageLength) msgLines = helper.GetSubLines(msg.Text, b.MessageLength, b.GetString("MessageClipped"))
} else { } else {
msgLines = helper.GetSubLines(msg.Text, 0) msgLines = helper.GetSubLines(msg.Text, 0, b.GetString("MessageClipped"))
} }
for i := range msgLines { for i := range msgLines {
if len(b.Local) >= b.MessageQueue { if len(b.Local) >= b.MessageQueue {
@ -316,12 +316,16 @@ func (b *Birc) endNames(client *girc.Client, event girc.Event) {
sort.Strings(b.names[channel]) sort.Strings(b.names[channel])
maxNamesPerPost := (300 / b.nicksPerRow()) * b.nicksPerRow() maxNamesPerPost := (300 / b.nicksPerRow()) * b.nicksPerRow()
for len(b.names[channel]) > maxNamesPerPost { for len(b.names[channel]) > maxNamesPerPost {
b.Remote <- config.Message{Username: b.Nick, Text: b.formatnicks(b.names[channel][0:maxNamesPerPost]), b.Remote <- config.Message{
Channel: channel, Account: b.Account} Username: b.Nick, Text: b.formatnicks(b.names[channel][0:maxNamesPerPost]),
Channel: channel, Account: b.Account,
}
b.names[channel] = b.names[channel][maxNamesPerPost:] b.names[channel] = b.names[channel][maxNamesPerPost:]
} }
b.Remote <- config.Message{Username: b.Nick, Text: b.formatnicks(b.names[channel]), b.Remote <- config.Message{
Channel: channel, Account: b.Account} Username: b.Nick, Text: b.formatnicks(b.names[channel]),
Channel: channel, Account: b.Account,
}
b.names[channel] = nil b.names[channel] = nil
b.i.Handlers.Clear(girc.RPL_NAMREPLY) b.i.Handlers.Clear(girc.RPL_NAMREPLY)
b.i.Handlers.Clear(girc.RPL_ENDOFNAMES) b.i.Handlers.Clear(girc.RPL_ENDOFNAMES)

View File

@ -248,9 +248,9 @@ func (b *Bmumble) processMessage(msg *config.Message) {
// If there is a maximum message length, split and truncate the lines // If there is a maximum message length, split and truncate the lines
var msgLines []string var msgLines []string
if maxLength := b.serverConfig.MaximumMessageLength; maxLength != nil { if maxLength := b.serverConfig.MaximumMessageLength; maxLength != nil {
msgLines = helper.GetSubLines(msg.Text, *maxLength-len(msg.Username)) msgLines = helper.GetSubLines(msg.Text, *maxLength-len(msg.Username), b.GetString("MessageClipped"))
} else { } else {
msgLines = helper.GetSubLines(msg.Text, 0) msgLines = helper.GetSubLines(msg.Text, 0, b.GetString("MessageClipped"))
} }
// Send the individual lindes // Send the individual lindes
for i := range msgLines { for i := range msgLines {

View File

@ -195,7 +195,7 @@ func (b *Bslack) Send(msg config.Message) (string, error) {
b.Log.Debugf("=> Receiving %#v", msg) b.Log.Debugf("=> Receiving %#v", msg)
} }
msg.Text = helper.ClipMessage(msg.Text, messageLength) msg.Text = helper.ClipMessage(msg.Text, messageLength, b.GetString("MessageClipped"))
msg.Text = b.replaceCodeFence(msg.Text) msg.Text = b.replaceCodeFence(msg.Text)
// Make a action /me of the message // Make a action /me of the message

View File

@ -76,20 +76,24 @@ MessageDelay=1300
#Maximum amount of messages to hold in queue. If queue is full #Maximum amount of messages to hold in queue. If queue is full
#messages will be dropped. #messages will be dropped.
#<message clipped> will be add to the message that fills the queue. #<clipped message> will be add to the message that fills the queue.
#OPTIONAL (default 30) #OPTIONAL (default 30)
MessageQueue=30 MessageQueue=30
#Maximum length of message sent to irc server. If it exceeds #Maximum length of message sent to irc server. If it exceeds
#<message clipped> will be add to the message. #<clipped message> will be add to the message.
#OPTIONAL (default 400) #OPTIONAL (default 400)
MessageLength=400 MessageLength=400
#Split messages on MessageLength instead of showing the <message clipped> #Split messages on MessageLength instead of showing the <clipped message>
#WARNING: this could lead to flooding #WARNING: this could lead to flooding
#OPTIONAL (default false) #OPTIONAL (default false)
MessageSplit=false MessageSplit=false
#Message to show when a message is too big
#Default "<clipped message>"
MessageClipped="<clipped message>"
#Delay in seconds to rejoin a channel when kicked #Delay in seconds to rejoin a channel when kicked
#OPTIONAL (default 0) #OPTIONAL (default 0)
RejoinDelay=0 RejoinDelay=0
@ -826,6 +830,10 @@ PreserveThreading=false
#OPTIONAL (default false) #OPTIONAL (default false)
ShowUserTyping=false ShowUserTyping=false
#Message to show when a message is too big
#Default "<clipped message>"
MessageClipped="<clipped message>"
################################################################### ###################################################################
#discord section #discord section
################################################################### ###################################################################
@ -961,6 +969,10 @@ ShowTopicChange=false
# Supported from the following bridges: slack # Supported from the following bridges: slack
SyncTopic=false SyncTopic=false
#Message to show when a message is too big
#Default "<clipped message>"
MessageClipped="<clipped message>"
################################################################### ###################################################################
#telegram section #telegram section
################################################################### ###################################################################
@ -1435,9 +1447,7 @@ StripNick=false
ShowTopicChange=false ShowTopicChange=false
################################################################### ###################################################################
#
# NCTalk (Nextcloud Talk) # NCTalk (Nextcloud Talk)
#
################################################################### ###################################################################
[nctalk.bridge] [nctalk.bridge]
@ -1460,9 +1470,7 @@ Password = "talkuserpass"
GuestSuffix = " (Guest)" GuestSuffix = " (Guest)"
################################################################### ###################################################################
#
# Mumble # Mumble
#
################################################################### ###################################################################
[mumble.bridge] [mumble.bridge]
@ -1505,9 +1513,14 @@ TLSCACertificate=mumble-ca.crt
# OPTIONAL (default false) # OPTIONAL (default false)
SkipTLSVerify=false SkipTLSVerify=false
#Message to show when a message is too big
#Default "<clipped message>"
MessageClipped="<clipped message>"
################################################################### ###################################################################
#VK #VK
################################################################### ###################################################################
#
[vk.myvk] [vk.myvk]
#Group access token #Group access token
#See https://vk.com/dev/bots_docs #See https://vk.com/dev/bots_docs
@ -1518,9 +1531,7 @@ Token="Yourtokenhere"
GroupID=123456789 GroupID=123456789
################################################################### ###################################################################
#
# WhatsApp # WhatsApp
#
################################################################### ###################################################################
[whatsapp.bridge] [whatsapp.bridge]
@ -1547,9 +1558,7 @@ Label="Organization"
################################################################### ###################################################################
#
# zulip # zulip
#
################################################################### ###################################################################
[zulip] [zulip]