From 6063bd789ddc5b6bf9f68c76b910e9e18ff773b4 Mon Sep 17 00:00:00 2001 From: Vitor Pamplona Date: Sun, 19 Feb 2023 15:36:43 -0500 Subject: [PATCH] Adds anti-spam filters --- .../amethyst/model/LocalCache.kt | 20 +++++++++++++++++++ 1 file changed, 20 insertions(+) diff --git a/app/src/main/java/com/vitorpamplona/amethyst/model/LocalCache.kt b/app/src/main/java/com/vitorpamplona/amethyst/model/LocalCache.kt index 67f062d03..c6028699b 100644 --- a/app/src/main/java/com/vitorpamplona/amethyst/model/LocalCache.kt +++ b/app/src/main/java/com/vitorpamplona/amethyst/model/LocalCache.kt @@ -1,6 +1,7 @@ package com.vitorpamplona.amethyst.model import android.util.Log +import android.util.LruCache import androidx.lifecycle.LiveData import com.fasterxml.jackson.databind.DeserializationFeature import com.fasterxml.jackson.module.kotlin.jacksonObjectMapper @@ -53,6 +54,9 @@ object LocalCache { val notes = ConcurrentHashMap() val channels = ConcurrentHashMap() + val recentMessages = LruCache(1000) + val spamMessages = LruCache(1000) + fun checkGetOrCreateUser(key: HexKey): User? { return try { val checkHex = Hex.decode(key) // Checks if this is a valid Hex @@ -118,7 +122,22 @@ object LocalCache { .format(DateTimeFormatter.ofPattern("uuuu MMM d hh:mm a")) } + fun isRepeatedMessageSpam(event: Event): Boolean { + // double list strategy: + // if duplicated, it goes into spam. 1000 spam messages are saved into the spam list. + + val hash = event.content.hashCode() + if (event.content.length > 50 && (recentMessages[hash] != null || spamMessages[hash] != null)) { + spamMessages.put(hash, hash) + return true + } + recentMessages.put(hash, hash) + return false + } + fun consume(event: TextNoteEvent, relay: Relay? = null) { + if (isRepeatedMessageSpam(event)) return + val note = getOrCreateNote(event.id.toHex()) val author = getOrCreateUser(event.pubKey.toHexKey()) @@ -403,6 +422,7 @@ object LocalCache { fun consume(event: ChannelMessageEvent, relay: Relay?) { if (event.channel.isNullOrBlank()) return + if (isRepeatedMessageSpam(event)) return val channel = getOrCreateChannel(event.channel)