Merge and modify 'pclzip' of https://github.com/bskrtich/PHPWord to make it work with the latest develop branch

This commit is contained in:
Ivan Lanin 2014-03-28 19:41:33 +07:00
commit 338ceabdf0
12 changed files with 6027 additions and 16 deletions

View File

@ -37,7 +37,7 @@ before_script:
script: script:
## PHP_CodeSniffer ## PHP_CodeSniffer
- phpcs --standard=PSR2 -n src/ - phpcs --standard=PSR2 -n src/ --ignore=src/PhpWord/Shared/PCLZip
- phpcs --standard=PSR2 -n tests/ - phpcs --standard=PSR2 -n tests/
## PHP Copy/Paste Detector ## PHP Copy/Paste Detector
#- php phpcpd.phar --verbose src/ #- php phpcpd.phar --verbose src/

View File

@ -16,6 +16,9 @@
<filter> <filter>
<whitelist> <whitelist>
<directory suffix=".php">./src</directory> <directory suffix=".php">./src</directory>
<exclude>
<directory suffix=".php">./src/PhpWord/Shared/PCLZip</directory>
</exclude>
</whitelist> </whitelist>
</filter> </filter>
</phpunit> </phpunit>

View File

@ -10,6 +10,7 @@
namespace PhpOffice\PhpWord\Reader; namespace PhpOffice\PhpWord\Reader;
use PhpOffice\PhpWord\PhpWord; use PhpOffice\PhpWord\PhpWord;
use PhpOffice\PhpWord\Settings;
use PhpOffice\PhpWord\DocumentProperties; use PhpOffice\PhpWord\DocumentProperties;
use PhpOffice\PhpWord\Exceptions\Exception; use PhpOffice\PhpWord\Exceptions\Exception;
@ -34,7 +35,8 @@ class Word2007 extends AbstractReader implements IReader
$return = false; $return = false;
// Load file // Load file
$zip = new \ZipArchive(); $zipClass = Settings::getZipClass();
$zip = new $zipClass();
if ($zip->open($pFilename) === true) { if ($zip->open($pFilename) === true) {
// check if it is an OOXML archive // check if it is an OOXML archive
$rels = simplexml_load_string($this->getFromZipArchive($zip, "_rels/.rels")); $rels = simplexml_load_string($this->getFromZipArchive($zip, "_rels/.rels"));
@ -59,7 +61,7 @@ class Word2007 extends AbstractReader implements IReader
/** /**
* Get zip content * Get zip content
* *
* @param \ZipArchive $archive * @param mixed $archive
* @param string $fileName * @param string $fileName
* @param bool $removeNamespace * @param bool $removeNamespace
* @return mixed * @return mixed
@ -101,7 +103,8 @@ class Word2007 extends AbstractReader implements IReader
// Initialisations // Initialisations
$word = new PhpWord(); $word = new PhpWord();
$zip = new \ZipArchive(); $zipClass = Settings::getZipClass();
$zip = new $zipClass();
$zip->open($pFilename); $zip->open($pFilename);
// Read properties and documents // Read properties and documents

View File

@ -17,7 +17,6 @@ use PhpOffice\PhpWord\Section\Link;
use PhpOffice\PhpWord\Section\ListItem; use PhpOffice\PhpWord\Section\ListItem;
use PhpOffice\PhpWord\Section\Object; use PhpOffice\PhpWord\Section\Object;
use PhpOffice\PhpWord\Section\PageBreak; use PhpOffice\PhpWord\Section\PageBreak;
use PhpOffice\PhpWord\Section\Settings;
use PhpOffice\PhpWord\Section\Table; use PhpOffice\PhpWord\Section\Table;
use PhpOffice\PhpWord\Section\Text; use PhpOffice\PhpWord\Section\Text;
use PhpOffice\PhpWord\Section\TextBreak; use PhpOffice\PhpWord\Section\TextBreak;
@ -75,7 +74,7 @@ class Section
public function __construct($sectionCount, $settings = null) public function __construct($sectionCount, $settings = null)
{ {
$this->_sectionCount = $sectionCount; $this->_sectionCount = $sectionCount;
$this->_settings = new Settings(); $this->_settings = new \PhpOffice\PhpWord\Section\Settings();
$this->setSettings($settings); $this->setSettings($settings);
} }

View File

@ -14,6 +14,10 @@ namespace PhpOffice\PhpWord;
*/ */
class Settings class Settings
{ {
/** Available Zip library classes */
const PCLZIP = 'PhpOffice\\PhpWord\\Shared\\ZipArchive';
const ZIPARCHIVE = 'ZipArchive';
/** /**
* Compatibility option for XMLWriter * Compatibility option for XMLWriter
* *
@ -21,6 +25,15 @@ class Settings
*/ */
private static $_xmlWriterCompatibility = true; private static $_xmlWriterCompatibility = true;
/**
* Name of the class used for Zip file management
* e.g.
* ZipArchive
*
* @var string
*/
private static $_zipClass = self::ZIPARCHIVE;
/** /**
* Set the compatibility option used by the XMLWriter * Set the compatibility option used by the XMLWriter
* *
@ -45,4 +58,34 @@ class Settings
{ {
return self::$_xmlWriterCompatibility; return self::$_xmlWriterCompatibility;
} }
/**
* Set the Zip handler Class that PHPWord should use for Zip file management (PCLZip or ZipArchive)
*
* @param string $zipClass The Zip handler class that PHPWord should use for Zip file management
* e.g. Settings::PCLZip or Settings::ZipArchive
* @return boolean Success or failure
*/
public static function setZipClass($zipClass)
{
if (($zipClass === self::PCLZIP) ||
($zipClass === self::ZIPARCHIVE)) {
self::$_zipClass = $zipClass;
return true;
}
return false;
} // function setZipClass()
/**
* Return the name of the Zip handler Class that PHPWord is configured to use (PCLZip or ZipArchive)
* or Zip file management
*
* @return string Name of the Zip handler Class that PHPWord is configured to use
* for Zip file management
* e.g. Settings::PCLZip or Settings::ZipArchive
*/
public static function getZipClass()
{
return self::$_zipClass;
} // function getZipClass()
} }

File diff suppressed because it is too large Load Diff

View File

@ -0,0 +1,204 @@
<?php
/**
* PHPWord
*
* @link https://github.com/PHPOffice/PHPWord
* @copyright 2014 PHPWord
* @license http://www.gnu.org/licenses/old-licenses/lgpl-2.1.txt LGPL
*/
namespace PhpOffice\PhpWord\Shared;
use PhpOffice\PhpWord\Exceptions\Exception;
// @codeCoverageIgnoreStart
if (!defined('PCLZIP_TEMPORARY_DIR')) {
// PCLZIP needs the temp path to end in a back slash
define('PCLZIP_TEMPORARY_DIR', sys_get_temp_dir() . '/');
}
require_once 'PCLZip/pclzip.lib.php';
// @codeCoverageIgnoreEnd
/**
* PCLZip wrapper
*
* @since 0.9.2
*/
class ZipArchive
{
/** constants */
const OVERWRITE = 'OVERWRITE';
const CREATE = 'CREATE';
/**
* Temporary storage directory
*
* @var string
*/
private $_tempDir;
/**
* Zip Archive Stream Handle
*
* @var string
*/
private $_zip;
/**
* Open a new zip archive
*
* @param string $fileName Filename for the zip archive
* @return boolean
*/
public function open($fileName)
{
$this->_tempDir = sys_get_temp_dir();
$this->_zip = new \PclZip($fileName);
return true;
}
/**
* Close this zip archive
*
* @codeCoverageIgnore
*/
public function close()
{
}
/**
* Add a new file to the zip archive.
*
* @param string $filename Directory/Name of the file to add to the zip archive
* @param string $localname Directory/Name of the file added to the zip
*/
public function addFile($filename, $localname = null)
{
$filename = realpath($filename);
$filenameParts = pathinfo($filename);
$localnameParts = pathinfo($localname);
// To Rename the file while adding it to the zip we
// need to create a temp file with the correct name
if ($filenameParts['basename'] != $localnameParts['basename']) {
$temppath = $this->_tempDir . '/' . $localnameParts['basename'];
copy($filename, $temppath);
$filename = $temppath;
$filenameParts = pathinfo($temppath);
}
$res = $this->_zip->add(
$filename,
PCLZIP_OPT_REMOVE_PATH,
$filenameParts['dirname'],
PCLZIP_OPT_ADD_PATH,
$localnameParts["dirname"]
);
if ($res == 0) {
throw new Exception("Error zipping files : " . $this->_zip->errorInfo(true));
return false;
}
return true;
}
/**
* Add a new file to the zip archive from a string of raw data.
*
* @param string $localname Directory/Name of the file to add to the zip archive
* @param string $contents String of data to add to the zip archive
*/
public function addFromString($localname, $contents)
{
$filenameParts = pathinfo($localname);
// Write $contents to a temp file
$handle = fopen($this->_tempDir . '/' . $filenameParts["basename"], "wb");
fwrite($handle, $contents);
fclose($handle);
// Add temp file to zip
$res = $this->_zip->add(
$this->_tempDir . '/' . $filenameParts["basename"],
PCLZIP_OPT_REMOVE_PATH,
$this->_tempDir,
PCLZIP_OPT_ADD_PATH,
$filenameParts["dirname"]
);
if ($res == 0) {
throw new Exception("Error zipping files : " . $this->_zip->errorInfo(true));
return false;
}
// Remove temp file
unlink($this->_tempDir . '/' . $filenameParts["basename"]);
return true;
}
/**
* Find if given fileName exist in archive (Emulate ZipArchive locateName())
*
* @param string $fileName Filename for the file in zip archive
* @return boolean
*/
public function locateName($fileName)
{
$list = $this->_zip->listContent();
$listCount = count($list);
$list_index = -1;
for ($i = 0; $i < $listCount; ++$i) {
if (strtolower($list[$i]["filename"]) == strtolower($fileName) ||
strtolower($list[$i]["stored_filename"]) == strtolower($fileName)) {
$list_index = $i;
break;
}
}
return ($list_index > -1);
}
/**
* Extract file from archive by given fileName (Emulate ZipArchive getFromName())
*
* @param string $fileName Filename for the file in zip archive
* @return string $contents File string contents
*/
public function getFromName($fileName)
{
$list = $this->_zip->listContent();
$listCount = count($list);
$list_index = -1;
for ($i = 0; $i < $listCount; ++$i) {
if (strtolower($list[$i]["filename"]) == strtolower($fileName) ||
strtolower($list[$i]["stored_filename"]) == strtolower($fileName)) {
$list_index = $i;
break;
}
}
$extracted = "";
if ($list_index != -1) {
$extracted = $this->_zip->extractByIndex($list_index, PCLZIP_OPT_EXTRACT_AS_STRING);
} else {
$filename = substr($fileName, 1);
$list_index = -1;
for ($i = 0; $i < $listCount; ++$i) {
if (strtolower($list[$i]["filename"]) == strtolower($fileName) ||
strtolower($list[$i]["stored_filename"]) == strtolower($fileName)) {
$list_index = $i;
break;
}
}
$extracted = $this->_zip->extractByIndex($list_index, PCLZIP_OPT_EXTRACT_AS_STRING);
}
if ((is_array($extracted)) && ($extracted != 0)) {
$contents = $extracted[0]["content"];
}
return $contents;
}
}

View File

@ -10,6 +10,7 @@
namespace PhpOffice\PhpWord\Shared; namespace PhpOffice\PhpWord\Shared;
use PhpOffice\PhpWord\Exceptions\Exception; use PhpOffice\PhpWord\Exceptions\Exception;
use PhpOffice\PhpWord\Settings;
/** /**
* Zip stream wrapper * Zip stream wrapper
@ -90,7 +91,8 @@ class ZipStreamWrapper
} }
// Open archive // Open archive
$this->_archive = new \ZipArchive(); $zipClass = Settings::getZipClass();
$this->_archive = new $zipClass();
$this->_archive->open($url['host']); $this->_archive->open($url['host']);
$this->_fileNameInArchive = $url['fragment']; $this->_fileNameInArchive = $url['fragment'];

View File

@ -10,6 +10,7 @@
namespace PhpOffice\PhpWord; namespace PhpOffice\PhpWord;
use PhpOffice\PhpWord\Exceptions\Exception; use PhpOffice\PhpWord\Exceptions\Exception;
use PhpOffice\PhpWord\Settings;
use PhpOffice\PhpWord\Shared\String; use PhpOffice\PhpWord\Shared\String;
/** /**
@ -57,7 +58,8 @@ class Template
throw new Exception("Could not copy the template from {$strFilename} to {$this->_tempFileName}."); throw new Exception("Could not copy the template from {$strFilename} to {$this->_tempFileName}.");
} }
$this->_objZip = new \ZipArchive(); $zipClass = Settings::getZipClass();
$this->_objZip = new $zipClass();
$this->_objZip->open($this->_tempFileName); $this->_objZip->open($this->_tempFileName);
$this->_documentXML = $this->_objZip->getFromName('word/document.xml'); $this->_documentXML = $this->_objZip->getFromName('word/document.xml');

View File

@ -12,6 +12,7 @@ namespace PhpOffice\PhpWord\Writer;
use PhpOffice\PhpWord\Exceptions\Exception; use PhpOffice\PhpWord\Exceptions\Exception;
use PhpOffice\PhpWord\PhpWord; use PhpOffice\PhpWord\PhpWord;
use PhpOffice\PhpWord\HashTable; use PhpOffice\PhpWord\HashTable;
use PhpOffice\PhpWord\Settings;
use PhpOffice\PhpWord\Writer\ODText\Content; use PhpOffice\PhpWord\Writer\ODText\Content;
use PhpOffice\PhpWord\Writer\ODText\Manifest; use PhpOffice\PhpWord\Writer\ODText\Manifest;
use PhpOffice\PhpWord\Writer\ODText\Meta; use PhpOffice\PhpWord\Writer\ODText\Meta;
@ -108,11 +109,23 @@ class ODText implements IWriter
// Create drawing dictionary // Create drawing dictionary
// Create new ZIP file and open it for writing // Create new ZIP file and open it for writing
$objZip = new \ZipArchive(); $zipClass = Settings::getZipClass();
$objZip = new $zipClass();
// Retrieve OVERWRITE and CREATE constants from the instantiated zip class
// This method of accessing constant values from a dynamic class should work with all appropriate versions of PHP
$ro = new \ReflectionObject($objZip);
$zipOverWrite = $ro->getConstant('OVERWRITE');
$zipCreate = $ro->getConstant('CREATE');
// Remove any existing file
if (file_exists($pFilename)) {
unlink($pFilename);
}
// Try opening the ZIP file // Try opening the ZIP file
if ($objZip->open($pFilename, \ZipArchive::OVERWRITE) !== true) { if ($objZip->open($pFilename, $zipOverWrite) !== true) {
if ($objZip->open($pFilename, \ZipArchive::CREATE) !== true) { if ($objZip->open($pFilename, $zipCreate) !== true) {
throw new Exception("Could not open " . $pFilename . " for writing."); throw new Exception("Could not open " . $pFilename . " for writing.");
} }
} }
@ -144,7 +157,8 @@ class ODText implements IWriter
$imagePath = substr($imagePath, 6); $imagePath = substr($imagePath, 6);
$imagePathSplitted = explode('#', $imagePath); $imagePathSplitted = explode('#', $imagePath);
$imageZip = new \ZipArchive(); $zipClass = Settings::getZipClass();
$imageZip = new $zipClass();
$imageZip->open($imagePathSplitted[0]); $imageZip->open($imagePathSplitted[0]);
$imageContents = $imageZip->getFromName($imagePathSplitted[1]); $imageContents = $imageZip->getFromName($imagePathSplitted[1]);
$imageZip->close(); $imageZip->close();

View File

@ -13,6 +13,7 @@ use PhpOffice\PhpWord\Exceptions\Exception;
use PhpOffice\PhpWord\PhpWord; use PhpOffice\PhpWord\PhpWord;
use PhpOffice\PhpWord\Footnote; use PhpOffice\PhpWord\Footnote;
use PhpOffice\PhpWord\Media; use PhpOffice\PhpWord\Media;
use PhpOffice\PhpWord\Settings;
use PhpOffice\PhpWord\Writer\Word2007\ContentTypes; use PhpOffice\PhpWord\Writer\Word2007\ContentTypes;
use PhpOffice\PhpWord\Writer\Word2007\DocProps; use PhpOffice\PhpWord\Writer\Word2007\DocProps;
use PhpOffice\PhpWord\Writer\Word2007\Document; use PhpOffice\PhpWord\Writer\Word2007\Document;
@ -117,16 +118,27 @@ class Word2007 implements IWriter
} }
// Create new ZIP file and open it for writing // Create new ZIP file and open it for writing
$objZip = new \ZipArchive(); $zipClass = Settings::getZipClass();
$objZip = new $zipClass();
// Retrieve OVERWRITE and CREATE constants from the instantiated zip class
// This method of accessing constant values from a dynamic class should work with all appropriate versions of PHP
$ro = new \ReflectionObject($objZip);
$zipOverWrite = $ro->getConstant('OVERWRITE');
$zipCreate = $ro->getConstant('CREATE');
// Remove any existing file
if (file_exists($pFilename)) {
unlink($pFilename);
}
// Try opening the ZIP file // Try opening the ZIP file
if ($objZip->open($pFilename, \ZipArchive::OVERWRITE) !== true) { if ($objZip->open($pFilename, $zipOverWrite) !== true) {
if ($objZip->open($pFilename, \ZipArchive::CREATE) !== true) { if ($objZip->open($pFilename, $zipCreate) !== true) {
throw new Exception("Could not open " . $pFilename . " for writing."); throw new Exception("Could not open " . $pFilename . " for writing.");
} }
} }
$sectionElements = array(); $sectionElements = array();
$_secElements = Media::getSectionMediaElements(); $_secElements = Media::getSectionMediaElements();
foreach ($_secElements as $element) { // loop through section media elements foreach ($_secElements as $element) { // loop through section media elements

View File

@ -0,0 +1,38 @@
<?php
/**
* PHPWord
*
* @link https://github.com/PHPOffice/PHPWord
* @copyright 2014 PHPWord
* @license http://www.gnu.org/licenses/old-licenses/lgpl-2.1.txt LGPL
*/
namespace PhpOffice\PhpWord\Tests\Shared;
use PhpOffice\PhpWord\Shared\ZipArchive;
/**
* Test class for PhpOffice\PhpWord\Shared\ZipArchive
*
* @runTestsInSeparateProcesses
*/
class ZipArchiveTest extends \PHPUnit_Framework_TestCase
{
/**
* Test add from file and string
*/
public function testAdd()
{
$existingFile = __DIR__ . "/../_files/documents/sheet.xls";
$zipFile = __DIR__ . "/../_files/documents/ziptest.zip";
$object = new ZipArchive();
$object->open($zipFile);
$object->addFile($existingFile, 'xls/new.xls');
$object->addFromString('content/string.txt', 'Test');
$this->assertTrue($object->locateName('xls/new.xls'));
$this->assertEquals('Test', $object->getFromName('content/string.txt'));
unlink($zipFile);
}
}