Skip to content

Commit

Permalink
feat: betterttv event client
Browse files Browse the repository at this point in the history
  • Loading branch information
ilotterytea committed Dec 30, 2024
1 parent 447c8d9 commit 98443fc
Show file tree
Hide file tree
Showing 4 changed files with 160 additions and 33 deletions.
2 changes: 1 addition & 1 deletion build.gradle
Original file line number Diff line number Diff line change
Expand Up @@ -26,7 +26,7 @@ dependencies {
implementation 'com.squareup.okhttp3:okhttp'
implementation 'org.hibernate.orm:hibernate-core:6.2.0.Final'
implementation 'org.postgresql:postgresql:42.7.2'
implementation("com.github.ilotterytea:emotes4j:0.1.2")
implementation("com.github.ilotterytea:emotes4j:0.2.0")

// Web related dependencies
annotationProcessor("io.micronaut:micronaut-http-validation")
Expand Down
46 changes: 40 additions & 6 deletions src/main/java/kz/ilotterytea/bot/Huinyabot.java
Original file line number Diff line number Diff line change
@@ -1,5 +1,9 @@
package kz.ilotterytea.bot;

import com.github.ilotterytea.emotes4j.betterttv.BetterTTVEventClient;
import com.github.ilotterytea.emotes4j.betterttv.events.EmoteCreateEvent;
import com.github.ilotterytea.emotes4j.betterttv.events.EmoteDeleteEvent;
import com.github.ilotterytea.emotes4j.betterttv.events.EmoteUpdateEvent;
import com.github.ilotterytea.emotes4j.seventv.SevenTVEventClient;
import com.github.ilotterytea.emotes4j.seventv.events.EmoteSetUpdateEvent;
import com.github.ilotterytea.emotes4j.seventv.events.HeartbeatEvent;
Expand Down Expand Up @@ -40,10 +44,11 @@ public class Huinyabot extends Bot {
private TwitchClient client;
private CommandLoader loader;
private SevenTVEventClient stvEventClient;
private BetterTTVEventClient betterTTVEventClient;
private OAuth2Credential credential;
private I18N i18N;

private final Logger LOGGER = LoggerFactory.getLogger(Huinyabot.class);
private final Logger log = LoggerFactory.getLogger(Huinyabot.class);

public TwitchClient getClient() {
return client;
Expand Down Expand Up @@ -102,15 +107,15 @@ public void init() {
// Join bot's chat:
if (credential.getUserName() != null && credential.getUserId() != null) {
client.getChat().joinChannel(credential.getUserName());
LOGGER.debug("Joined to bot's chat room!");
log.debug("Joined to bot's chat room!");

// Generate a new channel for bot if it doesn't exist:
List<Channel> channels = session.createQuery("from Channel where aliasId = :aliasId", Channel.class)
.setParameter("aliasId", credential.getUserId())
.getResultList();

if (channels.isEmpty()) {
LOGGER.debug("The bot doesn't have a channel entry. Creating a new one...");
log.debug("The bot doesn't have a channel entry. Creating a new one...");

Channel channel = new Channel(Integer.parseInt(credential.getUserId()), credential.getUserName());
ChannelPreferences preferences = new ChannelPreferences(channel);
Expand All @@ -136,7 +141,7 @@ public void init() {
// Join channel chats:
for (User twitchChannel : twitchChannels) {
client.getChat().joinChannel(twitchChannel.getLogin());
LOGGER.debug("Joined to " + twitchChannel.getLogin() + "'s chat room!");
log.debug("Joined to " + twitchChannel.getLogin() + "'s chat room!");
}
}

Expand All @@ -160,7 +165,7 @@ public void init() {
// Listening to stream events:
for (User listenableUser : listenableUsers) {
client.getClientHelper().enableStreamEventListener(listenableUser.getId(), listenableUser.getLogin());
LOGGER.debug("Listening for stream events for user " + listenableUser.getLogin());
log.debug("Listening for stream events for user " + listenableUser.getLogin());
}
}

Expand Down Expand Up @@ -208,7 +213,7 @@ public void run() {

// Setting up 7TV EventAPI
try {
LOGGER.info("Connecting to 7TV Events...");
log.info("Connecting to 7TV Events...");
stvEventClient = new SevenTVEventClient();
stvEventClient.getClient().connectBlocking();
stvEventClient.getEventManager().onEvent(EmoteSetUpdateEvent.class, EventHandlers::handleEmoteSetUpdate);
Expand All @@ -217,6 +222,31 @@ public void run() {
} catch (InterruptedException e) {
throw new RuntimeException(e);
}

// Setting up BetterTTV Events
try {
log.info("Connecting to BetterTTV Events...");
betterTTVEventClient = new BetterTTVEventClient();
betterTTVEventClient.getClient().connectBlocking();
betterTTVEventClient.getEventManager().onEvent(EmoteCreateEvent.class, EventHandlers::handleEmoteCreation);
betterTTVEventClient.getEventManager().onEvent(EmoteUpdateEvent.class, EventHandlers::handleEmoteUpdate);
betterTTVEventClient.getEventManager().onEvent(EmoteDeleteEvent.class, EventHandlers::handleEmoteDeletion);
} catch (InterruptedException e) {
throw new RuntimeException(e);
}

// Update BetterTTV subscribers every minute
new Timer().schedule(new TimerTask() {
@Override
public void run() {
// in case if SOMETHING HAPPENS (nothing ever happens)
try {
EventHandlers.subscribeChannels(betterTTVEventClient, ChannelFeature.NOTIFY_BTTV);
} catch (Exception e) {
log.error("An exception was thrown while checking new BetterTTV subscribers", e);
}
}
}, 0, 60000);
}

@Override
Expand All @@ -228,4 +258,8 @@ public void dispose() {
public SevenTVEventClient getSevenTVEventClient() {
return stvEventClient;
}

public BetterTTVEventClient getBetterTTVEventClient() {
return betterTTVEventClient;
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -11,6 +11,7 @@
*/
public enum ChannelFeature {
NOTIFY_7TV("notify_7tv_events"),
NOTIFY_BTTV("notify_betterttv_events"),
SILENT_MODE("silent_mode");

private String id;
Expand Down
144 changes: 118 additions & 26 deletions src/main/java/kz/ilotterytea/bot/handlers/EventHandlers.java
Original file line number Diff line number Diff line change
@@ -1,6 +1,11 @@
package kz.ilotterytea.bot.handlers;

import com.github.ilotterytea.emotes4j.betterttv.BetterTTVEventClient;
import com.github.ilotterytea.emotes4j.betterttv.events.EmoteCreateEvent;
import com.github.ilotterytea.emotes4j.betterttv.events.EmoteDeleteEvent;
import com.github.ilotterytea.emotes4j.betterttv.events.EmoteUpdateEvent;
import com.github.ilotterytea.emotes4j.core.EventClient;
import com.github.ilotterytea.emotes4j.seventv.SevenTVEventClient;
import com.github.ilotterytea.emotes4j.seventv.emotes.EventEmote;
import com.github.ilotterytea.emotes4j.seventv.events.EmoteSetUpdateEvent;
import com.github.ilotterytea.emotes4j.seventv.events.HeartbeatEvent;
Expand All @@ -12,35 +17,14 @@
import kz.ilotterytea.bot.utils.HibernateUtil;
import org.hibernate.Session;

import java.util.ArrayList;
import java.util.List;
import java.util.Map;
import java.util.Set;
import java.util.*;

public class EventHandlers {
public static void handleEmoteSetUpdate(EmoteSetUpdateEvent event) {
String aliasId = null;

for (Map.Entry<String, String> entry : Huinyabot.getInstance().getSevenTVEventClient().getSubscriptions().entrySet()) {
if (entry.getValue().equals(event.getEmoteSetId())) {
aliasId = entry.getKey();
break;
}
}
Optional<Channel> channelOptional = getChannelBySTV(Huinyabot.getInstance().getSevenTVEventClient(), event.getEmoteSetId());

if (aliasId == null) {
return;
}

Session session = HibernateUtil.getSessionFactory().openSession();
Channel channel = session.createQuery("from Channel where aliasId = :aliasId AND optOutTimestamp is null", Channel.class)
.setParameter("aliasId", aliasId)
.getSingleResult();
session.close();

if (channel.getPreferences().getFeatures().contains(ChannelFeature.SILENT_MODE)) {
return;
}
if (channelOptional.isEmpty()) return;
Channel channel = channelOptional.get();

String prefix = "7TV";
Huinyabot bot = Huinyabot.getInstance();
Expand Down Expand Up @@ -102,7 +86,62 @@ public static void handleHello(HelloEvent event) {
subscribeChannels(Huinyabot.getInstance().getSevenTVEventClient(), ChannelFeature.NOTIFY_7TV);
}

private static void subscribeChannels(EventClient eventClient, ChannelFeature feature) {
public static void handleEmoteCreation(EmoteCreateEvent event) {
Optional<Channel> channelOptional = getChannelByBTTV(Huinyabot.getInstance().getBetterTTVEventClient(), event.getChannel());

if (channelOptional.isEmpty()) return;
Channel channel = channelOptional.get();

String prefix = "BTTV";
Huinyabot bot = Huinyabot.getInstance();

String line = bot.getLocale().formattedText(channel.getPreferences().getLanguage(),
LineIds.NEW_EMOTE,
prefix,
event.getEmote().getCode()
);

bot.getClient().getChat().sendMessage(channel.getAliasName(), line);
}

public static void handleEmoteUpdate(EmoteUpdateEvent event) {
Optional<Channel> channelOptional = getChannelByBTTV(Huinyabot.getInstance().getBetterTTVEventClient(), event.getChannel());

if (channelOptional.isEmpty()) return;
Channel channel = channelOptional.get();

String prefix = "BTTV";
Huinyabot bot = Huinyabot.getInstance();

String line = bot.getLocale().formattedText(channel.getPreferences().getLanguage(),
LineIds.UPDATED_EMOTE,
prefix,
event.getOldEmote().getCode(),
event.getEmote().getCode()
);

bot.getClient().getChat().sendMessage(channel.getAliasName(), line);
}

public static void handleEmoteDeletion(EmoteDeleteEvent event) {
Optional<Channel> channelOptional = getChannelByBTTV(Huinyabot.getInstance().getBetterTTVEventClient(), event.getChannel());

if (channelOptional.isEmpty()) return;
Channel channel = channelOptional.get();

String prefix = "BTTV";
Huinyabot bot = Huinyabot.getInstance();

String line = bot.getLocale().formattedText(channel.getPreferences().getLanguage(),
LineIds.REMOVED_EMOTE,
prefix,
event.getEmote().getCode()
);

bot.getClient().getChat().sendMessage(channel.getAliasName(), line);
}

public static void subscribeChannels(EventClient<?> eventClient, ChannelFeature feature) {
Session session = HibernateUtil.getSessionFactory().openSession();
List<Channel> channels = session.createQuery("from Channel where optOutTimestamp is null", Channel.class).getResultList();
session.close();
Expand All @@ -126,4 +165,57 @@ private static void subscribeChannels(EventClient eventClient, ChannelFeature fe
eventClient.unsubscribeChannel(userId);
}
}

private static Optional<Channel> getChannelByBTTV(BetterTTVEventClient client, String id) {
String aliasId = null;

if (client.getSubscriptions().containsKey(id)) {
aliasId = id;
}

if (aliasId == null) {
return Optional.empty();
}

aliasId = aliasId.substring("twitch:".length());

Session session = HibernateUtil.getSessionFactory().openSession();
Channel channel = session.createQuery("from Channel where aliasId = :aliasId AND optOutTimestamp is null", Channel.class)
.setParameter("aliasId", aliasId)
.getSingleResult();
session.close();

if (channel.getPreferences().getFeatures().contains(ChannelFeature.SILENT_MODE) || !channel.getPreferences().getFeatures().contains(ChannelFeature.NOTIFY_BTTV)) {
return Optional.empty();
}

return Optional.of(channel);
}

private static Optional<Channel> getChannelBySTV(SevenTVEventClient client, String id) {
String aliasId = null;

for (Map.Entry<String, String> entry : client.getSubscriptions().entrySet()) {
if (entry.getValue().equals(id)) {
aliasId = entry.getKey();
break;
}
}

if (aliasId == null) {
return Optional.empty();
}

Session session = HibernateUtil.getSessionFactory().openSession();
Channel channel = session.createQuery("from Channel where aliasId = :aliasId AND optOutTimestamp is null", Channel.class)
.setParameter("aliasId", aliasId)
.getSingleResult();
session.close();

if (channel.getPreferences().getFeatures().contains(ChannelFeature.SILENT_MODE) || !channel.getPreferences().getFeatures().contains(ChannelFeature.NOTIFY_7TV)) {
return Optional.empty();
}

return Optional.of(channel);
}
}

0 comments on commit 98443fc

Please sign in to comment.