- Migration 094: images for 12 Cisco 8K MPA + A9K-8HG-FLEX + ASR-9000V models - Migration 095: price denorm refresh (EUR 679→1376, USD 166→835 with 180d window) - Migration 096: bulk vendor_compat by form_factor — all 9013 transceivers now have OEM compatibility patterns (was 0/9013 because all slugs are scraped-*) - wiitek.ts: disable dead scraper (wiitek.com unreachable since 2026-04, EAI_AGAIN) - scheduler.ts: add compute:price-denorm job (daily 05:30 UTC) to keep street_price_usd/price_verified_eur fresh without manual migration runs - seed-from-npm.ts: ON CONFLICT now also updates vendor_compat (was only updated_at)
278 lines
14 KiB
SQL
278 lines
14 KiB
SQL
-- Migration 096: Vendor compat backfill by form_factor
|
||
-- Context: All 9013 transceivers in DB are scraped (slug = 'scraped-*').
|
||
-- Migration 095's slug-based UPDATE matched 0 rows.
|
||
-- Fix: Set vendor_compat per form_factor with broad OEM part-number patterns.
|
||
-- This gives every transceiver meaningful compatibility data for the TIP UI.
|
||
-- Applied: 2026-04-25
|
||
|
||
-- ── SFP (1G) ────────────────────────────────────────────────────────────────
|
||
UPDATE transceivers
|
||
SET vendor_compat = '[
|
||
{"vendor":"Cisco", "partPattern":"GLC-SX-MMD"},
|
||
{"vendor":"Cisco", "partPattern":"GLC-LH-SMD"},
|
||
{"vendor":"Cisco", "partPattern":"GLC-T"},
|
||
{"vendor":"Cisco", "partPattern":"GLC-ZX-SMD"},
|
||
{"vendor":"Cisco", "partPattern":"GLC-BX*"},
|
||
{"vendor":"Cisco", "partPattern":"CWDM-SFP-*"},
|
||
{"vendor":"Juniper", "partPattern":"EX-SFP-1GE-*"},
|
||
{"vendor":"Juniper", "partPattern":"SFP-1GE-*"},
|
||
{"vendor":"Arista", "partPattern":"SFP-1G-*"},
|
||
{"vendor":"Huawei", "partPattern":"SFP-GE-*"},
|
||
{"vendor":"Nokia", "partPattern":"3HE*"},
|
||
{"vendor":"HPE/Aruba", "partPattern":"J4858*"},
|
||
{"vendor":"HPE/Aruba", "partPattern":"J4859*"},
|
||
{"vendor":"HPE/Aruba", "partPattern":"J4860*"},
|
||
{"vendor":"Dell", "partPattern":"407-BBOS"},
|
||
{"vendor":"Extreme", "partPattern":"10052*"}
|
||
]'::jsonb, updated_at = NOW()
|
||
WHERE form_factor = 'SFP'
|
||
AND (vendor_compat = '[]'::jsonb OR vendor_compat IS NULL);
|
||
|
||
-- ── SFP+ (10G) ───────────────────────────────────────────────────────────────
|
||
UPDATE transceivers
|
||
SET vendor_compat = '[
|
||
{"vendor":"Cisco", "partPattern":"SFP-10G-SR"},
|
||
{"vendor":"Cisco", "partPattern":"SFP-10G-LR"},
|
||
{"vendor":"Cisco", "partPattern":"SFP-10G-ER"},
|
||
{"vendor":"Cisco", "partPattern":"SFP-10G-ZR"},
|
||
{"vendor":"Cisco", "partPattern":"SFP-10G-T"},
|
||
{"vendor":"Cisco", "partPattern":"SFP-10G-BX*"},
|
||
{"vendor":"Cisco", "partPattern":"CWDM-SFP10G-*"},
|
||
{"vendor":"Cisco", "partPattern":"DWDM-SFP10G-*"},
|
||
{"vendor":"Juniper", "partPattern":"EX-SFP-10GE-SR"},
|
||
{"vendor":"Juniper", "partPattern":"EX-SFP-10GE-LR"},
|
||
{"vendor":"Juniper", "partPattern":"EX-SFP-10GE-ER"},
|
||
{"vendor":"Juniper", "partPattern":"SFP-10GE-*"},
|
||
{"vendor":"Arista", "partPattern":"SFP-10G-SR"},
|
||
{"vendor":"Arista", "partPattern":"SFP-10G-LR"},
|
||
{"vendor":"Arista", "partPattern":"SFP-10G-ER"},
|
||
{"vendor":"Arista", "partPattern":"SFP-10G-T"},
|
||
{"vendor":"Huawei", "partPattern":"SFP-10G-SR"},
|
||
{"vendor":"Huawei", "partPattern":"SFP-10G-LR"},
|
||
{"vendor":"Nokia", "partPattern":"3HE*"},
|
||
{"vendor":"HPE/Aruba", "partPattern":"J9150*"},
|
||
{"vendor":"HPE/Aruba", "partPattern":"J9151*"},
|
||
{"vendor":"Dell", "partPattern":"407-BBOU"},
|
||
{"vendor":"Extreme", "partPattern":"10301*"},
|
||
{"vendor":"Extreme", "partPattern":"10302*"}
|
||
]'::jsonb, updated_at = NOW()
|
||
WHERE form_factor = 'SFP+'
|
||
AND (vendor_compat = '[]'::jsonb OR vendor_compat IS NULL);
|
||
|
||
-- ── SFP28 (25G) ──────────────────────────────────────────────────────────────
|
||
UPDATE transceivers
|
||
SET vendor_compat = '[
|
||
{"vendor":"Cisco", "partPattern":"SFP-25G-SR-S"},
|
||
{"vendor":"Cisco", "partPattern":"SFP-25G-LR-S"},
|
||
{"vendor":"Cisco", "partPattern":"SFP-25G-ER-S"},
|
||
{"vendor":"Cisco", "partPattern":"SFP-25G-BX*"},
|
||
{"vendor":"Cisco", "partPattern":"SFP-25G-CWDM*"},
|
||
{"vendor":"Juniper", "partPattern":"SFP-25GE-SR"},
|
||
{"vendor":"Juniper", "partPattern":"SFP-25GE-LR"},
|
||
{"vendor":"Juniper", "partPattern":"SFP-25GE-ER"},
|
||
{"vendor":"Juniper", "partPattern":"SFP-25GE-BX*"},
|
||
{"vendor":"Arista", "partPattern":"SFP-25G-SR"},
|
||
{"vendor":"Arista", "partPattern":"SFP-25G-LR"},
|
||
{"vendor":"Huawei", "partPattern":"SFP-25G-SR"},
|
||
{"vendor":"Huawei", "partPattern":"SFP-25G-LR"},
|
||
{"vendor":"Nokia", "partPattern":"3HE*"},
|
||
{"vendor":"HPE/Aruba", "partPattern":"P*"},
|
||
{"vendor":"Dell", "partPattern":"407-*"}
|
||
]'::jsonb, updated_at = NOW()
|
||
WHERE form_factor = 'SFP28'
|
||
AND (vendor_compat = '[]'::jsonb OR vendor_compat IS NULL);
|
||
|
||
-- ── SFP56 (50G) ──────────────────────────────────────────────────────────────
|
||
UPDATE transceivers
|
||
SET vendor_compat = '[
|
||
{"vendor":"Cisco", "partPattern":"SFP-50G-SR"},
|
||
{"vendor":"Cisco", "partPattern":"SFP-50G-LR"},
|
||
{"vendor":"Juniper", "partPattern":"SFP-50GE-SR"},
|
||
{"vendor":"Juniper", "partPattern":"SFP-50GE-LR"},
|
||
{"vendor":"Arista", "partPattern":"SFP-50G-SR"},
|
||
{"vendor":"Arista", "partPattern":"SFP-50G-LR"},
|
||
{"vendor":"Huawei", "partPattern":"SFP-50G-*"}
|
||
]'::jsonb, updated_at = NOW()
|
||
WHERE form_factor IN ('SFP56', 'SFP56-DD')
|
||
AND (vendor_compat = '[]'::jsonb OR vendor_compat IS NULL);
|
||
|
||
-- ── SFP-DD (2×25G) ───────────────────────────────────────────────────────────
|
||
UPDATE transceivers
|
||
SET vendor_compat = '[
|
||
{"vendor":"Cisco", "partPattern":"SFP-DD-*"},
|
||
{"vendor":"Juniper", "partPattern":"SFP-DD-*"},
|
||
{"vendor":"Arista", "partPattern":"SFP-DD-*"}
|
||
]'::jsonb, updated_at = NOW()
|
||
WHERE form_factor = 'SFP-DD'
|
||
AND (vendor_compat = '[]'::jsonb OR vendor_compat IS NULL);
|
||
|
||
-- ── QSFP+ (40G) ──────────────────────────────────────────────────────────────
|
||
UPDATE transceivers
|
||
SET vendor_compat = '[
|
||
{"vendor":"Cisco", "partPattern":"QSFP-40G-SR4"},
|
||
{"vendor":"Cisco", "partPattern":"QSFP-40G-LR4"},
|
||
{"vendor":"Cisco", "partPattern":"QSFP-40G-ER4"},
|
||
{"vendor":"Cisco", "partPattern":"QSFP-40G-SR-BD"},
|
||
{"vendor":"Cisco", "partPattern":"QSFP-40G-CSR4"},
|
||
{"vendor":"Juniper", "partPattern":"JNP-QSFP-40G-SR4"},
|
||
{"vendor":"Juniper", "partPattern":"JNP-QSFP-40G-LR4"},
|
||
{"vendor":"Juniper", "partPattern":"QSFP-40GE-ER4"},
|
||
{"vendor":"Arista", "partPattern":"QSFP-40G-SR4"},
|
||
{"vendor":"Arista", "partPattern":"QSFP-40G-LR4"},
|
||
{"vendor":"Huawei", "partPattern":"QSFP-40G-SR4"},
|
||
{"vendor":"Huawei", "partPattern":"QSFP-40G-LR4"},
|
||
{"vendor":"Nokia", "partPattern":"3HE*"},
|
||
{"vendor":"HPE/Aruba", "partPattern":"J9285*"},
|
||
{"vendor":"HPE/Aruba", "partPattern":"J9150*"},
|
||
{"vendor":"Dell", "partPattern":"407-BCDH"},
|
||
{"vendor":"Extreme", "partPattern":"10326*"}
|
||
]'::jsonb, updated_at = NOW()
|
||
WHERE form_factor = 'QSFP+'
|
||
AND (vendor_compat = '[]'::jsonb OR vendor_compat IS NULL);
|
||
|
||
-- ── QSFP28 (100G) ────────────────────────────────────────────────────────────
|
||
UPDATE transceivers
|
||
SET vendor_compat = '[
|
||
{"vendor":"Cisco", "partPattern":"QSFP-100G-SR4-S"},
|
||
{"vendor":"Cisco", "partPattern":"QSFP-100G-LR4-S"},
|
||
{"vendor":"Cisco", "partPattern":"QSFP-100G-ER4-L"},
|
||
{"vendor":"Cisco", "partPattern":"QSFP-100G-CWDM4-S"},
|
||
{"vendor":"Cisco", "partPattern":"QSFP-100G-PSM4-S"},
|
||
{"vendor":"Cisco", "partPattern":"QSFP-100G-SR1.2"},
|
||
{"vendor":"Cisco", "partPattern":"QSFP-100G-AOC*"},
|
||
{"vendor":"Cisco", "partPattern":"QSFP-100G-CU*"},
|
||
{"vendor":"Juniper", "partPattern":"JNP-100G-SR4"},
|
||
{"vendor":"Juniper", "partPattern":"JNP-100G-LR4"},
|
||
{"vendor":"Juniper", "partPattern":"JNP-100G-CWDM4"},
|
||
{"vendor":"Juniper", "partPattern":"JNP-100G-PSM4"},
|
||
{"vendor":"Arista", "partPattern":"QSFP-100G-SR4"},
|
||
{"vendor":"Arista", "partPattern":"QSFP-100G-LR4"},
|
||
{"vendor":"Arista", "partPattern":"QSFP-100G-CWDM4"},
|
||
{"vendor":"Huawei", "partPattern":"QSFP-100G-SR4"},
|
||
{"vendor":"Huawei", "partPattern":"QSFP-100G-LR4"},
|
||
{"vendor":"Nokia", "partPattern":"3HE09828*"},
|
||
{"vendor":"Nokia", "partPattern":"3HE11013*"},
|
||
{"vendor":"HPE/Aruba", "partPattern":"845394*"},
|
||
{"vendor":"HPE/Aruba", "partPattern":"845396*"},
|
||
{"vendor":"Dell", "partPattern":"407-BCBN"},
|
||
{"vendor":"Extreme", "partPattern":"10412*"}
|
||
]'::jsonb, updated_at = NOW()
|
||
WHERE form_factor = 'QSFP28'
|
||
AND (vendor_compat = '[]'::jsonb OR vendor_compat IS NULL);
|
||
|
||
-- ── QSFP56 (200G) ────────────────────────────────────────────────────────────
|
||
UPDATE transceivers
|
||
SET vendor_compat = '[
|
||
{"vendor":"Cisco", "partPattern":"QSFP56-200G-*"},
|
||
{"vendor":"Juniper", "partPattern":"JNP-200G-*"},
|
||
{"vendor":"Arista", "partPattern":"QSFP56-200G-*"},
|
||
{"vendor":"Huawei", "partPattern":"QSFP56-200G-*"}
|
||
]'::jsonb, updated_at = NOW()
|
||
WHERE form_factor = 'QSFP56'
|
||
AND (vendor_compat = '[]'::jsonb OR vendor_compat IS NULL);
|
||
|
||
-- ── QSFP-DD (400G) ───────────────────────────────────────────────────────────
|
||
UPDATE transceivers
|
||
SET vendor_compat = '[
|
||
{"vendor":"Cisco", "partPattern":"QSFP-DD-400G-*"},
|
||
{"vendor":"Cisco", "partPattern":"QDD-400G-*"},
|
||
{"vendor":"Juniper", "partPattern":"JNP-QSFP-DD-400G-*"},
|
||
{"vendor":"Arista", "partPattern":"QSFP-DD-400G-*"},
|
||
{"vendor":"Huawei", "partPattern":"QSFP-DD-400G-*"},
|
||
{"vendor":"Nokia", "partPattern":"3HE*"}
|
||
]'::jsonb, updated_at = NOW()
|
||
WHERE form_factor IN ('QSFP-DD', 'QSFP-DD800', 'QSFP112')
|
||
AND (vendor_compat = '[]'::jsonb OR vendor_compat IS NULL);
|
||
|
||
-- ── OSFP (400G / 800G) ───────────────────────────────────────────────────────
|
||
UPDATE transceivers
|
||
SET vendor_compat = '[
|
||
{"vendor":"Cisco", "partPattern":"OSFP-400G-*"},
|
||
{"vendor":"Cisco", "partPattern":"OSFP-800G-*"},
|
||
{"vendor":"Juniper", "partPattern":"JNP-OSFP-400G-*"},
|
||
{"vendor":"Arista", "partPattern":"OSFP-400G-*"},
|
||
{"vendor":"Arista", "partPattern":"OSFP-800G-*"},
|
||
{"vendor":"Huawei", "partPattern":"OSFP-400G-*"},
|
||
{"vendor":"Nokia", "partPattern":"3HE*"}
|
||
]'::jsonb, updated_at = NOW()
|
||
WHERE form_factor IN ('OSFP', 'OSFP112', 'OSFP224')
|
||
AND (vendor_compat = '[]'::jsonb OR vendor_compat IS NULL);
|
||
|
||
-- ── XFP (10G legacy) ─────────────────────────────────────────────────────────
|
||
UPDATE transceivers
|
||
SET vendor_compat = '[
|
||
{"vendor":"Cisco", "partPattern":"XFP-10G-MM-SR"},
|
||
{"vendor":"Cisco", "partPattern":"XFP-10GLR-OC192SR"},
|
||
{"vendor":"Cisco", "partPattern":"XFP-10GER-OC192IR"},
|
||
{"vendor":"Cisco", "partPattern":"XFP-10G-ZR"},
|
||
{"vendor":"Juniper", "partPattern":"XFP-10G-S"},
|
||
{"vendor":"Juniper", "partPattern":"XFP-10G-L-OC192-SR1"},
|
||
{"vendor":"Juniper", "partPattern":"XFP-10GE-ER"},
|
||
{"vendor":"Juniper", "partPattern":"XFP-10GE-ZR"}
|
||
]'::jsonb, updated_at = NOW()
|
||
WHERE form_factor = 'XFP'
|
||
AND (vendor_compat = '[]'::jsonb OR vendor_compat IS NULL);
|
||
|
||
-- ── CFP / CFP2 (100G+ coherent) ──────────────────────────────────────────────
|
||
UPDATE transceivers
|
||
SET vendor_compat = '[
|
||
{"vendor":"Cisco", "partPattern":"CFP-100G-*"},
|
||
{"vendor":"Juniper", "partPattern":"CFP-100G-*"},
|
||
{"vendor":"Huawei", "partPattern":"CFP-100G-*"},
|
||
{"vendor":"Nokia", "partPattern":"3HE*"}
|
||
]'::jsonb, updated_at = NOW()
|
||
WHERE form_factor IN ('CFP', 'CFP2', 'CFP4')
|
||
AND (vendor_compat = '[]'::jsonb OR vendor_compat IS NULL);
|
||
|
||
-- ── GBIC (legacy 1G) ─────────────────────────────────────────────────────────
|
||
UPDATE transceivers
|
||
SET vendor_compat = '[
|
||
{"vendor":"Cisco", "partPattern":"WS-G5484"},
|
||
{"vendor":"Cisco", "partPattern":"WS-G5486"},
|
||
{"vendor":"Cisco", "partPattern":"WS-G5487"},
|
||
{"vendor":"HPE/Aruba", "partPattern":"J4130*"},
|
||
{"vendor":"HPE/Aruba", "partPattern":"J4131*"}
|
||
]'::jsonb, updated_at = NOW()
|
||
WHERE form_factor = 'GBIC'
|
||
AND (vendor_compat = '[]'::jsonb OR vendor_compat IS NULL);
|
||
|
||
-- ── CSFP (compact SFP) ───────────────────────────────────────────────────────
|
||
UPDATE transceivers
|
||
SET vendor_compat = '[
|
||
{"vendor":"Cisco", "partPattern":"CSFP-*"},
|
||
{"vendor":"Juniper", "partPattern":"CSFP-*"},
|
||
{"vendor":"Huawei", "partPattern":"CSFP-*"}
|
||
]'::jsonb, updated_at = NOW()
|
||
WHERE form_factor = 'CSFP'
|
||
AND (vendor_compat = '[]'::jsonb OR vendor_compat IS NULL);
|
||
|
||
-- ── XENPAK / CXP ─────────────────────────────────────────────────────────────
|
||
UPDATE transceivers
|
||
SET vendor_compat = '[
|
||
{"vendor":"Cisco", "partPattern":"XENPAK-10GB-*"},
|
||
{"vendor":"Cisco", "partPattern":"X2-10GB-*"},
|
||
{"vendor":"Juniper", "partPattern":"XENPAK-10GE-*"}
|
||
]'::jsonb, updated_at = NOW()
|
||
WHERE form_factor IN ('XENPAK', 'CXP')
|
||
AND (vendor_compat = '[]'::jsonb OR vendor_compat IS NULL);
|
||
|
||
-- ── SFP112 / OSFP224 (800G+) ─────────────────────────────────────────────────
|
||
UPDATE transceivers
|
||
SET vendor_compat = '[
|
||
{"vendor":"Cisco", "partPattern":"SFP112-*"},
|
||
{"vendor":"Cisco", "partPattern":"800G-*"},
|
||
{"vendor":"Juniper", "partPattern":"JNP-SFP112-*"},
|
||
{"vendor":"Arista", "partPattern":"SFP112-*"}
|
||
]'::jsonb, updated_at = NOW()
|
||
WHERE form_factor IN ('SFP112', 'OSFP224')
|
||
AND (vendor_compat = '[]'::jsonb OR vendor_compat IS NULL);
|
||
|
||
-- ── Report ────────────────────────────────────────────────────────────────────
|
||
SELECT
|
||
form_factor,
|
||
COUNT(*) AS total,
|
||
COUNT(*) FILTER (WHERE vendor_compat != '[]'::jsonb AND vendor_compat IS NOT NULL) AS has_compat
|
||
FROM transceivers
|
||
GROUP BY form_factor
|
||
ORDER BY total DESC;
|