feat: 新增 Docker 部署支持、Swoole/Octane 集成及相关优化

- 添加 Dockerfile 与多套 docker-compose 配置(开发/生产环境)
- 集成 Laravel Octane (Swoole) 提升性能
- 新增健康检查、监控脚本及部署文档
- 新增 Docker 镜像离线导入包(MySQL/Redis/Meilisearch)
- 优化文档转换、预览服务及队列任务
- 添加 CreateAdminUser 命令与路由健康检查接口
- 新增 Swoole 队列兼容性测试套件

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
This commit is contained in:
2026-02-28 15:51:19 +08:00
parent acf549c43c
commit 3c206e9e06
90 changed files with 12731 additions and 1255 deletions

View File

@@ -85,9 +85,16 @@ class DocumentConversionService
throw new \Exception("文档文件不存在: {$documentPath}");
}
// 创建临时工作目录
$tempDir = sys_get_temp_dir() . '/pandoc_' . uniqid();
mkdir($tempDir, 0755, true);
// 使用 Laravel 存储系统创建临时工作目录
$tempDirName = 'temp/pandoc_' . uniqid();
// 确保临时目录存在
if (!Storage::disk('local')->exists('temp')) {
Storage::disk('local')->makeDirectory('temp');
}
Storage::disk('local')->makeDirectory($tempDirName);
$tempDir = Storage::disk('local')->path($tempDirName);
$tempOutputPath = $tempDir . '/output.md';
@@ -128,10 +135,11 @@ class DocumentConversionService
'markdown' => $markdown,
'mediaDir' => $hasMedia ? $mediaDir : null,
'tempDir' => $tempDir,
'tempDirName' => $tempDirName, // 添加相对路径名
];
} catch (\Exception $e) {
// 清理临时目录
$this->deleteDirectory($tempDir);
Storage::disk('local')->deleteDirectory($tempDirName);
throw $e;
}
}

View File

@@ -92,15 +92,22 @@ class DocumentPreviewService
// 创建 HTML Writer
$htmlWriter = IOFactory::createWriter($phpWord, 'HTML');
// 将内容写入临时文件
$tempHtmlFile = tempnam(sys_get_temp_dir(), 'doc_preview_') . '.html';
$htmlWriter->save($tempHtmlFile);
// 使用 Laravel 存储系统创建临时文件
$tempFileName = 'temp/doc_preview_' . uniqid() . '.html';
// 确保临时目录存在
if (!Storage::disk('local')->exists('temp')) {
Storage::disk('local')->makeDirectory('temp');
}
$tempHtmlPath = Storage::disk('local')->path($tempFileName);
$htmlWriter->save($tempHtmlPath);
// 读取 HTML 内容
$htmlContent = file_get_contents($tempHtmlFile);
$htmlContent = Storage::disk('local')->get($tempFileName);
// 删除临时文件
unlink($tempHtmlFile);
Storage::disk('local')->delete($tempFileName);
// 将图片嵌入为 base64
$htmlContent = $this->embedImagesInHtml($htmlContent, $images);