134 lines
4.7 KiB
TypeScript
134 lines
4.7 KiB
TypeScript
import {
|
|
SlashCommandBuilder,
|
|
ChatInputCommandInteraction,
|
|
PermissionFlagsBits,
|
|
EmbedBuilder,
|
|
Colors,
|
|
ChannelType
|
|
} from 'discord.js';
|
|
import { prisma } from '../database';
|
|
import { t, SupportedLocale } from '../i18n';
|
|
import { MINI_GAMES, getAllMiniGames } from '../services/MiniGameRegistry';
|
|
|
|
export default {
|
|
data: new SlashCommandBuilder()
|
|
.setName('minigame')
|
|
.setDescription('Manage mini-games for the server.')
|
|
.setDescriptionLocalizations({
|
|
ko: '서버의 미니게임을 관리합니다.',
|
|
})
|
|
.setDefaultMemberPermissions(PermissionFlagsBits.Administrator)
|
|
// --- Toggle Subcommand ---
|
|
.addSubcommand(subcommand =>
|
|
subcommand
|
|
.setName('toggle')
|
|
.setDescription('Enable or disable a specific mini-game.')
|
|
.addStringOption(option =>
|
|
option.setName('game')
|
|
.setDescription('Mini-game to toggle')
|
|
.setRequired(true)
|
|
.addChoices(...Object.values(MINI_GAMES).map(g => ({ name: g.name, value: g.key })))
|
|
)
|
|
.addBooleanOption(option =>
|
|
option.setName('enable')
|
|
.setDescription('Whether to enable the mini-game')
|
|
.setRequired(true)
|
|
)
|
|
)
|
|
// --- Status Subcommand ---
|
|
.addSubcommand(subcommand =>
|
|
subcommand
|
|
.setName('status')
|
|
.setDescription('View the current status of all mini-games.')
|
|
)
|
|
// --- Channel Subcommand ---
|
|
.addSubcommand(subcommand =>
|
|
subcommand
|
|
.setName('channel')
|
|
.setDescription('Set a dedicated channel for a mini-game.')
|
|
.addStringOption(option =>
|
|
option.setName('game')
|
|
.setDescription('Mini-game to set channel for')
|
|
.setRequired(true)
|
|
.addChoices(...Object.values(MINI_GAMES).map(g => ({ name: g.name, value: g.key })))
|
|
)
|
|
.addChannelOption(option =>
|
|
option.setName('channel')
|
|
.setDescription('The channel to use (empty to allow all)')
|
|
.addChannelTypes(ChannelType.GuildText)
|
|
)
|
|
),
|
|
|
|
async execute(interaction: ChatInputCommandInteraction, locale: SupportedLocale) {
|
|
if (!interaction.guildId) return;
|
|
const subcommand = interaction.options.getSubcommand();
|
|
|
|
if (subcommand === 'toggle') {
|
|
const gameKey = interaction.options.getString('game', true);
|
|
const enable = interaction.options.getBoolean('enable', true);
|
|
|
|
await prisma.miniGameConfig.upsert({
|
|
where: { guildId_gameKey: { guildId: interaction.guildId, gameKey } },
|
|
update: { enabled: enable },
|
|
create: { guildId: interaction.guildId, gameKey, enabled: enable },
|
|
});
|
|
|
|
const game = MINI_GAMES[gameKey];
|
|
const state = enable ? '활성화' : '비활성화';
|
|
|
|
const embed = new EmbedBuilder()
|
|
.setColor(enable ? Colors.Green : Colors.Grey)
|
|
.setTitle('🎮 미니게임 설정 변경')
|
|
.setDescription(`${game.name} 미니게임이 **${state}**되었습니다.`);
|
|
|
|
return interaction.reply({ embeds: [embed], ephemeral: true });
|
|
}
|
|
|
|
if (subcommand === 'status') {
|
|
const configs = await prisma.miniGameConfig.findMany({
|
|
where: { guildId: interaction.guildId },
|
|
});
|
|
|
|
const embed = new EmbedBuilder()
|
|
.setColor(Colors.Blue)
|
|
.setTitle('🎮 미니게임 현황')
|
|
.setDescription('현재 서버의 미니게임 활성화 상태입니다.');
|
|
|
|
getAllMiniGames().forEach(game => {
|
|
const config = configs.find(c => c.gameKey === game.key);
|
|
const isEnabled = config?.enabled ?? false;
|
|
const channel = config?.channelId ? `<#${config.channelId}>` : '모든 채널';
|
|
|
|
embed.addFields({
|
|
name: game.name,
|
|
value: `상태: ${isEnabled ? '✅ 활성' : '❌ 비활성'}\n채널: ${channel}`,
|
|
inline: true,
|
|
});
|
|
});
|
|
|
|
return interaction.reply({ embeds: [embed], ephemeral: true });
|
|
}
|
|
|
|
if (subcommand === 'channel') {
|
|
const gameKey = interaction.options.getString('game', true);
|
|
const channel = interaction.options.getChannel('channel');
|
|
|
|
await prisma.miniGameConfig.upsert({
|
|
where: { guildId_gameKey: { guildId: interaction.guildId, gameKey } },
|
|
update: { channelId: channel?.id || null },
|
|
create: { guildId: interaction.guildId, gameKey, channelId: channel?.id || null },
|
|
});
|
|
|
|
const game = MINI_GAMES[gameKey];
|
|
const channelMsg = channel ? `<#${channel.id}>` : '모든 채널';
|
|
|
|
const embed = new EmbedBuilder()
|
|
.setColor(Colors.Gold)
|
|
.setTitle('🎮 미니게임 채널 설정')
|
|
.setDescription(`${game.name} 미니게임 전용 채널이 **${channelMsg}**로 설정되었습니다.`);
|
|
|
|
return interaction.reply({ embeds: [embed], ephemeral: true });
|
|
}
|
|
},
|
|
};
|