impl birthday feature
All checks were successful
Deploy to Dokku / docker (ubuntu-latest) (push) Successful in 36s
All checks were successful
Deploy to Dokku / docker (ubuntu-latest) (push) Successful in 36s
This commit is contained in:
parent
e7159ad514
commit
6d593246e8
@ -8,14 +8,15 @@ import lombok.extern.log4j.Log4j2;
|
||||
import org.springframework.boot.SpringApplication;
|
||||
import org.springframework.boot.autoconfigure.SpringBootApplication;
|
||||
import org.springframework.cache.annotation.EnableCaching;
|
||||
import org.springframework.scheduling.annotation.EnableScheduling;
|
||||
|
||||
import java.io.File;
|
||||
import java.nio.file.Files;
|
||||
import java.nio.file.StandardCopyOption;
|
||||
import java.util.Objects;
|
||||
|
||||
@EnableCaching
|
||||
@SpringBootApplication()
|
||||
@EnableCaching @EnableScheduling
|
||||
@SpringBootApplication
|
||||
@Log4j2(topic = "Ember")
|
||||
public class BatApplication {
|
||||
public static Gson GSON = new GsonBuilder().create();
|
||||
|
@ -44,19 +44,11 @@ public abstract class BatCommand implements BatCommandExecutor {
|
||||
*/
|
||||
private final Map<String, BatSubCommand> subCommands = new HashMap<>();
|
||||
|
||||
/**
|
||||
* The category of the command
|
||||
*/
|
||||
private Category category;
|
||||
|
||||
public BatCommand(@NonNull String name, @NonNull String description, boolean guildOnly, Permission... permissions) {
|
||||
this.name = name;
|
||||
this.description = description;
|
||||
this.requiredPermissions = List.of(permissions);
|
||||
|
||||
// Default values
|
||||
this.category = Category.GENERAL;
|
||||
|
||||
this.commandData = new CommandDataImpl(this.name, description)
|
||||
.setGuildOnly(guildOnly);
|
||||
}
|
||||
@ -101,20 +93,4 @@ public abstract class BatCommand implements BatCommandExecutor {
|
||||
public List<String> getOptions(SlashCommandInteraction interaction) {
|
||||
return interaction.getOptions().stream().map(OptionMapping::getName).toList();
|
||||
}
|
||||
|
||||
/**
|
||||
* The category of the command
|
||||
*/
|
||||
@AllArgsConstructor @Getter
|
||||
protected enum Category {
|
||||
GENERAL("General"),
|
||||
MODERATION("Moderation"),
|
||||
SERVER("Server"),
|
||||
BEAT_SABER("Beat Saber");
|
||||
|
||||
/**
|
||||
* The name of the category
|
||||
*/
|
||||
private final String name;
|
||||
}
|
||||
}
|
||||
|
@ -9,11 +9,16 @@ import lombok.Setter;
|
||||
*/
|
||||
@AllArgsConstructor
|
||||
@Getter @Setter
|
||||
public class Profile {
|
||||
public abstract class Profile {
|
||||
/**
|
||||
* The key of the profile.
|
||||
*/
|
||||
private String profileKey;
|
||||
|
||||
public Profile() {}
|
||||
|
||||
/**
|
||||
* Resets the profile
|
||||
*/
|
||||
public abstract void reset();
|
||||
}
|
||||
|
@ -1,5 +1,6 @@
|
||||
package cc.fascinated.bat.features;
|
||||
|
||||
import lombok.AllArgsConstructor;
|
||||
import lombok.Getter;
|
||||
import lombok.RequiredArgsConstructor;
|
||||
import org.springframework.stereotype.Component;
|
||||
@ -15,4 +16,25 @@ public abstract class Feature {
|
||||
* The name of the feature
|
||||
*/
|
||||
private final String name;
|
||||
|
||||
/**
|
||||
* The category of the feature
|
||||
*/
|
||||
private final Category category;
|
||||
|
||||
/**
|
||||
* The category of the feature
|
||||
*/
|
||||
@AllArgsConstructor @Getter
|
||||
public enum Category {
|
||||
GENERAL("General"),
|
||||
MODERATION("Moderation"),
|
||||
SERVER("Server"),
|
||||
BEAT_SABER("Beat Saber");
|
||||
|
||||
/**
|
||||
* The name of the category
|
||||
*/
|
||||
private final String name;
|
||||
}
|
||||
}
|
||||
|
@ -15,7 +15,7 @@ import org.springframework.stereotype.Component;
|
||||
public class AutoRoleFeature extends Feature {
|
||||
@Autowired
|
||||
public AutoRoleFeature(@NonNull ApplicationContext context, @NonNull CommandService commandService) {
|
||||
super("AutoRole");
|
||||
super("AutoRole", Category.SERVER);
|
||||
|
||||
commandService.registerCommand(context.getBean(AutoRoleCommand.class));
|
||||
}
|
||||
|
@ -30,7 +30,7 @@ public class ClearSubCommand extends BatSubCommand {
|
||||
public void execute(BatGuild guild, @NonNull BatUser user, @NonNull MessageChannel channel, Member member, @NonNull SlashCommandInteraction interaction) {
|
||||
AutoRoleProfile profile = guild.getProfile(AutoRoleProfile.class);
|
||||
|
||||
profile.clearRoles();
|
||||
profile.reset();
|
||||
guildService.saveGuild(guild);
|
||||
interaction.replyEmbeds(EmbedUtils.successEmbed()
|
||||
.setDescription("Successfully cleared all auto roles")
|
||||
|
@ -14,6 +14,8 @@ import java.util.List;
|
||||
*/
|
||||
@Setter @Getter
|
||||
public class AutoRoleProfile extends Profile {
|
||||
private static final int DEFAULT_MAX_ROLES = 10;
|
||||
|
||||
/**
|
||||
* The roles to assign when a user joins
|
||||
*/
|
||||
@ -70,13 +72,6 @@ public class AutoRoleProfile extends Profile {
|
||||
this.roleIds.remove(roleId);
|
||||
}
|
||||
|
||||
public void clearRoles() {
|
||||
if (this.roleIds == null) {
|
||||
this.roleIds = new ArrayList<>();
|
||||
}
|
||||
this.roleIds.clear();
|
||||
}
|
||||
|
||||
/**
|
||||
* Checks if a role is set to be assigned when a user joins
|
||||
*
|
||||
@ -108,4 +103,10 @@ public class AutoRoleProfile extends Profile {
|
||||
}
|
||||
return roles;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void reset() {
|
||||
roleIds.clear();
|
||||
maxRoles = DEFAULT_MAX_ROLES;
|
||||
}
|
||||
}
|
||||
|
@ -0,0 +1,41 @@
|
||||
package cc.fascinated.bat.features.birthday;
|
||||
|
||||
import cc.fascinated.bat.common.TimerUtils;
|
||||
import cc.fascinated.bat.features.Feature;
|
||||
import cc.fascinated.bat.features.birthday.command.BirthdayCommand;
|
||||
import cc.fascinated.bat.features.birthday.profile.BirthdayProfile;
|
||||
import cc.fascinated.bat.model.BatGuild;
|
||||
import cc.fascinated.bat.service.CommandService;
|
||||
import cc.fascinated.bat.service.GuildService;
|
||||
import lombok.NonNull;
|
||||
import org.springframework.context.ApplicationContext;
|
||||
import org.springframework.scheduling.annotation.Scheduled;
|
||||
import org.springframework.stereotype.Component;
|
||||
|
||||
import java.util.concurrent.TimeUnit;
|
||||
|
||||
/**
|
||||
* @author Fascinated (fascinated7)
|
||||
*/
|
||||
@Component
|
||||
public class BirthdayFeature extends Feature {
|
||||
private final GuildService guildService;
|
||||
|
||||
public BirthdayFeature(@NonNull ApplicationContext context, @NonNull CommandService commandService, @NonNull GuildService guildService) {
|
||||
super("Birthday", Category.GENERAL);
|
||||
this.guildService = guildService;
|
||||
|
||||
commandService.registerCommand(context.getBean(BirthdayCommand.class));
|
||||
}
|
||||
|
||||
/**
|
||||
* Check birthdays every day at midnight
|
||||
*/
|
||||
@Scheduled(cron = "0 0 0 * * *")
|
||||
private void checkBirthdays() {
|
||||
for (BatGuild guild : guildService.getAllGuilds()) {
|
||||
BirthdayProfile profile = guild.getProfile(BirthdayProfile.class);
|
||||
profile.checkBirthdays(guild);
|
||||
}
|
||||
}
|
||||
}
|
@ -0,0 +1,22 @@
|
||||
package cc.fascinated.bat.features.birthday.command;
|
||||
|
||||
import cc.fascinated.bat.command.BatCommand;
|
||||
import lombok.NonNull;
|
||||
import org.springframework.beans.factory.annotation.Autowired;
|
||||
import org.springframework.context.ApplicationContext;
|
||||
import org.springframework.stereotype.Component;
|
||||
|
||||
/**
|
||||
* @author Fascinated (fascinated7)
|
||||
*/
|
||||
@Component
|
||||
public class BirthdayCommand extends BatCommand {
|
||||
@Autowired
|
||||
public BirthdayCommand(@NonNull ApplicationContext context) {
|
||||
super("birthday", "Modify your birthday settings.", true);
|
||||
|
||||
super.addSubCommand("set", context.getBean(SetSubCommand.class));
|
||||
super.addSubCommand("remove", context.getBean(RemoveSubCommand.class));
|
||||
super.addSubCommand("channel", context.getBean(ChannelSubCommand.class));
|
||||
}
|
||||
}
|
@ -0,0 +1,68 @@
|
||||
package cc.fascinated.bat.features.birthday.command;
|
||||
|
||||
import cc.fascinated.bat.command.BatSubCommand;
|
||||
import cc.fascinated.bat.common.EmbedUtils;
|
||||
import cc.fascinated.bat.common.TextChannelUtils;
|
||||
import cc.fascinated.bat.features.birthday.profile.BirthdayProfile;
|
||||
import cc.fascinated.bat.features.scoresaber.profile.GuildUserScoreFeedProfile;
|
||||
import cc.fascinated.bat.model.BatGuild;
|
||||
import cc.fascinated.bat.model.BatUser;
|
||||
import cc.fascinated.bat.service.GuildService;
|
||||
import lombok.NonNull;
|
||||
import net.dv8tion.jda.api.entities.Member;
|
||||
import net.dv8tion.jda.api.entities.channel.ChannelType;
|
||||
import net.dv8tion.jda.api.entities.channel.middleman.MessageChannel;
|
||||
import net.dv8tion.jda.api.entities.channel.unions.GuildChannelUnion;
|
||||
import net.dv8tion.jda.api.interactions.commands.OptionMapping;
|
||||
import net.dv8tion.jda.api.interactions.commands.OptionType;
|
||||
import net.dv8tion.jda.api.interactions.commands.SlashCommandInteraction;
|
||||
import org.springframework.beans.factory.annotation.Autowired;
|
||||
import org.springframework.stereotype.Component;
|
||||
|
||||
/**
|
||||
* @author Fascinated (fascinated7)
|
||||
*/
|
||||
@Component("birthday:channel.sub")
|
||||
public class ChannelSubCommand extends BatSubCommand {
|
||||
private final GuildService guildService;
|
||||
|
||||
@Autowired
|
||||
public ChannelSubCommand(GuildService guildService) {
|
||||
super("channel", "Sets the birthday notification channel");
|
||||
super.addOption(OptionType.CHANNEL, "channel", "The channel birthdays will be sent in", false);
|
||||
this.guildService = guildService;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void execute(BatGuild guild, @NonNull BatUser user, @NonNull MessageChannel channel, Member member, @NonNull SlashCommandInteraction interaction) {
|
||||
BirthdayProfile profile = guild.getProfile(BirthdayProfile.class);
|
||||
OptionMapping option = interaction.getOption("channel");
|
||||
if (option == null) {
|
||||
if (!TextChannelUtils.isValidChannel(profile.getChannelId())) {
|
||||
interaction.replyEmbeds(EmbedUtils.errorEmbed()
|
||||
.setDescription("Please provide a channel to set the birthday channel to")
|
||||
.build()).queue();
|
||||
return;
|
||||
}
|
||||
interaction.replyEmbeds(EmbedUtils.genericEmbed()
|
||||
.setDescription("The current birthday channel is %s".formatted(TextChannelUtils.getChannelMention(profile.getChannelId())))
|
||||
.build()).queue();
|
||||
return;
|
||||
}
|
||||
|
||||
GuildChannelUnion targetChannel = option.getAsChannel();
|
||||
if (targetChannel.getType() != ChannelType.TEXT) {
|
||||
interaction.replyEmbeds(EmbedUtils.errorEmbed()
|
||||
.setDescription("Invalid channel type, please provide a text channel")
|
||||
.build()).queue();
|
||||
return;
|
||||
}
|
||||
|
||||
profile.setChannelId(targetChannel.getId());
|
||||
guildService.saveGuild(guild);
|
||||
|
||||
interaction.replyEmbeds(EmbedUtils.successEmbed()
|
||||
.setDescription("Successfully set the birthday channel to %s".formatted(targetChannel.asTextChannel().getAsMention()))
|
||||
.build()).queue();
|
||||
}
|
||||
}
|
@ -0,0 +1,47 @@
|
||||
package cc.fascinated.bat.features.birthday.command;
|
||||
|
||||
import cc.fascinated.bat.command.BatSubCommand;
|
||||
import cc.fascinated.bat.common.EmbedUtils;
|
||||
import cc.fascinated.bat.features.birthday.profile.BirthdayProfile;
|
||||
import cc.fascinated.bat.model.BatGuild;
|
||||
import cc.fascinated.bat.model.BatUser;
|
||||
import cc.fascinated.bat.service.GuildService;
|
||||
import lombok.NonNull;
|
||||
import net.dv8tion.jda.api.entities.Member;
|
||||
import net.dv8tion.jda.api.entities.channel.middleman.MessageChannel;
|
||||
import net.dv8tion.jda.api.interactions.commands.OptionMapping;
|
||||
import net.dv8tion.jda.api.interactions.commands.OptionType;
|
||||
import net.dv8tion.jda.api.interactions.commands.SlashCommandInteraction;
|
||||
import org.springframework.beans.factory.annotation.Autowired;
|
||||
import org.springframework.stereotype.Component;
|
||||
|
||||
import java.text.ParseException;
|
||||
import java.text.SimpleDateFormat;
|
||||
import java.util.Date;
|
||||
|
||||
|
||||
/**
|
||||
* @author Fascinated (fascinated7)
|
||||
*/
|
||||
@Component("birthday:remove.sub")
|
||||
public class RemoveSubCommand extends BatSubCommand {
|
||||
private final GuildService guildService;
|
||||
|
||||
@Autowired
|
||||
public RemoveSubCommand(GuildService guildService) {
|
||||
super("remove", "Remove your birthday from this guild");
|
||||
this.guildService = guildService;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void execute(BatGuild guild, @NonNull BatUser user, @NonNull MessageChannel channel, Member member, @NonNull SlashCommandInteraction interaction) {
|
||||
BirthdayProfile profile = guild.getProfile(BirthdayProfile.class);
|
||||
|
||||
profile.removeBirthday(user.getId());
|
||||
guildService.saveGuild(guild);
|
||||
|
||||
interaction.replyEmbeds(EmbedUtils.successEmbed()
|
||||
.setDescription("Your birthday has been removed from this guild")
|
||||
.build()).queue();
|
||||
}
|
||||
}
|
@ -0,0 +1,85 @@
|
||||
package cc.fascinated.bat.features.birthday.command;
|
||||
|
||||
import cc.fascinated.bat.command.BatSubCommand;
|
||||
import cc.fascinated.bat.common.EmbedUtils;
|
||||
import cc.fascinated.bat.features.birthday.profile.BirthdayProfile;
|
||||
import cc.fascinated.bat.model.BatGuild;
|
||||
import cc.fascinated.bat.model.BatUser;
|
||||
import cc.fascinated.bat.service.GuildService;
|
||||
import lombok.NonNull;
|
||||
import net.dv8tion.jda.api.entities.Member;
|
||||
import net.dv8tion.jda.api.entities.channel.middleman.MessageChannel;
|
||||
import net.dv8tion.jda.api.interactions.commands.OptionMapping;
|
||||
import net.dv8tion.jda.api.interactions.commands.OptionType;
|
||||
import net.dv8tion.jda.api.interactions.commands.SlashCommandInteraction;
|
||||
import org.springframework.beans.factory.annotation.Autowired;
|
||||
import org.springframework.stereotype.Component;
|
||||
|
||||
import java.text.ParseException;
|
||||
import java.text.SimpleDateFormat;
|
||||
import java.util.Date;
|
||||
|
||||
|
||||
/**
|
||||
* @author Fascinated (fascinated7)
|
||||
*/
|
||||
@Component("birthday:add.sub")
|
||||
public class SetSubCommand extends BatSubCommand {
|
||||
private static final SimpleDateFormat FORMATTER = new SimpleDateFormat("dd/MM/yyyy");
|
||||
private final GuildService guildService;
|
||||
|
||||
@Autowired
|
||||
public SetSubCommand(GuildService guildService) {
|
||||
super("set", "Add your birthday to this guild");
|
||||
super.addOption(OptionType.STRING, "birthday", "Your birthday (format: DAY/MONTH/YEAR - 01/05/2004)", true);
|
||||
this.guildService = guildService;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void execute(BatGuild guild, @NonNull BatUser user, @NonNull MessageChannel channel, Member member, @NonNull SlashCommandInteraction interaction) {
|
||||
BirthdayProfile profile = guild.getProfile(BirthdayProfile.class);
|
||||
|
||||
if (!profile.hasChannelSetup()) {
|
||||
interaction.replyEmbeds(EmbedUtils.errorEmbed()
|
||||
.setDescription("Birthdays have not been enabled in this guild. Please ask an administrator to enable them.")
|
||||
.build()).queue();
|
||||
return;
|
||||
}
|
||||
|
||||
OptionMapping birthdayOption = interaction.getOption("birthday");
|
||||
if (birthdayOption == null) {
|
||||
interaction.replyEmbeds(EmbedUtils.errorEmbed()
|
||||
.setDescription("You must provide a birthday")
|
||||
.build()).queue();
|
||||
return;
|
||||
}
|
||||
String birthdayString = birthdayOption.getAsString();
|
||||
Date birthday = parseBirthday(birthdayString);
|
||||
if (birthday == null) {
|
||||
interaction.replyEmbeds(EmbedUtils.errorEmbed()
|
||||
.setDescription("Invalid birthday format. Please use the format: DAY/MONTH/YEAR - 01/05/2004")
|
||||
.build()).queue();
|
||||
return;
|
||||
}
|
||||
|
||||
profile.addBirthday(member.getId(), birthday);
|
||||
guildService.saveGuild(guild);
|
||||
|
||||
interaction.replyEmbeds(EmbedUtils.successEmbed()
|
||||
.setDescription("You have updated your birthday!")
|
||||
.build()).queue();
|
||||
}
|
||||
|
||||
/**
|
||||
* Parses a birthday from the string
|
||||
*
|
||||
* @param birthday the date to parse
|
||||
* @return the birthday
|
||||
*/
|
||||
private Date parseBirthday(String birthday) {
|
||||
try {
|
||||
return FORMATTER.parse(birthday);
|
||||
} catch (ParseException ignored) {}
|
||||
return null;
|
||||
}
|
||||
}
|
@ -0,0 +1,210 @@
|
||||
package cc.fascinated.bat.features.birthday.profile;
|
||||
|
||||
import cc.fascinated.bat.common.Profile;
|
||||
import cc.fascinated.bat.model.BatGuild;
|
||||
import lombok.Getter;
|
||||
import lombok.Setter;
|
||||
import net.dv8tion.jda.api.entities.Guild;
|
||||
import net.dv8tion.jda.api.entities.Member;
|
||||
import net.dv8tion.jda.api.entities.channel.concrete.TextChannel;
|
||||
|
||||
import java.util.*;
|
||||
|
||||
/**
|
||||
* @author Fascinated (fascinated7)
|
||||
*/
|
||||
@Getter @Setter
|
||||
public class BirthdayProfile extends Profile {
|
||||
/**
|
||||
* The list of birthdays that are being tracked
|
||||
*/
|
||||
private Map<String, Date> birthdays;
|
||||
|
||||
/**
|
||||
* The channel ID of the birthday feed
|
||||
*/
|
||||
private String channelId;
|
||||
|
||||
public BirthdayProfile() {
|
||||
super("birthday");
|
||||
}
|
||||
|
||||
/**
|
||||
* Adds a birthday to be tracked
|
||||
*
|
||||
* @param userId the id of the user to track
|
||||
* @param birthday the birthday of the user
|
||||
*/
|
||||
public void addBirthday(String userId, Date birthday) {
|
||||
if (birthdays == null) {
|
||||
birthdays = new HashMap<>();
|
||||
}
|
||||
birthdays.put(userId, birthday);
|
||||
}
|
||||
|
||||
/**
|
||||
* Removes a birthday from being tracked
|
||||
*
|
||||
* @param userId the id of the user to remove
|
||||
*/
|
||||
public void removeBirthday(String userId) {
|
||||
if (birthdays == null) {
|
||||
birthdays = new HashMap<>();
|
||||
}
|
||||
birthdays.remove(userId);
|
||||
}
|
||||
|
||||
/**
|
||||
* Gets the birthday of a user
|
||||
*
|
||||
* @param userId the id of the user
|
||||
* @return the birthday of the user
|
||||
*/
|
||||
public Date getBirthday(String userId) {
|
||||
if (birthdays == null) {
|
||||
birthdays = new HashMap<>();
|
||||
}
|
||||
return birthdays.get(userId);
|
||||
}
|
||||
|
||||
/**
|
||||
* Checks if the profile has a channel setup
|
||||
*
|
||||
* @return if the profile has a channel setup
|
||||
*/
|
||||
public boolean hasChannelSetup() {
|
||||
return channelId != null;
|
||||
}
|
||||
|
||||
/**
|
||||
* Calculates the age of a user
|
||||
*
|
||||
* @param userId the id of the user
|
||||
* @return the age of the user
|
||||
*/
|
||||
public int calculateAge(String userId) {
|
||||
Date birthday = getBirthday(userId);
|
||||
if (birthday == null) {
|
||||
return 0; // or throw an exception
|
||||
}
|
||||
|
||||
Calendar birthdayCalendar = Calendar.getInstance();
|
||||
birthdayCalendar.setTime(birthday);
|
||||
|
||||
Calendar today = Calendar.getInstance();
|
||||
|
||||
int age = today.get(Calendar.YEAR) - birthdayCalendar.get(Calendar.YEAR);
|
||||
|
||||
// Check if the birthday hasn't occurred yet this year
|
||||
if (today.get(Calendar.DAY_OF_YEAR) < birthdayCalendar.get(Calendar.DAY_OF_YEAR)) {
|
||||
age--;
|
||||
}
|
||||
|
||||
return age;
|
||||
}
|
||||
|
||||
public boolean validate(BatGuild guild) {
|
||||
if (birthdays == null) {
|
||||
birthdays = new HashMap<>();
|
||||
}
|
||||
|
||||
List<String> toRemove = new ArrayList<>();
|
||||
Guild discordGuild = guild.getDiscordGuild();
|
||||
for (Map.Entry<String, Date> entry : birthdays.entrySet()) {
|
||||
String userId = entry.getKey();
|
||||
Date birthday = entry.getValue();
|
||||
|
||||
if (userId == null || birthday == null) { // this should never happen
|
||||
continue;
|
||||
}
|
||||
|
||||
// Check if the user is still in the guild, if not remove them
|
||||
Member member = discordGuild.getMemberById(userId);
|
||||
if (member == null) {
|
||||
toRemove.add(userId);
|
||||
}
|
||||
}
|
||||
|
||||
for (String userId : toRemove) {
|
||||
birthdays.remove(userId);
|
||||
}
|
||||
|
||||
if (channelId == null) {
|
||||
return false;
|
||||
}
|
||||
|
||||
if (discordGuild.getTextChannelById(channelId) == null) {
|
||||
channelId = null;
|
||||
return false;
|
||||
}
|
||||
return true;
|
||||
}
|
||||
|
||||
/**
|
||||
* Checks to see if it is any user's birthday
|
||||
*
|
||||
* @param guild the guild to check for
|
||||
*/
|
||||
public void checkBirthdays(BatGuild guild) {
|
||||
if (!validate(guild)) {
|
||||
return;
|
||||
}
|
||||
|
||||
// Get today's day and month
|
||||
Calendar today = Calendar.getInstance();
|
||||
int todayDay = today.get(Calendar.DAY_OF_MONTH);
|
||||
int todayMonth = today.get(Calendar.MONTH); // Note: January is 0
|
||||
|
||||
Iterator<Map.Entry<String, Date>> iterator = birthdays.entrySet().iterator();
|
||||
while (iterator.hasNext()) {
|
||||
Map.Entry<String, Date> entry = iterator.next();
|
||||
Date birthday = entry.getValue();
|
||||
|
||||
if (birthday == null) {
|
||||
iterator.remove();
|
||||
continue;
|
||||
}
|
||||
|
||||
Calendar birthdayCalendar = Calendar.getInstance();
|
||||
birthdayCalendar.setTime(birthday);
|
||||
|
||||
int birthdayDay = birthdayCalendar.get(Calendar.DAY_OF_MONTH);
|
||||
int birthdayMonth = birthdayCalendar.get(Calendar.MONTH);
|
||||
|
||||
// Check if the birthday matches today's day and month
|
||||
if (birthdayDay == todayDay && birthdayMonth == todayMonth) {
|
||||
notifyBirthday(guild, entry.getKey());
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Notifies a user that it is their birthday
|
||||
*
|
||||
* @param guild the guild
|
||||
* @param userId the id of the user
|
||||
*/
|
||||
private void notifyBirthday(BatGuild guild, String userId) {
|
||||
Guild discordGuild = guild.getDiscordGuild();
|
||||
Member member = discordGuild.getMemberById(userId);
|
||||
if (member == null) {
|
||||
return;
|
||||
}
|
||||
|
||||
TextChannel channel = discordGuild.getTextChannelById(channelId);
|
||||
if (channel == null) { // this should never happen
|
||||
channelId = null;
|
||||
return;
|
||||
}
|
||||
channel.sendMessage("Happy Birthday %s :tada: :birthday: You are now %s years old!".formatted(
|
||||
member.getAsMention(),
|
||||
calculateAge(userId)
|
||||
)).queue();
|
||||
}
|
||||
|
||||
@Override
|
||||
public void reset() {
|
||||
birthdays.clear();
|
||||
channelId = null;
|
||||
}
|
||||
}
|
@ -25,7 +25,7 @@ import org.springframework.stereotype.Component;
|
||||
public class ScoreSaberFeature extends Feature {
|
||||
@Autowired
|
||||
public ScoreSaberFeature(@NonNull ApplicationContext context, @NonNull CommandService commandService) {
|
||||
super("ScoreSaber");
|
||||
super("ScoreSaber", Category.BEAT_SABER);
|
||||
|
||||
commandService.registerCommand(context.getBean(ScoreSaberCommand.class));
|
||||
commandService.registerCommand(context.getBean(UserFeedCommand.class));
|
||||
|
@ -13,7 +13,6 @@ import org.springframework.stereotype.Component;
|
||||
public class NumberOneFeedCommand extends BatCommand {
|
||||
public NumberOneFeedCommand(@NonNull ApplicationContext context) {
|
||||
super("scoresaber-number-one-feed", "Modifies the settings for the feed.", true, Permission.MANAGE_SERVER);
|
||||
super.setCategory(Category.BEAT_SABER);
|
||||
|
||||
super.addSubCommand("channel", context.getBean(ChannelSubCommand.class));
|
||||
super.addSubCommand("reset", context.getBean(ResetSubCommand.class));
|
||||
|
@ -29,7 +29,7 @@ public class ResetSubCommand extends BatSubCommand {
|
||||
@Override
|
||||
public void execute(BatGuild guild, @NonNull BatUser user, @NonNull MessageChannel channel, Member member, @NonNull SlashCommandInteraction interaction) {
|
||||
GuildNumberOneScoreFeedProfile profile = guild.getProfile(GuildNumberOneScoreFeedProfile.class);
|
||||
profile.setChannelId(null);
|
||||
profile.reset();
|
||||
guildService.saveGuild(guild);
|
||||
|
||||
interaction.replyEmbeds(EmbedUtils.successEmbed()
|
||||
|
@ -0,0 +1,41 @@
|
||||
package cc.fascinated.bat.features.scoresaber.command.scoresaber;
|
||||
|
||||
import cc.fascinated.bat.command.BatSubCommand;
|
||||
import cc.fascinated.bat.common.EmbedUtils;
|
||||
import cc.fascinated.bat.features.scoresaber.profile.GuildUserScoreFeedProfile;
|
||||
import cc.fascinated.bat.features.scoresaber.profile.UserScoreSaberProfile;
|
||||
import cc.fascinated.bat.model.BatGuild;
|
||||
import cc.fascinated.bat.model.BatUser;
|
||||
import cc.fascinated.bat.service.ScoreSaberService;
|
||||
import cc.fascinated.bat.service.UserService;
|
||||
import lombok.NonNull;
|
||||
import net.dv8tion.jda.api.entities.Member;
|
||||
import net.dv8tion.jda.api.entities.channel.middleman.MessageChannel;
|
||||
import net.dv8tion.jda.api.interactions.commands.SlashCommandInteraction;
|
||||
import org.springframework.beans.factory.annotation.Autowired;
|
||||
import org.springframework.stereotype.Component;
|
||||
|
||||
/**
|
||||
* @author Fascinated (fascinated7)
|
||||
*/
|
||||
@Component("scoresaber:reset.sub")
|
||||
public class ResetSubCommand extends BatSubCommand {
|
||||
private final UserService userService;
|
||||
|
||||
@Autowired
|
||||
public ResetSubCommand(@NonNull UserService userService) {
|
||||
super("reset", "Resets the settings");
|
||||
this.userService = userService;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void execute(BatGuild guild, @NonNull BatUser user, @NonNull MessageChannel channel, Member member, @NonNull SlashCommandInteraction interaction) {
|
||||
UserScoreSaberProfile profile = guild.getProfile(UserScoreSaberProfile.class);
|
||||
profile.reset();
|
||||
userService.saveUser(user);
|
||||
|
||||
interaction.replyEmbeds(EmbedUtils.successEmbed()
|
||||
.setDescription("Successfully reset your settings.")
|
||||
.build()).queue();
|
||||
}
|
||||
}
|
@ -31,12 +31,12 @@ public class ScoreSaberCommand extends BatCommand {
|
||||
@Autowired
|
||||
public ScoreSaberCommand(@NonNull ScoreSaberService scoreSaberService, @NonNull ApplicationContext context) {
|
||||
super("scoresaber", "General ScoreSaber commands");
|
||||
super.setCategory(Category.BEAT_SABER);
|
||||
this.scoreSaberService = scoreSaberService;
|
||||
|
||||
super.addSubCommand("link", context.getBean(LinkSubCommand.class));
|
||||
super.addSubCommand("user", context.getBean(UserSubCommand.class));
|
||||
super.addSubCommand("me", context.getBean(MeSubCommand.class));
|
||||
super.addSubCommand("reset", context.getBean(ResetSubCommand.class));
|
||||
}
|
||||
|
||||
@Override
|
||||
|
@ -29,8 +29,7 @@ public class ResetSubCommand extends BatSubCommand {
|
||||
@Override
|
||||
public void execute(BatGuild guild, @NonNull BatUser user, @NonNull MessageChannel channel, Member member, @NonNull SlashCommandInteraction interaction) {
|
||||
GuildUserScoreFeedProfile profile = guild.getProfile(GuildUserScoreFeedProfile.class);
|
||||
profile.setChannelId(null);
|
||||
profile.getTrackedUsers().clear();
|
||||
profile.reset();
|
||||
guildService.saveGuild(guild);
|
||||
|
||||
interaction.replyEmbeds(EmbedUtils.successEmbed()
|
||||
|
@ -13,7 +13,6 @@ import org.springframework.stereotype.Component;
|
||||
public class UserFeedCommand extends BatCommand {
|
||||
public UserFeedCommand(@NonNull ApplicationContext context) {
|
||||
super("scoresaber-user-feed", "Modifies the settings for the feed.", true, Permission.MANAGE_SERVER);
|
||||
super.setCategory(Category.BEAT_SABER);
|
||||
|
||||
super.addSubCommand("user", context.getBean(UserSubCommand.class));
|
||||
super.addSubCommand("channel", context.getBean(ChannelSubCommand.class));
|
||||
|
@ -28,4 +28,9 @@ public class GuildNumberOneScoreFeedProfile extends Profile {
|
||||
public TextChannel getAsTextChannel() {
|
||||
return DiscordService.JDA.getTextChannelById(channelId);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void reset() {
|
||||
this.channelId = null;
|
||||
}
|
||||
}
|
||||
|
@ -72,4 +72,10 @@ public class GuildUserScoreFeedProfile extends Profile {
|
||||
public TextChannel getAsTextChannel() {
|
||||
return DiscordService.JDA.getTextChannelById(channelId);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void reset() {
|
||||
this.channelId = null;
|
||||
this.trackedUsers = null;
|
||||
}
|
||||
}
|
||||
|
@ -17,4 +17,9 @@ public class UserScoreSaberProfile extends Profile {
|
||||
public UserScoreSaberProfile() {
|
||||
super("scoresaber");
|
||||
}
|
||||
|
||||
@Override
|
||||
public void reset() {
|
||||
this.steamId = null;
|
||||
}
|
||||
}
|
||||
|
@ -12,6 +12,7 @@ import org.springframework.cache.annotation.Cacheable;
|
||||
import org.springframework.context.annotation.DependsOn;
|
||||
import org.springframework.stereotype.Service;
|
||||
|
||||
import java.util.List;
|
||||
import java.util.Optional;
|
||||
|
||||
/**
|
||||
@ -37,7 +38,7 @@ public class GuildService extends ListenerAdapter {
|
||||
* @param id The ID of the guild
|
||||
* @return The guild
|
||||
*/
|
||||
@Cacheable(cacheNames = {"guilds"}, key = "#id")
|
||||
// @Cacheable(cacheNames = {"guilds"}, key = "#id")
|
||||
public BatGuild getGuild(@NonNull String id) {
|
||||
long start = System.currentTimeMillis();
|
||||
Optional<BatGuild> optionalGuild = guildRepository.findById(id);
|
||||
@ -54,11 +55,20 @@ public class GuildService extends ListenerAdapter {
|
||||
*
|
||||
* @param guild The guild to save
|
||||
*/
|
||||
@CachePut(cacheNames = {"guilds"}, key = "#id")
|
||||
// @CachePut(cacheNames = {"guilds"}, key = "#id")
|
||||
public void saveGuild(@NonNull BatGuild guild) {
|
||||
guildRepository.save(guild);
|
||||
}
|
||||
|
||||
/**
|
||||
* Gets all guilds
|
||||
*
|
||||
* @return all guilds
|
||||
*/
|
||||
public List<BatGuild> getAllGuilds() {
|
||||
return guildRepository.findAll();
|
||||
}
|
||||
|
||||
@Override
|
||||
public final void onGuildJoin(GuildJoinEvent event) {
|
||||
log.info("Joined guild \"{}\"", event.getGuild().getId());
|
||||
|
@ -34,7 +34,7 @@ public class UserService {
|
||||
* @param id The ID of the user
|
||||
* @return The user
|
||||
*/
|
||||
@Cacheable(cacheNames = {"users"}, key = "#id")
|
||||
// @Cacheable(cacheNames = {"users"}, key = "#id")
|
||||
public BatUser getUser(@NonNull String id) {
|
||||
long start = System.currentTimeMillis();
|
||||
Optional<BatUser> optionalUser = userRepository.findById(id);
|
||||
@ -51,7 +51,7 @@ public class UserService {
|
||||
*
|
||||
* @param user The user to save
|
||||
*/
|
||||
@CachePut(cacheNames = {"users"}, key = "#id")
|
||||
// @CachePut(cacheNames = {"users"}, key = "#id")
|
||||
public void saveUser(@NonNull BatUser user) {
|
||||
userRepository.save(user);
|
||||
}
|
||||
|
Loading…
x
Reference in New Issue
Block a user