正在显示
22 个修改的文件
包含
4699 行增加
和
0 行删除
vendor/phpoffice/phpexcel/.gitattributes
0 → 100644
vendor/phpoffice/phpexcel/.gitignore
0 → 100644
vendor/phpoffice/phpexcel/.travis.yml
0 → 100644
1 | +language: php | ||
2 | + | ||
3 | +php: | ||
4 | + - 5.4 | ||
5 | + - 5.5 | ||
6 | + - 5.6 | ||
7 | + - 7.0 | ||
8 | + - hhvm | ||
9 | + | ||
10 | +matrix: | ||
11 | + allow_failures: | ||
12 | + - php: hhvm | ||
13 | + | ||
14 | +before_script: | ||
15 | + ## Packages | ||
16 | + - sudo apt-get -qq update > /dev/null | ||
17 | + ## Composer | ||
18 | + - composer self-update | ||
19 | + - composer install --prefer-source --dev | ||
20 | + - phpenv global "$TRAVIS_PHP_VERSION" | ||
21 | + | ||
22 | +script: | ||
23 | + ## PHP_CodeSniffer | ||
24 | + - ./vendor/bin/phpcs --report-width=200 --report-summary --report-full Classes/ unitTests/ --standard=PSR2 -n | ||
25 | + ## PHPUnit | ||
26 | + - phpunit -c ./unitTests/ | ||
27 | + | ||
28 | +notifications: | ||
29 | + email: false |
1 | +<?php | ||
2 | + | ||
3 | +/** PHPExcel root directory */ | ||
4 | +if (!defined('PHPEXCEL_ROOT')) { | ||
5 | + define('PHPEXCEL_ROOT', dirname(__FILE__) . '/'); | ||
6 | + require(PHPEXCEL_ROOT . 'PHPExcel/Autoloader.php'); | ||
7 | +} | ||
8 | + | ||
9 | +/** | ||
10 | + * PHPExcel | ||
11 | + * | ||
12 | + * Copyright (c) 2006 - 2015 PHPExcel | ||
13 | + * | ||
14 | + * This library is free software; you can redistribute it and/or | ||
15 | + * modify it under the terms of the GNU Lesser General Public | ||
16 | + * License as published by the Free Software Foundation; either | ||
17 | + * version 2.1 of the License, or (at your option) any later version. | ||
18 | + * | ||
19 | + * This library is distributed in the hope that it will be useful, | ||
20 | + * but WITHOUT ANY WARRANTY; without even the implied warranty of | ||
21 | + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU | ||
22 | + * Lesser General Public License for more details. | ||
23 | + * | ||
24 | + * You should have received a copy of the GNU Lesser General Public | ||
25 | + * License along with this library; if not, write to the Free Software | ||
26 | + * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA | ||
27 | + * | ||
28 | + * @category PHPExcel | ||
29 | + * @package PHPExcel | ||
30 | + * @copyright Copyright (c) 2006 - 2015 PHPExcel (http://www.codeplex.com/PHPExcel) | ||
31 | + * @license http://www.gnu.org/licenses/old-licenses/lgpl-2.1.txt LGPL | ||
32 | + * @version ##VERSION##, ##DATE## | ||
33 | + */ | ||
34 | +class PHPExcel | ||
35 | +{ | ||
36 | + /** | ||
37 | + * Unique ID | ||
38 | + * | ||
39 | + * @var string | ||
40 | + */ | ||
41 | + private $uniqueID; | ||
42 | + | ||
43 | + /** | ||
44 | + * Document properties | ||
45 | + * | ||
46 | + * @var PHPExcel_DocumentProperties | ||
47 | + */ | ||
48 | + private $properties; | ||
49 | + | ||
50 | + /** | ||
51 | + * Document security | ||
52 | + * | ||
53 | + * @var PHPExcel_DocumentSecurity | ||
54 | + */ | ||
55 | + private $security; | ||
56 | + | ||
57 | + /** | ||
58 | + * Collection of Worksheet objects | ||
59 | + * | ||
60 | + * @var PHPExcel_Worksheet[] | ||
61 | + */ | ||
62 | + private $workSheetCollection = array(); | ||
63 | + | ||
64 | + /** | ||
65 | + * Calculation Engine | ||
66 | + * | ||
67 | + * @var PHPExcel_Calculation | ||
68 | + */ | ||
69 | + private $calculationEngine; | ||
70 | + | ||
71 | + /** | ||
72 | + * Active sheet index | ||
73 | + * | ||
74 | + * @var integer | ||
75 | + */ | ||
76 | + private $activeSheetIndex = 0; | ||
77 | + | ||
78 | + /** | ||
79 | + * Named ranges | ||
80 | + * | ||
81 | + * @var PHPExcel_NamedRange[] | ||
82 | + */ | ||
83 | + private $namedRanges = array(); | ||
84 | + | ||
85 | + /** | ||
86 | + * CellXf supervisor | ||
87 | + * | ||
88 | + * @var PHPExcel_Style | ||
89 | + */ | ||
90 | + private $cellXfSupervisor; | ||
91 | + | ||
92 | + /** | ||
93 | + * CellXf collection | ||
94 | + * | ||
95 | + * @var PHPExcel_Style[] | ||
96 | + */ | ||
97 | + private $cellXfCollection = array(); | ||
98 | + | ||
99 | + /** | ||
100 | + * CellStyleXf collection | ||
101 | + * | ||
102 | + * @var PHPExcel_Style[] | ||
103 | + */ | ||
104 | + private $cellStyleXfCollection = array(); | ||
105 | + | ||
106 | + /** | ||
107 | + * hasMacros : this workbook have macros ? | ||
108 | + * | ||
109 | + * @var bool | ||
110 | + */ | ||
111 | + private $hasMacros = false; | ||
112 | + | ||
113 | + /** | ||
114 | + * macrosCode : all macros code (the vbaProject.bin file, this include form, code, etc.), null if no macro | ||
115 | + * | ||
116 | + * @var binary | ||
117 | + */ | ||
118 | + private $macrosCode; | ||
119 | + /** | ||
120 | + * macrosCertificate : if macros are signed, contains vbaProjectSignature.bin file, null if not signed | ||
121 | + * | ||
122 | + * @var binary | ||
123 | + */ | ||
124 | + private $macrosCertificate; | ||
125 | + | ||
126 | + /** | ||
127 | + * ribbonXMLData : null if workbook is'nt Excel 2007 or not contain a customized UI | ||
128 | + * | ||
129 | + * @var null|string | ||
130 | + */ | ||
131 | + private $ribbonXMLData; | ||
132 | + | ||
133 | + /** | ||
134 | + * ribbonBinObjects : null if workbook is'nt Excel 2007 or not contain embedded objects (picture(s)) for Ribbon Elements | ||
135 | + * ignored if $ribbonXMLData is null | ||
136 | + * | ||
137 | + * @var null|array | ||
138 | + */ | ||
139 | + private $ribbonBinObjects; | ||
140 | + | ||
141 | + /** | ||
142 | + * The workbook has macros ? | ||
143 | + * | ||
144 | + * @return boolean true if workbook has macros, false if not | ||
145 | + */ | ||
146 | + public function hasMacros() | ||
147 | + { | ||
148 | + return $this->hasMacros; | ||
149 | + } | ||
150 | + | ||
151 | + /** | ||
152 | + * Define if a workbook has macros | ||
153 | + * | ||
154 | + * @param boolean $hasMacros true|false | ||
155 | + */ | ||
156 | + public function setHasMacros($hasMacros = false) | ||
157 | + { | ||
158 | + $this->hasMacros = (bool) $hasMacros; | ||
159 | + } | ||
160 | + | ||
161 | + /** | ||
162 | + * Set the macros code | ||
163 | + * | ||
164 | + * @param string $MacrosCode string|null | ||
165 | + */ | ||
166 | + public function setMacrosCode($MacrosCode = null) | ||
167 | + { | ||
168 | + $this->macrosCode=$MacrosCode; | ||
169 | + $this->setHasMacros(!is_null($MacrosCode)); | ||
170 | + } | ||
171 | + | ||
172 | + /** | ||
173 | + * Return the macros code | ||
174 | + * | ||
175 | + * @return string|null | ||
176 | + */ | ||
177 | + public function getMacrosCode() | ||
178 | + { | ||
179 | + return $this->macrosCode; | ||
180 | + } | ||
181 | + | ||
182 | + /** | ||
183 | + * Set the macros certificate | ||
184 | + * | ||
185 | + * @param string|null $Certificate | ||
186 | + */ | ||
187 | + public function setMacrosCertificate($Certificate = null) | ||
188 | + { | ||
189 | + $this->macrosCertificate=$Certificate; | ||
190 | + } | ||
191 | + | ||
192 | + /** | ||
193 | + * Is the project signed ? | ||
194 | + * | ||
195 | + * @return boolean true|false | ||
196 | + */ | ||
197 | + public function hasMacrosCertificate() | ||
198 | + { | ||
199 | + return !is_null($this->macrosCertificate); | ||
200 | + } | ||
201 | + | ||
202 | + /** | ||
203 | + * Return the macros certificate | ||
204 | + * | ||
205 | + * @return string|null | ||
206 | + */ | ||
207 | + public function getMacrosCertificate() | ||
208 | + { | ||
209 | + return $this->macrosCertificate; | ||
210 | + } | ||
211 | + | ||
212 | + /** | ||
213 | + * Remove all macros, certificate from spreadsheet | ||
214 | + * | ||
215 | + */ | ||
216 | + public function discardMacros() | ||
217 | + { | ||
218 | + $this->hasMacros=false; | ||
219 | + $this->macrosCode=null; | ||
220 | + $this->macrosCertificate=null; | ||
221 | + } | ||
222 | + | ||
223 | + /** | ||
224 | + * set ribbon XML data | ||
225 | + * | ||
226 | + */ | ||
227 | + public function setRibbonXMLData($Target = null, $XMLData = null) | ||
228 | + { | ||
229 | + if (!is_null($Target) && !is_null($XMLData)) { | ||
230 | + $this->ribbonXMLData = array('target' => $Target, 'data' => $XMLData); | ||
231 | + } else { | ||
232 | + $this->ribbonXMLData = null; | ||
233 | + } | ||
234 | + } | ||
235 | + | ||
236 | + /** | ||
237 | + * retrieve ribbon XML Data | ||
238 | + * | ||
239 | + * return string|null|array | ||
240 | + */ | ||
241 | + public function getRibbonXMLData($What = 'all') //we need some constants here... | ||
242 | + { | ||
243 | + $ReturnData = null; | ||
244 | + $What = strtolower($What); | ||
245 | + switch ($What){ | ||
246 | + case 'all': | ||
247 | + $ReturnData = $this->ribbonXMLData; | ||
248 | + break; | ||
249 | + case 'target': | ||
250 | + case 'data': | ||
251 | + if (is_array($this->ribbonXMLData) && array_key_exists($What, $this->ribbonXMLData)) { | ||
252 | + $ReturnData = $this->ribbonXMLData[$What]; | ||
253 | + } | ||
254 | + break; | ||
255 | + } | ||
256 | + | ||
257 | + return $ReturnData; | ||
258 | + } | ||
259 | + | ||
260 | + /** | ||
261 | + * store binaries ribbon objects (pictures) | ||
262 | + * | ||
263 | + */ | ||
264 | + public function setRibbonBinObjects($BinObjectsNames = null, $BinObjectsData = null) | ||
265 | + { | ||
266 | + if (!is_null($BinObjectsNames) && !is_null($BinObjectsData)) { | ||
267 | + $this->ribbonBinObjects = array('names' => $BinObjectsNames, 'data' => $BinObjectsData); | ||
268 | + } else { | ||
269 | + $this->ribbonBinObjects = null; | ||
270 | + } | ||
271 | + } | ||
272 | + /** | ||
273 | + * return the extension of a filename. Internal use for a array_map callback (php<5.3 don't like lambda function) | ||
274 | + * | ||
275 | + */ | ||
276 | + private function getExtensionOnly($ThePath) | ||
277 | + { | ||
278 | + return pathinfo($ThePath, PATHINFO_EXTENSION); | ||
279 | + } | ||
280 | + | ||
281 | + /** | ||
282 | + * retrieve Binaries Ribbon Objects | ||
283 | + * | ||
284 | + */ | ||
285 | + public function getRibbonBinObjects($What = 'all') | ||
286 | + { | ||
287 | + $ReturnData = null; | ||
288 | + $What = strtolower($What); | ||
289 | + switch($What) { | ||
290 | + case 'all': | ||
291 | + return $this->ribbonBinObjects; | ||
292 | + break; | ||
293 | + case 'names': | ||
294 | + case 'data': | ||
295 | + if (is_array($this->ribbonBinObjects) && array_key_exists($What, $this->ribbonBinObjects)) { | ||
296 | + $ReturnData=$this->ribbonBinObjects[$What]; | ||
297 | + } | ||
298 | + break; | ||
299 | + case 'types': | ||
300 | + if (is_array($this->ribbonBinObjects) && | ||
301 | + array_key_exists('data', $this->ribbonBinObjects) && is_array($this->ribbonBinObjects['data'])) { | ||
302 | + $tmpTypes=array_keys($this->ribbonBinObjects['data']); | ||
303 | + $ReturnData = array_unique(array_map(array($this, 'getExtensionOnly'), $tmpTypes)); | ||
304 | + } else { | ||
305 | + $ReturnData=array(); // the caller want an array... not null if empty | ||
306 | + } | ||
307 | + break; | ||
308 | + } | ||
309 | + return $ReturnData; | ||
310 | + } | ||
311 | + | ||
312 | + /** | ||
313 | + * This workbook have a custom UI ? | ||
314 | + * | ||
315 | + * @return boolean true|false | ||
316 | + */ | ||
317 | + public function hasRibbon() | ||
318 | + { | ||
319 | + return !is_null($this->ribbonXMLData); | ||
320 | + } | ||
321 | + | ||
322 | + /** | ||
323 | + * This workbook have additionnal object for the ribbon ? | ||
324 | + * | ||
325 | + * @return boolean true|false | ||
326 | + */ | ||
327 | + public function hasRibbonBinObjects() | ||
328 | + { | ||
329 | + return !is_null($this->ribbonBinObjects); | ||
330 | + } | ||
331 | + | ||
332 | + /** | ||
333 | + * Check if a sheet with a specified code name already exists | ||
334 | + * | ||
335 | + * @param string $pSheetCodeName Name of the worksheet to check | ||
336 | + * @return boolean | ||
337 | + */ | ||
338 | + public function sheetCodeNameExists($pSheetCodeName) | ||
339 | + { | ||
340 | + return ($this->getSheetByCodeName($pSheetCodeName) !== null); | ||
341 | + } | ||
342 | + | ||
343 | + /** | ||
344 | + * Get sheet by code name. Warning : sheet don't have always a code name ! | ||
345 | + * | ||
346 | + * @param string $pName Sheet name | ||
347 | + * @return PHPExcel_Worksheet | ||
348 | + */ | ||
349 | + public function getSheetByCodeName($pName = '') | ||
350 | + { | ||
351 | + $worksheetCount = count($this->workSheetCollection); | ||
352 | + for ($i = 0; $i < $worksheetCount; ++$i) { | ||
353 | + if ($this->workSheetCollection[$i]->getCodeName() == $pName) { | ||
354 | + return $this->workSheetCollection[$i]; | ||
355 | + } | ||
356 | + } | ||
357 | + | ||
358 | + return null; | ||
359 | + } | ||
360 | + | ||
361 | + /** | ||
362 | + * Create a new PHPExcel with one Worksheet | ||
363 | + */ | ||
364 | + public function __construct() | ||
365 | + { | ||
366 | + $this->uniqueID = uniqid(); | ||
367 | + $this->calculationEngine = new PHPExcel_Calculation($this); | ||
368 | + | ||
369 | + // Initialise worksheet collection and add one worksheet | ||
370 | + $this->workSheetCollection = array(); | ||
371 | + $this->workSheetCollection[] = new PHPExcel_Worksheet($this); | ||
372 | + $this->activeSheetIndex = 0; | ||
373 | + | ||
374 | + // Create document properties | ||
375 | + $this->properties = new PHPExcel_DocumentProperties(); | ||
376 | + | ||
377 | + // Create document security | ||
378 | + $this->security = new PHPExcel_DocumentSecurity(); | ||
379 | + | ||
380 | + // Set named ranges | ||
381 | + $this->namedRanges = array(); | ||
382 | + | ||
383 | + // Create the cellXf supervisor | ||
384 | + $this->cellXfSupervisor = new PHPExcel_Style(true); | ||
385 | + $this->cellXfSupervisor->bindParent($this); | ||
386 | + | ||
387 | + // Create the default style | ||
388 | + $this->addCellXf(new PHPExcel_Style); | ||
389 | + $this->addCellStyleXf(new PHPExcel_Style); | ||
390 | + } | ||
391 | + | ||
392 | + /** | ||
393 | + * Code to execute when this worksheet is unset() | ||
394 | + * | ||
395 | + */ | ||
396 | + public function __destruct() | ||
397 | + { | ||
398 | + $this->calculationEngine = null; | ||
399 | + $this->disconnectWorksheets(); | ||
400 | + } | ||
401 | + | ||
402 | + /** | ||
403 | + * Disconnect all worksheets from this PHPExcel workbook object, | ||
404 | + * typically so that the PHPExcel object can be unset | ||
405 | + * | ||
406 | + */ | ||
407 | + public function disconnectWorksheets() | ||
408 | + { | ||
409 | + $worksheet = null; | ||
410 | + foreach ($this->workSheetCollection as $k => &$worksheet) { | ||
411 | + $worksheet->disconnectCells(); | ||
412 | + $this->workSheetCollection[$k] = null; | ||
413 | + } | ||
414 | + unset($worksheet); | ||
415 | + $this->workSheetCollection = array(); | ||
416 | + } | ||
417 | + | ||
418 | + /** | ||
419 | + * Return the calculation engine for this worksheet | ||
420 | + * | ||
421 | + * @return PHPExcel_Calculation | ||
422 | + */ | ||
423 | + public function getCalculationEngine() | ||
424 | + { | ||
425 | + return $this->calculationEngine; | ||
426 | + } // function getCellCacheController() | ||
427 | + | ||
428 | + /** | ||
429 | + * Get properties | ||
430 | + * | ||
431 | + * @return PHPExcel_DocumentProperties | ||
432 | + */ | ||
433 | + public function getProperties() | ||
434 | + { | ||
435 | + return $this->properties; | ||
436 | + } | ||
437 | + | ||
438 | + /** | ||
439 | + * Set properties | ||
440 | + * | ||
441 | + * @param PHPExcel_DocumentProperties $pValue | ||
442 | + */ | ||
443 | + public function setProperties(PHPExcel_DocumentProperties $pValue) | ||
444 | + { | ||
445 | + $this->properties = $pValue; | ||
446 | + } | ||
447 | + | ||
448 | + /** | ||
449 | + * Get security | ||
450 | + * | ||
451 | + * @return PHPExcel_DocumentSecurity | ||
452 | + */ | ||
453 | + public function getSecurity() | ||
454 | + { | ||
455 | + return $this->security; | ||
456 | + } | ||
457 | + | ||
458 | + /** | ||
459 | + * Set security | ||
460 | + * | ||
461 | + * @param PHPExcel_DocumentSecurity $pValue | ||
462 | + */ | ||
463 | + public function setSecurity(PHPExcel_DocumentSecurity $pValue) | ||
464 | + { | ||
465 | + $this->security = $pValue; | ||
466 | + } | ||
467 | + | ||
468 | + /** | ||
469 | + * Get active sheet | ||
470 | + * | ||
471 | + * @return PHPExcel_Worksheet | ||
472 | + * | ||
473 | + * @throws PHPExcel_Exception | ||
474 | + */ | ||
475 | + public function getActiveSheet() | ||
476 | + { | ||
477 | + return $this->getSheet($this->activeSheetIndex); | ||
478 | + } | ||
479 | + | ||
480 | + /** | ||
481 | + * Create sheet and add it to this workbook | ||
482 | + * | ||
483 | + * @param int|null $iSheetIndex Index where sheet should go (0,1,..., or null for last) | ||
484 | + * @return PHPExcel_Worksheet | ||
485 | + * @throws PHPExcel_Exception | ||
486 | + */ | ||
487 | + public function createSheet($iSheetIndex = null) | ||
488 | + { | ||
489 | + $newSheet = new PHPExcel_Worksheet($this); | ||
490 | + $this->addSheet($newSheet, $iSheetIndex); | ||
491 | + return $newSheet; | ||
492 | + } | ||
493 | + | ||
494 | + /** | ||
495 | + * Check if a sheet with a specified name already exists | ||
496 | + * | ||
497 | + * @param string $pSheetName Name of the worksheet to check | ||
498 | + * @return boolean | ||
499 | + */ | ||
500 | + public function sheetNameExists($pSheetName) | ||
501 | + { | ||
502 | + return ($this->getSheetByName($pSheetName) !== null); | ||
503 | + } | ||
504 | + | ||
505 | + /** | ||
506 | + * Add sheet | ||
507 | + * | ||
508 | + * @param PHPExcel_Worksheet $pSheet | ||
509 | + * @param int|null $iSheetIndex Index where sheet should go (0,1,..., or null for last) | ||
510 | + * @return PHPExcel_Worksheet | ||
511 | + * @throws PHPExcel_Exception | ||
512 | + */ | ||
513 | + public function addSheet(PHPExcel_Worksheet $pSheet, $iSheetIndex = null) | ||
514 | + { | ||
515 | + if ($this->sheetNameExists($pSheet->getTitle())) { | ||
516 | + throw new PHPExcel_Exception( | ||
517 | + "Workbook already contains a worksheet named '{$pSheet->getTitle()}'. Rename this worksheet first." | ||
518 | + ); | ||
519 | + } | ||
520 | + | ||
521 | + if ($iSheetIndex === null) { | ||
522 | + if ($this->activeSheetIndex < 0) { | ||
523 | + $this->activeSheetIndex = 0; | ||
524 | + } | ||
525 | + $this->workSheetCollection[] = $pSheet; | ||
526 | + } else { | ||
527 | + // Insert the sheet at the requested index | ||
528 | + array_splice( | ||
529 | + $this->workSheetCollection, | ||
530 | + $iSheetIndex, | ||
531 | + 0, | ||
532 | + array($pSheet) | ||
533 | + ); | ||
534 | + | ||
535 | + // Adjust active sheet index if necessary | ||
536 | + if ($this->activeSheetIndex >= $iSheetIndex) { | ||
537 | + ++$this->activeSheetIndex; | ||
538 | + } | ||
539 | + } | ||
540 | + | ||
541 | + if ($pSheet->getParent() === null) { | ||
542 | + $pSheet->rebindParent($this); | ||
543 | + } | ||
544 | + | ||
545 | + return $pSheet; | ||
546 | + } | ||
547 | + | ||
548 | + /** | ||
549 | + * Remove sheet by index | ||
550 | + * | ||
551 | + * @param int $pIndex Active sheet index | ||
552 | + * @throws PHPExcel_Exception | ||
553 | + */ | ||
554 | + public function removeSheetByIndex($pIndex = 0) | ||
555 | + { | ||
556 | + | ||
557 | + $numSheets = count($this->workSheetCollection); | ||
558 | + if ($pIndex > $numSheets - 1) { | ||
559 | + throw new PHPExcel_Exception( | ||
560 | + "You tried to remove a sheet by the out of bounds index: {$pIndex}. The actual number of sheets is {$numSheets}." | ||
561 | + ); | ||
562 | + } else { | ||
563 | + array_splice($this->workSheetCollection, $pIndex, 1); | ||
564 | + } | ||
565 | + // Adjust active sheet index if necessary | ||
566 | + if (($this->activeSheetIndex >= $pIndex) && | ||
567 | + ($pIndex > count($this->workSheetCollection) - 1)) { | ||
568 | + --$this->activeSheetIndex; | ||
569 | + } | ||
570 | + | ||
571 | + } | ||
572 | + | ||
573 | + /** | ||
574 | + * Get sheet by index | ||
575 | + * | ||
576 | + * @param int $pIndex Sheet index | ||
577 | + * @return PHPExcel_Worksheet | ||
578 | + * @throws PHPExcel_Exception | ||
579 | + */ | ||
580 | + public function getSheet($pIndex = 0) | ||
581 | + { | ||
582 | + if (!isset($this->workSheetCollection[$pIndex])) { | ||
583 | + $numSheets = $this->getSheetCount(); | ||
584 | + throw new PHPExcel_Exception( | ||
585 | + "Your requested sheet index: {$pIndex} is out of bounds. The actual number of sheets is {$numSheets}." | ||
586 | + ); | ||
587 | + } | ||
588 | + | ||
589 | + return $this->workSheetCollection[$pIndex]; | ||
590 | + } | ||
591 | + | ||
592 | + /** | ||
593 | + * Get all sheets | ||
594 | + * | ||
595 | + * @return PHPExcel_Worksheet[] | ||
596 | + */ | ||
597 | + public function getAllSheets() | ||
598 | + { | ||
599 | + return $this->workSheetCollection; | ||
600 | + } | ||
601 | + | ||
602 | + /** | ||
603 | + * Get sheet by name | ||
604 | + * | ||
605 | + * @param string $pName Sheet name | ||
606 | + * @return PHPExcel_Worksheet | ||
607 | + */ | ||
608 | + public function getSheetByName($pName = '') | ||
609 | + { | ||
610 | + $worksheetCount = count($this->workSheetCollection); | ||
611 | + for ($i = 0; $i < $worksheetCount; ++$i) { | ||
612 | + if ($this->workSheetCollection[$i]->getTitle() === $pName) { | ||
613 | + return $this->workSheetCollection[$i]; | ||
614 | + } | ||
615 | + } | ||
616 | + | ||
617 | + return null; | ||
618 | + } | ||
619 | + | ||
620 | + /** | ||
621 | + * Get index for sheet | ||
622 | + * | ||
623 | + * @param PHPExcel_Worksheet $pSheet | ||
624 | + * @return int Sheet index | ||
625 | + * @throws PHPExcel_Exception | ||
626 | + */ | ||
627 | + public function getIndex(PHPExcel_Worksheet $pSheet) | ||
628 | + { | ||
629 | + foreach ($this->workSheetCollection as $key => $value) { | ||
630 | + if ($value->getHashCode() == $pSheet->getHashCode()) { | ||
631 | + return $key; | ||
632 | + } | ||
633 | + } | ||
634 | + | ||
635 | + throw new PHPExcel_Exception("Sheet does not exist."); | ||
636 | + } | ||
637 | + | ||
638 | + /** | ||
639 | + * Set index for sheet by sheet name. | ||
640 | + * | ||
641 | + * @param string $sheetName Sheet name to modify index for | ||
642 | + * @param int $newIndex New index for the sheet | ||
643 | + * @return int New sheet index | ||
644 | + * @throws PHPExcel_Exception | ||
645 | + */ | ||
646 | + public function setIndexByName($sheetName, $newIndex) | ||
647 | + { | ||
648 | + $oldIndex = $this->getIndex($this->getSheetByName($sheetName)); | ||
649 | + $pSheet = array_splice( | ||
650 | + $this->workSheetCollection, | ||
651 | + $oldIndex, | ||
652 | + 1 | ||
653 | + ); | ||
654 | + array_splice( | ||
655 | + $this->workSheetCollection, | ||
656 | + $newIndex, | ||
657 | + 0, | ||
658 | + $pSheet | ||
659 | + ); | ||
660 | + return $newIndex; | ||
661 | + } | ||
662 | + | ||
663 | + /** | ||
664 | + * Get sheet count | ||
665 | + * | ||
666 | + * @return int | ||
667 | + */ | ||
668 | + public function getSheetCount() | ||
669 | + { | ||
670 | + return count($this->workSheetCollection); | ||
671 | + } | ||
672 | + | ||
673 | + /** | ||
674 | + * Get active sheet index | ||
675 | + * | ||
676 | + * @return int Active sheet index | ||
677 | + */ | ||
678 | + public function getActiveSheetIndex() | ||
679 | + { | ||
680 | + return $this->activeSheetIndex; | ||
681 | + } | ||
682 | + | ||
683 | + /** | ||
684 | + * Set active sheet index | ||
685 | + * | ||
686 | + * @param int $pIndex Active sheet index | ||
687 | + * @throws PHPExcel_Exception | ||
688 | + * @return PHPExcel_Worksheet | ||
689 | + */ | ||
690 | + public function setActiveSheetIndex($pIndex = 0) | ||
691 | + { | ||
692 | + $numSheets = count($this->workSheetCollection); | ||
693 | + | ||
694 | + if ($pIndex > $numSheets - 1) { | ||
695 | + throw new PHPExcel_Exception( | ||
696 | + "You tried to set a sheet active by the out of bounds index: {$pIndex}. The actual number of sheets is {$numSheets}." | ||
697 | + ); | ||
698 | + } else { | ||
699 | + $this->activeSheetIndex = $pIndex; | ||
700 | + } | ||
701 | + return $this->getActiveSheet(); | ||
702 | + } | ||
703 | + | ||
704 | + /** | ||
705 | + * Set active sheet index by name | ||
706 | + * | ||
707 | + * @param string $pValue Sheet title | ||
708 | + * @return PHPExcel_Worksheet | ||
709 | + * @throws PHPExcel_Exception | ||
710 | + */ | ||
711 | + public function setActiveSheetIndexByName($pValue = '') | ||
712 | + { | ||
713 | + if (($worksheet = $this->getSheetByName($pValue)) instanceof PHPExcel_Worksheet) { | ||
714 | + $this->setActiveSheetIndex($this->getIndex($worksheet)); | ||
715 | + return $worksheet; | ||
716 | + } | ||
717 | + | ||
718 | + throw new PHPExcel_Exception('Workbook does not contain sheet:' . $pValue); | ||
719 | + } | ||
720 | + | ||
721 | + /** | ||
722 | + * Get sheet names | ||
723 | + * | ||
724 | + * @return string[] | ||
725 | + */ | ||
726 | + public function getSheetNames() | ||
727 | + { | ||
728 | + $returnValue = array(); | ||
729 | + $worksheetCount = $this->getSheetCount(); | ||
730 | + for ($i = 0; $i < $worksheetCount; ++$i) { | ||
731 | + $returnValue[] = $this->getSheet($i)->getTitle(); | ||
732 | + } | ||
733 | + | ||
734 | + return $returnValue; | ||
735 | + } | ||
736 | + | ||
737 | + /** | ||
738 | + * Add external sheet | ||
739 | + * | ||
740 | + * @param PHPExcel_Worksheet $pSheet External sheet to add | ||
741 | + * @param int|null $iSheetIndex Index where sheet should go (0,1,..., or null for last) | ||
742 | + * @throws PHPExcel_Exception | ||
743 | + * @return PHPExcel_Worksheet | ||
744 | + */ | ||
745 | + public function addExternalSheet(PHPExcel_Worksheet $pSheet, $iSheetIndex = null) | ||
746 | + { | ||
747 | + if ($this->sheetNameExists($pSheet->getTitle())) { | ||
748 | + throw new PHPExcel_Exception("Workbook already contains a worksheet named '{$pSheet->getTitle()}'. Rename the external sheet first."); | ||
749 | + } | ||
750 | + | ||
751 | + // count how many cellXfs there are in this workbook currently, we will need this below | ||
752 | + $countCellXfs = count($this->cellXfCollection); | ||
753 | + | ||
754 | + // copy all the shared cellXfs from the external workbook and append them to the current | ||
755 | + foreach ($pSheet->getParent()->getCellXfCollection() as $cellXf) { | ||
756 | + $this->addCellXf(clone $cellXf); | ||
757 | + } | ||
758 | + | ||
759 | + // move sheet to this workbook | ||
760 | + $pSheet->rebindParent($this); | ||
761 | + | ||
762 | + // update the cellXfs | ||
763 | + foreach ($pSheet->getCellCollection(false) as $cellID) { | ||
764 | + $cell = $pSheet->getCell($cellID); | ||
765 | + $cell->setXfIndex($cell->getXfIndex() + $countCellXfs); | ||
766 | + } | ||
767 | + | ||
768 | + return $this->addSheet($pSheet, $iSheetIndex); | ||
769 | + } | ||
770 | + | ||
771 | + /** | ||
772 | + * Get named ranges | ||
773 | + * | ||
774 | + * @return PHPExcel_NamedRange[] | ||
775 | + */ | ||
776 | + public function getNamedRanges() | ||
777 | + { | ||
778 | + return $this->namedRanges; | ||
779 | + } | ||
780 | + | ||
781 | + /** | ||
782 | + * Add named range | ||
783 | + * | ||
784 | + * @param PHPExcel_NamedRange $namedRange | ||
785 | + * @return boolean | ||
786 | + */ | ||
787 | + public function addNamedRange(PHPExcel_NamedRange $namedRange) | ||
788 | + { | ||
789 | + if ($namedRange->getScope() == null) { | ||
790 | + // global scope | ||
791 | + $this->namedRanges[$namedRange->getName()] = $namedRange; | ||
792 | + } else { | ||
793 | + // local scope | ||
794 | + $this->namedRanges[$namedRange->getScope()->getTitle().'!'.$namedRange->getName()] = $namedRange; | ||
795 | + } | ||
796 | + return true; | ||
797 | + } | ||
798 | + | ||
799 | + /** | ||
800 | + * Get named range | ||
801 | + * | ||
802 | + * @param string $namedRange | ||
803 | + * @param PHPExcel_Worksheet|null $pSheet Scope. Use null for global scope | ||
804 | + * @return PHPExcel_NamedRange|null | ||
805 | + */ | ||
806 | + public function getNamedRange($namedRange, PHPExcel_Worksheet $pSheet = null) | ||
807 | + { | ||
808 | + $returnValue = null; | ||
809 | + | ||
810 | + if ($namedRange != '' && ($namedRange !== null)) { | ||
811 | + // first look for global defined name | ||
812 | + if (isset($this->namedRanges[$namedRange])) { | ||
813 | + $returnValue = $this->namedRanges[$namedRange]; | ||
814 | + } | ||
815 | + | ||
816 | + // then look for local defined name (has priority over global defined name if both names exist) | ||
817 | + if (($pSheet !== null) && isset($this->namedRanges[$pSheet->getTitle() . '!' . $namedRange])) { | ||
818 | + $returnValue = $this->namedRanges[$pSheet->getTitle() . '!' . $namedRange]; | ||
819 | + } | ||
820 | + } | ||
821 | + | ||
822 | + return $returnValue; | ||
823 | + } | ||
824 | + | ||
825 | + /** | ||
826 | + * Remove named range | ||
827 | + * | ||
828 | + * @param string $namedRange | ||
829 | + * @param PHPExcel_Worksheet|null $pSheet Scope: use null for global scope. | ||
830 | + * @return PHPExcel | ||
831 | + */ | ||
832 | + public function removeNamedRange($namedRange, PHPExcel_Worksheet $pSheet = null) | ||
833 | + { | ||
834 | + if ($pSheet === null) { | ||
835 | + if (isset($this->namedRanges[$namedRange])) { | ||
836 | + unset($this->namedRanges[$namedRange]); | ||
837 | + } | ||
838 | + } else { | ||
839 | + if (isset($this->namedRanges[$pSheet->getTitle() . '!' . $namedRange])) { | ||
840 | + unset($this->namedRanges[$pSheet->getTitle() . '!' . $namedRange]); | ||
841 | + } | ||
842 | + } | ||
843 | + return $this; | ||
844 | + } | ||
845 | + | ||
846 | + /** | ||
847 | + * Get worksheet iterator | ||
848 | + * | ||
849 | + * @return PHPExcel_WorksheetIterator | ||
850 | + */ | ||
851 | + public function getWorksheetIterator() | ||
852 | + { | ||
853 | + return new PHPExcel_WorksheetIterator($this); | ||
854 | + } | ||
855 | + | ||
856 | + /** | ||
857 | + * Copy workbook (!= clone!) | ||
858 | + * | ||
859 | + * @return PHPExcel | ||
860 | + */ | ||
861 | + public function copy() | ||
862 | + { | ||
863 | + $copied = clone $this; | ||
864 | + | ||
865 | + $worksheetCount = count($this->workSheetCollection); | ||
866 | + for ($i = 0; $i < $worksheetCount; ++$i) { | ||
867 | + $this->workSheetCollection[$i] = $this->workSheetCollection[$i]->copy(); | ||
868 | + $this->workSheetCollection[$i]->rebindParent($this); | ||
869 | + } | ||
870 | + | ||
871 | + return $copied; | ||
872 | + } | ||
873 | + | ||
874 | + /** | ||
875 | + * Implement PHP __clone to create a deep clone, not just a shallow copy. | ||
876 | + */ | ||
877 | + public function __clone() | ||
878 | + { | ||
879 | + foreach ($this as $key => $val) { | ||
880 | + if (is_object($val) || (is_array($val))) { | ||
881 | + $this->{$key} = unserialize(serialize($val)); | ||
882 | + } | ||
883 | + } | ||
884 | + } | ||
885 | + | ||
886 | + /** | ||
887 | + * Get the workbook collection of cellXfs | ||
888 | + * | ||
889 | + * @return PHPExcel_Style[] | ||
890 | + */ | ||
891 | + public function getCellXfCollection() | ||
892 | + { | ||
893 | + return $this->cellXfCollection; | ||
894 | + } | ||
895 | + | ||
896 | + /** | ||
897 | + * Get cellXf by index | ||
898 | + * | ||
899 | + * @param int $pIndex | ||
900 | + * @return PHPExcel_Style | ||
901 | + */ | ||
902 | + public function getCellXfByIndex($pIndex = 0) | ||
903 | + { | ||
904 | + return $this->cellXfCollection[$pIndex]; | ||
905 | + } | ||
906 | + | ||
907 | + /** | ||
908 | + * Get cellXf by hash code | ||
909 | + * | ||
910 | + * @param string $pValue | ||
911 | + * @return PHPExcel_Style|boolean False if no match found | ||
912 | + */ | ||
913 | + public function getCellXfByHashCode($pValue = '') | ||
914 | + { | ||
915 | + foreach ($this->cellXfCollection as $cellXf) { | ||
916 | + if ($cellXf->getHashCode() == $pValue) { | ||
917 | + return $cellXf; | ||
918 | + } | ||
919 | + } | ||
920 | + return false; | ||
921 | + } | ||
922 | + | ||
923 | + /** | ||
924 | + * Check if style exists in style collection | ||
925 | + * | ||
926 | + * @param PHPExcel_Style $pCellStyle | ||
927 | + * @return boolean | ||
928 | + */ | ||
929 | + public function cellXfExists($pCellStyle = null) | ||
930 | + { | ||
931 | + return in_array($pCellStyle, $this->cellXfCollection, true); | ||
932 | + } | ||
933 | + | ||
934 | + /** | ||
935 | + * Get default style | ||
936 | + * | ||
937 | + * @return PHPExcel_Style | ||
938 | + * @throws PHPExcel_Exception | ||
939 | + */ | ||
940 | + public function getDefaultStyle() | ||
941 | + { | ||
942 | + if (isset($this->cellXfCollection[0])) { | ||
943 | + return $this->cellXfCollection[0]; | ||
944 | + } | ||
945 | + throw new PHPExcel_Exception('No default style found for this workbook'); | ||
946 | + } | ||
947 | + | ||
948 | + /** | ||
949 | + * Add a cellXf to the workbook | ||
950 | + * | ||
951 | + * @param PHPExcel_Style $style | ||
952 | + */ | ||
953 | + public function addCellXf(PHPExcel_Style $style) | ||
954 | + { | ||
955 | + $this->cellXfCollection[] = $style; | ||
956 | + $style->setIndex(count($this->cellXfCollection) - 1); | ||
957 | + } | ||
958 | + | ||
959 | + /** | ||
960 | + * Remove cellXf by index. It is ensured that all cells get their xf index updated. | ||
961 | + * | ||
962 | + * @param integer $pIndex Index to cellXf | ||
963 | + * @throws PHPExcel_Exception | ||
964 | + */ | ||
965 | + public function removeCellXfByIndex($pIndex = 0) | ||
966 | + { | ||
967 | + if ($pIndex > count($this->cellXfCollection) - 1) { | ||
968 | + throw new PHPExcel_Exception("CellXf index is out of bounds."); | ||
969 | + } else { | ||
970 | + // first remove the cellXf | ||
971 | + array_splice($this->cellXfCollection, $pIndex, 1); | ||
972 | + | ||
973 | + // then update cellXf indexes for cells | ||
974 | + foreach ($this->workSheetCollection as $worksheet) { | ||
975 | + foreach ($worksheet->getCellCollection(false) as $cellID) { | ||
976 | + $cell = $worksheet->getCell($cellID); | ||
977 | + $xfIndex = $cell->getXfIndex(); | ||
978 | + if ($xfIndex > $pIndex) { | ||
979 | + // decrease xf index by 1 | ||
980 | + $cell->setXfIndex($xfIndex - 1); | ||
981 | + } elseif ($xfIndex == $pIndex) { | ||
982 | + // set to default xf index 0 | ||
983 | + $cell->setXfIndex(0); | ||
984 | + } | ||
985 | + } | ||
986 | + } | ||
987 | + } | ||
988 | + } | ||
989 | + | ||
990 | + /** | ||
991 | + * Get the cellXf supervisor | ||
992 | + * | ||
993 | + * @return PHPExcel_Style | ||
994 | + */ | ||
995 | + public function getCellXfSupervisor() | ||
996 | + { | ||
997 | + return $this->cellXfSupervisor; | ||
998 | + } | ||
999 | + | ||
1000 | + /** | ||
1001 | + * Get the workbook collection of cellStyleXfs | ||
1002 | + * | ||
1003 | + * @return PHPExcel_Style[] | ||
1004 | + */ | ||
1005 | + public function getCellStyleXfCollection() | ||
1006 | + { | ||
1007 | + return $this->cellStyleXfCollection; | ||
1008 | + } | ||
1009 | + | ||
1010 | + /** | ||
1011 | + * Get cellStyleXf by index | ||
1012 | + * | ||
1013 | + * @param integer $pIndex Index to cellXf | ||
1014 | + * @return PHPExcel_Style | ||
1015 | + */ | ||
1016 | + public function getCellStyleXfByIndex($pIndex = 0) | ||
1017 | + { | ||
1018 | + return $this->cellStyleXfCollection[$pIndex]; | ||
1019 | + } | ||
1020 | + | ||
1021 | + /** | ||
1022 | + * Get cellStyleXf by hash code | ||
1023 | + * | ||
1024 | + * @param string $pValue | ||
1025 | + * @return PHPExcel_Style|boolean False if no match found | ||
1026 | + */ | ||
1027 | + public function getCellStyleXfByHashCode($pValue = '') | ||
1028 | + { | ||
1029 | + foreach ($this->cellStyleXfCollection as $cellStyleXf) { | ||
1030 | + if ($cellStyleXf->getHashCode() == $pValue) { | ||
1031 | + return $cellStyleXf; | ||
1032 | + } | ||
1033 | + } | ||
1034 | + return false; | ||
1035 | + } | ||
1036 | + | ||
1037 | + /** | ||
1038 | + * Add a cellStyleXf to the workbook | ||
1039 | + * | ||
1040 | + * @param PHPExcel_Style $pStyle | ||
1041 | + */ | ||
1042 | + public function addCellStyleXf(PHPExcel_Style $pStyle) | ||
1043 | + { | ||
1044 | + $this->cellStyleXfCollection[] = $pStyle; | ||
1045 | + $pStyle->setIndex(count($this->cellStyleXfCollection) - 1); | ||
1046 | + } | ||
1047 | + | ||
1048 | + /** | ||
1049 | + * Remove cellStyleXf by index | ||
1050 | + * | ||
1051 | + * @param integer $pIndex Index to cellXf | ||
1052 | + * @throws PHPExcel_Exception | ||
1053 | + */ | ||
1054 | + public function removeCellStyleXfByIndex($pIndex = 0) | ||
1055 | + { | ||
1056 | + if ($pIndex > count($this->cellStyleXfCollection) - 1) { | ||
1057 | + throw new PHPExcel_Exception("CellStyleXf index is out of bounds."); | ||
1058 | + } else { | ||
1059 | + array_splice($this->cellStyleXfCollection, $pIndex, 1); | ||
1060 | + } | ||
1061 | + } | ||
1062 | + | ||
1063 | + /** | ||
1064 | + * Eliminate all unneeded cellXf and afterwards update the xfIndex for all cells | ||
1065 | + * and columns in the workbook | ||
1066 | + */ | ||
1067 | + public function garbageCollect() | ||
1068 | + { | ||
1069 | + // how many references are there to each cellXf ? | ||
1070 | + $countReferencesCellXf = array(); | ||
1071 | + foreach ($this->cellXfCollection as $index => $cellXf) { | ||
1072 | + $countReferencesCellXf[$index] = 0; | ||
1073 | + } | ||
1074 | + | ||
1075 | + foreach ($this->getWorksheetIterator() as $sheet) { | ||
1076 | + // from cells | ||
1077 | + foreach ($sheet->getCellCollection(false) as $cellID) { | ||
1078 | + $cell = $sheet->getCell($cellID); | ||
1079 | + ++$countReferencesCellXf[$cell->getXfIndex()]; | ||
1080 | + } | ||
1081 | + | ||
1082 | + // from row dimensions | ||
1083 | + foreach ($sheet->getRowDimensions() as $rowDimension) { | ||
1084 | + if ($rowDimension->getXfIndex() !== null) { | ||
1085 | + ++$countReferencesCellXf[$rowDimension->getXfIndex()]; | ||
1086 | + } | ||
1087 | + } | ||
1088 | + | ||
1089 | + // from column dimensions | ||
1090 | + foreach ($sheet->getColumnDimensions() as $columnDimension) { | ||
1091 | + ++$countReferencesCellXf[$columnDimension->getXfIndex()]; | ||
1092 | + } | ||
1093 | + } | ||
1094 | + | ||
1095 | + // remove cellXfs without references and create mapping so we can update xfIndex | ||
1096 | + // for all cells and columns | ||
1097 | + $countNeededCellXfs = 0; | ||
1098 | + $map = array(); | ||
1099 | + foreach ($this->cellXfCollection as $index => $cellXf) { | ||
1100 | + if ($countReferencesCellXf[$index] > 0 || $index == 0) { // we must never remove the first cellXf | ||
1101 | + ++$countNeededCellXfs; | ||
1102 | + } else { | ||
1103 | + unset($this->cellXfCollection[$index]); | ||
1104 | + } | ||
1105 | + $map[$index] = $countNeededCellXfs - 1; | ||
1106 | + } | ||
1107 | + $this->cellXfCollection = array_values($this->cellXfCollection); | ||
1108 | + | ||
1109 | + // update the index for all cellXfs | ||
1110 | + foreach ($this->cellXfCollection as $i => $cellXf) { | ||
1111 | + $cellXf->setIndex($i); | ||
1112 | + } | ||
1113 | + | ||
1114 | + // make sure there is always at least one cellXf (there should be) | ||
1115 | + if (empty($this->cellXfCollection)) { | ||
1116 | + $this->cellXfCollection[] = new PHPExcel_Style(); | ||
1117 | + } | ||
1118 | + | ||
1119 | + // update the xfIndex for all cells, row dimensions, column dimensions | ||
1120 | + foreach ($this->getWorksheetIterator() as $sheet) { | ||
1121 | + // for all cells | ||
1122 | + foreach ($sheet->getCellCollection(false) as $cellID) { | ||
1123 | + $cell = $sheet->getCell($cellID); | ||
1124 | + $cell->setXfIndex($map[$cell->getXfIndex()]); | ||
1125 | + } | ||
1126 | + | ||
1127 | + // for all row dimensions | ||
1128 | + foreach ($sheet->getRowDimensions() as $rowDimension) { | ||
1129 | + if ($rowDimension->getXfIndex() !== null) { | ||
1130 | + $rowDimension->setXfIndex($map[$rowDimension->getXfIndex()]); | ||
1131 | + } | ||
1132 | + } | ||
1133 | + | ||
1134 | + // for all column dimensions | ||
1135 | + foreach ($sheet->getColumnDimensions() as $columnDimension) { | ||
1136 | + $columnDimension->setXfIndex($map[$columnDimension->getXfIndex()]); | ||
1137 | + } | ||
1138 | + | ||
1139 | + // also do garbage collection for all the sheets | ||
1140 | + $sheet->garbageCollect(); | ||
1141 | + } | ||
1142 | + } | ||
1143 | + | ||
1144 | + /** | ||
1145 | + * Return the unique ID value assigned to this spreadsheet workbook | ||
1146 | + * | ||
1147 | + * @return string | ||
1148 | + */ | ||
1149 | + public function getID() | ||
1150 | + { | ||
1151 | + return $this->uniqueID; | ||
1152 | + } | ||
1153 | +} |
1 | +<?php | ||
2 | + | ||
3 | +PHPExcel_Autoloader::register(); | ||
4 | +// As we always try to run the autoloader before anything else, we can use it to do a few | ||
5 | +// simple checks and initialisations | ||
6 | +//PHPExcel_Shared_ZipStreamWrapper::register(); | ||
7 | +// check mbstring.func_overload | ||
8 | +if (ini_get('mbstring.func_overload') & 2) { | ||
9 | + throw new PHPExcel_Exception('Multibyte function overloading in PHP must be disabled for string functions (2).'); | ||
10 | +} | ||
11 | +PHPExcel_Shared_String::buildCharacterSets(); | ||
12 | + | ||
13 | +/** | ||
14 | + * PHPExcel | ||
15 | + * | ||
16 | + * Copyright (c) 2006 - 2015 PHPExcel | ||
17 | + * | ||
18 | + * This library is free software; you can redistribute it and/or | ||
19 | + * modify it under the terms of the GNU Lesser General Public | ||
20 | + * License as published by the Free Software Foundation; either | ||
21 | + * version 2.1 of the License, or (at your option) any later version. | ||
22 | + * | ||
23 | + * This library is distributed in the hope that it will be useful, | ||
24 | + * but WITHOUT ANY WARRANTY; without even the implied warranty of | ||
25 | + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU | ||
26 | + * Lesser General Public License for more details. | ||
27 | + * | ||
28 | + * You should have received a copy of the GNU Lesser General Public | ||
29 | + * License along with this library; if not, write to the Free Software | ||
30 | + * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA | ||
31 | + * | ||
32 | + * @category PHPExcel | ||
33 | + * @package PHPExcel | ||
34 | + * @copyright Copyright (c) 2006 - 2015 PHPExcel (http://www.codeplex.com/PHPExcel) | ||
35 | + * @license http://www.gnu.org/licenses/old-licenses/lgpl-2.1.txt LGPL | ||
36 | + * @version ##VERSION##, ##DATE## | ||
37 | + */ | ||
38 | +class PHPExcel_Autoloader | ||
39 | +{ | ||
40 | + /** | ||
41 | + * Register the Autoloader with SPL | ||
42 | + * | ||
43 | + */ | ||
44 | + public static function register() | ||
45 | + { | ||
46 | + if (function_exists('__autoload')) { | ||
47 | + // Register any existing autoloader function with SPL, so we don't get any clashes | ||
48 | + spl_autoload_register('__autoload'); | ||
49 | + } | ||
50 | + // Register ourselves with SPL | ||
51 | + if (version_compare(PHP_VERSION, '5.3.0') >= 0) { | ||
52 | + return spl_autoload_register(array('PHPExcel_Autoloader', 'load'), true, true); | ||
53 | + } else { | ||
54 | + return spl_autoload_register(array('PHPExcel_Autoloader', 'load')); | ||
55 | + } | ||
56 | + } | ||
57 | + | ||
58 | + /** | ||
59 | + * Autoload a class identified by name | ||
60 | + * | ||
61 | + * @param string $pClassName Name of the object to load | ||
62 | + */ | ||
63 | + public static function load($pClassName) | ||
64 | + { | ||
65 | + if ((class_exists($pClassName, false)) || (strpos($pClassName, 'PHPExcel') !== 0)) { | ||
66 | + // Either already loaded, or not a PHPExcel class request | ||
67 | + return false; | ||
68 | + } | ||
69 | + | ||
70 | + $pClassFilePath = PHPEXCEL_ROOT . | ||
71 | + str_replace('_', DIRECTORY_SEPARATOR, $pClassName) . | ||
72 | + '.php'; | ||
73 | + | ||
74 | + if ((file_exists($pClassFilePath) === false) || (is_readable($pClassFilePath) === false)) { | ||
75 | + // Can't load | ||
76 | + return false; | ||
77 | + } | ||
78 | + | ||
79 | + require($pClassFilePath); | ||
80 | + } | ||
81 | +} |
1 | +<?php | ||
2 | + | ||
3 | +/** | ||
4 | + * PHPExcel_CachedObjectStorage_APC | ||
5 | + * | ||
6 | + * Copyright (c) 2006 - 2015 PHPExcel | ||
7 | + * | ||
8 | + * This library is free software; you can redistribute it and/or | ||
9 | + * modify it under the terms of the GNU Lesser General Public | ||
10 | + * License as published by the Free Software Foundation; either | ||
11 | + * version 2.1 of the License, or (at your option) any later version. | ||
12 | + * | ||
13 | + * This library is distributed in the hope that it will be useful, | ||
14 | + * but WITHOUT ANY WARRANTY; without even the implied warranty of | ||
15 | + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU | ||
16 | + * Lesser General Public License for more details. | ||
17 | + * | ||
18 | + * You should have received a copy of the GNU Lesser General Public | ||
19 | + * License along with this library; if not, write to the Free Software | ||
20 | + * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA | ||
21 | + * | ||
22 | + * @category PHPExcel | ||
23 | + * @package PHPExcel_CachedObjectStorage | ||
24 | + * @copyright Copyright (c) 2006 - 2015 PHPExcel (http://www.codeplex.com/PHPExcel) | ||
25 | + * @license http://www.gnu.org/licenses/old-licenses/lgpl-2.1.txt LGPL | ||
26 | + * @version ##VERSION##, ##DATE## | ||
27 | + */ | ||
28 | +class PHPExcel_CachedObjectStorage_APC extends PHPExcel_CachedObjectStorage_CacheBase implements PHPExcel_CachedObjectStorage_ICache | ||
29 | +{ | ||
30 | + /** | ||
31 | + * Prefix used to uniquely identify cache data for this worksheet | ||
32 | + * | ||
33 | + * @access private | ||
34 | + * @var string | ||
35 | + */ | ||
36 | + private $cachePrefix = null; | ||
37 | + | ||
38 | + /** | ||
39 | + * Cache timeout | ||
40 | + * | ||
41 | + * @access private | ||
42 | + * @var integer | ||
43 | + */ | ||
44 | + private $cacheTime = 600; | ||
45 | + | ||
46 | + /** | ||
47 | + * Store cell data in cache for the current cell object if it's "dirty", | ||
48 | + * and the 'nullify' the current cell object | ||
49 | + * | ||
50 | + * @access private | ||
51 | + * @return void | ||
52 | + * @throws PHPExcel_Exception | ||
53 | + */ | ||
54 | + protected function storeData() | ||
55 | + { | ||
56 | + if ($this->currentCellIsDirty && !empty($this->currentObjectID)) { | ||
57 | + $this->currentObject->detach(); | ||
58 | + | ||
59 | + if (!apc_store( | ||
60 | + $this->cachePrefix . $this->currentObjectID . '.cache', | ||
61 | + serialize($this->currentObject), | ||
62 | + $this->cacheTime | ||
63 | + )) { | ||
64 | + $this->__destruct(); | ||
65 | + throw new PHPExcel_Exception('Failed to store cell ' . $this->currentObjectID . ' in APC'); | ||
66 | + } | ||
67 | + $this->currentCellIsDirty = false; | ||
68 | + } | ||
69 | + $this->currentObjectID = $this->currentObject = null; | ||
70 | + } | ||
71 | + | ||
72 | + /** | ||
73 | + * Add or Update a cell in cache identified by coordinate address | ||
74 | + * | ||
75 | + * @access public | ||
76 | + * @param string $pCoord Coordinate address of the cell to update | ||
77 | + * @param PHPExcel_Cell $cell Cell to update | ||
78 | + * @return PHPExcel_Cell | ||
79 | + * @throws PHPExcel_Exception | ||
80 | + */ | ||
81 | + public function addCacheData($pCoord, PHPExcel_Cell $cell) | ||
82 | + { | ||
83 | + if (($pCoord !== $this->currentObjectID) && ($this->currentObjectID !== null)) { | ||
84 | + $this->storeData(); | ||
85 | + } | ||
86 | + $this->cellCache[$pCoord] = true; | ||
87 | + | ||
88 | + $this->currentObjectID = $pCoord; | ||
89 | + $this->currentObject = $cell; | ||
90 | + $this->currentCellIsDirty = true; | ||
91 | + | ||
92 | + return $cell; | ||
93 | + } | ||
94 | + | ||
95 | + /** | ||
96 | + * Is a value set in the current PHPExcel_CachedObjectStorage_ICache for an indexed cell? | ||
97 | + * | ||
98 | + * @access public | ||
99 | + * @param string $pCoord Coordinate address of the cell to check | ||
100 | + * @throws PHPExcel_Exception | ||
101 | + * @return boolean | ||
102 | + */ | ||
103 | + public function isDataSet($pCoord) | ||
104 | + { | ||
105 | + // Check if the requested entry is the current object, or exists in the cache | ||
106 | + if (parent::isDataSet($pCoord)) { | ||
107 | + if ($this->currentObjectID == $pCoord) { | ||
108 | + return true; | ||
109 | + } | ||
110 | + // Check if the requested entry still exists in apc | ||
111 | + $success = apc_fetch($this->cachePrefix.$pCoord.'.cache'); | ||
112 | + if ($success === false) { | ||
113 | + // Entry no longer exists in APC, so clear it from the cache array | ||
114 | + parent::deleteCacheData($pCoord); | ||
115 | + throw new PHPExcel_Exception('Cell entry '.$pCoord.' no longer exists in APC cache'); | ||
116 | + } | ||
117 | + return true; | ||
118 | + } | ||
119 | + return false; | ||
120 | + } | ||
121 | + | ||
122 | + /** | ||
123 | + * Get cell at a specific coordinate | ||
124 | + * | ||
125 | + * @access public | ||
126 | + * @param string $pCoord Coordinate of the cell | ||
127 | + * @throws PHPExcel_Exception | ||
128 | + * @return PHPExcel_Cell Cell that was found, or null if not found | ||
129 | + */ | ||
130 | + public function getCacheData($pCoord) | ||
131 | + { | ||
132 | + if ($pCoord === $this->currentObjectID) { | ||
133 | + return $this->currentObject; | ||
134 | + } | ||
135 | + $this->storeData(); | ||
136 | + | ||
137 | + // Check if the entry that has been requested actually exists | ||
138 | + if (parent::isDataSet($pCoord)) { | ||
139 | + $obj = apc_fetch($this->cachePrefix . $pCoord . '.cache'); | ||
140 | + if ($obj === false) { | ||
141 | + // Entry no longer exists in APC, so clear it from the cache array | ||
142 | + parent::deleteCacheData($pCoord); | ||
143 | + throw new PHPExcel_Exception('Cell entry '.$pCoord.' no longer exists in APC cache'); | ||
144 | + } | ||
145 | + } else { | ||
146 | + // Return null if requested entry doesn't exist in cache | ||
147 | + return null; | ||
148 | + } | ||
149 | + | ||
150 | + // Set current entry to the requested entry | ||
151 | + $this->currentObjectID = $pCoord; | ||
152 | + $this->currentObject = unserialize($obj); | ||
153 | + // Re-attach this as the cell's parent | ||
154 | + $this->currentObject->attach($this); | ||
155 | + | ||
156 | + // Return requested entry | ||
157 | + return $this->currentObject; | ||
158 | + } | ||
159 | + | ||
160 | + /** | ||
161 | + * Get a list of all cell addresses currently held in cache | ||
162 | + * | ||
163 | + * @return string[] | ||
164 | + */ | ||
165 | + public function getCellList() | ||
166 | + { | ||
167 | + if ($this->currentObjectID !== null) { | ||
168 | + $this->storeData(); | ||
169 | + } | ||
170 | + | ||
171 | + return parent::getCellList(); | ||
172 | + } | ||
173 | + | ||
174 | + /** | ||
175 | + * Delete a cell in cache identified by coordinate address | ||
176 | + * | ||
177 | + * @access public | ||
178 | + * @param string $pCoord Coordinate address of the cell to delete | ||
179 | + * @throws PHPExcel_Exception | ||
180 | + */ | ||
181 | + public function deleteCacheData($pCoord) | ||
182 | + { | ||
183 | + // Delete the entry from APC | ||
184 | + apc_delete($this->cachePrefix.$pCoord.'.cache'); | ||
185 | + | ||
186 | + // Delete the entry from our cell address array | ||
187 | + parent::deleteCacheData($pCoord); | ||
188 | + } | ||
189 | + | ||
190 | + /** | ||
191 | + * Clone the cell collection | ||
192 | + * | ||
193 | + * @access public | ||
194 | + * @param PHPExcel_Worksheet $parent The new worksheet | ||
195 | + * @throws PHPExcel_Exception | ||
196 | + * @return void | ||
197 | + */ | ||
198 | + public function copyCellCollection(PHPExcel_Worksheet $parent) | ||
199 | + { | ||
200 | + parent::copyCellCollection($parent); | ||
201 | + // Get a new id for the new file name | ||
202 | + $baseUnique = $this->getUniqueID(); | ||
203 | + $newCachePrefix = substr(md5($baseUnique), 0, 8) . '.'; | ||
204 | + $cacheList = $this->getCellList(); | ||
205 | + foreach ($cacheList as $cellID) { | ||
206 | + if ($cellID != $this->currentObjectID) { | ||
207 | + $obj = apc_fetch($this->cachePrefix . $cellID . '.cache'); | ||
208 | + if ($obj === false) { | ||
209 | + // Entry no longer exists in APC, so clear it from the cache array | ||
210 | + parent::deleteCacheData($cellID); | ||
211 | + throw new PHPExcel_Exception('Cell entry ' . $cellID . ' no longer exists in APC'); | ||
212 | + } | ||
213 | + if (!apc_store($newCachePrefix . $cellID . '.cache', $obj, $this->cacheTime)) { | ||
214 | + $this->__destruct(); | ||
215 | + throw new PHPExcel_Exception('Failed to store cell ' . $cellID . ' in APC'); | ||
216 | + } | ||
217 | + } | ||
218 | + } | ||
219 | + $this->cachePrefix = $newCachePrefix; | ||
220 | + } | ||
221 | + | ||
222 | + /** | ||
223 | + * Clear the cell collection and disconnect from our parent | ||
224 | + * | ||
225 | + * @return void | ||
226 | + */ | ||
227 | + public function unsetWorksheetCells() | ||
228 | + { | ||
229 | + if ($this->currentObject !== null) { | ||
230 | + $this->currentObject->detach(); | ||
231 | + $this->currentObject = $this->currentObjectID = null; | ||
232 | + } | ||
233 | + | ||
234 | + // Flush the APC cache | ||
235 | + $this->__destruct(); | ||
236 | + | ||
237 | + $this->cellCache = array(); | ||
238 | + | ||
239 | + // detach ourself from the worksheet, so that it can then delete this object successfully | ||
240 | + $this->parent = null; | ||
241 | + } | ||
242 | + | ||
243 | + /** | ||
244 | + * Initialise this new cell collection | ||
245 | + * | ||
246 | + * @param PHPExcel_Worksheet $parent The worksheet for this cell collection | ||
247 | + * @param array of mixed $arguments Additional initialisation arguments | ||
248 | + */ | ||
249 | + public function __construct(PHPExcel_Worksheet $parent, $arguments) | ||
250 | + { | ||
251 | + $cacheTime = (isset($arguments['cacheTime'])) ? $arguments['cacheTime'] : 600; | ||
252 | + | ||
253 | + if ($this->cachePrefix === null) { | ||
254 | + $baseUnique = $this->getUniqueID(); | ||
255 | + $this->cachePrefix = substr(md5($baseUnique), 0, 8) . '.'; | ||
256 | + $this->cacheTime = $cacheTime; | ||
257 | + | ||
258 | + parent::__construct($parent); | ||
259 | + } | ||
260 | + } | ||
261 | + | ||
262 | + /** | ||
263 | + * Destroy this cell collection | ||
264 | + */ | ||
265 | + public function __destruct() | ||
266 | + { | ||
267 | + $cacheList = $this->getCellList(); | ||
268 | + foreach ($cacheList as $cellID) { | ||
269 | + apc_delete($this->cachePrefix . $cellID . '.cache'); | ||
270 | + } | ||
271 | + } | ||
272 | + | ||
273 | + /** | ||
274 | + * Identify whether the caching method is currently available | ||
275 | + * Some methods are dependent on the availability of certain extensions being enabled in the PHP build | ||
276 | + * | ||
277 | + * @return boolean | ||
278 | + */ | ||
279 | + public static function cacheMethodIsAvailable() | ||
280 | + { | ||
281 | + if (!function_exists('apc_store')) { | ||
282 | + return false; | ||
283 | + } | ||
284 | + if (apc_sma_info() === false) { | ||
285 | + return false; | ||
286 | + } | ||
287 | + | ||
288 | + return true; | ||
289 | + } | ||
290 | +} |
1 | +<?php | ||
2 | + | ||
3 | +/** | ||
4 | + * PHPExcel_CachedObjectStorage_CacheBase | ||
5 | + * | ||
6 | + * Copyright (c) 2006 - 2015 PHPExcel | ||
7 | + * | ||
8 | + * This library is free software; you can redistribute it and/or | ||
9 | + * modify it under the terms of the GNU Lesser General Public | ||
10 | + * License as published by the Free Software Foundation; either | ||
11 | + * version 2.1 of the License, or (at your option) any later version. | ||
12 | + * | ||
13 | + * This library is distributed in the hope that it will be useful, | ||
14 | + * but WITHOUT ANY WARRANTY; without even the implied warranty of | ||
15 | + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU | ||
16 | + * Lesser General Public License for more details. | ||
17 | + * | ||
18 | + * You should have received a copy of the GNU Lesser General Public | ||
19 | + * License along with this library; if not, write to the Free Software | ||
20 | + * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA | ||
21 | + * | ||
22 | + * @category PHPExcel | ||
23 | + * @package PHPExcel_CachedObjectStorage | ||
24 | + * @copyright Copyright (c) 2006 - 2015 PHPExcel (http://www.codeplex.com/PHPExcel) | ||
25 | + * @license http://www.gnu.org/licenses/old-licenses/lgpl-2.1.txt LGPL | ||
26 | + * @version ##VERSION##, ##DATE## | ||
27 | + */ | ||
28 | +abstract class PHPExcel_CachedObjectStorage_CacheBase | ||
29 | +{ | ||
30 | + /** | ||
31 | + * Parent worksheet | ||
32 | + * | ||
33 | + * @var PHPExcel_Worksheet | ||
34 | + */ | ||
35 | + protected $parent; | ||
36 | + | ||
37 | + /** | ||
38 | + * The currently active Cell | ||
39 | + * | ||
40 | + * @var PHPExcel_Cell | ||
41 | + */ | ||
42 | + protected $currentObject = null; | ||
43 | + | ||
44 | + /** | ||
45 | + * Coordinate address of the currently active Cell | ||
46 | + * | ||
47 | + * @var string | ||
48 | + */ | ||
49 | + protected $currentObjectID = null; | ||
50 | + | ||
51 | + /** | ||
52 | + * Flag indicating whether the currently active Cell requires saving | ||
53 | + * | ||
54 | + * @var boolean | ||
55 | + */ | ||
56 | + protected $currentCellIsDirty = true; | ||
57 | + | ||
58 | + /** | ||
59 | + * An array of cells or cell pointers for the worksheet cells held in this cache, | ||
60 | + * and indexed by their coordinate address within the worksheet | ||
61 | + * | ||
62 | + * @var array of mixed | ||
63 | + */ | ||
64 | + protected $cellCache = array(); | ||
65 | + | ||
66 | + /** | ||
67 | + * Initialise this new cell collection | ||
68 | + * | ||
69 | + * @param PHPExcel_Worksheet $parent The worksheet for this cell collection | ||
70 | + */ | ||
71 | + public function __construct(PHPExcel_Worksheet $parent) | ||
72 | + { | ||
73 | + // Set our parent worksheet. | ||
74 | + // This is maintained within the cache controller to facilitate re-attaching it to PHPExcel_Cell objects when | ||
75 | + // they are woken from a serialized state | ||
76 | + $this->parent = $parent; | ||
77 | + } | ||
78 | + | ||
79 | + /** | ||
80 | + * Return the parent worksheet for this cell collection | ||
81 | + * | ||
82 | + * @return PHPExcel_Worksheet | ||
83 | + */ | ||
84 | + public function getParent() | ||
85 | + { | ||
86 | + return $this->parent; | ||
87 | + } | ||
88 | + | ||
89 | + /** | ||
90 | + * Is a value set in the current PHPExcel_CachedObjectStorage_ICache for an indexed cell? | ||
91 | + * | ||
92 | + * @param string $pCoord Coordinate address of the cell to check | ||
93 | + * @return boolean | ||
94 | + */ | ||
95 | + public function isDataSet($pCoord) | ||
96 | + { | ||
97 | + if ($pCoord === $this->currentObjectID) { | ||
98 | + return true; | ||
99 | + } | ||
100 | + // Check if the requested entry exists in the cache | ||
101 | + return isset($this->cellCache[$pCoord]); | ||
102 | + } | ||
103 | + | ||
104 | + /** | ||
105 | + * Move a cell object from one address to another | ||
106 | + * | ||
107 | + * @param string $fromAddress Current address of the cell to move | ||
108 | + * @param string $toAddress Destination address of the cell to move | ||
109 | + * @return boolean | ||
110 | + */ | ||
111 | + public function moveCell($fromAddress, $toAddress) | ||
112 | + { | ||
113 | + if ($fromAddress === $this->currentObjectID) { | ||
114 | + $this->currentObjectID = $toAddress; | ||
115 | + } | ||
116 | + $this->currentCellIsDirty = true; | ||
117 | + if (isset($this->cellCache[$fromAddress])) { | ||
118 | + $this->cellCache[$toAddress] = &$this->cellCache[$fromAddress]; | ||
119 | + unset($this->cellCache[$fromAddress]); | ||
120 | + } | ||
121 | + | ||
122 | + return true; | ||
123 | + } | ||
124 | + | ||
125 | + /** | ||
126 | + * Add or Update a cell in cache | ||
127 | + * | ||
128 | + * @param PHPExcel_Cell $cell Cell to update | ||
129 | + * @return PHPExcel_Cell | ||
130 | + * @throws PHPExcel_Exception | ||
131 | + */ | ||
132 | + public function updateCacheData(PHPExcel_Cell $cell) | ||
133 | + { | ||
134 | + return $this->addCacheData($cell->getCoordinate(), $cell); | ||
135 | + } | ||
136 | + | ||
137 | + /** | ||
138 | + * Delete a cell in cache identified by coordinate address | ||
139 | + * | ||
140 | + * @param string $pCoord Coordinate address of the cell to delete | ||
141 | + * @throws PHPExcel_Exception | ||
142 | + */ | ||
143 | + public function deleteCacheData($pCoord) | ||
144 | + { | ||
145 | + if ($pCoord === $this->currentObjectID && !is_null($this->currentObject)) { | ||
146 | + $this->currentObject->detach(); | ||
147 | + $this->currentObjectID = $this->currentObject = null; | ||
148 | + } | ||
149 | + | ||
150 | + if (is_object($this->cellCache[$pCoord])) { | ||
151 | + $this->cellCache[$pCoord]->detach(); | ||
152 | + unset($this->cellCache[$pCoord]); | ||
153 | + } | ||
154 | + $this->currentCellIsDirty = false; | ||
155 | + } | ||
156 | + | ||
157 | + /** | ||
158 | + * Get a list of all cell addresses currently held in cache | ||
159 | + * | ||
160 | + * @return string[] | ||
161 | + */ | ||
162 | + public function getCellList() | ||
163 | + { | ||
164 | + return array_keys($this->cellCache); | ||
165 | + } | ||
166 | + | ||
167 | + /** | ||
168 | + * Sort the list of all cell addresses currently held in cache by row and column | ||
169 | + * | ||
170 | + * @return string[] | ||
171 | + */ | ||
172 | + public function getSortedCellList() | ||
173 | + { | ||
174 | + $sortKeys = array(); | ||
175 | + foreach ($this->getCellList() as $coord) { | ||
176 | + sscanf($coord, '%[A-Z]%d', $column, $row); | ||
177 | + $sortKeys[sprintf('%09d%3s', $row, $column)] = $coord; | ||
178 | + } | ||
179 | + ksort($sortKeys); | ||
180 | + | ||
181 | + return array_values($sortKeys); | ||
182 | + } | ||
183 | + | ||
184 | + /** | ||
185 | + * Get highest worksheet column and highest row that have cell records | ||
186 | + * | ||
187 | + * @return array Highest column name and highest row number | ||
188 | + */ | ||
189 | + public function getHighestRowAndColumn() | ||
190 | + { | ||
191 | + // Lookup highest column and highest row | ||
192 | + $col = array('A' => '1A'); | ||
193 | + $row = array(1); | ||
194 | + foreach ($this->getCellList() as $coord) { | ||
195 | + sscanf($coord, '%[A-Z]%d', $c, $r); | ||
196 | + $row[$r] = $r; | ||
197 | + $col[$c] = strlen($c).$c; | ||
198 | + } | ||
199 | + if (!empty($row)) { | ||
200 | + // Determine highest column and row | ||
201 | + $highestRow = max($row); | ||
202 | + $highestColumn = substr(max($col), 1); | ||
203 | + } | ||
204 | + | ||
205 | + return array( | ||
206 | + 'row' => $highestRow, | ||
207 | + 'column' => $highestColumn | ||
208 | + ); | ||
209 | + } | ||
210 | + | ||
211 | + /** | ||
212 | + * Return the cell address of the currently active cell object | ||
213 | + * | ||
214 | + * @return string | ||
215 | + */ | ||
216 | + public function getCurrentAddress() | ||
217 | + { | ||
218 | + return $this->currentObjectID; | ||
219 | + } | ||
220 | + | ||
221 | + /** | ||
222 | + * Return the column address of the currently active cell object | ||
223 | + * | ||
224 | + * @return string | ||
225 | + */ | ||
226 | + public function getCurrentColumn() | ||
227 | + { | ||
228 | + sscanf($this->currentObjectID, '%[A-Z]%d', $column, $row); | ||
229 | + return $column; | ||
230 | + } | ||
231 | + | ||
232 | + /** | ||
233 | + * Return the row address of the currently active cell object | ||
234 | + * | ||
235 | + * @return integer | ||
236 | + */ | ||
237 | + public function getCurrentRow() | ||
238 | + { | ||
239 | + sscanf($this->currentObjectID, '%[A-Z]%d', $column, $row); | ||
240 | + return (integer) $row; | ||
241 | + } | ||
242 | + | ||
243 | + /** | ||
244 | + * Get highest worksheet column | ||
245 | + * | ||
246 | + * @param string $row Return the highest column for the specified row, | ||
247 | + * or the highest column of any row if no row number is passed | ||
248 | + * @return string Highest column name | ||
249 | + */ | ||
250 | + public function getHighestColumn($row = null) | ||
251 | + { | ||
252 | + if ($row == null) { | ||
253 | + $colRow = $this->getHighestRowAndColumn(); | ||
254 | + return $colRow['column']; | ||
255 | + } | ||
256 | + | ||
257 | + $columnList = array(1); | ||
258 | + foreach ($this->getCellList() as $coord) { | ||
259 | + sscanf($coord, '%[A-Z]%d', $c, $r); | ||
260 | + if ($r != $row) { | ||
261 | + continue; | ||
262 | + } | ||
263 | + $columnList[] = PHPExcel_Cell::columnIndexFromString($c); | ||
264 | + } | ||
265 | + return PHPExcel_Cell::stringFromColumnIndex(max($columnList) - 1); | ||
266 | + } | ||
267 | + | ||
268 | + /** | ||
269 | + * Get highest worksheet row | ||
270 | + * | ||
271 | + * @param string $column Return the highest row for the specified column, | ||
272 | + * or the highest row of any column if no column letter is passed | ||
273 | + * @return int Highest row number | ||
274 | + */ | ||
275 | + public function getHighestRow($column = null) | ||
276 | + { | ||
277 | + if ($column == null) { | ||
278 | + $colRow = $this->getHighestRowAndColumn(); | ||
279 | + return $colRow['row']; | ||
280 | + } | ||
281 | + | ||
282 | + $rowList = array(0); | ||
283 | + foreach ($this->getCellList() as $coord) { | ||
284 | + sscanf($coord, '%[A-Z]%d', $c, $r); | ||
285 | + if ($c != $column) { | ||
286 | + continue; | ||
287 | + } | ||
288 | + $rowList[] = $r; | ||
289 | + } | ||
290 | + | ||
291 | + return max($rowList); | ||
292 | + } | ||
293 | + | ||
294 | + /** | ||
295 | + * Generate a unique ID for cache referencing | ||
296 | + * | ||
297 | + * @return string Unique Reference | ||
298 | + */ | ||
299 | + protected function getUniqueID() | ||
300 | + { | ||
301 | + if (function_exists('posix_getpid')) { | ||
302 | + $baseUnique = posix_getpid(); | ||
303 | + } else { | ||
304 | + $baseUnique = mt_rand(); | ||
305 | + } | ||
306 | + return uniqid($baseUnique, true); | ||
307 | + } | ||
308 | + | ||
309 | + /** | ||
310 | + * Clone the cell collection | ||
311 | + * | ||
312 | + * @param PHPExcel_Worksheet $parent The new worksheet | ||
313 | + * @return void | ||
314 | + */ | ||
315 | + public function copyCellCollection(PHPExcel_Worksheet $parent) | ||
316 | + { | ||
317 | + $this->currentCellIsDirty; | ||
318 | + $this->storeData(); | ||
319 | + | ||
320 | + $this->parent = $parent; | ||
321 | + if (($this->currentObject !== null) && (is_object($this->currentObject))) { | ||
322 | + $this->currentObject->attach($this); | ||
323 | + } | ||
324 | + } // function copyCellCollection() | ||
325 | + | ||
326 | + /** | ||
327 | + * Remove a row, deleting all cells in that row | ||
328 | + * | ||
329 | + * @param string $row Row number to remove | ||
330 | + * @return void | ||
331 | + */ | ||
332 | + public function removeRow($row) | ||
333 | + { | ||
334 | + foreach ($this->getCellList() as $coord) { | ||
335 | + sscanf($coord, '%[A-Z]%d', $c, $r); | ||
336 | + if ($r == $row) { | ||
337 | + $this->deleteCacheData($coord); | ||
338 | + } | ||
339 | + } | ||
340 | + } | ||
341 | + | ||
342 | + /** | ||
343 | + * Remove a column, deleting all cells in that column | ||
344 | + * | ||
345 | + * @param string $column Column ID to remove | ||
346 | + * @return void | ||
347 | + */ | ||
348 | + public function removeColumn($column) | ||
349 | + { | ||
350 | + foreach ($this->getCellList() as $coord) { | ||
351 | + sscanf($coord, '%[A-Z]%d', $c, $r); | ||
352 | + if ($c == $column) { | ||
353 | + $this->deleteCacheData($coord); | ||
354 | + } | ||
355 | + } | ||
356 | + } | ||
357 | + | ||
358 | + /** | ||
359 | + * Identify whether the caching method is currently available | ||
360 | + * Some methods are dependent on the availability of certain extensions being enabled in the PHP build | ||
361 | + * | ||
362 | + * @return boolean | ||
363 | + */ | ||
364 | + public static function cacheMethodIsAvailable() | ||
365 | + { | ||
366 | + return true; | ||
367 | + } | ||
368 | +} |
1 | +<?php | ||
2 | + | ||
3 | +/** | ||
4 | + * PHPExcel_CachedObjectStorage_DiscISAM | ||
5 | + * | ||
6 | + * Copyright (c) 2006 - 2015 PHPExcel | ||
7 | + * | ||
8 | + * This library is free software; you can redistribute it and/or | ||
9 | + * modify it under the terms of the GNU Lesser General Public | ||
10 | + * License as published by the Free Software Foundation; either | ||
11 | + * version 2.1 of the License, or (at your option) any later version. | ||
12 | + * | ||
13 | + * This library is distributed in the hope that it will be useful, | ||
14 | + * but WITHOUT ANY WARRANTY; without even the implied warranty of | ||
15 | + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU | ||
16 | + * Lesser General Public License for more details. | ||
17 | + * | ||
18 | + * You should have received a copy of the GNU Lesser General Public | ||
19 | + * License along with this library; if not, write to the Free Software | ||
20 | + * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA | ||
21 | + * | ||
22 | + * @category PHPExcel | ||
23 | + * @package PHPExcel_CachedObjectStorage | ||
24 | + * @copyright Copyright (c) 2006 - 2015 PHPExcel (http://www.codeplex.com/PHPExcel) | ||
25 | + * @license http://www.gnu.org/licenses/old-licenses/lgpl-2.1.txt LGPL | ||
26 | + * @version ##VERSION##, ##DATE## | ||
27 | + */ | ||
28 | +class PHPExcel_CachedObjectStorage_DiscISAM extends PHPExcel_CachedObjectStorage_CacheBase implements PHPExcel_CachedObjectStorage_ICache | ||
29 | +{ | ||
30 | + /** | ||
31 | + * Name of the file for this cache | ||
32 | + * | ||
33 | + * @var string | ||
34 | + */ | ||
35 | + private $fileName = null; | ||
36 | + | ||
37 | + /** | ||
38 | + * File handle for this cache file | ||
39 | + * | ||
40 | + * @var resource | ||
41 | + */ | ||
42 | + private $fileHandle = null; | ||
43 | + | ||
44 | + /** | ||
45 | + * Directory/Folder where the cache file is located | ||
46 | + * | ||
47 | + * @var string | ||
48 | + */ | ||
49 | + private $cacheDirectory = null; | ||
50 | + | ||
51 | + /** | ||
52 | + * Store cell data in cache for the current cell object if it's "dirty", | ||
53 | + * and the 'nullify' the current cell object | ||
54 | + * | ||
55 | + * @return void | ||
56 | + * @throws PHPExcel_Exception | ||
57 | + */ | ||
58 | + protected function storeData() | ||
59 | + { | ||
60 | + if ($this->currentCellIsDirty && !empty($this->currentObjectID)) { | ||
61 | + $this->currentObject->detach(); | ||
62 | + | ||
63 | + fseek($this->fileHandle, 0, SEEK_END); | ||
64 | + | ||
65 | + $this->cellCache[$this->currentObjectID] = array( | ||
66 | + 'ptr' => ftell($this->fileHandle), | ||
67 | + 'sz' => fwrite($this->fileHandle, serialize($this->currentObject)) | ||
68 | + ); | ||
69 | + $this->currentCellIsDirty = false; | ||
70 | + } | ||
71 | + $this->currentObjectID = $this->currentObject = null; | ||
72 | + } | ||
73 | + | ||
74 | + /** | ||
75 | + * Add or Update a cell in cache identified by coordinate address | ||
76 | + * | ||
77 | + * @param string $pCoord Coordinate address of the cell to update | ||
78 | + * @param PHPExcel_Cell $cell Cell to update | ||
79 | + * @return PHPExcel_Cell | ||
80 | + * @throws PHPExcel_Exception | ||
81 | + */ | ||
82 | + public function addCacheData($pCoord, PHPExcel_Cell $cell) | ||
83 | + { | ||
84 | + if (($pCoord !== $this->currentObjectID) && ($this->currentObjectID !== null)) { | ||
85 | + $this->storeData(); | ||
86 | + } | ||
87 | + | ||
88 | + $this->currentObjectID = $pCoord; | ||
89 | + $this->currentObject = $cell; | ||
90 | + $this->currentCellIsDirty = true; | ||
91 | + | ||
92 | + return $cell; | ||
93 | + } | ||
94 | + | ||
95 | + /** | ||
96 | + * Get cell at a specific coordinate | ||
97 | + * | ||
98 | + * @param string $pCoord Coordinate of the cell | ||
99 | + * @throws PHPExcel_Exception | ||
100 | + * @return PHPExcel_Cell Cell that was found, or null if not found | ||
101 | + */ | ||
102 | + public function getCacheData($pCoord) | ||
103 | + { | ||
104 | + if ($pCoord === $this->currentObjectID) { | ||
105 | + return $this->currentObject; | ||
106 | + } | ||
107 | + $this->storeData(); | ||
108 | + | ||
109 | + // Check if the entry that has been requested actually exists | ||
110 | + if (!isset($this->cellCache[$pCoord])) { | ||
111 | + // Return null if requested entry doesn't exist in cache | ||
112 | + return null; | ||
113 | + } | ||
114 | + | ||
115 | + // Set current entry to the requested entry | ||
116 | + $this->currentObjectID = $pCoord; | ||
117 | + fseek($this->fileHandle, $this->cellCache[$pCoord]['ptr']); | ||
118 | + $this->currentObject = unserialize(fread($this->fileHandle, $this->cellCache[$pCoord]['sz'])); | ||
119 | + // Re-attach this as the cell's parent | ||
120 | + $this->currentObject->attach($this); | ||
121 | + | ||
122 | + // Return requested entry | ||
123 | + return $this->currentObject; | ||
124 | + } | ||
125 | + | ||
126 | + /** | ||
127 | + * Get a list of all cell addresses currently held in cache | ||
128 | + * | ||
129 | + * @return string[] | ||
130 | + */ | ||
131 | + public function getCellList() | ||
132 | + { | ||
133 | + if ($this->currentObjectID !== null) { | ||
134 | + $this->storeData(); | ||
135 | + } | ||
136 | + | ||
137 | + return parent::getCellList(); | ||
138 | + } | ||
139 | + | ||
140 | + /** | ||
141 | + * Clone the cell collection | ||
142 | + * | ||
143 | + * @param PHPExcel_Worksheet $parent The new worksheet | ||
144 | + */ | ||
145 | + public function copyCellCollection(PHPExcel_Worksheet $parent) | ||
146 | + { | ||
147 | + parent::copyCellCollection($parent); | ||
148 | + // Get a new id for the new file name | ||
149 | + $baseUnique = $this->getUniqueID(); | ||
150 | + $newFileName = $this->cacheDirectory.'/PHPExcel.'.$baseUnique.'.cache'; | ||
151 | + // Copy the existing cell cache file | ||
152 | + copy($this->fileName, $newFileName); | ||
153 | + $this->fileName = $newFileName; | ||
154 | + // Open the copied cell cache file | ||
155 | + $this->fileHandle = fopen($this->fileName, 'a+'); | ||
156 | + } | ||
157 | + | ||
158 | + /** | ||
159 | + * Clear the cell collection and disconnect from our parent | ||
160 | + * | ||
161 | + */ | ||
162 | + public function unsetWorksheetCells() | ||
163 | + { | ||
164 | + if (!is_null($this->currentObject)) { | ||
165 | + $this->currentObject->detach(); | ||
166 | + $this->currentObject = $this->currentObjectID = null; | ||
167 | + } | ||
168 | + $this->cellCache = array(); | ||
169 | + | ||
170 | + // detach ourself from the worksheet, so that it can then delete this object successfully | ||
171 | + $this->parent = null; | ||
172 | + | ||
173 | + // Close down the temporary cache file | ||
174 | + $this->__destruct(); | ||
175 | + } | ||
176 | + | ||
177 | + /** | ||
178 | + * Initialise this new cell collection | ||
179 | + * | ||
180 | + * @param PHPExcel_Worksheet $parent The worksheet for this cell collection | ||
181 | + * @param array of mixed $arguments Additional initialisation arguments | ||
182 | + */ | ||
183 | + public function __construct(PHPExcel_Worksheet $parent, $arguments) | ||
184 | + { | ||
185 | + $this->cacheDirectory = ((isset($arguments['dir'])) && ($arguments['dir'] !== null)) | ||
186 | + ? $arguments['dir'] | ||
187 | + : PHPExcel_Shared_File::sys_get_temp_dir(); | ||
188 | + | ||
189 | + parent::__construct($parent); | ||
190 | + if (is_null($this->fileHandle)) { | ||
191 | + $baseUnique = $this->getUniqueID(); | ||
192 | + $this->fileName = $this->cacheDirectory.'/PHPExcel.'.$baseUnique.'.cache'; | ||
193 | + $this->fileHandle = fopen($this->fileName, 'a+'); | ||
194 | + } | ||
195 | + } | ||
196 | + | ||
197 | + /** | ||
198 | + * Destroy this cell collection | ||
199 | + */ | ||
200 | + public function __destruct() | ||
201 | + { | ||
202 | + if (!is_null($this->fileHandle)) { | ||
203 | + fclose($this->fileHandle); | ||
204 | + unlink($this->fileName); | ||
205 | + } | ||
206 | + $this->fileHandle = null; | ||
207 | + } | ||
208 | +} |
1 | +<?php | ||
2 | + | ||
3 | +/** | ||
4 | + * PHPExcel_CachedObjectStorage_ICache | ||
5 | + * | ||
6 | + * Copyright (c) 2006 - 2015 PHPExcel | ||
7 | + * | ||
8 | + * This library is free software; you can redistribute it and/or | ||
9 | + * modify it under the terms of the GNU Lesser General Public | ||
10 | + * License as published by the Free Software Foundation; either | ||
11 | + * version 2.1 of the License, or (at your option) any later version. | ||
12 | + * | ||
13 | + * This library is distributed in the hope that it will be useful, | ||
14 | + * but WITHOUT ANY WARRANTY; without even the implied warranty of | ||
15 | + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU | ||
16 | + * Lesser General Public License for more details. | ||
17 | + * | ||
18 | + * You should have received a copy of the GNU Lesser General Public | ||
19 | + * License along with this library; if not, write to the Free Software | ||
20 | + * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA | ||
21 | + * | ||
22 | + * @category PHPExcel | ||
23 | + * @package PHPExcel_CachedObjectStorage | ||
24 | + * @copyright Copyright (c) 2006 - 2015 PHPExcel (http://www.codeplex.com/PHPExcel) | ||
25 | + * @license http://www.gnu.org/licenses/old-licenses/lgpl-2.1.txt LGPL | ||
26 | + * @version ##VERSION##, ##DATE## | ||
27 | + */ | ||
28 | +interface PHPExcel_CachedObjectStorage_ICache | ||
29 | +{ | ||
30 | + /** | ||
31 | + * Add or Update a cell in cache identified by coordinate address | ||
32 | + * | ||
33 | + * @param string $pCoord Coordinate address of the cell to update | ||
34 | + * @param PHPExcel_Cell $cell Cell to update | ||
35 | + * @return PHPExcel_Cell | ||
36 | + * @throws PHPExcel_Exception | ||
37 | + */ | ||
38 | + public function addCacheData($pCoord, PHPExcel_Cell $cell); | ||
39 | + | ||
40 | + /** | ||
41 | + * Add or Update a cell in cache | ||
42 | + * | ||
43 | + * @param PHPExcel_Cell $cell Cell to update | ||
44 | + * @return PHPExcel_Cell | ||
45 | + * @throws PHPExcel_Exception | ||
46 | + */ | ||
47 | + public function updateCacheData(PHPExcel_Cell $cell); | ||
48 | + | ||
49 | + /** | ||
50 | + * Fetch a cell from cache identified by coordinate address | ||
51 | + * | ||
52 | + * @param string $pCoord Coordinate address of the cell to retrieve | ||
53 | + * @return PHPExcel_Cell Cell that was found, or null if not found | ||
54 | + * @throws PHPExcel_Exception | ||
55 | + */ | ||
56 | + public function getCacheData($pCoord); | ||
57 | + | ||
58 | + /** | ||
59 | + * Delete a cell in cache identified by coordinate address | ||
60 | + * | ||
61 | + * @param string $pCoord Coordinate address of the cell to delete | ||
62 | + * @throws PHPExcel_Exception | ||
63 | + */ | ||
64 | + public function deleteCacheData($pCoord); | ||
65 | + | ||
66 | + /** | ||
67 | + * Is a value set in the current PHPExcel_CachedObjectStorage_ICache for an indexed cell? | ||
68 | + * | ||
69 | + * @param string $pCoord Coordinate address of the cell to check | ||
70 | + * @return boolean | ||
71 | + */ | ||
72 | + public function isDataSet($pCoord); | ||
73 | + | ||
74 | + /** | ||
75 | + * Get a list of all cell addresses currently held in cache | ||
76 | + * | ||
77 | + * @return string[] | ||
78 | + */ | ||
79 | + public function getCellList(); | ||
80 | + | ||
81 | + /** | ||
82 | + * Get the list of all cell addresses currently held in cache sorted by column and row | ||
83 | + * | ||
84 | + * @return string[] | ||
85 | + */ | ||
86 | + public function getSortedCellList(); | ||
87 | + | ||
88 | + /** | ||
89 | + * Clone the cell collection | ||
90 | + * | ||
91 | + * @param PHPExcel_Worksheet $parent The new worksheet | ||
92 | + * @return void | ||
93 | + */ | ||
94 | + public function copyCellCollection(PHPExcel_Worksheet $parent); | ||
95 | + | ||
96 | + /** | ||
97 | + * Identify whether the caching method is currently available | ||
98 | + * Some methods are dependent on the availability of certain extensions being enabled in the PHP build | ||
99 | + * | ||
100 | + * @return boolean | ||
101 | + */ | ||
102 | + public static function cacheMethodIsAvailable(); | ||
103 | +} |
1 | +<?php | ||
2 | + | ||
3 | +/** | ||
4 | + * PHPExcel_CachedObjectStorage_Igbinary | ||
5 | + * | ||
6 | + * Copyright (c) 2006 - 2015 PHPExcel | ||
7 | + * | ||
8 | + * This library is free software; you can redistribute it and/or | ||
9 | + * modify it under the terms of the GNU Lesser General Public | ||
10 | + * License as published by the Free Software Foundation; either | ||
11 | + * version 2.1 of the License, or (at your option) any later version. | ||
12 | + * | ||
13 | + * This library is distributed in the hope that it will be useful, | ||
14 | + * but WITHOUT ANY WARRANTY; without even the implied warranty of | ||
15 | + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU | ||
16 | + * Lesser General Public License for more details. | ||
17 | + * | ||
18 | + * You should have received a copy of the GNU Lesser General Public | ||
19 | + * License along with this library; if not, write to the Free Software | ||
20 | + * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA | ||
21 | + * | ||
22 | + * @category PHPExcel | ||
23 | + * @package PHPExcel_CachedObjectStorage | ||
24 | + * @copyright Copyright (c) 2006 - 2015 PHPExcel (http://www.codeplex.com/PHPExcel) | ||
25 | + * @license http://www.gnu.org/licenses/old-licenses/lgpl-2.1.txt LGPL | ||
26 | + * @version ##VERSION##, ##DATE## | ||
27 | + */ | ||
28 | +class PHPExcel_CachedObjectStorage_Igbinary extends PHPExcel_CachedObjectStorage_CacheBase implements PHPExcel_CachedObjectStorage_ICache | ||
29 | +{ | ||
30 | + /** | ||
31 | + * Store cell data in cache for the current cell object if it's "dirty", | ||
32 | + * and the 'nullify' the current cell object | ||
33 | + * | ||
34 | + * @return void | ||
35 | + * @throws PHPExcel_Exception | ||
36 | + */ | ||
37 | + protected function storeData() | ||
38 | + { | ||
39 | + if ($this->currentCellIsDirty && !empty($this->currentObjectID)) { | ||
40 | + $this->currentObject->detach(); | ||
41 | + | ||
42 | + $this->cellCache[$this->currentObjectID] = igbinary_serialize($this->currentObject); | ||
43 | + $this->currentCellIsDirty = false; | ||
44 | + } | ||
45 | + $this->currentObjectID = $this->currentObject = null; | ||
46 | + } // function _storeData() | ||
47 | + | ||
48 | + | ||
49 | + /** | ||
50 | + * Add or Update a cell in cache identified by coordinate address | ||
51 | + * | ||
52 | + * @param string $pCoord Coordinate address of the cell to update | ||
53 | + * @param PHPExcel_Cell $cell Cell to update | ||
54 | + * @return PHPExcel_Cell | ||
55 | + * @throws PHPExcel_Exception | ||
56 | + */ | ||
57 | + public function addCacheData($pCoord, PHPExcel_Cell $cell) | ||
58 | + { | ||
59 | + if (($pCoord !== $this->currentObjectID) && ($this->currentObjectID !== null)) { | ||
60 | + $this->storeData(); | ||
61 | + } | ||
62 | + | ||
63 | + $this->currentObjectID = $pCoord; | ||
64 | + $this->currentObject = $cell; | ||
65 | + $this->currentCellIsDirty = true; | ||
66 | + | ||
67 | + return $cell; | ||
68 | + } // function addCacheData() | ||
69 | + | ||
70 | + | ||
71 | + /** | ||
72 | + * Get cell at a specific coordinate | ||
73 | + * | ||
74 | + * @param string $pCoord Coordinate of the cell | ||
75 | + * @throws PHPExcel_Exception | ||
76 | + * @return PHPExcel_Cell Cell that was found, or null if not found | ||
77 | + */ | ||
78 | + public function getCacheData($pCoord) | ||
79 | + { | ||
80 | + if ($pCoord === $this->currentObjectID) { | ||
81 | + return $this->currentObject; | ||
82 | + } | ||
83 | + $this->storeData(); | ||
84 | + | ||
85 | + // Check if the entry that has been requested actually exists | ||
86 | + if (!isset($this->cellCache[$pCoord])) { | ||
87 | + // Return null if requested entry doesn't exist in cache | ||
88 | + return null; | ||
89 | + } | ||
90 | + | ||
91 | + // Set current entry to the requested entry | ||
92 | + $this->currentObjectID = $pCoord; | ||
93 | + $this->currentObject = igbinary_unserialize($this->cellCache[$pCoord]); | ||
94 | + // Re-attach this as the cell's parent | ||
95 | + $this->currentObject->attach($this); | ||
96 | + | ||
97 | + // Return requested entry | ||
98 | + return $this->currentObject; | ||
99 | + } // function getCacheData() | ||
100 | + | ||
101 | + | ||
102 | + /** | ||
103 | + * Get a list of all cell addresses currently held in cache | ||
104 | + * | ||
105 | + * @return string[] | ||
106 | + */ | ||
107 | + public function getCellList() | ||
108 | + { | ||
109 | + if ($this->currentObjectID !== null) { | ||
110 | + $this->storeData(); | ||
111 | + } | ||
112 | + | ||
113 | + return parent::getCellList(); | ||
114 | + } | ||
115 | + | ||
116 | + | ||
117 | + /** | ||
118 | + * Clear the cell collection and disconnect from our parent | ||
119 | + * | ||
120 | + * @return void | ||
121 | + */ | ||
122 | + public function unsetWorksheetCells() | ||
123 | + { | ||
124 | + if (!is_null($this->currentObject)) { | ||
125 | + $this->currentObject->detach(); | ||
126 | + $this->currentObject = $this->currentObjectID = null; | ||
127 | + } | ||
128 | + $this->cellCache = array(); | ||
129 | + | ||
130 | + // detach ourself from the worksheet, so that it can then delete this object successfully | ||
131 | + $this->parent = null; | ||
132 | + } // function unsetWorksheetCells() | ||
133 | + | ||
134 | + | ||
135 | + /** | ||
136 | + * Identify whether the caching method is currently available | ||
137 | + * Some methods are dependent on the availability of certain extensions being enabled in the PHP build | ||
138 | + * | ||
139 | + * @return boolean | ||
140 | + */ | ||
141 | + public static function cacheMethodIsAvailable() | ||
142 | + { | ||
143 | + if (!function_exists('igbinary_serialize')) { | ||
144 | + return false; | ||
145 | + } | ||
146 | + | ||
147 | + return true; | ||
148 | + } | ||
149 | +} |
1 | +<?php | ||
2 | + | ||
3 | +/** | ||
4 | + * PHPExcel_CachedObjectStorage_Memcache | ||
5 | + * | ||
6 | + * Copyright (c) 2006 - 2015 PHPExcel | ||
7 | + * | ||
8 | + * This library is free software; you can redistribute it and/or | ||
9 | + * modify it under the terms of the GNU Lesser General Public | ||
10 | + * License as published by the Free Software Foundation; either | ||
11 | + * version 2.1 of the License, or (at your option) any later version. | ||
12 | + * | ||
13 | + * This library is distributed in the hope that it will be useful, | ||
14 | + * but WITHOUT ANY WARRANTY; without even the implied warranty of | ||
15 | + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU | ||
16 | + * Lesser General Public License for more details. | ||
17 | + * | ||
18 | + * You should have received a copy of the GNU Lesser General Public | ||
19 | + * License along with this library; if not, write to the Free Software | ||
20 | + * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA | ||
21 | + * | ||
22 | + * @category PHPExcel | ||
23 | + * @package PHPExcel_CachedObjectStorage | ||
24 | + * @copyright Copyright (c) 2006 - 2015 PHPExcel (http://www.codeplex.com/PHPExcel) | ||
25 | + * @license http://www.gnu.org/licenses/old-licenses/lgpl-2.1.txt LGPL | ||
26 | + * @version ##VERSION##, ##DATE## | ||
27 | + */ | ||
28 | +class PHPExcel_CachedObjectStorage_Memcache extends PHPExcel_CachedObjectStorage_CacheBase implements PHPExcel_CachedObjectStorage_ICache | ||
29 | +{ | ||
30 | + /** | ||
31 | + * Prefix used to uniquely identify cache data for this worksheet | ||
32 | + * | ||
33 | + * @var string | ||
34 | + */ | ||
35 | + private $cachePrefix = null; | ||
36 | + | ||
37 | + /** | ||
38 | + * Cache timeout | ||
39 | + * | ||
40 | + * @var integer | ||
41 | + */ | ||
42 | + private $cacheTime = 600; | ||
43 | + | ||
44 | + /** | ||
45 | + * Memcache interface | ||
46 | + * | ||
47 | + * @var resource | ||
48 | + */ | ||
49 | + private $memcache = null; | ||
50 | + | ||
51 | + | ||
52 | + /** | ||
53 | + * Store cell data in cache for the current cell object if it's "dirty", | ||
54 | + * and the 'nullify' the current cell object | ||
55 | + * | ||
56 | + * @return void | ||
57 | + * @throws PHPExcel_Exception | ||
58 | + */ | ||
59 | + protected function storeData() | ||
60 | + { | ||
61 | + if ($this->currentCellIsDirty && !empty($this->currentObjectID)) { | ||
62 | + $this->currentObject->detach(); | ||
63 | + | ||
64 | + $obj = serialize($this->currentObject); | ||
65 | + if (!$this->memcache->replace($this->cachePrefix . $this->currentObjectID . '.cache', $obj, null, $this->cacheTime)) { | ||
66 | + if (!$this->memcache->add($this->cachePrefix . $this->currentObjectID . '.cache', $obj, null, $this->cacheTime)) { | ||
67 | + $this->__destruct(); | ||
68 | + throw new PHPExcel_Exception("Failed to store cell {$this->currentObjectID} in MemCache"); | ||
69 | + } | ||
70 | + } | ||
71 | + $this->currentCellIsDirty = false; | ||
72 | + } | ||
73 | + $this->currentObjectID = $this->currentObject = null; | ||
74 | + } // function _storeData() | ||
75 | + | ||
76 | + | ||
77 | + /** | ||
78 | + * Add or Update a cell in cache identified by coordinate address | ||
79 | + * | ||
80 | + * @param string $pCoord Coordinate address of the cell to update | ||
81 | + * @param PHPExcel_Cell $cell Cell to update | ||
82 | + * @return PHPExcel_Cell | ||
83 | + * @throws PHPExcel_Exception | ||
84 | + */ | ||
85 | + public function addCacheData($pCoord, PHPExcel_Cell $cell) | ||
86 | + { | ||
87 | + if (($pCoord !== $this->currentObjectID) && ($this->currentObjectID !== null)) { | ||
88 | + $this->storeData(); | ||
89 | + } | ||
90 | + $this->cellCache[$pCoord] = true; | ||
91 | + | ||
92 | + $this->currentObjectID = $pCoord; | ||
93 | + $this->currentObject = $cell; | ||
94 | + $this->currentCellIsDirty = true; | ||
95 | + | ||
96 | + return $cell; | ||
97 | + } // function addCacheData() | ||
98 | + | ||
99 | + | ||
100 | + /** | ||
101 | + * Is a value set in the current PHPExcel_CachedObjectStorage_ICache for an indexed cell? | ||
102 | + * | ||
103 | + * @param string $pCoord Coordinate address of the cell to check | ||
104 | + * @return boolean | ||
105 | + * @return boolean | ||
106 | + */ | ||
107 | + public function isDataSet($pCoord) | ||
108 | + { | ||
109 | + // Check if the requested entry is the current object, or exists in the cache | ||
110 | + if (parent::isDataSet($pCoord)) { | ||
111 | + if ($this->currentObjectID == $pCoord) { | ||
112 | + return true; | ||
113 | + } | ||
114 | + // Check if the requested entry still exists in Memcache | ||
115 | + $success = $this->memcache->get($this->cachePrefix.$pCoord.'.cache'); | ||
116 | + if ($success === false) { | ||
117 | + // Entry no longer exists in Memcache, so clear it from the cache array | ||
118 | + parent::deleteCacheData($pCoord); | ||
119 | + throw new PHPExcel_Exception('Cell entry '.$pCoord.' no longer exists in MemCache'); | ||
120 | + } | ||
121 | + return true; | ||
122 | + } | ||
123 | + return false; | ||
124 | + } | ||
125 | + | ||
126 | + | ||
127 | + /** | ||
128 | + * Get cell at a specific coordinate | ||
129 | + * | ||
130 | + * @param string $pCoord Coordinate of the cell | ||
131 | + * @throws PHPExcel_Exception | ||
132 | + * @return PHPExcel_Cell Cell that was found, or null if not found | ||
133 | + */ | ||
134 | + public function getCacheData($pCoord) | ||
135 | + { | ||
136 | + if ($pCoord === $this->currentObjectID) { | ||
137 | + return $this->currentObject; | ||
138 | + } | ||
139 | + $this->storeData(); | ||
140 | + | ||
141 | + // Check if the entry that has been requested actually exists | ||
142 | + if (parent::isDataSet($pCoord)) { | ||
143 | + $obj = $this->memcache->get($this->cachePrefix . $pCoord . '.cache'); | ||
144 | + if ($obj === false) { | ||
145 | + // Entry no longer exists in Memcache, so clear it from the cache array | ||
146 | + parent::deleteCacheData($pCoord); | ||
147 | + throw new PHPExcel_Exception("Cell entry {$pCoord} no longer exists in MemCache"); | ||
148 | + } | ||
149 | + } else { | ||
150 | + // Return null if requested entry doesn't exist in cache | ||
151 | + return null; | ||
152 | + } | ||
153 | + | ||
154 | + // Set current entry to the requested entry | ||
155 | + $this->currentObjectID = $pCoord; | ||
156 | + $this->currentObject = unserialize($obj); | ||
157 | + // Re-attach this as the cell's parent | ||
158 | + $this->currentObject->attach($this); | ||
159 | + | ||
160 | + // Return requested entry | ||
161 | + return $this->currentObject; | ||
162 | + } | ||
163 | + | ||
164 | + /** | ||
165 | + * Get a list of all cell addresses currently held in cache | ||
166 | + * | ||
167 | + * @return string[] | ||
168 | + */ | ||
169 | + public function getCellList() | ||
170 | + { | ||
171 | + if ($this->currentObjectID !== null) { | ||
172 | + $this->storeData(); | ||
173 | + } | ||
174 | + | ||
175 | + return parent::getCellList(); | ||
176 | + } | ||
177 | + | ||
178 | + /** | ||
179 | + * Delete a cell in cache identified by coordinate address | ||
180 | + * | ||
181 | + * @param string $pCoord Coordinate address of the cell to delete | ||
182 | + * @throws PHPExcel_Exception | ||
183 | + */ | ||
184 | + public function deleteCacheData($pCoord) | ||
185 | + { | ||
186 | + // Delete the entry from Memcache | ||
187 | + $this->memcache->delete($this->cachePrefix . $pCoord . '.cache'); | ||
188 | + | ||
189 | + // Delete the entry from our cell address array | ||
190 | + parent::deleteCacheData($pCoord); | ||
191 | + } | ||
192 | + | ||
193 | + /** | ||
194 | + * Clone the cell collection | ||
195 | + * | ||
196 | + * @param PHPExcel_Worksheet $parent The new worksheet | ||
197 | + * @return void | ||
198 | + */ | ||
199 | + public function copyCellCollection(PHPExcel_Worksheet $parent) | ||
200 | + { | ||
201 | + parent::copyCellCollection($parent); | ||
202 | + // Get a new id for the new file name | ||
203 | + $baseUnique = $this->getUniqueID(); | ||
204 | + $newCachePrefix = substr(md5($baseUnique), 0, 8) . '.'; | ||
205 | + $cacheList = $this->getCellList(); | ||
206 | + foreach ($cacheList as $cellID) { | ||
207 | + if ($cellID != $this->currentObjectID) { | ||
208 | + $obj = $this->memcache->get($this->cachePrefix.$cellID.'.cache'); | ||
209 | + if ($obj === false) { | ||
210 | + // Entry no longer exists in Memcache, so clear it from the cache array | ||
211 | + parent::deleteCacheData($cellID); | ||
212 | + throw new PHPExcel_Exception("Cell entry {$cellID} no longer exists in MemCache"); | ||
213 | + } | ||
214 | + if (!$this->memcache->add($newCachePrefix . $cellID . '.cache', $obj, null, $this->cacheTime)) { | ||
215 | + $this->__destruct(); | ||
216 | + throw new PHPExcel_Exception("Failed to store cell {$cellID} in MemCache"); | ||
217 | + } | ||
218 | + } | ||
219 | + } | ||
220 | + $this->cachePrefix = $newCachePrefix; | ||
221 | + } | ||
222 | + | ||
223 | + /** | ||
224 | + * Clear the cell collection and disconnect from our parent | ||
225 | + * | ||
226 | + * @return void | ||
227 | + */ | ||
228 | + public function unsetWorksheetCells() | ||
229 | + { | ||
230 | + if (!is_null($this->currentObject)) { | ||
231 | + $this->currentObject->detach(); | ||
232 | + $this->currentObject = $this->currentObjectID = null; | ||
233 | + } | ||
234 | + | ||
235 | + // Flush the Memcache cache | ||
236 | + $this->__destruct(); | ||
237 | + | ||
238 | + $this->cellCache = array(); | ||
239 | + | ||
240 | + // detach ourself from the worksheet, so that it can then delete this object successfully | ||
241 | + $this->parent = null; | ||
242 | + } | ||
243 | + | ||
244 | + /** | ||
245 | + * Initialise this new cell collection | ||
246 | + * | ||
247 | + * @param PHPExcel_Worksheet $parent The worksheet for this cell collection | ||
248 | + * @param array of mixed $arguments Additional initialisation arguments | ||
249 | + */ | ||
250 | + public function __construct(PHPExcel_Worksheet $parent, $arguments) | ||
251 | + { | ||
252 | + $memcacheServer = (isset($arguments['memcacheServer'])) ? $arguments['memcacheServer'] : 'localhost'; | ||
253 | + $memcachePort = (isset($arguments['memcachePort'])) ? $arguments['memcachePort'] : 11211; | ||
254 | + $cacheTime = (isset($arguments['cacheTime'])) ? $arguments['cacheTime'] : 600; | ||
255 | + | ||
256 | + if (is_null($this->cachePrefix)) { | ||
257 | + $baseUnique = $this->getUniqueID(); | ||
258 | + $this->cachePrefix = substr(md5($baseUnique), 0, 8) . '.'; | ||
259 | + | ||
260 | + // Set a new Memcache object and connect to the Memcache server | ||
261 | + $this->memcache = new Memcache(); | ||
262 | + if (!$this->memcache->addServer($memcacheServer, $memcachePort, false, 50, 5, 5, true, array($this, 'failureCallback'))) { | ||
263 | + throw new PHPExcel_Exception("Could not connect to MemCache server at {$memcacheServer}:{$memcachePort}"); | ||
264 | + } | ||
265 | + $this->cacheTime = $cacheTime; | ||
266 | + | ||
267 | + parent::__construct($parent); | ||
268 | + } | ||
269 | + } | ||
270 | + | ||
271 | + /** | ||
272 | + * Memcache error handler | ||
273 | + * | ||
274 | + * @param string $host Memcache server | ||
275 | + * @param integer $port Memcache port | ||
276 | + * @throws PHPExcel_Exception | ||
277 | + */ | ||
278 | + public function failureCallback($host, $port) | ||
279 | + { | ||
280 | + throw new PHPExcel_Exception("memcache {$host}:{$port} failed"); | ||
281 | + } | ||
282 | + | ||
283 | + /** | ||
284 | + * Destroy this cell collection | ||
285 | + */ | ||
286 | + public function __destruct() | ||
287 | + { | ||
288 | + $cacheList = $this->getCellList(); | ||
289 | + foreach ($cacheList as $cellID) { | ||
290 | + $this->memcache->delete($this->cachePrefix.$cellID . '.cache'); | ||
291 | + } | ||
292 | + } | ||
293 | + | ||
294 | + /** | ||
295 | + * Identify whether the caching method is currently available | ||
296 | + * Some methods are dependent on the availability of certain extensions being enabled in the PHP build | ||
297 | + * | ||
298 | + * @return boolean | ||
299 | + */ | ||
300 | + public static function cacheMethodIsAvailable() | ||
301 | + { | ||
302 | + if (!function_exists('memcache_add')) { | ||
303 | + return false; | ||
304 | + } | ||
305 | + | ||
306 | + return true; | ||
307 | + } | ||
308 | +} |
1 | +<?php | ||
2 | + | ||
3 | +/** | ||
4 | + * PHPExcel_CachedObjectStorage_Memory | ||
5 | + * | ||
6 | + * Copyright (c) 2006 - 2015 PHPExcel | ||
7 | + * | ||
8 | + * This library is free software; you can redistribute it and/or | ||
9 | + * modify it under the terms of the GNU Lesser General Public | ||
10 | + * License as published by the Free Software Foundation; either | ||
11 | + * version 2.1 of the License, or (at your option) any later version. | ||
12 | + * | ||
13 | + * This library is distributed in the hope that it will be useful, | ||
14 | + * but WITHOUT ANY WARRANTY; without even the implied warranty of | ||
15 | + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU | ||
16 | + * Lesser General Public License for more details. | ||
17 | + * | ||
18 | + * You should have received a copy of the GNU Lesser General Public | ||
19 | + * License along with this library; if not, write to the Free Software | ||
20 | + * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA | ||
21 | + * | ||
22 | + * @category PHPExcel | ||
23 | + * @package PHPExcel_CachedObjectStorage | ||
24 | + * @copyright Copyright (c) 2006 - 2015 PHPExcel (http://www.codeplex.com/PHPExcel) | ||
25 | + * @license http://www.gnu.org/licenses/old-licenses/lgpl-2.1.txt LGPL | ||
26 | + * @version ##VERSION##, ##DATE## | ||
27 | + */ | ||
28 | +class PHPExcel_CachedObjectStorage_Memory extends PHPExcel_CachedObjectStorage_CacheBase implements PHPExcel_CachedObjectStorage_ICache | ||
29 | +{ | ||
30 | + /** | ||
31 | + * Dummy method callable from CacheBase, but unused by Memory cache | ||
32 | + * | ||
33 | + * @return void | ||
34 | + */ | ||
35 | + protected function storeData() | ||
36 | + { | ||
37 | + } | ||
38 | + | ||
39 | + /** | ||
40 | + * Add or Update a cell in cache identified by coordinate address | ||
41 | + * | ||
42 | + * @param string $pCoord Coordinate address of the cell to update | ||
43 | + * @param PHPExcel_Cell $cell Cell to update | ||
44 | + * @return PHPExcel_Cell | ||
45 | + * @throws PHPExcel_Exception | ||
46 | + */ | ||
47 | + public function addCacheData($pCoord, PHPExcel_Cell $cell) | ||
48 | + { | ||
49 | + $this->cellCache[$pCoord] = $cell; | ||
50 | + | ||
51 | + // Set current entry to the new/updated entry | ||
52 | + $this->currentObjectID = $pCoord; | ||
53 | + | ||
54 | + return $cell; | ||
55 | + } | ||
56 | + | ||
57 | + | ||
58 | + /** | ||
59 | + * Get cell at a specific coordinate | ||
60 | + * | ||
61 | + * @param string $pCoord Coordinate of the cell | ||
62 | + * @throws PHPExcel_Exception | ||
63 | + * @return PHPExcel_Cell Cell that was found, or null if not found | ||
64 | + */ | ||
65 | + public function getCacheData($pCoord) | ||
66 | + { | ||
67 | + // Check if the entry that has been requested actually exists | ||
68 | + if (!isset($this->cellCache[$pCoord])) { | ||
69 | + $this->currentObjectID = null; | ||
70 | + // Return null if requested entry doesn't exist in cache | ||
71 | + return null; | ||
72 | + } | ||
73 | + | ||
74 | + // Set current entry to the requested entry | ||
75 | + $this->currentObjectID = $pCoord; | ||
76 | + | ||
77 | + // Return requested entry | ||
78 | + return $this->cellCache[$pCoord]; | ||
79 | + } | ||
80 | + | ||
81 | + | ||
82 | + /** | ||
83 | + * Clone the cell collection | ||
84 | + * | ||
85 | + * @param PHPExcel_Worksheet $parent The new worksheet | ||
86 | + */ | ||
87 | + public function copyCellCollection(PHPExcel_Worksheet $parent) | ||
88 | + { | ||
89 | + parent::copyCellCollection($parent); | ||
90 | + | ||
91 | + $newCollection = array(); | ||
92 | + foreach ($this->cellCache as $k => &$cell) { | ||
93 | + $newCollection[$k] = clone $cell; | ||
94 | + $newCollection[$k]->attach($this); | ||
95 | + } | ||
96 | + | ||
97 | + $this->cellCache = $newCollection; | ||
98 | + } | ||
99 | + | ||
100 | + /** | ||
101 | + * Clear the cell collection and disconnect from our parent | ||
102 | + * | ||
103 | + */ | ||
104 | + public function unsetWorksheetCells() | ||
105 | + { | ||
106 | + // Because cells are all stored as intact objects in memory, we need to detach each one from the parent | ||
107 | + foreach ($this->cellCache as $k => &$cell) { | ||
108 | + $cell->detach(); | ||
109 | + $this->cellCache[$k] = null; | ||
110 | + } | ||
111 | + unset($cell); | ||
112 | + | ||
113 | + $this->cellCache = array(); | ||
114 | + | ||
115 | + // detach ourself from the worksheet, so that it can then delete this object successfully | ||
116 | + $this->parent = null; | ||
117 | + } | ||
118 | +} |
1 | +<?php | ||
2 | + | ||
3 | +/** | ||
4 | + * PHPExcel_CachedObjectStorage_MemoryGZip | ||
5 | + * | ||
6 | + * Copyright (c) 2006 - 2015 PHPExcel | ||
7 | + * | ||
8 | + * This library is free software; you can redistribute it and/or | ||
9 | + * modify it under the terms of the GNU Lesser General Public | ||
10 | + * License as published by the Free Software Foundation; either | ||
11 | + * version 2.1 of the License, or (at your option) any later version. | ||
12 | + * | ||
13 | + * This library is distributed in the hope that it will be useful, | ||
14 | + * but WITHOUT ANY WARRANTY; without even the implied warranty of | ||
15 | + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU | ||
16 | + * Lesser General Public License for more details. | ||
17 | + * | ||
18 | + * You should have received a copy of the GNU Lesser General Public | ||
19 | + * License along with this library; if not, write to the Free Software | ||
20 | + * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA | ||
21 | + * | ||
22 | + * @category PHPExcel | ||
23 | + * @package PHPExcel_CachedObjectStorage | ||
24 | + * @copyright Copyright (c) 2006 - 2015 PHPExcel (http://www.codeplex.com/PHPExcel) | ||
25 | + * @license http://www.gnu.org/licenses/old-licenses/lgpl-2.1.txt LGPL | ||
26 | + * @version ##VERSION##, ##DATE## | ||
27 | + */ | ||
28 | +class PHPExcel_CachedObjectStorage_MemoryGZip extends PHPExcel_CachedObjectStorage_CacheBase implements PHPExcel_CachedObjectStorage_ICache | ||
29 | +{ | ||
30 | + /** | ||
31 | + * Store cell data in cache for the current cell object if it's "dirty", | ||
32 | + * and the 'nullify' the current cell object | ||
33 | + * | ||
34 | + * @return void | ||
35 | + * @throws PHPExcel_Exception | ||
36 | + */ | ||
37 | + protected function storeData() | ||
38 | + { | ||
39 | + if ($this->currentCellIsDirty && !empty($this->currentObjectID)) { | ||
40 | + $this->currentObject->detach(); | ||
41 | + | ||
42 | + $this->cellCache[$this->currentObjectID] = gzdeflate(serialize($this->currentObject)); | ||
43 | + $this->currentCellIsDirty = false; | ||
44 | + } | ||
45 | + $this->currentObjectID = $this->currentObject = null; | ||
46 | + } | ||
47 | + | ||
48 | + | ||
49 | + /** | ||
50 | + * Add or Update a cell in cache identified by coordinate address | ||
51 | + * | ||
52 | + * @param string $pCoord Coordinate address of the cell to update | ||
53 | + * @param PHPExcel_Cell $cell Cell to update | ||
54 | + * @return PHPExcel_Cell | ||
55 | + * @throws PHPExcel_Exception | ||
56 | + */ | ||
57 | + public function addCacheData($pCoord, PHPExcel_Cell $cell) | ||
58 | + { | ||
59 | + if (($pCoord !== $this->currentObjectID) && ($this->currentObjectID !== null)) { | ||
60 | + $this->storeData(); | ||
61 | + } | ||
62 | + | ||
63 | + $this->currentObjectID = $pCoord; | ||
64 | + $this->currentObject = $cell; | ||
65 | + $this->currentCellIsDirty = true; | ||
66 | + | ||
67 | + return $cell; | ||
68 | + } | ||
69 | + | ||
70 | + | ||
71 | + /** | ||
72 | + * Get cell at a specific coordinate | ||
73 | + * | ||
74 | + * @param string $pCoord Coordinate of the cell | ||
75 | + * @throws PHPExcel_Exception | ||
76 | + * @return PHPExcel_Cell Cell that was found, or null if not found | ||
77 | + */ | ||
78 | + public function getCacheData($pCoord) | ||
79 | + { | ||
80 | + if ($pCoord === $this->currentObjectID) { | ||
81 | + return $this->currentObject; | ||
82 | + } | ||
83 | + $this->storeData(); | ||
84 | + | ||
85 | + // Check if the entry that has been requested actually exists | ||
86 | + if (!isset($this->cellCache[$pCoord])) { | ||
87 | + // Return null if requested entry doesn't exist in cache | ||
88 | + return null; | ||
89 | + } | ||
90 | + | ||
91 | + // Set current entry to the requested entry | ||
92 | + $this->currentObjectID = $pCoord; | ||
93 | + $this->currentObject = unserialize(gzinflate($this->cellCache[$pCoord])); | ||
94 | + // Re-attach this as the cell's parent | ||
95 | + $this->currentObject->attach($this); | ||
96 | + | ||
97 | + // Return requested entry | ||
98 | + return $this->currentObject; | ||
99 | + } | ||
100 | + | ||
101 | + | ||
102 | + /** | ||
103 | + * Get a list of all cell addresses currently held in cache | ||
104 | + * | ||
105 | + * @return string[] | ||
106 | + */ | ||
107 | + public function getCellList() | ||
108 | + { | ||
109 | + if ($this->currentObjectID !== null) { | ||
110 | + $this->storeData(); | ||
111 | + } | ||
112 | + | ||
113 | + return parent::getCellList(); | ||
114 | + } | ||
115 | + | ||
116 | + | ||
117 | + /** | ||
118 | + * Clear the cell collection and disconnect from our parent | ||
119 | + * | ||
120 | + * @return void | ||
121 | + */ | ||
122 | + public function unsetWorksheetCells() | ||
123 | + { | ||
124 | + if (!is_null($this->currentObject)) { | ||
125 | + $this->currentObject->detach(); | ||
126 | + $this->currentObject = $this->currentObjectID = null; | ||
127 | + } | ||
128 | + $this->cellCache = array(); | ||
129 | + | ||
130 | + // detach ourself from the worksheet, so that it can then delete this object successfully | ||
131 | + $this->parent = null; | ||
132 | + } | ||
133 | +} |
1 | +<?php | ||
2 | + | ||
3 | +/** | ||
4 | + * PHPExcel_CachedObjectStorage_MemorySerialized | ||
5 | + * | ||
6 | + * Copyright (c) 2006 - 2015 PHPExcel | ||
7 | + * | ||
8 | + * This library is free software; you can redistribute it and/or | ||
9 | + * modify it under the terms of the GNU Lesser General Public | ||
10 | + * License as published by the Free Software Foundation; either | ||
11 | + * version 2.1 of the License, or (at your option) any later version. | ||
12 | + * | ||
13 | + * This library is distributed in the hope that it will be useful, | ||
14 | + * but WITHOUT ANY WARRANTY; without even the implied warranty of | ||
15 | + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU | ||
16 | + * Lesser General Public License for more details. | ||
17 | + * | ||
18 | + * You should have received a copy of the GNU Lesser General Public | ||
19 | + * License along with this library; if not, write to the Free Software | ||
20 | + * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA | ||
21 | + * | ||
22 | + * @category PHPExcel | ||
23 | + * @package PHPExcel_CachedObjectStorage | ||
24 | + * @copyright Copyright (c) 2006 - 2015 PHPExcel (http://www.codeplex.com/PHPExcel) | ||
25 | + * @license http://www.gnu.org/licenses/old-licenses/lgpl-2.1.txt LGPL | ||
26 | + * @version ##VERSION##, ##DATE## | ||
27 | + */ | ||
28 | +class PHPExcel_CachedObjectStorage_MemorySerialized extends PHPExcel_CachedObjectStorage_CacheBase implements PHPExcel_CachedObjectStorage_ICache | ||
29 | +{ | ||
30 | + /** | ||
31 | + * Store cell data in cache for the current cell object if it's "dirty", | ||
32 | + * and the 'nullify' the current cell object | ||
33 | + * | ||
34 | + * @return void | ||
35 | + * @throws PHPExcel_Exception | ||
36 | + */ | ||
37 | + protected function storeData() | ||
38 | + { | ||
39 | + if ($this->currentCellIsDirty && !empty($this->currentObjectID)) { | ||
40 | + $this->currentObject->detach(); | ||
41 | + | ||
42 | + $this->cellCache[$this->currentObjectID] = serialize($this->currentObject); | ||
43 | + $this->currentCellIsDirty = false; | ||
44 | + } | ||
45 | + $this->currentObjectID = $this->currentObject = null; | ||
46 | + } | ||
47 | + | ||
48 | + /** | ||
49 | + * Add or Update a cell in cache identified by coordinate address | ||
50 | + * | ||
51 | + * @param string $pCoord Coordinate address of the cell to update | ||
52 | + * @param PHPExcel_Cell $cell Cell to update | ||
53 | + * @return PHPExcel_Cell | ||
54 | + * @throws PHPExcel_Exception | ||
55 | + */ | ||
56 | + public function addCacheData($pCoord, PHPExcel_Cell $cell) | ||
57 | + { | ||
58 | + if (($pCoord !== $this->currentObjectID) && ($this->currentObjectID !== null)) { | ||
59 | + $this->storeData(); | ||
60 | + } | ||
61 | + | ||
62 | + $this->currentObjectID = $pCoord; | ||
63 | + $this->currentObject = $cell; | ||
64 | + $this->currentCellIsDirty = true; | ||
65 | + | ||
66 | + return $cell; | ||
67 | + } | ||
68 | + | ||
69 | + /** | ||
70 | + * Get cell at a specific coordinate | ||
71 | + * | ||
72 | + * @param string $pCoord Coordinate of the cell | ||
73 | + * @throws PHPExcel_Exception | ||
74 | + * @return PHPExcel_Cell Cell that was found, or null if not found | ||
75 | + */ | ||
76 | + public function getCacheData($pCoord) | ||
77 | + { | ||
78 | + if ($pCoord === $this->currentObjectID) { | ||
79 | + return $this->currentObject; | ||
80 | + } | ||
81 | + $this->storeData(); | ||
82 | + | ||
83 | + // Check if the entry that has been requested actually exists | ||
84 | + if (!isset($this->cellCache[$pCoord])) { | ||
85 | + // Return null if requested entry doesn't exist in cache | ||
86 | + return null; | ||
87 | + } | ||
88 | + | ||
89 | + // Set current entry to the requested entry | ||
90 | + $this->currentObjectID = $pCoord; | ||
91 | + $this->currentObject = unserialize($this->cellCache[$pCoord]); | ||
92 | + // Re-attach this as the cell's parent | ||
93 | + $this->currentObject->attach($this); | ||
94 | + | ||
95 | + // Return requested entry | ||
96 | + return $this->currentObject; | ||
97 | + } | ||
98 | + | ||
99 | + /** | ||
100 | + * Get a list of all cell addresses currently held in cache | ||
101 | + * | ||
102 | + * @return string[] | ||
103 | + */ | ||
104 | + public function getCellList() | ||
105 | + { | ||
106 | + if ($this->currentObjectID !== null) { | ||
107 | + $this->storeData(); | ||
108 | + } | ||
109 | + | ||
110 | + return parent::getCellList(); | ||
111 | + } | ||
112 | + | ||
113 | + /** | ||
114 | + * Clear the cell collection and disconnect from our parent | ||
115 | + * | ||
116 | + * @return void | ||
117 | + */ | ||
118 | + public function unsetWorksheetCells() | ||
119 | + { | ||
120 | + if (!is_null($this->currentObject)) { | ||
121 | + $this->currentObject->detach(); | ||
122 | + $this->currentObject = $this->currentObjectID = null; | ||
123 | + } | ||
124 | + $this->cellCache = array(); | ||
125 | + | ||
126 | + // detach ourself from the worksheet, so that it can then delete this object successfully | ||
127 | + $this->parent = null; | ||
128 | + } | ||
129 | +} |
1 | +<?php | ||
2 | + | ||
3 | +/** | ||
4 | + * PHPExcel_CachedObjectStorage_PHPTemp | ||
5 | + * | ||
6 | + * Copyright (c) 2006 - 2015 PHPExcel | ||
7 | + * | ||
8 | + * This library is free software; you can redistribute it and/or | ||
9 | + * modify it under the terms of the GNU Lesser General Public | ||
10 | + * License as published by the Free Software Foundation; either | ||
11 | + * version 2.1 of the License, or (at your option) any later version. | ||
12 | + * | ||
13 | + * This library is distributed in the hope that it will be useful, | ||
14 | + * but WITHOUT ANY WARRANTY; without even the implied warranty of | ||
15 | + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU | ||
16 | + * Lesser General Public License for more details. | ||
17 | + * | ||
18 | + * You should have received a copy of the GNU Lesser General Public | ||
19 | + * License along with this library; if not, write to the Free Software | ||
20 | + * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA | ||
21 | + * | ||
22 | + * @category PHPExcel | ||
23 | + * @package PHPExcel_CachedObjectStorage | ||
24 | + * @copyright Copyright (c) 2006 - 2015 PHPExcel (http://www.codeplex.com/PHPExcel) | ||
25 | + * @license http://www.gnu.org/licenses/old-licenses/lgpl-2.1.txt LGPL | ||
26 | + * @version ##VERSION##, ##DATE## | ||
27 | + */ | ||
28 | +class PHPExcel_CachedObjectStorage_PHPTemp extends PHPExcel_CachedObjectStorage_CacheBase implements PHPExcel_CachedObjectStorage_ICache | ||
29 | +{ | ||
30 | + /** | ||
31 | + * Name of the file for this cache | ||
32 | + * | ||
33 | + * @var string | ||
34 | + */ | ||
35 | + private $fileHandle = null; | ||
36 | + | ||
37 | + /** | ||
38 | + * Memory limit to use before reverting to file cache | ||
39 | + * | ||
40 | + * @var integer | ||
41 | + */ | ||
42 | + private $memoryCacheSize = null; | ||
43 | + | ||
44 | + /** | ||
45 | + * Store cell data in cache for the current cell object if it's "dirty", | ||
46 | + * and the 'nullify' the current cell object | ||
47 | + * | ||
48 | + * @return void | ||
49 | + * @throws PHPExcel_Exception | ||
50 | + */ | ||
51 | + protected function storeData() | ||
52 | + { | ||
53 | + if ($this->currentCellIsDirty && !empty($this->currentObjectID)) { | ||
54 | + $this->currentObject->detach(); | ||
55 | + | ||
56 | + fseek($this->fileHandle, 0, SEEK_END); | ||
57 | + | ||
58 | + $this->cellCache[$this->currentObjectID] = array( | ||
59 | + 'ptr' => ftell($this->fileHandle), | ||
60 | + 'sz' => fwrite($this->fileHandle, serialize($this->currentObject)) | ||
61 | + ); | ||
62 | + $this->currentCellIsDirty = false; | ||
63 | + } | ||
64 | + $this->currentObjectID = $this->currentObject = null; | ||
65 | + } | ||
66 | + | ||
67 | + | ||
68 | + /** | ||
69 | + * Add or Update a cell in cache identified by coordinate address | ||
70 | + * | ||
71 | + * @param string $pCoord Coordinate address of the cell to update | ||
72 | + * @param PHPExcel_Cell $cell Cell to update | ||
73 | + * @return PHPExcel_Cell | ||
74 | + * @throws PHPExcel_Exception | ||
75 | + */ | ||
76 | + public function addCacheData($pCoord, PHPExcel_Cell $cell) | ||
77 | + { | ||
78 | + if (($pCoord !== $this->currentObjectID) && ($this->currentObjectID !== null)) { | ||
79 | + $this->storeData(); | ||
80 | + } | ||
81 | + | ||
82 | + $this->currentObjectID = $pCoord; | ||
83 | + $this->currentObject = $cell; | ||
84 | + $this->currentCellIsDirty = true; | ||
85 | + | ||
86 | + return $cell; | ||
87 | + } | ||
88 | + | ||
89 | + | ||
90 | + /** | ||
91 | + * Get cell at a specific coordinate | ||
92 | + * | ||
93 | + * @param string $pCoord Coordinate of the cell | ||
94 | + * @throws PHPExcel_Exception | ||
95 | + * @return PHPExcel_Cell Cell that was found, or null if not found | ||
96 | + */ | ||
97 | + public function getCacheData($pCoord) | ||
98 | + { | ||
99 | + if ($pCoord === $this->currentObjectID) { | ||
100 | + return $this->currentObject; | ||
101 | + } | ||
102 | + $this->storeData(); | ||
103 | + | ||
104 | + // Check if the entry that has been requested actually exists | ||
105 | + if (!isset($this->cellCache[$pCoord])) { | ||
106 | + // Return null if requested entry doesn't exist in cache | ||
107 | + return null; | ||
108 | + } | ||
109 | + | ||
110 | + // Set current entry to the requested entry | ||
111 | + $this->currentObjectID = $pCoord; | ||
112 | + fseek($this->fileHandle, $this->cellCache[$pCoord]['ptr']); | ||
113 | + $this->currentObject = unserialize(fread($this->fileHandle, $this->cellCache[$pCoord]['sz'])); | ||
114 | + // Re-attach this as the cell's parent | ||
115 | + $this->currentObject->attach($this); | ||
116 | + | ||
117 | + // Return requested entry | ||
118 | + return $this->currentObject; | ||
119 | + } | ||
120 | + | ||
121 | + /** | ||
122 | + * Get a list of all cell addresses currently held in cache | ||
123 | + * | ||
124 | + * @return string[] | ||
125 | + */ | ||
126 | + public function getCellList() | ||
127 | + { | ||
128 | + if ($this->currentObjectID !== null) { | ||
129 | + $this->storeData(); | ||
130 | + } | ||
131 | + | ||
132 | + return parent::getCellList(); | ||
133 | + } | ||
134 | + | ||
135 | + /** | ||
136 | + * Clone the cell collection | ||
137 | + * | ||
138 | + * @param PHPExcel_Worksheet $parent The new worksheet | ||
139 | + * @return void | ||
140 | + */ | ||
141 | + public function copyCellCollection(PHPExcel_Worksheet $parent) | ||
142 | + { | ||
143 | + parent::copyCellCollection($parent); | ||
144 | + // Open a new stream for the cell cache data | ||
145 | + $newFileHandle = fopen('php://temp/maxmemory:' . $this->memoryCacheSize, 'a+'); | ||
146 | + // Copy the existing cell cache data to the new stream | ||
147 | + fseek($this->fileHandle, 0); | ||
148 | + while (!feof($this->fileHandle)) { | ||
149 | + fwrite($newFileHandle, fread($this->fileHandle, 1024)); | ||
150 | + } | ||
151 | + $this->fileHandle = $newFileHandle; | ||
152 | + } | ||
153 | + | ||
154 | + /** | ||
155 | + * Clear the cell collection and disconnect from our parent | ||
156 | + * | ||
157 | + * @return void | ||
158 | + */ | ||
159 | + public function unsetWorksheetCells() | ||
160 | + { | ||
161 | + if (!is_null($this->currentObject)) { | ||
162 | + $this->currentObject->detach(); | ||
163 | + $this->currentObject = $this->currentObjectID = null; | ||
164 | + } | ||
165 | + $this->cellCache = array(); | ||
166 | + | ||
167 | + // detach ourself from the worksheet, so that it can then delete this object successfully | ||
168 | + $this->parent = null; | ||
169 | + | ||
170 | + // Close down the php://temp file | ||
171 | + $this->__destruct(); | ||
172 | + } | ||
173 | + | ||
174 | + /** | ||
175 | + * Initialise this new cell collection | ||
176 | + * | ||
177 | + * @param PHPExcel_Worksheet $parent The worksheet for this cell collection | ||
178 | + * @param array of mixed $arguments Additional initialisation arguments | ||
179 | + */ | ||
180 | + public function __construct(PHPExcel_Worksheet $parent, $arguments) | ||
181 | + { | ||
182 | + $this->memoryCacheSize = (isset($arguments['memoryCacheSize'])) ? $arguments['memoryCacheSize'] : '1MB'; | ||
183 | + | ||
184 | + parent::__construct($parent); | ||
185 | + if (is_null($this->fileHandle)) { | ||
186 | + $this->fileHandle = fopen('php://temp/maxmemory:' . $this->memoryCacheSize, 'a+'); | ||
187 | + } | ||
188 | + } | ||
189 | + | ||
190 | + /** | ||
191 | + * Destroy this cell collection | ||
192 | + */ | ||
193 | + public function __destruct() | ||
194 | + { | ||
195 | + if (!is_null($this->fileHandle)) { | ||
196 | + fclose($this->fileHandle); | ||
197 | + } | ||
198 | + $this->fileHandle = null; | ||
199 | + } | ||
200 | +} |
1 | +<?php | ||
2 | + | ||
3 | +/** | ||
4 | + * PHPExcel_CachedObjectStorage_SQLite | ||
5 | + * | ||
6 | + * Copyright (c) 2006 - 2015 PHPExcel | ||
7 | + * | ||
8 | + * This library is free software; you can redistribute it and/or | ||
9 | + * modify it under the terms of the GNU Lesser General Public | ||
10 | + * License as published by the Free Software Foundation; either | ||
11 | + * version 2.1 of the License, or (at your option) any later version. | ||
12 | + * | ||
13 | + * This library is distributed in the hope that it will be useful, | ||
14 | + * but WITHOUT ANY WARRANTY; without even the implied warranty of | ||
15 | + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU | ||
16 | + * Lesser General Public License for more details. | ||
17 | + * | ||
18 | + * You should have received a copy of the GNU Lesser General Public | ||
19 | + * License along with this library; if not, write to the Free Software | ||
20 | + * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA | ||
21 | + * | ||
22 | + * @category PHPExcel | ||
23 | + * @package PHPExcel_CachedObjectStorage | ||
24 | + * @copyright Copyright (c) 2006 - 2015 PHPExcel (http://www.codeplex.com/PHPExcel) | ||
25 | + * @license http://www.gnu.org/licenses/old-licenses/lgpl-2.1.txt LGPL | ||
26 | + * @version ##VERSION##, ##DATE## | ||
27 | + */ | ||
28 | +class PHPExcel_CachedObjectStorage_SQLite extends PHPExcel_CachedObjectStorage_CacheBase implements PHPExcel_CachedObjectStorage_ICache | ||
29 | +{ | ||
30 | + /** | ||
31 | + * Database table name | ||
32 | + * | ||
33 | + * @var string | ||
34 | + */ | ||
35 | + private $TableName = null; | ||
36 | + | ||
37 | + /** | ||
38 | + * Database handle | ||
39 | + * | ||
40 | + * @var resource | ||
41 | + */ | ||
42 | + private $DBHandle = null; | ||
43 | + | ||
44 | + /** | ||
45 | + * Store cell data in cache for the current cell object if it's "dirty", | ||
46 | + * and the 'nullify' the current cell object | ||
47 | + * | ||
48 | + * @return void | ||
49 | + * @throws PHPExcel_Exception | ||
50 | + */ | ||
51 | + protected function storeData() | ||
52 | + { | ||
53 | + if ($this->currentCellIsDirty && !empty($this->currentObjectID)) { | ||
54 | + $this->currentObject->detach(); | ||
55 | + | ||
56 | + if (!$this->DBHandle->queryExec("INSERT OR REPLACE INTO kvp_".$this->TableName." VALUES('".$this->currentObjectID."','".sqlite_escape_string(serialize($this->currentObject))."')")) { | ||
57 | + throw new PHPExcel_Exception(sqlite_error_string($this->DBHandle->lastError())); | ||
58 | + } | ||
59 | + $this->currentCellIsDirty = false; | ||
60 | + } | ||
61 | + $this->currentObjectID = $this->currentObject = null; | ||
62 | + } | ||
63 | + | ||
64 | + /** | ||
65 | + * Add or Update a cell in cache identified by coordinate address | ||
66 | + * | ||
67 | + * @param string $pCoord Coordinate address of the cell to update | ||
68 | + * @param PHPExcel_Cell $cell Cell to update | ||
69 | + * @return PHPExcel_Cell | ||
70 | + * @throws PHPExcel_Exception | ||
71 | + */ | ||
72 | + public function addCacheData($pCoord, PHPExcel_Cell $cell) | ||
73 | + { | ||
74 | + if (($pCoord !== $this->currentObjectID) && ($this->currentObjectID !== null)) { | ||
75 | + $this->storeData(); | ||
76 | + } | ||
77 | + | ||
78 | + $this->currentObjectID = $pCoord; | ||
79 | + $this->currentObject = $cell; | ||
80 | + $this->currentCellIsDirty = true; | ||
81 | + | ||
82 | + return $cell; | ||
83 | + } | ||
84 | + | ||
85 | + /** | ||
86 | + * Get cell at a specific coordinate | ||
87 | + * | ||
88 | + * @param string $pCoord Coordinate of the cell | ||
89 | + * @throws PHPExcel_Exception | ||
90 | + * @return PHPExcel_Cell Cell that was found, or null if not found | ||
91 | + */ | ||
92 | + public function getCacheData($pCoord) | ||
93 | + { | ||
94 | + if ($pCoord === $this->currentObjectID) { | ||
95 | + return $this->currentObject; | ||
96 | + } | ||
97 | + $this->storeData(); | ||
98 | + | ||
99 | + $query = "SELECT value FROM kvp_".$this->TableName." WHERE id='".$pCoord."'"; | ||
100 | + $cellResultSet = $this->DBHandle->query($query, SQLITE_ASSOC); | ||
101 | + if ($cellResultSet === false) { | ||
102 | + throw new PHPExcel_Exception(sqlite_error_string($this->DBHandle->lastError())); | ||
103 | + } elseif ($cellResultSet->numRows() == 0) { | ||
104 | + // Return null if requested entry doesn't exist in cache | ||
105 | + return null; | ||
106 | + } | ||
107 | + | ||
108 | + // Set current entry to the requested entry | ||
109 | + $this->currentObjectID = $pCoord; | ||
110 | + | ||
111 | + $cellResult = $cellResultSet->fetchSingle(); | ||
112 | + $this->currentObject = unserialize($cellResult); | ||
113 | + // Re-attach this as the cell's parent | ||
114 | + $this->currentObject->attach($this); | ||
115 | + | ||
116 | + // Return requested entry | ||
117 | + return $this->currentObject; | ||
118 | + } | ||
119 | + | ||
120 | + /** | ||
121 | + * Is a value set for an indexed cell? | ||
122 | + * | ||
123 | + * @param string $pCoord Coordinate address of the cell to check | ||
124 | + * @return boolean | ||
125 | + */ | ||
126 | + public function isDataSet($pCoord) | ||
127 | + { | ||
128 | + if ($pCoord === $this->currentObjectID) { | ||
129 | + return true; | ||
130 | + } | ||
131 | + | ||
132 | + // Check if the requested entry exists in the cache | ||
133 | + $query = "SELECT id FROM kvp_".$this->TableName." WHERE id='".$pCoord."'"; | ||
134 | + $cellResultSet = $this->DBHandle->query($query, SQLITE_ASSOC); | ||
135 | + if ($cellResultSet === false) { | ||
136 | + throw new PHPExcel_Exception(sqlite_error_string($this->DBHandle->lastError())); | ||
137 | + } elseif ($cellResultSet->numRows() == 0) { | ||
138 | + // Return null if requested entry doesn't exist in cache | ||
139 | + return false; | ||
140 | + } | ||
141 | + return true; | ||
142 | + } | ||
143 | + | ||
144 | + /** | ||
145 | + * Delete a cell in cache identified by coordinate address | ||
146 | + * | ||
147 | + * @param string $pCoord Coordinate address of the cell to delete | ||
148 | + * @throws PHPExcel_Exception | ||
149 | + */ | ||
150 | + public function deleteCacheData($pCoord) | ||
151 | + { | ||
152 | + if ($pCoord === $this->currentObjectID) { | ||
153 | + $this->currentObject->detach(); | ||
154 | + $this->currentObjectID = $this->currentObject = null; | ||
155 | + } | ||
156 | + | ||
157 | + // Check if the requested entry exists in the cache | ||
158 | + $query = "DELETE FROM kvp_".$this->TableName." WHERE id='".$pCoord."'"; | ||
159 | + if (!$this->DBHandle->queryExec($query)) { | ||
160 | + throw new PHPExcel_Exception(sqlite_error_string($this->DBHandle->lastError())); | ||
161 | + } | ||
162 | + | ||
163 | + $this->currentCellIsDirty = false; | ||
164 | + } | ||
165 | + | ||
166 | + /** | ||
167 | + * Move a cell object from one address to another | ||
168 | + * | ||
169 | + * @param string $fromAddress Current address of the cell to move | ||
170 | + * @param string $toAddress Destination address of the cell to move | ||
171 | + * @return boolean | ||
172 | + */ | ||
173 | + public function moveCell($fromAddress, $toAddress) | ||
174 | + { | ||
175 | + if ($fromAddress === $this->currentObjectID) { | ||
176 | + $this->currentObjectID = $toAddress; | ||
177 | + } | ||
178 | + | ||
179 | + $query = "DELETE FROM kvp_".$this->TableName." WHERE id='".$toAddress."'"; | ||
180 | + $result = $this->DBHandle->exec($query); | ||
181 | + if ($result === false) { | ||
182 | + throw new PHPExcel_Exception($this->DBHandle->lastErrorMsg()); | ||
183 | + } | ||
184 | + | ||
185 | + $query = "UPDATE kvp_".$this->TableName." SET id='".$toAddress."' WHERE id='".$fromAddress."'"; | ||
186 | + $result = $this->DBHandle->exec($query); | ||
187 | + if ($result === false) { | ||
188 | + throw new PHPExcel_Exception($this->DBHandle->lastErrorMsg()); | ||
189 | + } | ||
190 | + | ||
191 | + return true; | ||
192 | + } | ||
193 | + | ||
194 | + /** | ||
195 | + * Get a list of all cell addresses currently held in cache | ||
196 | + * | ||
197 | + * @return string[] | ||
198 | + */ | ||
199 | + public function getCellList() | ||
200 | + { | ||
201 | + if ($this->currentObjectID !== null) { | ||
202 | + $this->storeData(); | ||
203 | + } | ||
204 | + | ||
205 | + $query = "SELECT id FROM kvp_".$this->TableName; | ||
206 | + $cellIdsResult = $this->DBHandle->unbufferedQuery($query, SQLITE_ASSOC); | ||
207 | + if ($cellIdsResult === false) { | ||
208 | + throw new PHPExcel_Exception(sqlite_error_string($this->DBHandle->lastError())); | ||
209 | + } | ||
210 | + | ||
211 | + $cellKeys = array(); | ||
212 | + foreach ($cellIdsResult as $row) { | ||
213 | + $cellKeys[] = $row['id']; | ||
214 | + } | ||
215 | + | ||
216 | + return $cellKeys; | ||
217 | + } | ||
218 | + | ||
219 | + /** | ||
220 | + * Clone the cell collection | ||
221 | + * | ||
222 | + * @param PHPExcel_Worksheet $parent The new worksheet | ||
223 | + * @return void | ||
224 | + */ | ||
225 | + public function copyCellCollection(PHPExcel_Worksheet $parent) | ||
226 | + { | ||
227 | + $this->currentCellIsDirty; | ||
228 | + $this->storeData(); | ||
229 | + | ||
230 | + // Get a new id for the new table name | ||
231 | + $tableName = str_replace('.', '_', $this->getUniqueID()); | ||
232 | + if (!$this->DBHandle->queryExec('CREATE TABLE kvp_'.$tableName.' (id VARCHAR(12) PRIMARY KEY, value BLOB) | ||
233 | + AS SELECT * FROM kvp_'.$this->TableName) | ||
234 | + ) { | ||
235 | + throw new PHPExcel_Exception(sqlite_error_string($this->DBHandle->lastError())); | ||
236 | + } | ||
237 | + | ||
238 | + // Copy the existing cell cache file | ||
239 | + $this->TableName = $tableName; | ||
240 | + } | ||
241 | + | ||
242 | + /** | ||
243 | + * Clear the cell collection and disconnect from our parent | ||
244 | + * | ||
245 | + * @return void | ||
246 | + */ | ||
247 | + public function unsetWorksheetCells() | ||
248 | + { | ||
249 | + if (!is_null($this->currentObject)) { | ||
250 | + $this->currentObject->detach(); | ||
251 | + $this->currentObject = $this->currentObjectID = null; | ||
252 | + } | ||
253 | + // detach ourself from the worksheet, so that it can then delete this object successfully | ||
254 | + $this->parent = null; | ||
255 | + | ||
256 | + // Close down the temporary cache file | ||
257 | + $this->__destruct(); | ||
258 | + } | ||
259 | + | ||
260 | + /** | ||
261 | + * Initialise this new cell collection | ||
262 | + * | ||
263 | + * @param PHPExcel_Worksheet $parent The worksheet for this cell collection | ||
264 | + */ | ||
265 | + public function __construct(PHPExcel_Worksheet $parent) | ||
266 | + { | ||
267 | + parent::__construct($parent); | ||
268 | + if (is_null($this->DBHandle)) { | ||
269 | + $this->TableName = str_replace('.', '_', $this->getUniqueID()); | ||
270 | + $_DBName = ':memory:'; | ||
271 | + | ||
272 | + $this->DBHandle = new SQLiteDatabase($_DBName); | ||
273 | + if ($this->DBHandle === false) { | ||
274 | + throw new PHPExcel_Exception(sqlite_error_string($this->DBHandle->lastError())); | ||
275 | + } | ||
276 | + if (!$this->DBHandle->queryExec('CREATE TABLE kvp_'.$this->TableName.' (id VARCHAR(12) PRIMARY KEY, value BLOB)')) { | ||
277 | + throw new PHPExcel_Exception(sqlite_error_string($this->DBHandle->lastError())); | ||
278 | + } | ||
279 | + } | ||
280 | + } | ||
281 | + | ||
282 | + /** | ||
283 | + * Destroy this cell collection | ||
284 | + */ | ||
285 | + public function __destruct() | ||
286 | + { | ||
287 | + if (!is_null($this->DBHandle)) { | ||
288 | + $this->DBHandle->queryExec('DROP TABLE kvp_'.$this->TableName); | ||
289 | + } | ||
290 | + $this->DBHandle = null; | ||
291 | + } | ||
292 | + | ||
293 | + /** | ||
294 | + * Identify whether the caching method is currently available | ||
295 | + * Some methods are dependent on the availability of certain extensions being enabled in the PHP build | ||
296 | + * | ||
297 | + * @return boolean | ||
298 | + */ | ||
299 | + public static function cacheMethodIsAvailable() | ||
300 | + { | ||
301 | + if (!function_exists('sqlite_open')) { | ||
302 | + return false; | ||
303 | + } | ||
304 | + | ||
305 | + return true; | ||
306 | + } | ||
307 | +} |
1 | +<?php | ||
2 | + | ||
3 | +/** | ||
4 | + * PHPExcel_CachedObjectStorage_SQLite3 | ||
5 | + * | ||
6 | + * Copyright (c) 2006 - 2015 PHPExcel | ||
7 | + * | ||
8 | + * This library is free software; you can redistribute it and/or | ||
9 | + * modify it under the terms of the GNU Lesser General Public | ||
10 | + * License as published by the Free Software Foundation; either | ||
11 | + * version 2.1 of the License, or (at your option) any later version. | ||
12 | + * | ||
13 | + * This library is distributed in the hope that it will be useful, | ||
14 | + * but WITHOUT ANY WARRANTY; without even the implied warranty of | ||
15 | + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU | ||
16 | + * Lesser General Public License for more details. | ||
17 | + * | ||
18 | + * You should have received a copy of the GNU Lesser General Public | ||
19 | + * License along with this library; if not, write to the Free Software | ||
20 | + * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA | ||
21 | + * | ||
22 | + * @category PHPExcel | ||
23 | + * @package PHPExcel_CachedObjectStorage | ||
24 | + * @copyright Copyright (c) 2006 - 2015 PHPExcel (http://www.codeplex.com/PHPExcel) | ||
25 | + * @license http://www.gnu.org/licenses/old-licenses/lgpl-2.1.txt LGPL | ||
26 | + * @version ##VERSION##, ##DATE## | ||
27 | + */ | ||
28 | +class PHPExcel_CachedObjectStorage_SQLite3 extends PHPExcel_CachedObjectStorage_CacheBase implements PHPExcel_CachedObjectStorage_ICache | ||
29 | +{ | ||
30 | + /** | ||
31 | + * Database table name | ||
32 | + * | ||
33 | + * @var string | ||
34 | + */ | ||
35 | + private $TableName = null; | ||
36 | + | ||
37 | + /** | ||
38 | + * Database handle | ||
39 | + * | ||
40 | + * @var resource | ||
41 | + */ | ||
42 | + private $DBHandle = null; | ||
43 | + | ||
44 | + /** | ||
45 | + * Prepared statement for a SQLite3 select query | ||
46 | + * | ||
47 | + * @var SQLite3Stmt | ||
48 | + */ | ||
49 | + private $selectQuery; | ||
50 | + | ||
51 | + /** | ||
52 | + * Prepared statement for a SQLite3 insert query | ||
53 | + * | ||
54 | + * @var SQLite3Stmt | ||
55 | + */ | ||
56 | + private $insertQuery; | ||
57 | + | ||
58 | + /** | ||
59 | + * Prepared statement for a SQLite3 update query | ||
60 | + * | ||
61 | + * @var SQLite3Stmt | ||
62 | + */ | ||
63 | + private $updateQuery; | ||
64 | + | ||
65 | + /** | ||
66 | + * Prepared statement for a SQLite3 delete query | ||
67 | + * | ||
68 | + * @var SQLite3Stmt | ||
69 | + */ | ||
70 | + private $deleteQuery; | ||
71 | + | ||
72 | + /** | ||
73 | + * Store cell data in cache for the current cell object if it's "dirty", | ||
74 | + * and the 'nullify' the current cell object | ||
75 | + * | ||
76 | + * @return void | ||
77 | + * @throws PHPExcel_Exception | ||
78 | + */ | ||
79 | + protected function storeData() | ||
80 | + { | ||
81 | + if ($this->currentCellIsDirty && !empty($this->currentObjectID)) { | ||
82 | + $this->currentObject->detach(); | ||
83 | + | ||
84 | + $this->insertQuery->bindValue('id', $this->currentObjectID, SQLITE3_TEXT); | ||
85 | + $this->insertQuery->bindValue('data', serialize($this->currentObject), SQLITE3_BLOB); | ||
86 | + $result = $this->insertQuery->execute(); | ||
87 | + if ($result === false) { | ||
88 | + throw new PHPExcel_Exception($this->DBHandle->lastErrorMsg()); | ||
89 | + } | ||
90 | + $this->currentCellIsDirty = false; | ||
91 | + } | ||
92 | + $this->currentObjectID = $this->currentObject = null; | ||
93 | + } | ||
94 | + | ||
95 | + /** | ||
96 | + * Add or Update a cell in cache identified by coordinate address | ||
97 | + * | ||
98 | + * @param string $pCoord Coordinate address of the cell to update | ||
99 | + * @param PHPExcel_Cell $cell Cell to update | ||
100 | + * @return PHPExcel_Cell | ||
101 | + * @throws PHPExcel_Exception | ||
102 | + */ | ||
103 | + public function addCacheData($pCoord, PHPExcel_Cell $cell) | ||
104 | + { | ||
105 | + if (($pCoord !== $this->currentObjectID) && ($this->currentObjectID !== null)) { | ||
106 | + $this->storeData(); | ||
107 | + } | ||
108 | + | ||
109 | + $this->currentObjectID = $pCoord; | ||
110 | + $this->currentObject = $cell; | ||
111 | + $this->currentCellIsDirty = true; | ||
112 | + | ||
113 | + return $cell; | ||
114 | + } | ||
115 | + | ||
116 | + /** | ||
117 | + * Get cell at a specific coordinate | ||
118 | + * | ||
119 | + * @param string $pCoord Coordinate of the cell | ||
120 | + * @throws PHPExcel_Exception | ||
121 | + * @return PHPExcel_Cell Cell that was found, or null if not found | ||
122 | + */ | ||
123 | + public function getCacheData($pCoord) | ||
124 | + { | ||
125 | + if ($pCoord === $this->currentObjectID) { | ||
126 | + return $this->currentObject; | ||
127 | + } | ||
128 | + $this->storeData(); | ||
129 | + | ||
130 | + $this->selectQuery->bindValue('id', $pCoord, SQLITE3_TEXT); | ||
131 | + $cellResult = $this->selectQuery->execute(); | ||
132 | + if ($cellResult === false) { | ||
133 | + throw new PHPExcel_Exception($this->DBHandle->lastErrorMsg()); | ||
134 | + } | ||
135 | + $cellData = $cellResult->fetchArray(SQLITE3_ASSOC); | ||
136 | + if ($cellData === false) { | ||
137 | + // Return null if requested entry doesn't exist in cache | ||
138 | + return null; | ||
139 | + } | ||
140 | + | ||
141 | + // Set current entry to the requested entry | ||
142 | + $this->currentObjectID = $pCoord; | ||
143 | + | ||
144 | + $this->currentObject = unserialize($cellData['value']); | ||
145 | + // Re-attach this as the cell's parent | ||
146 | + $this->currentObject->attach($this); | ||
147 | + | ||
148 | + // Return requested entry | ||
149 | + return $this->currentObject; | ||
150 | + } | ||
151 | + | ||
152 | + /** | ||
153 | + * Is a value set for an indexed cell? | ||
154 | + * | ||
155 | + * @param string $pCoord Coordinate address of the cell to check | ||
156 | + * @return boolean | ||
157 | + */ | ||
158 | + public function isDataSet($pCoord) | ||
159 | + { | ||
160 | + if ($pCoord === $this->currentObjectID) { | ||
161 | + return true; | ||
162 | + } | ||
163 | + | ||
164 | + // Check if the requested entry exists in the cache | ||
165 | + $this->selectQuery->bindValue('id', $pCoord, SQLITE3_TEXT); | ||
166 | + $cellResult = $this->selectQuery->execute(); | ||
167 | + if ($cellResult === false) { | ||
168 | + throw new PHPExcel_Exception($this->DBHandle->lastErrorMsg()); | ||
169 | + } | ||
170 | + $cellData = $cellResult->fetchArray(SQLITE3_ASSOC); | ||
171 | + | ||
172 | + return ($cellData === false) ? false : true; | ||
173 | + } | ||
174 | + | ||
175 | + /** | ||
176 | + * Delete a cell in cache identified by coordinate address | ||
177 | + * | ||
178 | + * @param string $pCoord Coordinate address of the cell to delete | ||
179 | + * @throws PHPExcel_Exception | ||
180 | + */ | ||
181 | + public function deleteCacheData($pCoord) | ||
182 | + { | ||
183 | + if ($pCoord === $this->currentObjectID) { | ||
184 | + $this->currentObject->detach(); | ||
185 | + $this->currentObjectID = $this->currentObject = null; | ||
186 | + } | ||
187 | + | ||
188 | + // Check if the requested entry exists in the cache | ||
189 | + $this->deleteQuery->bindValue('id', $pCoord, SQLITE3_TEXT); | ||
190 | + $result = $this->deleteQuery->execute(); | ||
191 | + if ($result === false) { | ||
192 | + throw new PHPExcel_Exception($this->DBHandle->lastErrorMsg()); | ||
193 | + } | ||
194 | + | ||
195 | + $this->currentCellIsDirty = false; | ||
196 | + } | ||
197 | + | ||
198 | + /** | ||
199 | + * Move a cell object from one address to another | ||
200 | + * | ||
201 | + * @param string $fromAddress Current address of the cell to move | ||
202 | + * @param string $toAddress Destination address of the cell to move | ||
203 | + * @return boolean | ||
204 | + */ | ||
205 | + public function moveCell($fromAddress, $toAddress) | ||
206 | + { | ||
207 | + if ($fromAddress === $this->currentObjectID) { | ||
208 | + $this->currentObjectID = $toAddress; | ||
209 | + } | ||
210 | + | ||
211 | + $this->deleteQuery->bindValue('id', $toAddress, SQLITE3_TEXT); | ||
212 | + $result = $this->deleteQuery->execute(); | ||
213 | + if ($result === false) { | ||
214 | + throw new PHPExcel_Exception($this->DBHandle->lastErrorMsg()); | ||
215 | + } | ||
216 | + | ||
217 | + $this->updateQuery->bindValue('toid', $toAddress, SQLITE3_TEXT); | ||
218 | + $this->updateQuery->bindValue('fromid', $fromAddress, SQLITE3_TEXT); | ||
219 | + $result = $this->updateQuery->execute(); | ||
220 | + if ($result === false) { | ||
221 | + throw new PHPExcel_Exception($this->DBHandle->lastErrorMsg()); | ||
222 | + } | ||
223 | + | ||
224 | + return true; | ||
225 | + } | ||
226 | + | ||
227 | + /** | ||
228 | + * Get a list of all cell addresses currently held in cache | ||
229 | + * | ||
230 | + * @return string[] | ||
231 | + */ | ||
232 | + public function getCellList() | ||
233 | + { | ||
234 | + if ($this->currentObjectID !== null) { | ||
235 | + $this->storeData(); | ||
236 | + } | ||
237 | + | ||
238 | + $query = "SELECT id FROM kvp_".$this->TableName; | ||
239 | + $cellIdsResult = $this->DBHandle->query($query); | ||
240 | + if ($cellIdsResult === false) { | ||
241 | + throw new PHPExcel_Exception($this->DBHandle->lastErrorMsg()); | ||
242 | + } | ||
243 | + | ||
244 | + $cellKeys = array(); | ||
245 | + while ($row = $cellIdsResult->fetchArray(SQLITE3_ASSOC)) { | ||
246 | + $cellKeys[] = $row['id']; | ||
247 | + } | ||
248 | + | ||
249 | + return $cellKeys; | ||
250 | + } | ||
251 | + | ||
252 | + /** | ||
253 | + * Clone the cell collection | ||
254 | + * | ||
255 | + * @param PHPExcel_Worksheet $parent The new worksheet | ||
256 | + * @return void | ||
257 | + */ | ||
258 | + public function copyCellCollection(PHPExcel_Worksheet $parent) | ||
259 | + { | ||
260 | + $this->currentCellIsDirty; | ||
261 | + $this->storeData(); | ||
262 | + | ||
263 | + // Get a new id for the new table name | ||
264 | + $tableName = str_replace('.', '_', $this->getUniqueID()); | ||
265 | + if (!$this->DBHandle->exec('CREATE TABLE kvp_'.$tableName.' (id VARCHAR(12) PRIMARY KEY, value BLOB) | ||
266 | + AS SELECT * FROM kvp_'.$this->TableName) | ||
267 | + ) { | ||
268 | + throw new PHPExcel_Exception($this->DBHandle->lastErrorMsg()); | ||
269 | + } | ||
270 | + | ||
271 | + // Copy the existing cell cache file | ||
272 | + $this->TableName = $tableName; | ||
273 | + } | ||
274 | + | ||
275 | + /** | ||
276 | + * Clear the cell collection and disconnect from our parent | ||
277 | + * | ||
278 | + * @return void | ||
279 | + */ | ||
280 | + public function unsetWorksheetCells() | ||
281 | + { | ||
282 | + if (!is_null($this->currentObject)) { | ||
283 | + $this->currentObject->detach(); | ||
284 | + $this->currentObject = $this->currentObjectID = null; | ||
285 | + } | ||
286 | + // detach ourself from the worksheet, so that it can then delete this object successfully | ||
287 | + $this->parent = null; | ||
288 | + | ||
289 | + // Close down the temporary cache file | ||
290 | + $this->__destruct(); | ||
291 | + } | ||
292 | + | ||
293 | + /** | ||
294 | + * Initialise this new cell collection | ||
295 | + * | ||
296 | + * @param PHPExcel_Worksheet $parent The worksheet for this cell collection | ||
297 | + */ | ||
298 | + public function __construct(PHPExcel_Worksheet $parent) | ||
299 | + { | ||
300 | + parent::__construct($parent); | ||
301 | + if (is_null($this->DBHandle)) { | ||
302 | + $this->TableName = str_replace('.', '_', $this->getUniqueID()); | ||
303 | + $_DBName = ':memory:'; | ||
304 | + | ||
305 | + $this->DBHandle = new SQLite3($_DBName); | ||
306 | + if ($this->DBHandle === false) { | ||
307 | + throw new PHPExcel_Exception($this->DBHandle->lastErrorMsg()); | ||
308 | + } | ||
309 | + if (!$this->DBHandle->exec('CREATE TABLE kvp_'.$this->TableName.' (id VARCHAR(12) PRIMARY KEY, value BLOB)')) { | ||
310 | + throw new PHPExcel_Exception($this->DBHandle->lastErrorMsg()); | ||
311 | + } | ||
312 | + } | ||
313 | + | ||
314 | + $this->selectQuery = $this->DBHandle->prepare("SELECT value FROM kvp_".$this->TableName." WHERE id = :id"); | ||
315 | + $this->insertQuery = $this->DBHandle->prepare("INSERT OR REPLACE INTO kvp_".$this->TableName." VALUES(:id,:data)"); | ||
316 | + $this->updateQuery = $this->DBHandle->prepare("UPDATE kvp_".$this->TableName." SET id=:toId WHERE id=:fromId"); | ||
317 | + $this->deleteQuery = $this->DBHandle->prepare("DELETE FROM kvp_".$this->TableName." WHERE id = :id"); | ||
318 | + } | ||
319 | + | ||
320 | + /** | ||
321 | + * Destroy this cell collection | ||
322 | + */ | ||
323 | + public function __destruct() | ||
324 | + { | ||
325 | + if (!is_null($this->DBHandle)) { | ||
326 | + $this->DBHandle->exec('DROP TABLE kvp_'.$this->TableName); | ||
327 | + $this->DBHandle->close(); | ||
328 | + } | ||
329 | + $this->DBHandle = null; | ||
330 | + } | ||
331 | + | ||
332 | + /** | ||
333 | + * Identify whether the caching method is currently available | ||
334 | + * Some methods are dependent on the availability of certain extensions being enabled in the PHP build | ||
335 | + * | ||
336 | + * @return boolean | ||
337 | + */ | ||
338 | + public static function cacheMethodIsAvailable() | ||
339 | + { | ||
340 | + if (!class_exists('SQLite3', false)) { | ||
341 | + return false; | ||
342 | + } | ||
343 | + | ||
344 | + return true; | ||
345 | + } | ||
346 | +} |
1 | +<?php | ||
2 | + | ||
3 | +/** | ||
4 | + * PHPExcel_CachedObjectStorage_Wincache | ||
5 | + * | ||
6 | + * Copyright (c) 2006 - 2015 PHPExcel | ||
7 | + * | ||
8 | + * This library is free software; you can redistribute it and/or | ||
9 | + * modify it under the terms of the GNU Lesser General Public | ||
10 | + * License as published by the Free Software Foundation; either | ||
11 | + * version 2.1 of the License, or (at your option) any later version. | ||
12 | + * | ||
13 | + * This library is distributed in the hope that it will be useful, | ||
14 | + * but WITHOUT ANY WARRANTY; without even the implied warranty of | ||
15 | + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU | ||
16 | + * Lesser General Public License for more details. | ||
17 | + * | ||
18 | + * You should have received a copy of the GNU Lesser General Public | ||
19 | + * License along with this library; if not, write to the Free Software | ||
20 | + * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA | ||
21 | + * | ||
22 | + * @category PHPExcel | ||
23 | + * @package PHPExcel_CachedObjectStorage | ||
24 | + * @copyright Copyright (c) 2006 - 2015 PHPExcel (http://www.codeplex.com/PHPExcel) | ||
25 | + * @license http://www.gnu.org/licenses/old-licenses/lgpl-2.1.txt LGPL | ||
26 | + * @version ##VERSION##, ##DATE## | ||
27 | + */ | ||
28 | +class PHPExcel_CachedObjectStorage_Wincache extends PHPExcel_CachedObjectStorage_CacheBase implements PHPExcel_CachedObjectStorage_ICache | ||
29 | +{ | ||
30 | + /** | ||
31 | + * Prefix used to uniquely identify cache data for this worksheet | ||
32 | + * | ||
33 | + * @var string | ||
34 | + */ | ||
35 | + private $cachePrefix = null; | ||
36 | + | ||
37 | + /** | ||
38 | + * Cache timeout | ||
39 | + * | ||
40 | + * @var integer | ||
41 | + */ | ||
42 | + private $cacheTime = 600; | ||
43 | + | ||
44 | + | ||
45 | + /** | ||
46 | + * Store cell data in cache for the current cell object if it's "dirty", | ||
47 | + * and the 'nullify' the current cell object | ||
48 | + * | ||
49 | + * @return void | ||
50 | + * @throws PHPExcel_Exception | ||
51 | + */ | ||
52 | + protected function storeData() | ||
53 | + { | ||
54 | + if ($this->currentCellIsDirty && !empty($this->currentObjectID)) { | ||
55 | + $this->currentObject->detach(); | ||
56 | + | ||
57 | + $obj = serialize($this->currentObject); | ||
58 | + if (wincache_ucache_exists($this->cachePrefix.$this->currentObjectID.'.cache')) { | ||
59 | + if (!wincache_ucache_set($this->cachePrefix.$this->currentObjectID.'.cache', $obj, $this->cacheTime)) { | ||
60 | + $this->__destruct(); | ||
61 | + throw new PHPExcel_Exception('Failed to store cell '.$this->currentObjectID.' in WinCache'); | ||
62 | + } | ||
63 | + } else { | ||
64 | + if (!wincache_ucache_add($this->cachePrefix.$this->currentObjectID.'.cache', $obj, $this->cacheTime)) { | ||
65 | + $this->__destruct(); | ||
66 | + throw new PHPExcel_Exception('Failed to store cell '.$this->currentObjectID.' in WinCache'); | ||
67 | + } | ||
68 | + } | ||
69 | + $this->currentCellIsDirty = false; | ||
70 | + } | ||
71 | + | ||
72 | + $this->currentObjectID = $this->currentObject = null; | ||
73 | + } | ||
74 | + | ||
75 | + /** | ||
76 | + * Add or Update a cell in cache identified by coordinate address | ||
77 | + * | ||
78 | + * @param string $pCoord Coordinate address of the cell to update | ||
79 | + * @param PHPExcel_Cell $cell Cell to update | ||
80 | + * @return PHPExcel_Cell | ||
81 | + * @throws PHPExcel_Exception | ||
82 | + */ | ||
83 | + public function addCacheData($pCoord, PHPExcel_Cell $cell) | ||
84 | + { | ||
85 | + if (($pCoord !== $this->currentObjectID) && ($this->currentObjectID !== null)) { | ||
86 | + $this->storeData(); | ||
87 | + } | ||
88 | + $this->cellCache[$pCoord] = true; | ||
89 | + | ||
90 | + $this->currentObjectID = $pCoord; | ||
91 | + $this->currentObject = $cell; | ||
92 | + $this->currentCellIsDirty = true; | ||
93 | + | ||
94 | + return $cell; | ||
95 | + } | ||
96 | + | ||
97 | + /** | ||
98 | + * Is a value set in the current PHPExcel_CachedObjectStorage_ICache for an indexed cell? | ||
99 | + * | ||
100 | + * @param string $pCoord Coordinate address of the cell to check | ||
101 | + * @return boolean | ||
102 | + */ | ||
103 | + public function isDataSet($pCoord) | ||
104 | + { | ||
105 | + // Check if the requested entry is the current object, or exists in the cache | ||
106 | + if (parent::isDataSet($pCoord)) { | ||
107 | + if ($this->currentObjectID == $pCoord) { | ||
108 | + return true; | ||
109 | + } | ||
110 | + // Check if the requested entry still exists in cache | ||
111 | + $success = wincache_ucache_exists($this->cachePrefix.$pCoord.'.cache'); | ||
112 | + if ($success === false) { | ||
113 | + // Entry no longer exists in Wincache, so clear it from the cache array | ||
114 | + parent::deleteCacheData($pCoord); | ||
115 | + throw new PHPExcel_Exception('Cell entry '.$pCoord.' no longer exists in WinCache'); | ||
116 | + } | ||
117 | + return true; | ||
118 | + } | ||
119 | + return false; | ||
120 | + } | ||
121 | + | ||
122 | + | ||
123 | + /** | ||
124 | + * Get cell at a specific coordinate | ||
125 | + * | ||
126 | + * @param string $pCoord Coordinate of the cell | ||
127 | + * @throws PHPExcel_Exception | ||
128 | + * @return PHPExcel_Cell Cell that was found, or null if not found | ||
129 | + */ | ||
130 | + public function getCacheData($pCoord) | ||
131 | + { | ||
132 | + if ($pCoord === $this->currentObjectID) { | ||
133 | + return $this->currentObject; | ||
134 | + } | ||
135 | + $this->storeData(); | ||
136 | + | ||
137 | + // Check if the entry that has been requested actually exists | ||
138 | + $obj = null; | ||
139 | + if (parent::isDataSet($pCoord)) { | ||
140 | + $success = false; | ||
141 | + $obj = wincache_ucache_get($this->cachePrefix.$pCoord.'.cache', $success); | ||
142 | + if ($success === false) { | ||
143 | + // Entry no longer exists in WinCache, so clear it from the cache array | ||
144 | + parent::deleteCacheData($pCoord); | ||
145 | + throw new PHPExcel_Exception('Cell entry '.$pCoord.' no longer exists in WinCache'); | ||
146 | + } | ||
147 | + } else { | ||
148 | + // Return null if requested entry doesn't exist in cache | ||
149 | + return null; | ||
150 | + } | ||
151 | + | ||
152 | + // Set current entry to the requested entry | ||
153 | + $this->currentObjectID = $pCoord; | ||
154 | + $this->currentObject = unserialize($obj); | ||
155 | + // Re-attach this as the cell's parent | ||
156 | + $this->currentObject->attach($this); | ||
157 | + | ||
158 | + // Return requested entry | ||
159 | + return $this->currentObject; | ||
160 | + } | ||
161 | + | ||
162 | + | ||
163 | + /** | ||
164 | + * Get a list of all cell addresses currently held in cache | ||
165 | + * | ||
166 | + * @return string[] | ||
167 | + */ | ||
168 | + public function getCellList() | ||
169 | + { | ||
170 | + if ($this->currentObjectID !== null) { | ||
171 | + $this->storeData(); | ||
172 | + } | ||
173 | + | ||
174 | + return parent::getCellList(); | ||
175 | + } | ||
176 | + | ||
177 | + /** | ||
178 | + * Delete a cell in cache identified by coordinate address | ||
179 | + * | ||
180 | + * @param string $pCoord Coordinate address of the cell to delete | ||
181 | + * @throws PHPExcel_Exception | ||
182 | + */ | ||
183 | + public function deleteCacheData($pCoord) | ||
184 | + { | ||
185 | + // Delete the entry from Wincache | ||
186 | + wincache_ucache_delete($this->cachePrefix.$pCoord.'.cache'); | ||
187 | + | ||
188 | + // Delete the entry from our cell address array | ||
189 | + parent::deleteCacheData($pCoord); | ||
190 | + } | ||
191 | + | ||
192 | + /** | ||
193 | + * Clone the cell collection | ||
194 | + * | ||
195 | + * @param PHPExcel_Worksheet $parent The new worksheet | ||
196 | + * @return void | ||
197 | + */ | ||
198 | + public function copyCellCollection(PHPExcel_Worksheet $parent) | ||
199 | + { | ||
200 | + parent::copyCellCollection($parent); | ||
201 | + // Get a new id for the new file name | ||
202 | + $baseUnique = $this->getUniqueID(); | ||
203 | + $newCachePrefix = substr(md5($baseUnique), 0, 8) . '.'; | ||
204 | + $cacheList = $this->getCellList(); | ||
205 | + foreach ($cacheList as $cellID) { | ||
206 | + if ($cellID != $this->currentObjectID) { | ||
207 | + $success = false; | ||
208 | + $obj = wincache_ucache_get($this->cachePrefix.$cellID.'.cache', $success); | ||
209 | + if ($success === false) { | ||
210 | + // Entry no longer exists in WinCache, so clear it from the cache array | ||
211 | + parent::deleteCacheData($cellID); | ||
212 | + throw new PHPExcel_Exception('Cell entry '.$cellID.' no longer exists in Wincache'); | ||
213 | + } | ||
214 | + if (!wincache_ucache_add($newCachePrefix.$cellID.'.cache', $obj, $this->cacheTime)) { | ||
215 | + $this->__destruct(); | ||
216 | + throw new PHPExcel_Exception('Failed to store cell '.$cellID.' in Wincache'); | ||
217 | + } | ||
218 | + } | ||
219 | + } | ||
220 | + $this->cachePrefix = $newCachePrefix; | ||
221 | + } | ||
222 | + | ||
223 | + | ||
224 | + /** | ||
225 | + * Clear the cell collection and disconnect from our parent | ||
226 | + * | ||
227 | + * @return void | ||
228 | + */ | ||
229 | + public function unsetWorksheetCells() | ||
230 | + { | ||
231 | + if (!is_null($this->currentObject)) { | ||
232 | + $this->currentObject->detach(); | ||
233 | + $this->currentObject = $this->currentObjectID = null; | ||
234 | + } | ||
235 | + | ||
236 | + // Flush the WinCache cache | ||
237 | + $this->__destruct(); | ||
238 | + | ||
239 | + $this->cellCache = array(); | ||
240 | + | ||
241 | + // detach ourself from the worksheet, so that it can then delete this object successfully | ||
242 | + $this->parent = null; | ||
243 | + } | ||
244 | + | ||
245 | + /** | ||
246 | + * Initialise this new cell collection | ||
247 | + * | ||
248 | + * @param PHPExcel_Worksheet $parent The worksheet for this cell collection | ||
249 | + * @param array of mixed $arguments Additional initialisation arguments | ||
250 | + */ | ||
251 | + public function __construct(PHPExcel_Worksheet $parent, $arguments) | ||
252 | + { | ||
253 | + $cacheTime = (isset($arguments['cacheTime'])) ? $arguments['cacheTime'] : 600; | ||
254 | + | ||
255 | + if (is_null($this->cachePrefix)) { | ||
256 | + $baseUnique = $this->getUniqueID(); | ||
257 | + $this->cachePrefix = substr(md5($baseUnique), 0, 8).'.'; | ||
258 | + $this->cacheTime = $cacheTime; | ||
259 | + | ||
260 | + parent::__construct($parent); | ||
261 | + } | ||
262 | + } | ||
263 | + | ||
264 | + /** | ||
265 | + * Destroy this cell collection | ||
266 | + */ | ||
267 | + public function __destruct() | ||
268 | + { | ||
269 | + $cacheList = $this->getCellList(); | ||
270 | + foreach ($cacheList as $cellID) { | ||
271 | + wincache_ucache_delete($this->cachePrefix.$cellID.'.cache'); | ||
272 | + } | ||
273 | + } | ||
274 | + | ||
275 | + /** | ||
276 | + * Identify whether the caching method is currently available | ||
277 | + * Some methods are dependent on the availability of certain extensions being enabled in the PHP build | ||
278 | + * | ||
279 | + * @return boolean | ||
280 | + */ | ||
281 | + public static function cacheMethodIsAvailable() | ||
282 | + { | ||
283 | + if (!function_exists('wincache_ucache_add')) { | ||
284 | + return false; | ||
285 | + } | ||
286 | + | ||
287 | + return true; | ||
288 | + } | ||
289 | +} |
1 | +<?php | ||
2 | + | ||
3 | +/** | ||
4 | + * PHPExcel_CachedObjectStorageFactory | ||
5 | + * | ||
6 | + * Copyright (c) 2006 - 2015 PHPExcel | ||
7 | + * | ||
8 | + * This library is free software; you can redistribute it and/or | ||
9 | + * modify it under the terms of the GNU Lesser General Public | ||
10 | + * License as published by the Free Software Foundation; either | ||
11 | + * version 2.1 of the License, or (at your option) any later version. | ||
12 | + * | ||
13 | + * This library is distributed in the hope that it will be useful, | ||
14 | + * but WITHOUT ANY WARRANTY; without even the implied warranty of | ||
15 | + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU | ||
16 | + * Lesser General Public License for more details. | ||
17 | + * | ||
18 | + * You should have received a copy of the GNU Lesser General Public | ||
19 | + * License along with this library; if not, write to the Free Software | ||
20 | + * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA | ||
21 | + * | ||
22 | + * @category PHPExcel | ||
23 | + * @package PHPExcel_CachedObjectStorage | ||
24 | + * @copyright Copyright (c) 2006 - 2015 PHPExcel (http://www.codeplex.com/PHPExcel) | ||
25 | + * @license http://www.gnu.org/licenses/old-licenses/lgpl-2.1.txt LGPL | ||
26 | + * @version ##VERSION##, ##DATE## | ||
27 | + */ | ||
28 | +class PHPExcel_CachedObjectStorageFactory | ||
29 | +{ | ||
30 | + const cache_in_memory = 'Memory'; | ||
31 | + const cache_in_memory_gzip = 'MemoryGZip'; | ||
32 | + const cache_in_memory_serialized = 'MemorySerialized'; | ||
33 | + const cache_igbinary = 'Igbinary'; | ||
34 | + const cache_to_discISAM = 'DiscISAM'; | ||
35 | + const cache_to_apc = 'APC'; | ||
36 | + const cache_to_memcache = 'Memcache'; | ||
37 | + const cache_to_phpTemp = 'PHPTemp'; | ||
38 | + const cache_to_wincache = 'Wincache'; | ||
39 | + const cache_to_sqlite = 'SQLite'; | ||
40 | + const cache_to_sqlite3 = 'SQLite3'; | ||
41 | + | ||
42 | + /** | ||
43 | + * Name of the method used for cell cacheing | ||
44 | + * | ||
45 | + * @var string | ||
46 | + */ | ||
47 | + private static $cacheStorageMethod = null; | ||
48 | + | ||
49 | + /** | ||
50 | + * Name of the class used for cell cacheing | ||
51 | + * | ||
52 | + * @var string | ||
53 | + */ | ||
54 | + private static $cacheStorageClass = null; | ||
55 | + | ||
56 | + /** | ||
57 | + * List of all possible cache storage methods | ||
58 | + * | ||
59 | + * @var string[] | ||
60 | + */ | ||
61 | + private static $storageMethods = array( | ||
62 | + self::cache_in_memory, | ||
63 | + self::cache_in_memory_gzip, | ||
64 | + self::cache_in_memory_serialized, | ||
65 | + self::cache_igbinary, | ||
66 | + self::cache_to_phpTemp, | ||
67 | + self::cache_to_discISAM, | ||
68 | + self::cache_to_apc, | ||
69 | + self::cache_to_memcache, | ||
70 | + self::cache_to_wincache, | ||
71 | + self::cache_to_sqlite, | ||
72 | + self::cache_to_sqlite3, | ||
73 | + ); | ||
74 | + | ||
75 | + /** | ||
76 | + * Default arguments for each cache storage method | ||
77 | + * | ||
78 | + * @var array of mixed array | ||
79 | + */ | ||
80 | + private static $storageMethodDefaultParameters = array( | ||
81 | + self::cache_in_memory => array( | ||
82 | + ), | ||
83 | + self::cache_in_memory_gzip => array( | ||
84 | + ), | ||
85 | + self::cache_in_memory_serialized => array( | ||
86 | + ), | ||
87 | + self::cache_igbinary => array( | ||
88 | + ), | ||
89 | + self::cache_to_phpTemp => array( 'memoryCacheSize' => '1MB' | ||
90 | + ), | ||
91 | + self::cache_to_discISAM => array( 'dir' => null | ||
92 | + ), | ||
93 | + self::cache_to_apc => array( 'cacheTime' => 600 | ||
94 | + ), | ||
95 | + self::cache_to_memcache => array( 'memcacheServer' => 'localhost', | ||
96 | + 'memcachePort' => 11211, | ||
97 | + 'cacheTime' => 600 | ||
98 | + ), | ||
99 | + self::cache_to_wincache => array( 'cacheTime' => 600 | ||
100 | + ), | ||
101 | + self::cache_to_sqlite => array( | ||
102 | + ), | ||
103 | + self::cache_to_sqlite3 => array( | ||
104 | + ), | ||
105 | + ); | ||
106 | + | ||
107 | + /** | ||
108 | + * Arguments for the active cache storage method | ||
109 | + * | ||
110 | + * @var array of mixed array | ||
111 | + */ | ||
112 | + private static $storageMethodParameters = array(); | ||
113 | + | ||
114 | + /** | ||
115 | + * Return the current cache storage method | ||
116 | + * | ||
117 | + * @return string|null | ||
118 | + **/ | ||
119 | + public static function getCacheStorageMethod() | ||
120 | + { | ||
121 | + return self::$cacheStorageMethod; | ||
122 | + } | ||
123 | + | ||
124 | + /** | ||
125 | + * Return the current cache storage class | ||
126 | + * | ||
127 | + * @return PHPExcel_CachedObjectStorage_ICache|null | ||
128 | + **/ | ||
129 | + public static function getCacheStorageClass() | ||
130 | + { | ||
131 | + return self::$cacheStorageClass; | ||
132 | + } | ||
133 | + | ||
134 | + /** | ||
135 | + * Return the list of all possible cache storage methods | ||
136 | + * | ||
137 | + * @return string[] | ||
138 | + **/ | ||
139 | + public static function getAllCacheStorageMethods() | ||
140 | + { | ||
141 | + return self::$storageMethods; | ||
142 | + } | ||
143 | + | ||
144 | + /** | ||
145 | + * Return the list of all available cache storage methods | ||
146 | + * | ||
147 | + * @return string[] | ||
148 | + **/ | ||
149 | + public static function getCacheStorageMethods() | ||
150 | + { | ||
151 | + $activeMethods = array(); | ||
152 | + foreach (self::$storageMethods as $storageMethod) { | ||
153 | + $cacheStorageClass = 'PHPExcel_CachedObjectStorage_' . $storageMethod; | ||
154 | + if (call_user_func(array($cacheStorageClass, 'cacheMethodIsAvailable'))) { | ||
155 | + $activeMethods[] = $storageMethod; | ||
156 | + } | ||
157 | + } | ||
158 | + return $activeMethods; | ||
159 | + } | ||
160 | + | ||
161 | + /** | ||
162 | + * Identify the cache storage method to use | ||
163 | + * | ||
164 | + * @param string $method Name of the method to use for cell cacheing | ||
165 | + * @param array of mixed $arguments Additional arguments to pass to the cell caching class | ||
166 | + * when instantiating | ||
167 | + * @return boolean | ||
168 | + **/ | ||
169 | + public static function initialize($method = self::cache_in_memory, $arguments = array()) | ||
170 | + { | ||
171 | + if (!in_array($method, self::$storageMethods)) { | ||
172 | + return false; | ||
173 | + } | ||
174 | + | ||
175 | + $cacheStorageClass = 'PHPExcel_CachedObjectStorage_'.$method; | ||
176 | + if (!call_user_func(array( $cacheStorageClass, | ||
177 | + 'cacheMethodIsAvailable'))) { | ||
178 | + return false; | ||
179 | + } | ||
180 | + | ||
181 | + self::$storageMethodParameters[$method] = self::$storageMethodDefaultParameters[$method]; | ||
182 | + foreach ($arguments as $k => $v) { | ||
183 | + if (array_key_exists($k, self::$storageMethodParameters[$method])) { | ||
184 | + self::$storageMethodParameters[$method][$k] = $v; | ||
185 | + } | ||
186 | + } | ||
187 | + | ||
188 | + if (self::$cacheStorageMethod === null) { | ||
189 | + self::$cacheStorageClass = 'PHPExcel_CachedObjectStorage_' . $method; | ||
190 | + self::$cacheStorageMethod = $method; | ||
191 | + } | ||
192 | + return true; | ||
193 | + } | ||
194 | + | ||
195 | + /** | ||
196 | + * Initialise the cache storage | ||
197 | + * | ||
198 | + * @param PHPExcel_Worksheet $parent Enable cell caching for this worksheet | ||
199 | + * @return PHPExcel_CachedObjectStorage_ICache | ||
200 | + **/ | ||
201 | + public static function getInstance(PHPExcel_Worksheet $parent) | ||
202 | + { | ||
203 | + $cacheMethodIsAvailable = true; | ||
204 | + if (self::$cacheStorageMethod === null) { | ||
205 | + $cacheMethodIsAvailable = self::initialize(); | ||
206 | + } | ||
207 | + | ||
208 | + if ($cacheMethodIsAvailable) { | ||
209 | + $instance = new self::$cacheStorageClass( | ||
210 | + $parent, | ||
211 | + self::$storageMethodParameters[self::$cacheStorageMethod] | ||
212 | + ); | ||
213 | + if ($instance !== null) { | ||
214 | + return $instance; | ||
215 | + } | ||
216 | + } | ||
217 | + | ||
218 | + return false; | ||
219 | + } | ||
220 | + | ||
221 | + /** | ||
222 | + * Clear the cache storage | ||
223 | + * | ||
224 | + **/ | ||
225 | + public static function finalize() | ||
226 | + { | ||
227 | + self::$cacheStorageMethod = null; | ||
228 | + self::$cacheStorageClass = null; | ||
229 | + self::$storageMethodParameters = array(); | ||
230 | + } | ||
231 | +} |
1 | +<?php | ||
2 | + | ||
3 | +/** | ||
4 | + * PHPExcel_CalcEngine_CyclicReferenceStack | ||
5 | + * | ||
6 | + * Copyright (c) 2006 - 2015 PHPExcel | ||
7 | + * | ||
8 | + * This library is free software; you can redistribute it and/or | ||
9 | + * modify it under the terms of the GNU Lesser General Public | ||
10 | + * License as published by the Free Software Foundation; either | ||
11 | + * version 2.1 of the License, or (at your option) any later version. | ||
12 | + * | ||
13 | + * This library is distributed in the hope that it will be useful, | ||
14 | + * but WITHOUT ANY WARRANTY; without even the implied warranty of | ||
15 | + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU | ||
16 | + * Lesser General Public License for more details. | ||
17 | + * | ||
18 | + * You should have received a copy of the GNU Lesser General Public | ||
19 | + * License along with this library; if not, write to the Free Software | ||
20 | + * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA | ||
21 | + * | ||
22 | + * @category PHPExcel | ||
23 | + * @package PHPExcel_Calculation | ||
24 | + * @copyright Copyright (c) 2006 - 2015 PHPExcel (http://www.codeplex.com/PHPExcel) | ||
25 | + * @license http://www.gnu.org/licenses/old-licenses/lgpl-2.1.txt LGPL | ||
26 | + * @version ##VERSION##, ##DATE## | ||
27 | + */ | ||
28 | +class PHPExcel_CalcEngine_CyclicReferenceStack | ||
29 | +{ | ||
30 | + /** | ||
31 | + * The call stack for calculated cells | ||
32 | + * | ||
33 | + * @var mixed[] | ||
34 | + */ | ||
35 | + private $stack = array(); | ||
36 | + | ||
37 | + /** | ||
38 | + * Return the number of entries on the stack | ||
39 | + * | ||
40 | + * @return integer | ||
41 | + */ | ||
42 | + public function count() | ||
43 | + { | ||
44 | + return count($this->stack); | ||
45 | + } | ||
46 | + | ||
47 | + /** | ||
48 | + * Push a new entry onto the stack | ||
49 | + * | ||
50 | + * @param mixed $value | ||
51 | + */ | ||
52 | + public function push($value) | ||
53 | + { | ||
54 | + $this->stack[$value] = $value; | ||
55 | + } | ||
56 | + | ||
57 | + /** | ||
58 | + * Pop the last entry from the stack | ||
59 | + * | ||
60 | + * @return mixed | ||
61 | + */ | ||
62 | + public function pop() | ||
63 | + { | ||
64 | + return array_pop($this->stack); | ||
65 | + } | ||
66 | + | ||
67 | + /** | ||
68 | + * Test to see if a specified entry exists on the stack | ||
69 | + * | ||
70 | + * @param mixed $value The value to test | ||
71 | + */ | ||
72 | + public function onStack($value) | ||
73 | + { | ||
74 | + return isset($this->stack[$value]); | ||
75 | + } | ||
76 | + | ||
77 | + /** | ||
78 | + * Clear the stack | ||
79 | + */ | ||
80 | + public function clear() | ||
81 | + { | ||
82 | + $this->stack = array(); | ||
83 | + } | ||
84 | + | ||
85 | + /** | ||
86 | + * Return an array of all entries on the stack | ||
87 | + * | ||
88 | + * @return mixed[] | ||
89 | + */ | ||
90 | + public function showStack() | ||
91 | + { | ||
92 | + return $this->stack; | ||
93 | + } | ||
94 | +} |
1 | +<?php | ||
2 | + | ||
3 | +/** | ||
4 | + * PHPExcel_CalcEngine_Logger | ||
5 | + * | ||
6 | + * Copyright (c) 2006 - 2015 PHPExcel | ||
7 | + * | ||
8 | + * This library is free software; you can redistribute it and/or | ||
9 | + * modify it under the terms of the GNU Lesser General Public | ||
10 | + * License as published by the Free Software Foundation; either | ||
11 | + * version 2.1 of the License, or (at your option) any later version. | ||
12 | + * | ||
13 | + * This library is distributed in the hope that it will be useful, | ||
14 | + * but WITHOUT ANY WARRANTY; without even the implied warranty of | ||
15 | + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU | ||
16 | + * Lesser General Public License for more details. | ||
17 | + * | ||
18 | + * You should have received a copy of the GNU Lesser General Public | ||
19 | + * License along with this library; if not, write to the Free Software | ||
20 | + * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA | ||
21 | + * | ||
22 | + * @category PHPExcel | ||
23 | + * @package PHPExcel_Calculation | ||
24 | + * @copyright Copyright (c) 2006 - 2015 PHPExcel (http://www.codeplex.com/PHPExcel) | ||
25 | + * @license http://www.gnu.org/licenses/old-licenses/lgpl-2.1.txt LGPL | ||
26 | + * @version ##VERSION##, ##DATE## | ||
27 | + */ | ||
28 | +class PHPExcel_CalcEngine_Logger | ||
29 | +{ | ||
30 | + /** | ||
31 | + * Flag to determine whether a debug log should be generated by the calculation engine | ||
32 | + * If true, then a debug log will be generated | ||
33 | + * If false, then a debug log will not be generated | ||
34 | + * | ||
35 | + * @var boolean | ||
36 | + */ | ||
37 | + private $writeDebugLog = false; | ||
38 | + | ||
39 | + /** | ||
40 | + * Flag to determine whether a debug log should be echoed by the calculation engine | ||
41 | + * If true, then a debug log will be echoed | ||
42 | + * If false, then a debug log will not be echoed | ||
43 | + * A debug log can only be echoed if it is generated | ||
44 | + * | ||
45 | + * @var boolean | ||
46 | + */ | ||
47 | + private $echoDebugLog = false; | ||
48 | + | ||
49 | + /** | ||
50 | + * The debug log generated by the calculation engine | ||
51 | + * | ||
52 | + * @var string[] | ||
53 | + */ | ||
54 | + private $debugLog = array(); | ||
55 | + | ||
56 | + /** | ||
57 | + * The calculation engine cell reference stack | ||
58 | + * | ||
59 | + * @var PHPExcel_CalcEngine_CyclicReferenceStack | ||
60 | + */ | ||
61 | + private $cellStack; | ||
62 | + | ||
63 | + /** | ||
64 | + * Instantiate a Calculation engine logger | ||
65 | + * | ||
66 | + * @param PHPExcel_CalcEngine_CyclicReferenceStack $stack | ||
67 | + */ | ||
68 | + public function __construct(PHPExcel_CalcEngine_CyclicReferenceStack $stack) | ||
69 | + { | ||
70 | + $this->cellStack = $stack; | ||
71 | + } | ||
72 | + | ||
73 | + /** | ||
74 | + * Enable/Disable Calculation engine logging | ||
75 | + * | ||
76 | + * @param boolean $pValue | ||
77 | + */ | ||
78 | + public function setWriteDebugLog($pValue = false) | ||
79 | + { | ||
80 | + $this->writeDebugLog = $pValue; | ||
81 | + } | ||
82 | + | ||
83 | + /** | ||
84 | + * Return whether calculation engine logging is enabled or disabled | ||
85 | + * | ||
86 | + * @return boolean | ||
87 | + */ | ||
88 | + public function getWriteDebugLog() | ||
89 | + { | ||
90 | + return $this->writeDebugLog; | ||
91 | + } | ||
92 | + | ||
93 | + /** | ||
94 | + * Enable/Disable echoing of debug log information | ||
95 | + * | ||
96 | + * @param boolean $pValue | ||
97 | + */ | ||
98 | + public function setEchoDebugLog($pValue = false) | ||
99 | + { | ||
100 | + $this->echoDebugLog = $pValue; | ||
101 | + } | ||
102 | + | ||
103 | + /** | ||
104 | + * Return whether echoing of debug log information is enabled or disabled | ||
105 | + * | ||
106 | + * @return boolean | ||
107 | + */ | ||
108 | + public function getEchoDebugLog() | ||
109 | + { | ||
110 | + return $this->echoDebugLog; | ||
111 | + } | ||
112 | + | ||
113 | + /** | ||
114 | + * Write an entry to the calculation engine debug log | ||
115 | + */ | ||
116 | + public function writeDebugLog() | ||
117 | + { | ||
118 | + // Only write the debug log if logging is enabled | ||
119 | + if ($this->writeDebugLog) { | ||
120 | + $message = implode(func_get_args()); | ||
121 | + $cellReference = implode(' -> ', $this->cellStack->showStack()); | ||
122 | + if ($this->echoDebugLog) { | ||
123 | + echo $cellReference, | ||
124 | + ($this->cellStack->count() > 0 ? ' => ' : ''), | ||
125 | + $message, | ||
126 | + PHP_EOL; | ||
127 | + } | ||
128 | + $this->debugLog[] = $cellReference . | ||
129 | + ($this->cellStack->count() > 0 ? ' => ' : '') . | ||
130 | + $message; | ||
131 | + } | ||
132 | + } | ||
133 | + | ||
134 | + /** | ||
135 | + * Clear the calculation engine debug log | ||
136 | + */ | ||
137 | + public function clearLog() | ||
138 | + { | ||
139 | + $this->debugLog = array(); | ||
140 | + } | ||
141 | + | ||
142 | + /** | ||
143 | + * Return the calculation engine debug log | ||
144 | + * | ||
145 | + * @return string[] | ||
146 | + */ | ||
147 | + public function getLog() | ||
148 | + { | ||
149 | + return $this->debugLog; | ||
150 | + } | ||
151 | +} |
此 diff 太大无法显示。
-
请 注册 或 登录 后发表评论