Add channel/role autocomplete dropdowns via datalist + /api/guild/resources endpoint
Some checks failed
Deploy Discord Bot / deploy (push) Has been cancelled

This commit is contained in:
Pepe44DEV
2026-07-01 02:48:12 +02:00
parent 85fd5ec915
commit a8150bf3b6
2 changed files with 87 additions and 0 deletions

View File

@@ -106,6 +106,35 @@ router.get('/guild/logs', requireAuth, (req, res) => {
res.json({ logs });
});
router.get('/guild/resources', requireAuth, async (req, res) => {
const guildId = typeof req.query.guildId === 'string' ? req.query.guildId : undefined;
if (!guildId) return res.status(400).json({ error: 'guildId required' });
const guild = context.client?.guilds.cache.get(guildId);
if (!guild) return res.status(404).json({ error: 'guild not found' });
const channels = guild.channels.cache
.filter((c) => c.isTextBased() || c.isVoiceBased())
.map((c) => ({
id: c.id,
name: c.name,
type: c.isVoiceBased() ? 'voice' : 'text',
parentId: c.parentId
}))
.sort((a, b) => a.name.localeCompare(b.name));
const roles = guild.roles.cache
.filter((r) => r.name !== '@everyone')
.map((r) => ({
id: r.id,
name: r.name,
color: r.hexColor
}))
.sort((a, b) => b.rawPosition - a.rawPosition);
const categories = guild.channels.cache
.filter((c) => c.type === 4)
.map((c) => ({ id: c.id, name: c.name }))
.sort((a, b) => a.name.localeCompare(b.name));
res.json({ channels, roles, categories });
});
router.get('/overview', requireAuth, async (req, res) => {
const guildId = typeof req.query.guildId === 'string' ? req.query.guildId : undefined;
try {

View File

@@ -105,6 +105,9 @@ router.get('/', (req, res) => {
</main>
</div>
</div>
<datalist id="channelList"></datalist>
<datalist id="roleList"></datalist>
<datalist id="categoryList"></datalist>
<script>
${baseScript}
async function ensureAuth() {
@@ -1090,6 +1093,9 @@ router.get('/', (req, res) => {
</div>
</div>
<datalist id="channelList"></datalist>
<datalist id="roleList"></datalist>
<datalist id="categoryList"></datalist>
<div id="toast" class="toast"></div>
<script>
${baseScript}
@@ -1708,6 +1714,56 @@ router.get('/', (req, res) => {
reader.readAsDataURL(file);
}
async function loadResources(guildId) {
if (!guildId) return;
const res = await fetch('/api/guild/resources?guildId=' + encodeURIComponent(guildId));
if (!res.ok) return;
const data = await res.json();
const channelList = document.getElementById('channelList');
const roleList = document.getElementById('roleList');
const categoryList = document.getElementById('categoryList');
if (channelList) {
channelList.innerHTML = '';
(data.channels || []).forEach((c) => {
const opt = document.createElement('option');
opt.value = c.id;
opt.textContent = '#' + c.name + ' (' + c.id + ')';
channelList.appendChild(opt);
});
}
if (roleList) {
roleList.innerHTML = '';
(data.roles || []).forEach((r) => {
const opt = document.createElement('option');
opt.value = r.id;
opt.textContent = '@' + r.name + ' (' + r.id + ')';
roleList.appendChild(opt);
});
}
if (categoryList) {
categoryList.innerHTML = '';
(data.categories || []).forEach((c) => {
const opt = document.createElement('option');
opt.value = c.id;
opt.textContent = c.name + ' (' + c.id + ')';
categoryList.appendChild(opt);
});
}
document.querySelectorAll('input[placeholder*="123456"]').forEach((el) => {
if (!el.hasAttribute('list')) el.setAttribute('list', 'channelList');
});
['automationActionValue', 'eventRole', 'statuspageChannel'].forEach((id) => {
const el = document.getElementById(id);
if (el && !el.hasAttribute('list')) el.setAttribute('list', 'roleList');
});
document.querySelectorAll('input[name="supportRoleId"], input[name="logChannelId"]').forEach((el) => {
if (!el.hasAttribute('list')) el.setAttribute('list', 'channelList');
});
document.querySelectorAll('textarea[id$="Role"], textarea[id*="Role"]').forEach((el) => {
if (!el.hasAttribute('list')) el.setAttribute('list', 'roleList');
});
}
function formatDate(value) {
if (!value) return '-';
const dt = new Date(value);
@@ -1814,6 +1870,7 @@ router.get('/', (req, res) => {
if (data.guilds?.length) {
currentGuild = currentGuild || guildSelect.value || data.guilds[0].id;
guildSelect.value = currentGuild;
await loadResources(currentGuild);
await loadSettings(currentGuild);
await loadModules();
await loadOverview();
@@ -2727,6 +2784,7 @@ router.get('/', (req, res) => {
guildSelect.addEventListener('change', async (e) => {
currentGuild = e.target.value;
await loadResources(currentGuild);
await loadSettings(currentGuild);
await loadOverview();
await loadTickets();