Spending lots of time on useless discord bots makes to make the pain go away
This commit is contained in:
105
lib/himbucks.go
105
lib/himbucks.go
@ -20,92 +20,48 @@ type HimbucksEntry struct {
|
||||
MessageCount int
|
||||
}
|
||||
|
||||
func ProcessMessage(s *discordgo.Session, m *discordgo.MessageCreate) error {
|
||||
// Ignore bot messages
|
||||
if m.Author.Bot {
|
||||
return nil
|
||||
}
|
||||
|
||||
// Start transaction for user creation/lookup and himbucks entry
|
||||
func ProcessHimbucks(s *discordgo.Session, m *discordgo.MessageCreate, ctx *ProcessContext) error {
|
||||
tx, err := DBClient.Begin()
|
||||
if err != nil {
|
||||
return fmt.Errorf("failed to start transaction: %w", err)
|
||||
}
|
||||
defer tx.Rollback()
|
||||
|
||||
// Get user from database, create if doesn't exist
|
||||
var userID int
|
||||
err = tx.QueryRow("SELECT id FROM users WHERE discord_id = ?", m.Author.ID).Scan(&userID)
|
||||
if err == sql.ErrNoRows {
|
||||
// Store user in database using existing StoreUser function within transaction
|
||||
result, err := tx.Exec(
|
||||
"INSERT INTO users (discord_id, username) VALUES (?, ?)",
|
||||
m.Author.ID, m.Author.Username)
|
||||
if err != nil {
|
||||
return fmt.Errorf("failed to store user: %w", err)
|
||||
}
|
||||
|
||||
id, err := result.LastInsertId()
|
||||
if err != nil {
|
||||
return fmt.Errorf("failed to get new user ID: %w", err)
|
||||
}
|
||||
userID = int(id)
|
||||
|
||||
// Immediately create corresponding himbucks entry
|
||||
_, err = tx.Exec(`
|
||||
INSERT INTO himbucks (user_id, guild_id, balance, message_count)
|
||||
VALUES (?, ?, 0, 0)`,
|
||||
userID, m.GuildID)
|
||||
if err != nil {
|
||||
return fmt.Errorf("failed to create initial himbucks entry: %w", err)
|
||||
}
|
||||
} else if err != nil {
|
||||
return fmt.Errorf("failed to query user: %w", err)
|
||||
}
|
||||
|
||||
// For existing users, ensure himbucks entry exists
|
||||
_, err = tx.Exec(`
|
||||
INSERT INTO himbucks (user_id, guild_id, balance, message_count)
|
||||
VALUES (?, ?, 0, 0)
|
||||
ON CONFLICT (user_id, guild_id) DO NOTHING`,
|
||||
userID, m.GuildID)
|
||||
if err != nil {
|
||||
return fmt.Errorf("failed to create himbucks entry: %w", err)
|
||||
}
|
||||
|
||||
// Process the message count and rewards
|
||||
// Get current state
|
||||
var messageCount int
|
||||
var lastEarnedAt sql.NullTime
|
||||
var lastRewardAt sql.NullTime
|
||||
|
||||
err = tx.QueryRow(`
|
||||
SELECT message_count, last_earned_at
|
||||
FROM himbucks
|
||||
SELECT message_count, last_reward_at
|
||||
FROM guild_profiles
|
||||
WHERE user_id = ? AND guild_id = ?`,
|
||||
userID, m.GuildID).Scan(&messageCount, &lastEarnedAt)
|
||||
ctx.UserID, ctx.GuildID).Scan(&messageCount, &lastRewardAt)
|
||||
if err != nil {
|
||||
return fmt.Errorf("failed to get message count: %w", err)
|
||||
}
|
||||
|
||||
messageCount++
|
||||
shouldReward := messageCount >= MessageCountThreshold &&
|
||||
(!lastEarnedAt.Valid || time.Since(lastEarnedAt.Time) >= CooldownPeriod)
|
||||
(!lastRewardAt.Valid || time.Since(lastRewardAt.Time) >= CooldownPeriod)
|
||||
|
||||
if shouldReward {
|
||||
_, err = tx.Exec(`
|
||||
UPDATE himbucks
|
||||
SET balance = balance + ?, message_count = 0, last_earned_at = CURRENT_TIMESTAMP
|
||||
UPDATE guild_profiles
|
||||
SET currency_balance = currency_balance + ?,
|
||||
message_count = 0,
|
||||
last_reward_at = CURRENT_TIMESTAMP
|
||||
WHERE user_id = ? AND guild_id = ?`,
|
||||
HimbucksPerReward, userID, m.GuildID)
|
||||
HimbucksPerReward, ctx.UserID, ctx.GuildID)
|
||||
} else {
|
||||
_, err = tx.Exec(`
|
||||
UPDATE himbucks
|
||||
UPDATE guild_profiles
|
||||
SET message_count = ?
|
||||
WHERE user_id = ? AND guild_id = ?`,
|
||||
messageCount, userID, m.GuildID)
|
||||
messageCount, ctx.UserID, ctx.GuildID)
|
||||
}
|
||||
|
||||
if err != nil {
|
||||
return fmt.Errorf("failed to update himbucks: %w", err)
|
||||
return fmt.Errorf("failed to update profile: %w", err)
|
||||
}
|
||||
|
||||
return tx.Commit()
|
||||
@ -113,25 +69,24 @@ func ProcessMessage(s *discordgo.Session, m *discordgo.MessageCreate) error {
|
||||
|
||||
func GetBalance(discordID, guildID string) (int, error) {
|
||||
var balance int
|
||||
|
||||
queryError := DBClient.QueryRow(`
|
||||
SELECT h.balance
|
||||
FROM himbucks h
|
||||
JOIN users u ON h.user_id = u.id
|
||||
WHERE u.discord_id = ? AND h.guild_id = ?`,
|
||||
err := DBClient.QueryRow(`
|
||||
SELECT gp.currency_balance
|
||||
FROM guild_profiles gp
|
||||
JOIN users u ON gp.user_id = u.id
|
||||
WHERE u.discord_id = ? AND gp.guild_id = ?`,
|
||||
discordID, guildID).Scan(&balance)
|
||||
if queryError == sql.ErrNoRows {
|
||||
if err == sql.ErrNoRows {
|
||||
return 0, nil
|
||||
}
|
||||
if queryError != nil {
|
||||
return 0, fmt.Errorf("failed to get balance: %w", queryError)
|
||||
if err != nil {
|
||||
return 0, fmt.Errorf("failed to get balance: %w", err)
|
||||
}
|
||||
return balance, nil
|
||||
}
|
||||
|
||||
func SyncBalance() error {
|
||||
// First perform the regular sync
|
||||
_, syncError := DBConnector.Sync()
|
||||
|
||||
if syncError != nil {
|
||||
fmt.Println("Error syncing database:", syncError)
|
||||
return syncError
|
||||
@ -142,12 +97,12 @@ func SyncBalance() error {
|
||||
|
||||
func GetLeaderboard(guildID string, limit int) ([]HimbucksEntry, error) {
|
||||
rows, err := DBClient.Query(`
|
||||
SELECT u.username, h.balance, h.message_count
|
||||
FROM himbucks h
|
||||
JOIN users u ON h.user_id = u.id
|
||||
WHERE h.guild_id = ?
|
||||
ORDER BY h.balance DESC
|
||||
LIMIT ?`,
|
||||
SELECT u.username, gp.currency_balance, gp.message_count
|
||||
FROM guild_profiles gp
|
||||
JOIN users u ON gp.user_id = u.id
|
||||
WHERE gp.guild_id = ?
|
||||
ORDER BY gp.currency_balance DESC
|
||||
LIMIT ?`,
|
||||
guildID, limit)
|
||||
if err != nil {
|
||||
return nil, fmt.Errorf("failed to get leaderboard: %w", err)
|
||||
|
Reference in New Issue
Block a user