PHPWord保存文件save方法 “Could not close zip file.”错误,及中文处理

文章讲述了在接手一个不再维护的老PHP项目时,遇到使用PHPWord库生成docx文档的需求。由于PHPWord版本较旧,没有TemplateProcessor类,作者使用Template类并遇到Couldnotclosezipfile.错误。通过检查和创建缺失目录解决了该问题,然后发现文档内容为空和中文替换失败的问题,分别通过修正document.xml路径和处理中文编码来解决。
摘要由CSDN通过智能技术生成

        这是一个老的PHP项目,上家公司不维护了,我们公司接手过来,而我领到了一个导出word文档的需求,而项目中已经有PHPWord(ps:是个老版本,还不知道有没有改过),所以直接使用项目中的PHPWord来实现。

        写了一个公共的方法,使用一个模板来生成docx文档(ps:文档统一使用docx的格式,看网上的说法,使用doc格式有问题,没有求证),这里由于PHPWord的版本较老,没有网上常提到的TemplateProcessor类,但有Template类可以使用。

/**
 * 自定义docx文档生成
 * @param $docxTemplatePath docx文档模板路径 (含文件名及文件后缀)
 * @param $docxDownloadPath 生成docx文档目录 (用于docx文档下载)
 * @param $fileName         生成docx文档名称 (含文件后缀)
 * @param $data             用于替换模板标记的数据
 * @return void
 * @throws Exception
 */
function DocxGeneration($docxTemplatePath, $docxDownloadPath, $fileName, $data) {
    require_once('./ThinkPHP/Library/Vendor/PHPWord/PhpWord.php');
    require_once('./ThinkPHP/Library/Vendor/PHPWord/PHPWord/Autoloader.php');
    require_once('./ThinkPHP/Library/Vendor/PHPWord/PHPWord/Template.php');

    $tmp = new Template($docxTemplatePath);

    // data = array(key1=>value1, key2=>value2);
    foreach ($data as $key => $val) {
        $tmp->setValue($key, $val);
    }
    
    $tmp->save($docxDownloadPath . "/" .$fileName);
}

        但在最后使用save方法进行文件保存的时候报了一个“Could not close zip file.”的错误,于是打断点在Template类中找到抛出错误的地方。

// Close zip file
if($this->_objZip->close() === false) {
    throw new Exception('Could not close zip file.');
}

        但从这里提供的信息太少,网上的答案是没有权限,但是我把存储模板和存放文档的目录权限开放,依旧没有解决这个问题,直到我看到了这个对象要使用的一个目录路径,而项目中却没有这个目录,这肯定会出现错误,于是我手动的创建了这个目录,“Could not close zip file.”的问题就解决了!

         然而却没有在指定的目录下生成文档,也无法替换模板中的标记,进过反复调试,找到两处原因。

一:是获取document.xml的路径错误,导致生成文档内容为空,Template类中写的是document2.xml,修改为document.xml。

$this->_documentXML = $this->_objZip->getFromName('word/document2.xml');// 改为document.xml

二:中文文件名和中文值导致无法保存和替换模板中的标记,通过对文件名和替换数据设置编码格式解决。

// Template类中,save方法最后rename文件前,对中文文件名处理
$strFilename = iconv('utf-8' , 'gbk' ,$strFilename);

// Template类中,setValue方法在对模板文档进行标记替换前,对中文数据处理
$replace = iconv('utf-8', 'GB2312//IGNORE', $replace);
$replace = iconv('gbk', 'utf-8', $replace);

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 1
    评论
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值