updates, dokploy
All checks were successful
Cross Compile Go / build (push) Successful in 12m11s

This commit is contained in:
ilbinek
2026-04-09 01:39:37 +02:00
parent fcebe00175
commit e39a92c6d3
14 changed files with 450 additions and 276 deletions

View File

@@ -9,7 +9,7 @@ import (
func CheckAllowed(c *gin.Context) {
secret := c.GetHeader("X-SECRET-KEY")
if secret != initializers.SECRET {
if secret != initializers.SecretKey {
c.JSON(http.StatusForbidden, gin.H{"error": "Forbidden"})
c.Abort()
return
@@ -18,7 +18,7 @@ func CheckAllowed(c *gin.Context) {
func CheckAdmin(c *gin.Context) {
adminSecret := c.GetHeader("X-ADMIN-KEY")
if adminSecret != initializers.ADMIN_SECRET {
if adminSecret != initializers.AdminSecret {
c.JSON(http.StatusForbidden, gin.H{"error": "Forbidden"})
c.Abort()
return

View File

@@ -52,113 +52,6 @@ func convertToSimplifiedAddonWithoutFiles(addon models.Addon) models.SimplifiedA
func GetDuplicates(c *gin.Context) {
id := c.Param("id")
// First check if addon exists (lightweight query)
var exists bool
if err := initializers.DB.Model(&models.Addon{}).Select("1").Where("id = ?", id).Limit(1).Find(&exists).Error; err != nil {
c.JSON(http.StatusNotFound, gin.H{"error": "Addon not found"})
return
}
// Get only the hashes from source addon files (don't load full addon yet)
var sourceHashes []string
if err := initializers.DB.Model(&models.AddonFile{}).
Where("addon_id = ? AND hash != ''", id).
Pluck("hash", &sourceHashes).Error; err != nil {
c.JSON(http.StatusInternalServerError, gin.H{"error": "Failed to fetch source addon files"})
return
}
// Now load the full source addon for the response
var sourceAddon models.Addon
if err := initializers.DB.Preload("AddonFiles").First(&sourceAddon, "id = ?", id).Error; err != nil {
c.JSON(http.StatusNotFound, gin.H{"error": "Addon not found"})
return
}
simplifiedSourceAddon := convertToSimplifiedAddon(sourceAddon)
if len(sourceHashes) == 0 {
c.JSON(http.StatusOK, models.DuplicatesResponse{
SourceAddon: simplifiedSourceAddon,
DuplicateAddons: make(map[string]models.AddonWithDuplicates),
})
return
}
// Single query with JOIN to get all data
type DuplicateRow struct {
Hash string
Path string
Version string
AddonID string
AddonName string
AddonType string
Summary string
Preview string
Author string
SubscriberCount int
CurrentVersionNumber string
}
var duplicates []DuplicateRow
err := initializers.DB.Table("addon_files af").
Select(`af.hash, af.path, af.version, af.addon_id,
a.name as addon_name, a.type as addon_type, a.summary,
a.preview, a.author, a.subscriber_count, a.current_version_number`).
Joins("INNER JOIN addons a ON a.id = af.addon_id").
Joins("LEFT JOIN whitelisted_hashes wh ON wh.hash = af.hash").
Where(`af.hash IN ?
AND af.addon_id != ?
AND af.deleted_at IS NULL
AND wh.hash IS NULL`,
sourceHashes, id).
Scan(&duplicates).Error
if err != nil {
c.JSON(http.StatusInternalServerError, gin.H{"error": "Failed to fetch duplicates"})
return
}
// Build response from single result set
response := models.DuplicatesResponse{
SourceAddon: simplifiedSourceAddon,
DuplicateAddons: make(map[string]models.AddonWithDuplicates),
}
for _, dup := range duplicates {
if _, exists := response.DuplicateAddons[dup.AddonID]; !exists {
response.DuplicateAddons[dup.AddonID] = models.AddonWithDuplicates{
Addon: models.SimplifiedAddon{
ID: dup.AddonID,
Name: dup.AddonName,
Type: dup.AddonType,
Summary: dup.Summary,
Preview: dup.Preview,
Author: dup.Author,
SubscriberCount: dup.SubscriberCount,
CurrentVersionNumber: dup.CurrentVersionNumber,
AddonFiles: []models.SimplifiedAddonFile{},
},
Duplicates: []models.DuplicateFileInfo{},
}
}
entry := response.DuplicateAddons[dup.AddonID]
entry.Duplicates = append(entry.Duplicates, models.DuplicateFileInfo{
Path: dup.Path,
Hash: dup.Hash,
Version: dup.Version,
AddonID: dup.AddonID,
})
response.DuplicateAddons[dup.AddonID] = entry
}
c.JSON(http.StatusOK, response)
}
/*func GetDuplicates(c *gin.Context) {
id := c.Param("id")
fmt.Println("Fetching addon with ID:", id)
// Fetch the source addon with its files
@@ -236,6 +129,19 @@ func GetDuplicates(c *gin.Context) {
}
}
// Set Recheck flag for source addon and all duplicate addons
if err := initializers.DB.Model(&models.Addon{}).Where("id = ?", id).Update("recheck", true).Error; err != nil {
c.JSON(http.StatusInternalServerError, gin.H{"error": "Failed to update source addon"})
return
}
for _, addon := range duplicateAddons {
if err := initializers.DB.Model(&models.Addon{}).Where("id = ?", addon.ID).Update("recheck", true).Error; err != nil {
c.JSON(http.StatusInternalServerError, gin.H{"error": "Failed to update duplicate addon"})
return
}
}
// Build the response
response := models.DuplicatesResponse{
SourceAddon: simplifiedSourceAddon,
@@ -269,7 +175,7 @@ func GetDuplicates(c *gin.Context) {
}
c.JSON(http.StatusOK, response)
}*/
}
func GetPossibleAddons(c *gin.Context) {
query := c.Query("q")

View File

@@ -105,7 +105,7 @@ func SaveIndexingResult(c *gin.Context) {
return
}
if initializers.DiscordWebhook != "" {
if initializers.DiscordWebhookURL != "" {
text := "Indexing of addon " + addon.Name + " (" + addon.ID + ") was successful."
colour := 2228479
nbr := strconv.Itoa(len(result.Files))
@@ -118,16 +118,16 @@ func SaveIndexingResult(c *gin.Context) {
percentage := 0.0
if addonsCount > 0 {
percentage = (float64(addonsCount - addonsToBeIndexed) / float64(addonsCount)) * 100
percentage = (float64(addonsCount-addonsToBeIndexed) / float64(addonsCount)) * 100
}
txt := fmt.Sprintf("%d/%d (%.2f%%).", addonsCount - addonsToBeIndexed, addonsCount, percentage)
txt := fmt.Sprintf("%d/%d (%.2f%%).", addonsCount-addonsToBeIndexed, addonsCount, percentage)
myEmbed := models.CustomEmbed{
Title: text,
Title: text,
Description: fmt.Sprintf("Files Indexed: %s\nOverall Progress: %s", nbr, txt),
Color: colour,
Timestamp: time.Now(),
Color: colour,
Timestamp: time.Now(),
Image: models.CustomImage{
URL: addon.Preview,
},
@@ -152,10 +152,10 @@ func SaveIndexingResult(c *gin.Context) {
myHook := models.CustomHook{
Username: "Reforger Crawler",
Embeds: []models.CustomEmbed{myEmbed},
Embeds: []models.CustomEmbed{myEmbed},
}
err := SendCustomWebhook(initializers.DiscordWebhook, myHook)
err := SendCustomWebhook(initializers.DiscordWebhookURL, myHook)
if err != nil {
fmt.Println("Error sending webhook:", err)
}
@@ -208,27 +208,27 @@ func checkIndexingTimeout() {
}
func SendCustomWebhook(webhookURL string, hook models.CustomHook) error {
payload, err := json.Marshal(hook)
if err != nil {
return err
}
payload, err := json.Marshal(hook)
if err != nil {
return err
}
req, err := http.NewRequest("POST", webhookURL, bytes.NewBuffer(payload))
if err != nil {
return err
}
req.Header.Set("Content-Type", "application/json")
req, err := http.NewRequest("POST", webhookURL, bytes.NewBuffer(payload))
if err != nil {
return err
}
req.Header.Set("Content-Type", "application/json")
client := &http.Client{}
resp, err := client.Do(req)
if err != nil {
return err
}
defer resp.Body.Close()
client := &http.Client{}
resp, err := client.Do(req)
if err != nil {
return err
}
defer resp.Body.Close()
if resp.StatusCode < 200 || resp.StatusCode > 299 {
return fmt.Errorf("webhook failed with status code %d", resp.StatusCode)
}
if resp.StatusCode < 200 || resp.StatusCode > 299 {
return fmt.Errorf("webhook failed with status code %d", resp.StatusCode)
}
return nil
}
return nil
}

View File

@@ -1,7 +1,9 @@
package controllers
import (
"bytes"
"fmt"
"io"
"strconv"
"time"
@@ -15,10 +17,14 @@ var nbrOfUnsentWebhooks int
func CreateAddon(c *gin.Context) {
var addonR models.Addon
body := make([]byte, 0)
c.Request.Body.Read(body)
fmt.Println(body)
err := c.ShouldBindJSON(&addonR)
body, err := io.ReadAll(c.Request.Body)
if err != nil {
c.JSON(400, gin.H{"error": "Failed to read request body"})
return
}
fmt.Println(string(body))
c.Request.Body = io.NopCloser(bytes.NewBuffer(body))
err = c.ShouldBindJSON(&addonR)
if err != nil {
c.JSON(400, gin.H{"error": "Invalid JSON"})
return
@@ -44,7 +50,7 @@ func CreateAddon(c *gin.Context) {
nbrOfUnsentWebhooks = 0
go func() {
webhookURL := initializers.ScraperWebhook
webhookURL := initializers.ScraperWebhookURL
if webhookURL != "" {
text := fmt.Sprintf("New %d addons found\nLast: %s (%s).", oldNbr, addon.ID, addon.Name)
colour := 2228479
@@ -102,44 +108,44 @@ func CreateAddon(c *gin.Context) {
// send webhook about update
go func() {
webhookURL := initializers.ScraperWebhook
if webhookURL != "" {
text := fmt.Sprintf("Addon: %s (%s) updated", addon.ID, addon.Name)
colour := 2228479
size := fmt.Sprintf("%.2f MB", float64(addon.CurrentVersionSize)/1_000_000)
webhookURL := initializers.ScraperWebhookURL
if webhookURL != "" {
text := fmt.Sprintf("Addon: %s (%s) updated", addon.ID, addon.Name)
colour := 2228479
size := fmt.Sprintf("%.2f MB", float64(addon.CurrentVersionSize)/1_000_000)
myEmbed := models.CustomEmbed{
Title: text,
Color: colour,
Timestamp: time.Now(),
Image: models.CustomImage{
URL: addon.Preview,
},
Fields: []models.CustomEmbedField{
{
Name: "Size",
Value: size,
Inline: true,
myEmbed := models.CustomEmbed{
Title: text,
Color: colour,
Timestamp: time.Now(),
Image: models.CustomImage{
URL: addon.Preview,
},
{
Name: "Current Version",
Value: addon.CurrentVersionNumber,
Inline: true,
Fields: []models.CustomEmbedField{
{
Name: "Size",
Value: size,
Inline: true,
},
{
Name: "Current Version",
Value: addon.CurrentVersionNumber,
Inline: true,
},
},
},
}
}
myHook := models.CustomHook{
Username: "Reforger Crawler",
Embeds: []models.CustomEmbed{myEmbed},
}
myHook := models.CustomHook{
Username: "Reforger Crawler",
Embeds: []models.CustomEmbed{myEmbed},
}
err := SendCustomWebhook(webhookURL, myHook)
if err != nil {
fmt.Println("Error sending webhook:", err)
err := SendCustomWebhook(webhookURL, myHook)
if err != nil {
fmt.Println("Error sending webhook:", err)
}
}
}
}()
}()
}
}
c.JSON(200, gin.H{"status": "success"})