2026-04-14 15:54:53 +02:00

196 lines
6.1 KiB
Lua

ESX = exports['es_extended']:getSharedObject()
-- =====================
-- WEBHOOK HELPER
-- =====================
local function SendRefundWebhook(title, message, color)
if not Config.WebhookRefund or Config.WebhookRefund == "" then return end
local embed = {
{
["color"] = color or 10181046,
["title"] = "**" .. title .. "**",
["description"] = message,
["footer"] = { ["text"] = os.date("%d.%m.%Y | %H:%M:%S") },
}
}
PerformHttpRequest(Config.WebhookRefund, function() end, 'POST', json.encode({username = "Refund System", embeds = embed}), { ['Content-Type'] = 'application/json' })
end
-- =====================
-- SQL SETUP
-- =====================
MySQL.ready(function()
MySQL.query.await([[
CREATE TABLE IF NOT EXISTS refund_codes (
id INT AUTO_INCREMENT PRIMARY KEY,
code VARCHAR(10) NOT NULL UNIQUE,
items JSON DEFAULT NULL,
money INT DEFAULT 0,
bank_money INT DEFAULT 0,
reason TEXT,
created_by VARCHAR(100) NOT NULL,
created_by_id VARCHAR(30) NOT NULL,
discord_channel_id VARCHAR(30),
redeemed_by_identifier VARCHAR(60) DEFAULT NULL,
redeemed_by_name VARCHAR(100) DEFAULT NULL,
redeemed_at TIMESTAMP NULL DEFAULT NULL,
created_at TIMESTAMP DEFAULT CURRENT_TIMESTAMP,
INDEX idx_code (code),
INDEX idx_redeemed (redeemed_at)
)
]])
print('[mercyv-refund] Database ready')
end)
-- =====================
-- HELPERS
-- =====================
local function GetIdentifier(source)
local xPlayer = ESX.GetPlayerFromId(source)
if not xPlayer then return nil end
return xPlayer.getIdentifier()
end
local function GetPlayerName(source)
local xPlayer = ESX.GetPlayerFromId(source)
if not xPlayer then return 'Unbekannt' end
return xPlayer.getName()
end
local function SendMessage(source, msg)
TriggerClientEvent('chat:addMessage', source, {
color = {155, 89, 182},
multiline = true,
args = {'Refund', msg}
})
end
-- =====================
-- CODE EINLOESEN
-- =====================
local function redeemCode(source, codeStr)
local xPlayer = ESX.GetPlayerFromId(source)
if not xPlayer then return end
local identifier = GetIdentifier(source)
local playerName = GetPlayerName(source)
if not identifier then
SendMessage(source, '~r~Fehler: Spieler konnte nicht identifiziert werden.')
return
end
-- Code in DB suchen
local result = MySQL.query.await('SELECT * FROM refund_codes WHERE code = ?', { codeStr })
if not result or #result == 0 then
SendMessage(source, '~r~Ungueltiger Code.')
return
end
local row = result[1]
-- Bereits eingeloest?
if row.redeemed_at ~= nil then
SendMessage(source, '~r~Dieser Code wurde bereits eingeloest.')
return
end
-- Items geben
local itemsGiven = {}
local itemsFailed = {}
if row.items and row.items ~= '' then
local items = json.decode(row.items)
if items and type(items) == 'table' then
for _, itemData in ipairs(items) do
local success = pcall(function()
exports['codem-inventory']:AddItem(source, itemData.item, itemData.amount)
end)
if success then
table.insert(itemsGiven, itemData.amount .. 'x ' .. itemData.item)
else
table.insert(itemsFailed, itemData.amount .. 'x ' .. itemData.item)
end
end
end
end
-- Geld geben
if row.money and row.money > 0 then
xPlayer.addMoney(row.money)
end
if row.bank_money and row.bank_money > 0 then
xPlayer.addAccountMoney('bank', row.bank_money)
end
-- Code als eingeloest markieren
MySQL.query.await(
'UPDATE refund_codes SET redeemed_by_identifier = ?, redeemed_by_name = ?, redeemed_at = NOW() WHERE code = ?',
{ identifier, playerName, codeStr }
)
-- Spieler benachrichtigen
local msg = '~g~Code erfolgreich eingeloest!'
if #itemsGiven > 0 then
msg = msg .. '\n~w~Items: ' .. table.concat(itemsGiven, ', ')
end
if row.money and row.money > 0 then
msg = msg .. '\n~w~Bargeld: $' .. tostring(row.money)
end
if row.bank_money and row.bank_money > 0 then
msg = msg .. '\n~w~Bank: $' .. tostring(row.bank_money)
end
if #itemsFailed > 0 then
msg = msg .. '\n~r~Fehlgeschlagen: ' .. table.concat(itemsFailed, ', ')
end
SendMessage(source, msg)
-- Webhook Log
local webhookMsg = '**Spieler:** ' .. playerName .. '\n'
webhookMsg = webhookMsg .. '**Identifier:** ' .. identifier .. '\n'
webhookMsg = webhookMsg .. '**Code:** `' .. codeStr .. '`\n'
webhookMsg = webhookMsg .. '**Grund:** ' .. (row.reason or 'Kein Grund') .. '\n'
if #itemsGiven > 0 then
webhookMsg = webhookMsg .. '**Items erhalten:** ' .. table.concat(itemsGiven, ', ') .. '\n'
end
if #itemsFailed > 0 then
webhookMsg = webhookMsg .. '**Items fehlgeschlagen:** ' .. table.concat(itemsFailed, ', ') .. '\n'
end
if row.money and row.money > 0 then
webhookMsg = webhookMsg .. '**Bargeld:** $' .. tostring(row.money) .. '\n'
end
if row.bank_money and row.bank_money > 0 then
webhookMsg = webhookMsg .. '**Bank:** $' .. tostring(row.bank_money) .. '\n'
end
local webhookColor = #itemsFailed > 0 and 15158332 or 3066993 -- Rot bei Fehlern, Gruen bei Erfolg
SendRefundWebhook('Code eingeloest', webhookMsg, webhookColor)
print('[mercyv-refund] Code ' .. codeStr .. ' eingeloest von ' .. playerName .. ' (' .. identifier .. ')')
end
-- =====================
-- F8 COMMAND
-- =====================
RegisterCommand('code', function(source, args)
if source == 0 then return end -- Kein RCON
if not args[1] or args[1] == '' then
SendMessage(source, '~y~Benutze: code <CODE>')
return
end
redeemCode(source, args[1])
end, false)
print('[mercyv-refund] Resource gestartet')