This commit is contained in:
mzl
2025-12-12 09:47:34 +00:00
parent 909f169aae
commit f99b2a84ca
6 changed files with 404 additions and 120 deletions
+68 -20
View File
@@ -12,11 +12,6 @@ class FbFileImportService
{
/**
* 导入指定目录下所有 .xlsx 文件
*
* @param string $dir 绝对目录路径
* @param int $channelId 渠道ID(写入 fb_leads.channel)
* @return int 实际导入的文件数量(按文件数计,不是行数)
* @throws BusinessException
*/
public function importDir(string $dir, int $channelId): int
{
@@ -37,10 +32,8 @@ class FbFileImportService
continue;
}
// 这里可以再做一道保险:如果已经有同名的 .done 文件,可以认为它已经导过,直接跳过
$doneFlag = $filePath . '.done';
if (is_file($doneFlag)) {
// 理论上不会出现(因为 .xlsx 已经被改名了),但防御性写法无害
continue;
}
@@ -61,11 +54,6 @@ class FbFileImportService
/**
* 导入单个 Excel 到 fb_leads
*
* @param string $filePath
* @param int $channelId 渠道ID
* @return int 导入的记录条数
* @throws BusinessException
*/
public function importOneFile(string $filePath, int $channelId): int
{
@@ -85,8 +73,9 @@ class FbFileImportService
$headerRow = array_shift($rows);
$mapper = new FbLeadHeaderMapper();
// 如有未知字段,会在这里抛异常
$colToField = $mapper->buildColumnFieldMap($headerRow);
$res = $mapper->buildColumnFieldMap($headerRow);
$colToField = $res['colToField'];
$unknownCols = $res['unknownCols'];
$insertData = [];
$now = time();
@@ -103,20 +92,34 @@ class FbFileImportService
$item['is_organic'] = $this->normalizeIsOrganic($raw);
break;
case 'fb_created_time':
// ✅ 方案B:写入 DATETIME 字符串
$item['fb_created_time'] = $this->normalizeCreatedTime($raw);
break;
default:
// 小增强:字符串统一 trim(避免 " xxx ")
if (is_string($raw)) {
$raw = trim($raw);
}
$item[$field] = $raw;
break;
}
}
// 未知列收集到 extra_data(宽松模式)
$extra = [];
foreach ($unknownCols as $colIndex => $rawHeader) {
$val = $row[$colIndex] ?? null;
if ($val === null || $val === '') continue;
$extra[$rawHeader] = is_string($val) ? trim($val) : $val;
}
$item['extra_data'] = $extra ? json_encode($extra, JSON_UNESCAPED_UNICODE) : null;
$item['source_file'] = $sourceFile;
$item['channel'] = $channelId; // 👈 渠道ID记录到 fb_leads
$item['channel'] = $channelId;
$item['created_at'] = $now;
$item['updated_at'] = $now;
$item['sync_status'] = 0; // 未同步到 inquiry_log
$item['sync_status'] = 0;
$insertData[] = $item;
}
@@ -136,7 +139,7 @@ class FbFileImportService
if (is_bool($raw)) {
return $raw ? 1 : 0;
}
$str = strtolower((string)$raw);
$str = strtolower(trim((string)$raw));
if ($str === '') {
return 0;
}
@@ -144,10 +147,55 @@ class FbFileImportService
}
/**
* FB 创建时间目前按原始字符串存储
* ✅ 方案B:把 FB 创建时间统一转成 MySQL DATETIME(Y-m-d H:i:s)
*
* 支持:
* - "10/13/25" / "12/8/25"
* - "2025-12-08 13:22:11"
* - Excel 日期序列(数字)
*
* 解析失败:返回 null(让 DB 用默认值/允许为空)
* 注意:如果你的 fb_created_time 列是 NOT NULL 且无默认值,请把 null 改成 '1970-01-01 00:00:00'
*/
protected function normalizeCreatedTime($raw)
protected function normalizeCreatedTime($raw): ?string
{
return $raw;
if ($raw === null || $raw === '') {
return null;
}
// Excel 日期序列:数字
if (is_numeric($raw)) {
$n = (float)$raw;
// Excel serial date -> unix timestamp
$ts = (int)round(($n - 25569) * 86400);
if ($ts > 0) {
return date('Y-m-d H:i:s', $ts);
}
return null;
}
$s = trim((string)$raw);
if ($s === '') {
return null;
}
// 1) strtotime 能解析很多格式
$ts = strtotime($s);
if ($ts !== false) {
return date('Y-m-d H:i:s', $ts);
}
// 2) 兼容 m/d/yy(如 10/13/25)
if (preg_match('#^(\d{1,2})/(\d{1,2})/(\d{2})$#', $s, $m)) {
$mm = (int)$m[1];
$dd = (int)$m[2];
$yy = (int)$m[3];
$year = 2000 + $yy; // FB 导出通常是 20xx
$ts2 = mktime(0, 0, 0, $mm, $dd, $year);
return date('Y-m-d H:i:s', $ts2);
}
// 3) 兜底:无法解析
return null;
}
}