diff --git a/application/api/controller/Production.php b/application/api/controller/Production.php index 72b7a51..62c4776 100644 --- a/application/api/controller/Production.php +++ b/application/api/controller/Production.php @@ -4100,7 +4100,7 @@ class Production extends Base */ public function createArticlePdf($aParam = []){ - //获取参数 + //获取参数 $aParam = empty($aParam) ? $this->request->post() : $aParam; //必填值验证 @@ -4115,69 +4115,14 @@ class Production extends Base if(empty($aProductionArticle)){ return json_encode(array('status' => 3,'msg' => 'No articles found' )); } - - //内容 - $oLatexContent = new \app\common\LatexContent; - - //内容生成 - //获取第一页内容 - $aResult = $oLatexContent->buildFirst($aProductionArticle); - $iStatus = empty($aResult['status']) ? 0 : $aResult['status']; - $sMsg = empty($aResult['msg']) ? 'Content generation failed-First' : $aResult['msg']; - $sFirstTemplateInfo = empty($aResult['data']) ? '' : $aResult['data']; - - if($iStatus != 1){ - return json_encode(array('status' => 4,'msg' => $sMsg)); + //关联文章ID + $iArticleId = empty($aProductionArticle['article_id']) ? 0 : $aProductionArticle['article_id']; + if(empty($iArticleId)){ + return json_encode(array('status' => 4,'msg' => 'Unbound article' )); } - if(empty($sFirstTemplateInfo)){ - return json_encode(array('status' => 5,'msg' => 'Article content retrieval failed')); - } - - //获取参考文献 - $aResult = $this->creatReferences($aProductionArticle); - $iStatus = empty($aResult['status']) ? 0 : $aResult['status']; - $sMsg = empty($aResult['msg']) ? 'Content generation failed-Reference' : $aResult['msg']; - $aResult = empty($aResult['data']) ? [] : $aResult['data']; - $sReferences = empty($aResult['references']) ? '' : $aResult['references'];//参考文献内容 - $aReferencesLists = empty($aResult['references_list']) ? [] : $aResult['references_list'];//参考文献数组 - if($iStatus != 1){ - return json_encode(array('status' => 8,'msg' => $sMsg)); - } - if(empty($sReferences)){ - return json_encode(array('status' => 9,'msg' => 'Article content retrieval failed')); - } - - //生成主内容 - $aResult = $oLatexContent->buildMain(['production_article' => $aProductionArticle,'references' => $aReferencesLists]); - $iStatus = empty($aResult['status']) ? 0 : $aResult['status']; - $sMsg = empty($aResult['msg']) ? 'Content generation failed-Main' : $aResult['msg']; - $sMainTemplateInfo = empty($aResult['data']) ? '' : $aResult['data']; - if($iStatus != 1){ - return json_encode(array('status' => 6,'msg' => $sMsg)); - } - if(empty($sMainTemplateInfo)){ - return json_encode(array('status' => 7,'msg' => 'Article content retrieval failed')); - } - - //创建基础目录 - $sDir = ROOT_PATH . 'public' . DS . 'latex' . DS . 'tex_' . $iPArticleId; - if (!is_dir($sDir)) { - mkdir($sDir, 0755, true); - } - - //生成Reference文件 - $sFileUrl = $sDir. DS . 'references_' . $iPArticleId . '.bib'; - file_put_contents($sFileUrl, $sReferences); - if(!file_exists($sFileUrl)){ - return json_encode(array('status' => 10,'msg' => 'Reference file generation failed')); - } - - //生成运行文件.tex - $sTexName = 'article_' . $iPArticleId; - $sTexFileUrl = $sDir. DS . $sTexName .'.tex'; - $sTemplateInfo = $sFirstTemplateInfo."\n".$sMainTemplateInfo; - file_put_contents($sTexFileUrl, $sTemplateInfo); - return json_encode(array('status' => 1,'msg' => 'PDF generated successfully')); + //调用生成Tex队列 + Queue::push('app\api\job\ArticleCreateTex@fire', ['p_article_id' => $iPArticleId], 'ArticleCreateTex'); + return json_encode(array('status' => 1,'msg' => 'PDF generation in progress, please wait')); } /** @@ -4220,7 +4165,7 @@ class Production extends Base * 生成初稿-处理正文内容表格/图片相关联 * @param p_article_id 生产环境文章信息 */ - public function dealMainFigureOrTable(){ + public function dealMainFigureOrTable($aParam = []){ //获取参数 $aParam = empty($aParam) ? $this->request->post() : $aParam; @@ -4237,11 +4182,11 @@ class Production extends Base return json_encode(array('status' => 3,'msg' => 'The content is empty' )); } //查询图片信息 - $aWhere = ['article_id' => $iArticleId,'type' => 1,'state' => 0]; - $aImageMain = Db::name('article_main')->where($aWhere)->order('sort asc')->column('ami_id'); - //查询图片信息 - $aWhere = ['article_id' => $iArticleId,'type' => 2,'state' => 0]; - $aTableMain = Db::name('article_main')->where($aWhere)->order('sort asc')->column('amt_id'); + $aWhere = ['article_id' => $iArticleId,'state' => 0]; + $aImageMain = Db::name('article_main_image')->where($aWhere)->order('ami_id asc')->column('ami_id'); + //查询表格信息 + $aWhere = ['article_id' => $iArticleId,'state' => 0]; + $aTableMain = Db::name('article_main_table')->where($aWhere)->order('amt_id asc')->column('amt_id'); //数据处理 $aUpdate = []; @@ -4284,4 +4229,211 @@ class Production extends Base return json_encode(array('status' => 1,'msg' => 'success')); } + /** + * 生成latex .tex文件 + * @param article_id 文章ID + */ + public function execCreateTex($aParam = []){ + + //获取参数 + $aParam = empty($aParam) ? $this->request->post() : $aParam; + + //必填值验证 + $iPArticleId = empty($aParam['p_article_id']) ? '' : $aParam['p_article_id']; + if(empty($iPArticleId)){ + return json_encode(array('status' => 2,'msg' => 'Please select an article' )); + } + + //查询文章 + $aWhere = ['p_article_id' => $iPArticleId,'state' => ['in',[0,2]]]; + $aProductionArticle = Db::name('production_article')->where($aWhere)->find(); + if(empty($aProductionArticle)){ + return json_encode(array('status' => 3,'msg' => 'No articles found' )); + } + //关联文章ID + $iArticleId = empty($aProductionArticle['article_id']) ? 0 : $aProductionArticle['article_id']; + if(empty($iArticleId)){ + return json_encode(array('status' => 4,'msg' => 'Unbound article' )); + } + //内容 + $oLatexContent = new \app\common\LatexContent; + + //内容生成 + //获取第一页内容 + $aResult = $oLatexContent->buildFirst($aProductionArticle); + $iStatus = empty($aResult['status']) ? 0 : $aResult['status']; + $sMsg = empty($aResult['msg']) ? 'Content generation failed-First' : $aResult['msg']; + $sFirstTemplateInfo = empty($aResult['data']) ? '' : $aResult['data']; + + if($iStatus != 1){ + return json_encode(array('status' => 5,'msg' => $sMsg)); + } + if(empty($sFirstTemplateInfo)){ + return json_encode(array('status' => 6,'msg' => 'Article content retrieval failed')); + } + + //获取参考文献 + $aResult = $this->creatReferences($aProductionArticle); + $iStatus = empty($aResult['status']) ? 0 : $aResult['status']; + $sMsg = empty($aResult['msg']) ? 'Content generation failed-Reference' : $aResult['msg']; + $aResult = empty($aResult['data']) ? [] : $aResult['data']; + $sReferences = empty($aResult['references']) ? '' : $aResult['references'];//参考文献内容 + $aReferencesLists = empty($aResult['references_list']) ? [] : $aResult['references_list'];//参考文献数组 + if($iStatus != 1){ + return json_encode(array('status' => 8,'msg' => $sMsg)); + } + if(empty($sReferences)){ + return json_encode(array('status' => 9,'msg' => 'Article content retrieval failed')); + } + + //生成主内容 + $aResult = $oLatexContent->buildMain(['production_article' => $aProductionArticle,'references' => $aReferencesLists]); + $iStatus = empty($aResult['status']) ? 0 : $aResult['status']; + $sMsg = empty($aResult['msg']) ? 'Content generation failed-Main' : $aResult['msg']; + $sMainTemplateInfo = empty($aResult['data']) ? '' : $aResult['data']; + if($iStatus != 1){ + return json_encode(array('status' => 6,'msg' => $sMsg)); + } + if(empty($sMainTemplateInfo)){ + return json_encode(array('status' => 7,'msg' => 'Article content retrieval failed')); + } + + //创建基础目录 + $sDir = ROOT_PATH . 'public' . DS . 'latex' . DS . 'tex_' . $iArticleId; + if (!is_dir($sDir)) { + mkdir($sDir, 0755, true); + } + + //生成Reference文件 + $sFileUrl = $sDir. DS . 'references_' . $iArticleId . '.bib'; + file_put_contents($sFileUrl, $sReferences); + if(!file_exists($sFileUrl)){ + return json_encode(array('status' => 10,'msg' => 'Reference file generation failed')); + } + //生成运行文件.tex + $sTexName = 'article_' . $iArticleId; + $sTexFileUrl = $sDir. DS . $sTexName .'.tex'; + $sTemplateInfo = $sFirstTemplateInfo."\n".$sMainTemplateInfo; + file_put_contents($sTexFileUrl, $sTemplateInfo); + if(!file_exists($sTexFileUrl)){ + return json_encode(array('status' => 11,'msg' => 'tex file generation failed')); + } + //调用生成PDF队列 + $queue = Queue::push('app\api\job\ArticleCreatePdf@fire', ['p_article_id' => $iPArticleId], 'ArticleCreatePdf'); + //生成长表格PDF + $aLongTableId = empty($aResult['long_table_id']) ? [] : $aResult['long_table_id']; + var_dump($aLongTableId); + if(!empty($aLongTableId)){ //调用生成长表格队列 + $longtablequeue = Queue::push('app\api\job\ArticleCreateLongTable@fire', ['p_article_id' => $iPArticleId,'long_table_id' => $aLongTableId], 'ArticleCreateLongTable'); + var_dump($longtablequeue); + } + return json_encode(array('status' => 1,'msg' => 'tex file generated successfully')); + } + + /** + * 命令行生成PDF + * @param article_id 文章ID + */ + public function execCreatePdf($aParam = []){ + + //获取参数 + $aParam = empty($aParam) ? $this->request->post() : $aParam; + + //必填值验证 + $iPArticleId = empty($aParam['p_article_id']) ? '' : $aParam['p_article_id']; + if(empty($iPArticleId)){ + return json_encode(array('status' => 2,'msg' => 'Please select an article' )); + } + + //查询文章 + $aWhere = ['p_article_id' => $iPArticleId,'state' => ['in',[0,2]]]; + $aProductionArticle = Db::name('production_article')->field('article_id,pdf_id')->where($aWhere)->find(); + if(empty($aProductionArticle)){ + return json_encode(array('status' => 3,'msg' => 'No articles found' )); + } + $iArticleId = empty($aProductionArticle['article_id']) ? 0 : $aProductionArticle['article_id']; + if(empty($iArticleId)){ + return json_encode(array('status' => 4,'msg' => 'Unbound article' )); + } + //日志查询 + if(!empty($aProductionArticle['pdf_id'])){ + $aWhere = ['article_id' => $iArticleId,'p_article_id' => $iPArticleId,'pdf_id' => $aProductionArticle['pdf_id']]; + $aPdf = Db::name('production_article_pdf')->field('url')->where($aWhere)->find(); + $sPdfUrl = empty($aPdf['url']) ? '' : trim(basename($aPdf['url']),'.pdf'); + } + + //验证参考文献Reference文件是否存在 + $sDir = ROOT_PATH . 'public' . DS . 'latex' . DS . 'tex_' . $iArticleId; + $sFileUrl = $sDir. DS . 'references_' . $iArticleId . '.bib'; + if(!file_exists($sFileUrl)){ + return json_encode(array('status' => 4,'msg' => 'Reference file generation failed')); + } + + //验证生成运行文件.tex是否存在 + $sTexName = 'article_' . $iArticleId; + $sTexFileUrl = $sDir. DS . $sTexName .'.tex'; + if(!file_exists($sTexFileUrl)){ + return json_encode(array('status' => 5,'msg' => 'Latex.tex file not generated')); + } + + //命令行生成PDF + $aOutput = []; + $iReturnCode = 0; + $sLatexDir = '/usr/bin/';//'/usr/bin/';//latex执行目录 + $sPdfName = $sTexName.'_'.uniqid();//PDF文件名 + + //切换目录 + chdir($sDir); + + //清理所有编译缓存文件 + if(!empty($sPdfUrl)){ + $delFiles = [ + "{$sPdfUrl}.aux", "{$sPdfUrl}.bbl", "{$sPdfUrl}.blg", + "{$sPdfUrl}.bcf", "{$sPdfUrl}.run.xml", "{$sPdfUrl}.log", + "{$sPdfUrl}.out", "{$sPdfUrl}.toc" + ]; + foreach ($delFiles as $file) { + if(!file_exists($file)){ + continue; + } + unlink($file); + } + } + + $sPdfFilePath = $sDir. DS . $sPdfName.'.pdf'; + // 编译命令 + $command = "{$sLatexDir}xelatex -interaction=nonstopmode -jobname={$sPdfName} -file-line-error {$sTexName}.tex 2>&1 ; "; + //生成参考文献 + $command .= "{$sLatexDir}biber --debug --logfile={$sDir}/biber_error.log --input-directory={$sDir} --output-directory={$sDir} {$sPdfName} 2>&1 ; "; + $command .= "{$sLatexDir}xelatex -interaction=nonstopmode -jobname={$sPdfName} -file-line-error {$sTexName}.tex 2>&1 ; "; + $command .= "{$sLatexDir}xelatex -interaction=nonstopmode -jobname={$sPdfName} -file-line-error {$sTexName}.tex 2>&1"; + //执行命令并获取结果 + exec($command, $aOutput, $iReturnCode); + $sOutput = implode("\n", $aOutput); + //验证是否生成 + if (!in_array($iReturnCode,[0,1])) { + return json_encode(array('status' => 6,'msg' => 'PDF generation failed:'.$iReturnCode)); + } + if(!file_exists($sPdfFilePath)){ + return json_encode(array('status' => 7,'msg' => 'PDF generation failed')); + } + + //写入日志 + Db::startTrans(); + $sUrl = str_replace(ROOT_PATH . 'public' , '', $sPdfFilePath); + $aInsert = ['article_id' => $iArticleId,'p_article_id' => $iPArticleId,'url' => trim($sUrl,'/'),'create_time' => time()]; + $iId = Db::name('production_article_pdf')->insertGetId($aInsert); + if(empty($iId)){ + return json_encode(['status' => 8,'msg' => 'Log insertion failed']); + } + //更新生产表关联ID + $aUpdate = ['pdf_id' => $iId]; + $aWhere = ['p_article_id' => $iPArticleId]; + $update_result = DB::name('production_article')->where($aWhere)->limit(1)->update($aUpdate); + if($update_result === false){ + return json_encode(['status' => 9,'msg' => 'Log insertion failed']); + } + Db::commit(); + return json_encode(array('status' => 1,'msg' => 'PDF generated successfully')); + } }