HotTRDealsBackend/workers/trendingDealList.worker.js
2026-02-07 22:42:02 +00:00

115 lines
3.6 KiB
JavaScript
Raw Permalink Blame History

This file contains ambiguous Unicode characters

This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

const { Worker } = require("bullmq")
const Redis = require("ioredis")
const { getRedisConnectionOptions } = require("../services/redis/connection")
const TRENDING_DEAL_TTL_SECONDS = 12 * 60 * 60
const TRENDING_DEAL_LIMIT = 1000
const TRENDING_DEAL_WINDOW_DAYS = 2 // Test için burayı 30 yapıp deneyebilirsin
function createRedisClient() {
return new Redis(getRedisConnectionOptions())
}
function parseSearchResults(results = []) {
const ids = [];
// i=1'den başlıyoruz (results[0] toplam sayıdır), ikişer ikişer atlıyoruz
for (let i = 1; i < results.length; i += 2) {
const key = results[i]; // Örn: "deals:cache:20"
const value = results[i + 1]; // Örn: ["$", "[{\"id\":20,...}]"]
try {
// Dialect 3 formatında JSON her zaman bir array string'i olarak gelir: [0] = "$", [1] = "[{...}]"
// JSON.parse(value[1])[0] diyerek direkt objeye ulaşıyoruz.
const [deal] = JSON.parse(value[1]);
ids.push(Number(deal.id));
} catch {
// Eğer JSON'da bir sorun olursa, ID'yi key'den (deals:cache:20) güvenli bir şekilde çek
const idFromKey = key.split(":")[2];
if (idFromKey) ids.push(Number(idFromKey));
}
}
return ids;
}
async function buildTrendingDealList() {
const redis = createRedisClient()
try {
const now = Date.now()
// windowMs'i tam sayıya yuvarlayalım
const windowMs = Math.floor(Number(TRENDING_DEAL_WINDOW_DAYS) * 24 * 60 * 60 * 1000)
const cutoffMs = now - windowMs
// DEBUG: Zaman aralığını kontrol edelim
console.log(`🕒 Şu an: ${new Date(now).toISOString()}`)
console.log(`🕒 Cutoff (Eşik): ${new Date(cutoffMs).toISOString()}`)
/**
* SORGUNUN ANALİZİ:
* 1. @status:{ACTIVE} -> Veritabanında 'ACTIVE' (BÜYÜK HARF) olduğundan emin ol.
* 2. @createdAtTs:[${cutoffMs} +inf] -> Sayısal aralık.
*/
const query = `@status:{ACTIVE} @createdAtTs:[${cutoffMs} +inf]`
console.log(`🔍 Redis Query: FT.SEARCH idx:deals "${query}" SORTBY score DESC DIALECT 3`)
const results = await redis.call(
"FT.SEARCH",
"idx:deals",
query,
"SORTBY", "score", "DESC",
"LIMIT", "0", String(TRENDING_DEAL_LIMIT),
"DIALECT", "3",
"RETURN", "1", "$"
)
// Redis kaç tane döküman buldu?
const totalFound = results[0] || 0
console.log(`📊 Redis Toplam Bulunan: ${totalFound}`)
const dealIds = parseSearchResults(results)
const runId = String(now)
const payload = {
id: runId,
createdAt: new Date(now).toISOString(),
total: dealIds.length,
dealIds,
}
const key = `deals:lists:trending:${runId}`
await redis.call("JSON.SET", key, "$", JSON.stringify(payload))
await redis.expire(key, TRENDING_DEAL_TTL_SECONDS)
await redis.set("deals:lists:trending:latest", runId, "EX", TRENDING_DEAL_TTL_SECONDS)
return { id: runId, total: dealIds.length }
} catch (error) {
console.error("❌ buildTrendingDealList Hatası:", error.message)
throw error
} finally {
redis.disconnect()
}
}
async function handler() {
return buildTrendingDealList()
}
function startTrendingDealListWorker() {
const worker = new Worker("trendingdeal-list", handler, {
connection: getRedisConnectionOptions(),
concurrency: 1,
})
worker.on("completed", (job) => {
console.log(`✅ Trending Deal Listesi Bitti. Bulunan ID Sayısı: ${job.returnvalue?.total}`)
})
worker.on("failed", (job, err) => {
console.error(`❌ Trending Deal Worker Hatası!`, err.message)
})
return worker
}
module.exports = { startTrendingDealListWorker }