goofybot/src/pterodactyl/displayer.js
2026-04-15 23:55:13 +02:00

155 lines
4.2 KiB
JavaScript

const DEFAULT_UPDATE_TEXT = "Panneau Minecraft";
const getMinecraftStatus = async () => {
const address = process.env.MINECRAFT_SERVER_ADDRESS;
if (!address) {
throw new Error("MINECRAFT_SERVER_ADDRESS manquant dans l'environnement");
}
const response = await fetch(`https://api.mcsrvstat.us/3/${encodeURIComponent(address)}`);
if (!response.ok) {
throw new Error(`Impossible de recuperer le statut Minecraft (HTTP ${response.status})`);
}
const data = await response.json();
const online = Boolean(data.online);
const playersOnline = data.players?.online ?? 0;
const playersMax = data.players?.max ?? 0;
const version = data.version || "Inconnue";
const motd = Array.isArray(data.motd?.clean) ? data.motd.clean.join("\n") : "";
const playerList = Array.isArray(data.players?.list) ? data.players.list : [];
return {
address,
online,
playersOnline,
playersMax,
version,
motd,
playerList
};
};
const getPterodactylState = async (headers) => {
const panelUrl = process.env.PTERODACTYL_PANEL_URL;
const serverId = process.env.PTERODACTYL_SERVER_ID;
if (!headers || !panelUrl || !serverId) {
return "inconnu";
}
try {
const stateResponse = await fetch(`${panelUrl}/api/client/servers/${serverId}/resources`, {
method: "GET",
headers
});
if (!stateResponse.ok) {
return "inconnu";
}
const stateData = await stateResponse.json();
return stateData?.attributes?.current_state || "inconnu";
} catch (error) {
return "inconnu";
}
};
const buildPanelEmbed = (status, panelState) => {
const stateText = status.online ? "🟢 En ligne" : "🔴 Hors ligne";
const playersText = `${status.playersOnline}/${status.playersMax}`;
const playersListText = status.playerList.length > 0 ? status.playerList.join(", ") : "Aucun joueur connecte";
return {
color: status.online ? 0x57F287 : 0xED4245,
title: `Serveur Minecraft - ${stateText}`,
description: status.motd || DEFAULT_UPDATE_TEXT,
fields: [
{
name: "Adresse",
value: status.address,
inline: true
},
{
name: "Joueurs",
value: playersText,
inline: true
},
{
name: "Version",
value: status.version,
inline: true
},
{
name: "Etat du panel",
value: panelState,
inline: true
},
{
name: "Joueurs connectes",
value: playersListText,
inline: false
}
],
timestamp: new Date().toISOString(),
footer: {
text: "Actualisation automatique"
}
};
};
const resolvePanelMessage = async (client, channelId, messageId) => {
const channel = await client.channels.fetch(channelId);
if (!channel || !channel.isTextBased()) {
throw new Error(`Salon non textuel ou introuvable: ${channelId}`);
}
if (messageId) {
try {
const message = await channel.messages.fetch(messageId);
return { channel, message };
} catch (error) {
console.log(`⚠️ Message ${messageId} introuvable. Creation d'un nouveau panneau.`);
}
}
const newMessage = await channel.send({
content: "Initialisation du panneau Minecraft..."
});
console.log(`✅ Nouveau message panneau cree: ID ${newMessage.id}`);
console.log(`👉 Ajoute DISPLAYER_MESSAGE_ID=${newMessage.id} dans ton .env pour le lier de facon persistante.`);
return { channel, message: newMessage };
};
const update = async (headers, numbers, client, token) => {
try {
const channelId = process.env.DISPLAYER_CHANNEL_ID;
const messageId = process.env.DISPLAYER_MESSAGE_ID;
if (!channelId) {
console.log("⚠️ DISPLAYER_CHANNEL_ID non defini, mise a jour panneau ignoree.");
return;
}
const status = await getMinecraftStatus();
const panelState = await getPterodactylState(headers);
const embed = buildPanelEmbed(status, panelState);
const { message } = await resolvePanelMessage(client, channelId, messageId);
await message.edit({
content: "",
embeds: [embed]
});
console.log(`📊 Panneau Minecraft mis a jour (${status.playersOnline}/${status.playersMax})`);
} catch (error) {
console.log(`❌ Erreur displayer: ${error.message}`);
}
};
module.exports = update;