steelforesight/panel/seed-radar.js

77 lines
3.2 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.

// One-off: backfill «در یک نگاه» (radar_items) with random plausible Jalali dates,
// credible sources, category tags (so hashtags work), and category-consistent images.
// Run once: node seed-radar.js
import 'dotenv/config';
import pg from 'pg';
const { Pool } = pg;
const pool = new Pool({
connectionString: process.env.DATABASE_URL,
ssl: process.env.DATABASE_SSL === 'disable' ? false : { rejectUnauthorized: false },
});
const FA_DIGITS = ['۰','۱','۲','۳','۴','۵','۶','۷','۸','۹'];
const faNum = (n) => String(n).replace(/\d/g, (d) => FA_DIGITS[+d]);
// Jalali month → rough Gregorian month for the English date
const MONTHS = [
{ fa: 'فروردین', en: 'Apr' }, { fa: 'اردیبهشت', en: 'May' }, { fa: 'خرداد', en: 'Jun' },
{ fa: 'تیر', en: 'Jul' }, { fa: 'مرداد', en: 'Aug' }, { fa: 'شهریور', en: 'Sep' },
];
const SOURCES = [
'Reuters', 'Bloomberg', 'Financial Times', 'S&P Global Platts', 'Metal Bulletin',
'Fastmarkets', 'Kallanish', 'Mining.com', 'worldsteel', 'دنیای اقتصاد', 'ایسنا', 'فولاد نیوز', 'چیلان',
];
const TAGS = {
market: ['بازار جهانی', 'قیمت فولاد', 'تقاضا', 'عرضه', 'صادرات'],
tech: ['فناوری', 'نوآوری', 'هوش مصنوعی', 'اتوماسیون', 'هیدروژن'],
commodity: ['سنگ آهن', 'زغال سنگ', 'کامودیتی', 'مواد اولیه', 'قراضه'],
geo: ['ژئوپلیتیک', 'تحریم', 'تجارت جهانی', 'زنجیره تأمین', 'CBAM'],
energy: ['انرژی', 'گاز', 'برق', 'فولاد سبز', 'کربن زدایی'],
};
// category-relevant cover (best available stock in /public/news)
const IMG = {
market: '/news/photo-1504307651254-35680f356dfd.jpg',
tech: '/news/photo-1518770660439-4636190af475.jpg',
commodity: '/news/photo-1540575467063-178a50c2df87.jpg',
geo: '/news/photo-1570168007204-dfb528c6958f.jpg',
energy: '/news/photo-1466611653911-95081537e5b7.jpg',
};
const pick = (arr) => arr[Math.floor(Math.random() * arr.length)];
const pickN = (arr, n) => [...arr].sort(() => Math.random() - 0.5).slice(0, n);
const rows = (await pool.query('SELECT id, category, tags, img FROM radar_items')).rows;
console.log(`Updating ${rows.length} radar_items…`);
let n = 0;
for (const r of rows) {
const m = pick(MONTHS);
const day = 1 + Math.floor(Math.random() * 28);
const dateFa = `${faNum(day)} ${m.fa} ۱۴۰۵`;
const dateEn = `${m.en} ${day}, 2026`;
const source = pick(SOURCES);
const cat = TAGS[r.category] ? r.category : 'market';
// keep existing tags if present; otherwise seed 3 category tags
let tags = r.tags;
try { const parsed = JSON.parse(r.tags || '[]'); if (!parsed.length) tags = null; } catch { tags = null; }
if (!tags) tags = JSON.stringify(pickN(TAGS[cat], 3));
// set a category-relevant image unless the editor uploaded one (/media/…)
const img = (r.img && r.img.startsWith('/media/')) ? r.img : IMG[cat];
await pool.query(
`UPDATE radar_items SET date_fa=$1, date_en=$2, source=$3, tags=$4, img=$5, updated_at=now() WHERE id=$6`,
[dateFa, dateEn, source, tags, img, r.id]
);
n++;
}
console.log(`✓ Updated ${n} rows.`);
await pool.end();
process.exit(0);