// 图片URL处理工具 const DOMAIN_CONFIG = require('../config/domain').DOMAIN_CONFIG; // 将完整URL转换为相对路径(用于存储到数据库) function toRelativeUrl(url) { if (!url) return ''; // 移除域名前缀,保留相对路径 const baseUrl = DOMAIN_CONFIG.BASE_URL; if (url.startsWith(baseUrl)) { return url.replace(baseUrl, ''); } // 从 BASE_URL 中提取主机名用于构建动态正则 let hostname = '' try { hostname = new URL(baseUrl).hostname } catch (e) { hostname = '' } // 移除其他已知前缀 const patterns = [ hostname ? new RegExp(`^https?://${hostname.replace(/\./g, '\\.')}(:\\d+)?`) : null, /^https?:\/\/localhost(:\d+)?/ ].filter(Boolean) for (const pattern of patterns) { if (pattern.test(url)) { return url.replace(pattern, ''); } } return url; } // 将相对路径转换为完整URL(用于返回给前端,图片URL不带端口) function toFullUrl(url) { if (!url) return ''; // 如果已经是完整URL,替换路径并移除端口 if (url.startsWith('http://') || url.startsWith('https://')) { // 将 /uploads/goods/ 替换为 /img/,并移除端口 return url.replace('/uploads/goods/', '/img/').replace(/:\d+/, ''); } // 如果是相对路径,拼接图片域名(不带端口)并替换路径 const imgDomain = DOMAIN_CONFIG.IMG_DOMAIN || DOMAIN_CONFIG.BASE_URL.replace(/:\d+/, ''); if (url.startsWith('/')) { // 将 /uploads/goods/ 替换为 /img/ return imgDomain + url.replace('/uploads/goods/', '/img/'); } if (url.startsWith('img/')) { return imgDomain + '/' + url; } // 处理可能的 uploads/goods/ 开头的路径 if (url.startsWith('uploads/goods/')) { return imgDomain + '/img/' + url.replace('uploads/goods/', ''); } return url; } // 处理商品图片字段 function processGoodsImages(goods) { if (!goods) return goods; const processItem = (item) => { if (item.images) { try { const images = JSON.parse(item.images); const fullUrls = images.map(img => toFullUrl(img)); item.images = JSON.stringify(fullUrls); } catch (e) { // 如果不是JSON格式,保持原样 } } return item; }; if (Array.isArray(goods)) { return goods.map(processItem); } return processItem(goods); } module.exports = { toRelativeUrl, toFullUrl, processGoodsImages };