diff --git a/CHANGELOG.md b/CHANGELOG.md index 326682fe..e963100f 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -2,6 +2,7 @@ ## Unreleased ### Fixed +- Update bundled PhpSpreadsheet to 5.10.0 to address known spreadsheet processing vulnerabilities. - Restore report tiles for recipients of shared panoramas. - Replace the report folder icon with a downward arrow when expanded and remove redundant trailing folder arrows. - Use the URL to select content and open its navigation folders without saving navigation state or changing the URL when toggling folders; keep Overview groups collapsed. diff --git a/vendor/autoload.php b/vendor/autoload.php index b9320543..57f457ad 100644 --- a/vendor/autoload.php +++ b/vendor/autoload.php @@ -19,4 +19,4 @@ require_once __DIR__ . '/composer/autoload_real.php'; -return ComposerAutoloaderInit524e760e56b0620cb9bc3d8d9ad8543d::getLoader(); +return ComposerAutoloaderInitbae58d66b0357c26ca5c29c77e2a2a8a::getLoader(); diff --git a/vendor/composer/autoload_classmap.php b/vendor/composer/autoload_classmap.php index 0fb0a2c1..28ee599b 100644 --- a/vendor/composer/autoload_classmap.php +++ b/vendor/composer/autoload_classmap.php @@ -6,5 +6,550 @@ $baseDir = dirname($vendorDir); return array( + 'Complex\\Complex' => $vendorDir . '/markbaker/complex/classes/src/Complex.php', + 'Complex\\Exception' => $vendorDir . '/markbaker/complex/classes/src/Exception.php', + 'Complex\\Functions' => $vendorDir . '/markbaker/complex/classes/src/Functions.php', + 'Complex\\Operations' => $vendorDir . '/markbaker/complex/classes/src/Operations.php', 'Composer\\InstalledVersions' => $vendorDir . '/composer/InstalledVersions.php', + 'Composer\\Pcre\\MatchAllResult' => $vendorDir . '/composer/pcre/src/MatchAllResult.php', + 'Composer\\Pcre\\MatchAllStrictGroupsResult' => $vendorDir . '/composer/pcre/src/MatchAllStrictGroupsResult.php', + 'Composer\\Pcre\\MatchAllWithOffsetsResult' => $vendorDir . '/composer/pcre/src/MatchAllWithOffsetsResult.php', + 'Composer\\Pcre\\MatchResult' => $vendorDir . '/composer/pcre/src/MatchResult.php', + 'Composer\\Pcre\\MatchStrictGroupsResult' => $vendorDir . '/composer/pcre/src/MatchStrictGroupsResult.php', + 'Composer\\Pcre\\MatchWithOffsetsResult' => $vendorDir . '/composer/pcre/src/MatchWithOffsetsResult.php', + 'Composer\\Pcre\\PHPStan\\InvalidRegexPatternRule' => $vendorDir . '/composer/pcre/src/PHPStan/InvalidRegexPatternRule.php', + 'Composer\\Pcre\\PHPStan\\PregMatchFlags' => $vendorDir . '/composer/pcre/src/PHPStan/PregMatchFlags.php', + 'Composer\\Pcre\\PHPStan\\PregMatchParameterOutTypeExtension' => $vendorDir . '/composer/pcre/src/PHPStan/PregMatchParameterOutTypeExtension.php', + 'Composer\\Pcre\\PHPStan\\PregMatchTypeSpecifyingExtension' => $vendorDir . '/composer/pcre/src/PHPStan/PregMatchTypeSpecifyingExtension.php', + 'Composer\\Pcre\\PHPStan\\PregReplaceCallbackClosureTypeExtension' => $vendorDir . '/composer/pcre/src/PHPStan/PregReplaceCallbackClosureTypeExtension.php', + 'Composer\\Pcre\\PHPStan\\UnsafeStrictGroupsCallRule' => $vendorDir . '/composer/pcre/src/PHPStan/UnsafeStrictGroupsCallRule.php', + 'Composer\\Pcre\\PcreException' => $vendorDir . '/composer/pcre/src/PcreException.php', + 'Composer\\Pcre\\Preg' => $vendorDir . '/composer/pcre/src/Preg.php', + 'Composer\\Pcre\\Regex' => $vendorDir . '/composer/pcre/src/Regex.php', + 'Composer\\Pcre\\ReplaceResult' => $vendorDir . '/composer/pcre/src/ReplaceResult.php', + 'Composer\\Pcre\\UnexpectedNullMatchException' => $vendorDir . '/composer/pcre/src/UnexpectedNullMatchException.php', + 'Matrix\\Builder' => $vendorDir . '/markbaker/matrix/classes/src/Builder.php', + 'Matrix\\Decomposition\\Decomposition' => $vendorDir . '/markbaker/matrix/classes/src/Decomposition/Decomposition.php', + 'Matrix\\Decomposition\\LU' => $vendorDir . '/markbaker/matrix/classes/src/Decomposition/LU.php', + 'Matrix\\Decomposition\\QR' => $vendorDir . '/markbaker/matrix/classes/src/Decomposition/QR.php', + 'Matrix\\Div0Exception' => $vendorDir . '/markbaker/matrix/classes/src/Div0Exception.php', + 'Matrix\\Exception' => $vendorDir . '/markbaker/matrix/classes/src/Exception.php', + 'Matrix\\Functions' => $vendorDir . '/markbaker/matrix/classes/src/Functions.php', + 'Matrix\\Matrix' => $vendorDir . '/markbaker/matrix/classes/src/Matrix.php', + 'Matrix\\Operations' => $vendorDir . '/markbaker/matrix/classes/src/Operations.php', + 'Matrix\\Operators\\Addition' => $vendorDir . '/markbaker/matrix/classes/src/Operators/Addition.php', + 'Matrix\\Operators\\DirectSum' => $vendorDir . '/markbaker/matrix/classes/src/Operators/DirectSum.php', + 'Matrix\\Operators\\Division' => $vendorDir . '/markbaker/matrix/classes/src/Operators/Division.php', + 'Matrix\\Operators\\Multiplication' => $vendorDir . '/markbaker/matrix/classes/src/Operators/Multiplication.php', + 'Matrix\\Operators\\Operator' => $vendorDir . '/markbaker/matrix/classes/src/Operators/Operator.php', + 'Matrix\\Operators\\Subtraction' => $vendorDir . '/markbaker/matrix/classes/src/Operators/Subtraction.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\ArrayEnabled' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/ArrayEnabled.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\BinaryComparison' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/BinaryComparison.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Calculation' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Calculation.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\CalculationBase' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/CalculationBase.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\CalculationLocale' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/CalculationLocale.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\CalculationParserOnly' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/CalculationParserOnly.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Category' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Category.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Database\\DAverage' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Database/DAverage.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Database\\DCount' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Database/DCount.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Database\\DCountA' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Database/DCountA.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Database\\DGet' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Database/DGet.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Database\\DMax' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Database/DMax.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Database\\DMin' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Database/DMin.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Database\\DProduct' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Database/DProduct.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Database\\DStDev' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Database/DStDev.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Database\\DStDevP' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Database/DStDevP.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Database\\DSum' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Database/DSum.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Database\\DVar' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Database/DVar.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Database\\DVarP' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Database/DVarP.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Database\\DatabaseAbstract' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Database/DatabaseAbstract.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\DateTimeExcel\\Constants' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/DateTimeExcel/Constants.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\DateTimeExcel\\Current' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/DateTimeExcel/Current.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\DateTimeExcel\\Date' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/DateTimeExcel/Date.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\DateTimeExcel\\DateParts' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/DateTimeExcel/DateParts.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\DateTimeExcel\\DateValue' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/DateTimeExcel/DateValue.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\DateTimeExcel\\Days' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/DateTimeExcel/Days.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\DateTimeExcel\\Days360' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/DateTimeExcel/Days360.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\DateTimeExcel\\Difference' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/DateTimeExcel/Difference.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\DateTimeExcel\\Helpers' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/DateTimeExcel/Helpers.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\DateTimeExcel\\Month' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/DateTimeExcel/Month.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\DateTimeExcel\\NetworkDays' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/DateTimeExcel/NetworkDays.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\DateTimeExcel\\Time' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/DateTimeExcel/Time.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\DateTimeExcel\\TimeParts' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/DateTimeExcel/TimeParts.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\DateTimeExcel\\TimeValue' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/DateTimeExcel/TimeValue.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\DateTimeExcel\\Week' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/DateTimeExcel/Week.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\DateTimeExcel\\WorkDay' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/DateTimeExcel/WorkDay.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\DateTimeExcel\\YearFrac' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/DateTimeExcel/YearFrac.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Engine\\ArrayArgumentHelper' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Engine/ArrayArgumentHelper.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Engine\\ArrayArgumentProcessor' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Engine/ArrayArgumentProcessor.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Engine\\BranchPruner' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Engine/BranchPruner.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Engine\\CyclicReferenceStack' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Engine/CyclicReferenceStack.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Engine\\FormattedNumber' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Engine/FormattedNumber.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Engine\\Logger' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Engine/Logger.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Engine\\Operands\\Operand' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Engine/Operands/Operand.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Engine\\Operands\\StructuredReference' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Engine/Operands/StructuredReference.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Engineering\\BesselI' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Engineering/BesselI.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Engineering\\BesselJ' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Engineering/BesselJ.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Engineering\\BesselK' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Engineering/BesselK.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Engineering\\BesselY' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Engineering/BesselY.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Engineering\\BitWise' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Engineering/BitWise.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Engineering\\Compare' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Engineering/Compare.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Engineering\\Complex' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Engineering/Complex.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Engineering\\ComplexFunctions' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Engineering/ComplexFunctions.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Engineering\\ComplexOperations' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Engineering/ComplexOperations.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Engineering\\Constants' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Engineering/Constants.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Engineering\\ConvertBase' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Engineering/ConvertBase.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Engineering\\ConvertBinary' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Engineering/ConvertBinary.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Engineering\\ConvertDecimal' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Engineering/ConvertDecimal.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Engineering\\ConvertHex' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Engineering/ConvertHex.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Engineering\\ConvertOctal' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Engineering/ConvertOctal.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Engineering\\ConvertUOM' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Engineering/ConvertUOM.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Engineering\\EngineeringValidations' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Engineering/EngineeringValidations.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Engineering\\Erf' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Engineering/Erf.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Engineering\\ErfC' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Engineering/ErfC.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Exception' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Exception.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\ExceptionHandler' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/ExceptionHandler.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Financial\\Amortization' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Financial/Amortization.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Financial\\CashFlow\\CashFlowValidations' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Financial/CashFlow/CashFlowValidations.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Financial\\CashFlow\\Constant\\Periodic' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Financial/CashFlow/Constant/Periodic.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Financial\\CashFlow\\Constant\\Periodic\\Cumulative' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Financial/CashFlow/Constant/Periodic/Cumulative.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Financial\\CashFlow\\Constant\\Periodic\\Interest' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Financial/CashFlow/Constant/Periodic/Interest.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Financial\\CashFlow\\Constant\\Periodic\\InterestAndPrincipal' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Financial/CashFlow/Constant/Periodic/InterestAndPrincipal.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Financial\\CashFlow\\Constant\\Periodic\\Payments' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Financial/CashFlow/Constant/Periodic/Payments.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Financial\\CashFlow\\Single' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Financial/CashFlow/Single.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Financial\\CashFlow\\Variable\\NonPeriodic' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Financial/CashFlow/Variable/NonPeriodic.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Financial\\CashFlow\\Variable\\Periodic' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Financial/CashFlow/Variable/Periodic.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Financial\\Constants' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Financial/Constants.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Financial\\Coupons' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Financial/Coupons.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Financial\\Depreciation' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Financial/Depreciation.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Financial\\Dollar' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Financial/Dollar.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Financial\\FinancialValidations' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Financial/FinancialValidations.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Financial\\Helpers' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Financial/Helpers.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Financial\\InterestRate' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Financial/InterestRate.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Financial\\Securities\\AccruedInterest' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Financial/Securities/AccruedInterest.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Financial\\Securities\\Price' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Financial/Securities/Price.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Financial\\Securities\\Rates' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Financial/Securities/Rates.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Financial\\Securities\\SecurityValidations' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Financial/Securities/SecurityValidations.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Financial\\Securities\\Yields' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Financial/Securities/Yields.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Financial\\TreasuryBill' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Financial/TreasuryBill.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\FormulaParser' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/FormulaParser.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\FormulaToken' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/FormulaToken.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\FunctionArray' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/FunctionArray.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Functions' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Functions.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Information\\ErrorValue' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Information/ErrorValue.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Information\\ExcelError' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Information/ExcelError.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Information\\Info' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Information/Info.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Information\\Value' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Information/Value.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Internal\\ExcelArrayPseudoFunctions' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Internal/ExcelArrayPseudoFunctions.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Internal\\MakeMatrix' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Internal/MakeMatrix.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Internal\\WildcardMatch' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Internal/WildcardMatch.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Logical\\Boolean' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Logical/Boolean.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Logical\\Conditional' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Logical/Conditional.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Logical\\Operations' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Logical/Operations.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\LookupRef\\Address' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/LookupRef/Address.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\LookupRef\\ChooseRowsEtc' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/LookupRef/ChooseRowsEtc.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\LookupRef\\ExcelMatch' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/LookupRef/ExcelMatch.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\LookupRef\\Filter' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/LookupRef/Filter.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\LookupRef\\Formula' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/LookupRef/Formula.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\LookupRef\\HLookup' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/LookupRef/HLookup.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\LookupRef\\Helpers' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/LookupRef/Helpers.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\LookupRef\\Hstack' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/LookupRef/Hstack.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\LookupRef\\Hyperlink' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/LookupRef/Hyperlink.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\LookupRef\\Indirect' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/LookupRef/Indirect.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\LookupRef\\Lookup' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/LookupRef/Lookup.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\LookupRef\\LookupBase' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/LookupRef/LookupBase.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\LookupRef\\LookupRefValidations' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/LookupRef/LookupRefValidations.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\LookupRef\\Matrix' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/LookupRef/Matrix.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\LookupRef\\Offset' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/LookupRef/Offset.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\LookupRef\\RowColumnInformation' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/LookupRef/RowColumnInformation.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\LookupRef\\Selection' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/LookupRef/Selection.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\LookupRef\\Sort' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/LookupRef/Sort.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\LookupRef\\TorowTocol' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/LookupRef/TorowTocol.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\LookupRef\\Unique' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/LookupRef/Unique.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\LookupRef\\VLookup' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/LookupRef/VLookup.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\LookupRef\\Vstack' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/LookupRef/Vstack.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\LookupRef\\XLookup' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/LookupRef/XLookup.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\MathTrig\\Absolute' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/MathTrig/Absolute.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\MathTrig\\Angle' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/MathTrig/Angle.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\MathTrig\\Arabic' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/MathTrig/Arabic.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\MathTrig\\Base' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/MathTrig/Base.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\MathTrig\\Ceiling' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/MathTrig/Ceiling.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\MathTrig\\Combinations' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/MathTrig/Combinations.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\MathTrig\\Exp' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/MathTrig/Exp.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\MathTrig\\Factorial' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/MathTrig/Factorial.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\MathTrig\\Floor' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/MathTrig/Floor.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\MathTrig\\Gcd' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/MathTrig/Gcd.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\MathTrig\\Helpers' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/MathTrig/Helpers.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\MathTrig\\IntClass' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/MathTrig/IntClass.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\MathTrig\\Lcm' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/MathTrig/Lcm.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\MathTrig\\Logarithms' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/MathTrig/Logarithms.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\MathTrig\\MatrixFunctions' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/MathTrig/MatrixFunctions.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\MathTrig\\Operations' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/MathTrig/Operations.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\MathTrig\\Random' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/MathTrig/Random.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\MathTrig\\Roman' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/MathTrig/Roman.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\MathTrig\\Round' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/MathTrig/Round.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\MathTrig\\SeriesSum' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/MathTrig/SeriesSum.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\MathTrig\\Sign' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/MathTrig/Sign.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\MathTrig\\Sqrt' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/MathTrig/Sqrt.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\MathTrig\\Subtotal' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/MathTrig/Subtotal.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\MathTrig\\Sum' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/MathTrig/Sum.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\MathTrig\\SumSquares' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/MathTrig/SumSquares.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\MathTrig\\Trig\\Cosecant' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/MathTrig/Trig/Cosecant.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\MathTrig\\Trig\\Cosine' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/MathTrig/Trig/Cosine.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\MathTrig\\Trig\\Cotangent' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/MathTrig/Trig/Cotangent.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\MathTrig\\Trig\\Secant' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/MathTrig/Trig/Secant.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\MathTrig\\Trig\\Sine' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/MathTrig/Trig/Sine.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\MathTrig\\Trig\\Tangent' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/MathTrig/Trig/Tangent.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\MathTrig\\Trunc' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/MathTrig/Trunc.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Statistical\\AggregateBase' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Statistical/AggregateBase.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Statistical\\Averages' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Statistical/Averages.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Statistical\\Averages\\Mean' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Statistical/Averages/Mean.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Statistical\\Conditional' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Statistical/Conditional.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Statistical\\Confidence' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Statistical/Confidence.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Statistical\\Counts' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Statistical/Counts.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Statistical\\Deviations' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Statistical/Deviations.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Statistical\\Distributions\\Beta' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Statistical/Distributions/Beta.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Statistical\\Distributions\\Binomial' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Statistical/Distributions/Binomial.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Statistical\\Distributions\\ChiSquared' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Statistical/Distributions/ChiSquared.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Statistical\\Distributions\\DistributionValidations' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Statistical/Distributions/DistributionValidations.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Statistical\\Distributions\\Exponential' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Statistical/Distributions/Exponential.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Statistical\\Distributions\\F' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Statistical/Distributions/F.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Statistical\\Distributions\\Fisher' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Statistical/Distributions/Fisher.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Statistical\\Distributions\\Gamma' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Statistical/Distributions/Gamma.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Statistical\\Distributions\\GammaBase' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Statistical/Distributions/GammaBase.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Statistical\\Distributions\\HyperGeometric' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Statistical/Distributions/HyperGeometric.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Statistical\\Distributions\\LogNormal' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Statistical/Distributions/LogNormal.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Statistical\\Distributions\\NewtonRaphson' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Statistical/Distributions/NewtonRaphson.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Statistical\\Distributions\\Normal' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Statistical/Distributions/Normal.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Statistical\\Distributions\\Poisson' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Statistical/Distributions/Poisson.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Statistical\\Distributions\\StandardNormal' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Statistical/Distributions/StandardNormal.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Statistical\\Distributions\\StudentT' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Statistical/Distributions/StudentT.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Statistical\\Distributions\\Weibull' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Statistical/Distributions/Weibull.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Statistical\\MaxMinBase' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Statistical/MaxMinBase.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Statistical\\Maximum' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Statistical/Maximum.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Statistical\\Minimum' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Statistical/Minimum.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Statistical\\Percentiles' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Statistical/Percentiles.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Statistical\\Permutations' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Statistical/Permutations.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Statistical\\Size' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Statistical/Size.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Statistical\\StandardDeviations' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Statistical/StandardDeviations.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Statistical\\Standardize' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Statistical/Standardize.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Statistical\\StatisticalValidations' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Statistical/StatisticalValidations.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Statistical\\Trends' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Statistical/Trends.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Statistical\\VarianceBase' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Statistical/VarianceBase.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Statistical\\Variances' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Statistical/Variances.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\TextData\\CaseConvert' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/TextData/CaseConvert.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\TextData\\CharacterConvert' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/TextData/CharacterConvert.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\TextData\\Concatenate' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/TextData/Concatenate.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\TextData\\Extract' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/TextData/Extract.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\TextData\\Format' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/TextData/Format.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\TextData\\Helpers' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/TextData/Helpers.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\TextData\\Replace' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/TextData/Replace.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\TextData\\Search' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/TextData/Search.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\TextData\\Text' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/TextData/Text.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\TextData\\Thai' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/TextData/Thai.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\TextData\\Trim' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/TextData/Trim.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Token\\Stack' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Token/Stack.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Web\\Service' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Web/Service.php', + 'PhpOffice\\PhpSpreadsheet\\CellReferenceHelper' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/CellReferenceHelper.php', + 'PhpOffice\\PhpSpreadsheet\\Cell\\AddressHelper' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Cell/AddressHelper.php', + 'PhpOffice\\PhpSpreadsheet\\Cell\\AddressRange' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Cell/AddressRange.php', + 'PhpOffice\\PhpSpreadsheet\\Cell\\AdvancedValueBinder' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Cell/AdvancedValueBinder.php', + 'PhpOffice\\PhpSpreadsheet\\Cell\\Cell' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Cell/Cell.php', + 'PhpOffice\\PhpSpreadsheet\\Cell\\CellAddress' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Cell/CellAddress.php', + 'PhpOffice\\PhpSpreadsheet\\Cell\\CellRange' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Cell/CellRange.php', + 'PhpOffice\\PhpSpreadsheet\\Cell\\ColumnRange' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Cell/ColumnRange.php', + 'PhpOffice\\PhpSpreadsheet\\Cell\\Coordinate' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Cell/Coordinate.php', + 'PhpOffice\\PhpSpreadsheet\\Cell\\DataType' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Cell/DataType.php', + 'PhpOffice\\PhpSpreadsheet\\Cell\\DataValidation' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Cell/DataValidation.php', + 'PhpOffice\\PhpSpreadsheet\\Cell\\DataValidator' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Cell/DataValidator.php', + 'PhpOffice\\PhpSpreadsheet\\Cell\\DefaultValueBinder' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Cell/DefaultValueBinder.php', + 'PhpOffice\\PhpSpreadsheet\\Cell\\Hyperlink' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Cell/Hyperlink.php', + 'PhpOffice\\PhpSpreadsheet\\Cell\\IValueBinder' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Cell/IValueBinder.php', + 'PhpOffice\\PhpSpreadsheet\\Cell\\IgnoredErrors' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Cell/IgnoredErrors.php', + 'PhpOffice\\PhpSpreadsheet\\Cell\\RowRange' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Cell/RowRange.php', + 'PhpOffice\\PhpSpreadsheet\\Cell\\StringValueBinder' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Cell/StringValueBinder.php', + 'PhpOffice\\PhpSpreadsheet\\Chart\\Axis' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Chart/Axis.php', + 'PhpOffice\\PhpSpreadsheet\\Chart\\AxisText' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Chart/AxisText.php', + 'PhpOffice\\PhpSpreadsheet\\Chart\\Chart' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Chart/Chart.php', + 'PhpOffice\\PhpSpreadsheet\\Chart\\ChartColor' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Chart/ChartColor.php', + 'PhpOffice\\PhpSpreadsheet\\Chart\\DataSeries' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Chart/DataSeries.php', + 'PhpOffice\\PhpSpreadsheet\\Chart\\DataSeriesValues' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Chart/DataSeriesValues.php', + 'PhpOffice\\PhpSpreadsheet\\Chart\\DataTable' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Chart/DataTable.php', + 'PhpOffice\\PhpSpreadsheet\\Chart\\Exception' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Chart/Exception.php', + 'PhpOffice\\PhpSpreadsheet\\Chart\\GridLines' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Chart/GridLines.php', + 'PhpOffice\\PhpSpreadsheet\\Chart\\Layout' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Chart/Layout.php', + 'PhpOffice\\PhpSpreadsheet\\Chart\\Legend' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Chart/Legend.php', + 'PhpOffice\\PhpSpreadsheet\\Chart\\PlotArea' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Chart/PlotArea.php', + 'PhpOffice\\PhpSpreadsheet\\Chart\\Properties' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Chart/Properties.php', + 'PhpOffice\\PhpSpreadsheet\\Chart\\Renderer\\IRenderer' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Chart/Renderer/IRenderer.php', + 'PhpOffice\\PhpSpreadsheet\\Chart\\Renderer\\JpGraph' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Chart/Renderer/JpGraph.php', + 'PhpOffice\\PhpSpreadsheet\\Chart\\Renderer\\JpGraphRendererBase' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Chart/Renderer/JpGraphRendererBase.php', + 'PhpOffice\\PhpSpreadsheet\\Chart\\Renderer\\MtJpGraphRenderer' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Chart/Renderer/MtJpGraphRenderer.php', + 'PhpOffice\\PhpSpreadsheet\\Chart\\Title' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Chart/Title.php', + 'PhpOffice\\PhpSpreadsheet\\Chart\\TrendLine' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Chart/TrendLine.php', + 'PhpOffice\\PhpSpreadsheet\\Collection\\Cells' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Collection/Cells.php', + 'PhpOffice\\PhpSpreadsheet\\Collection\\CellsFactory' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Collection/CellsFactory.php', + 'PhpOffice\\PhpSpreadsheet\\Collection\\Memory\\SimpleCache1' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Collection/Memory/SimpleCache1.php', + 'PhpOffice\\PhpSpreadsheet\\Collection\\Memory\\SimpleCache3' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Collection/Memory/SimpleCache3.php', + 'PhpOffice\\PhpSpreadsheet\\Comment' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Comment.php', + 'PhpOffice\\PhpSpreadsheet\\DefinedName' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/DefinedName.php', + 'PhpOffice\\PhpSpreadsheet\\Document\\Properties' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Document/Properties.php', + 'PhpOffice\\PhpSpreadsheet\\Document\\Security' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Document/Security.php', + 'PhpOffice\\PhpSpreadsheet\\Exception' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Exception.php', + 'PhpOffice\\PhpSpreadsheet\\HashTable' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/HashTable.php', + 'PhpOffice\\PhpSpreadsheet\\Helper\\Dimension' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Helper/Dimension.php', + 'PhpOffice\\PhpSpreadsheet\\Helper\\Downloader' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Helper/Downloader.php', + 'PhpOffice\\PhpSpreadsheet\\Helper\\Handler' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Helper/Handler.php', + 'PhpOffice\\PhpSpreadsheet\\Helper\\Html' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Helper/Html.php', + 'PhpOffice\\PhpSpreadsheet\\Helper\\Sample' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Helper/Sample.php', + 'PhpOffice\\PhpSpreadsheet\\Helper\\Size' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Helper/Size.php', + 'PhpOffice\\PhpSpreadsheet\\Helper\\TextGrid' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Helper/TextGrid.php', + 'PhpOffice\\PhpSpreadsheet\\Helper\\TextGridRightAlign' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Helper/TextGridRightAlign.php', + 'PhpOffice\\PhpSpreadsheet\\IComparable' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/IComparable.php', + 'PhpOffice\\PhpSpreadsheet\\IOFactory' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/IOFactory.php', + 'PhpOffice\\PhpSpreadsheet\\NamedFormula' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/NamedFormula.php', + 'PhpOffice\\PhpSpreadsheet\\NamedRange' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/NamedRange.php', + 'PhpOffice\\PhpSpreadsheet\\Reader\\BaseReader' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/BaseReader.php', + 'PhpOffice\\PhpSpreadsheet\\Reader\\Csv' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Csv.php', + 'PhpOffice\\PhpSpreadsheet\\Reader\\CsvNoEscape' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/CsvNoEscape.php', + 'PhpOffice\\PhpSpreadsheet\\Reader\\Csv\\Delimiter' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Csv/Delimiter.php', + 'PhpOffice\\PhpSpreadsheet\\Reader\\DefaultReadFilter' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/DefaultReadFilter.php', + 'PhpOffice\\PhpSpreadsheet\\Reader\\EmptyWorksheetInfo' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/EmptyWorksheetInfo.php', + 'PhpOffice\\PhpSpreadsheet\\Reader\\Exception' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Exception.php', + 'PhpOffice\\PhpSpreadsheet\\Reader\\Gnumeric' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Gnumeric.php', + 'PhpOffice\\PhpSpreadsheet\\Reader\\Gnumeric\\PageSetup' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Gnumeric/PageSetup.php', + 'PhpOffice\\PhpSpreadsheet\\Reader\\Gnumeric\\Properties' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Gnumeric/Properties.php', + 'PhpOffice\\PhpSpreadsheet\\Reader\\Gnumeric\\Styles' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Gnumeric/Styles.php', + 'PhpOffice\\PhpSpreadsheet\\Reader\\Html' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Html.php', + 'PhpOffice\\PhpSpreadsheet\\Reader\\IReadFilter' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/IReadFilter.php', + 'PhpOffice\\PhpSpreadsheet\\Reader\\IReader' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/IReader.php', + 'PhpOffice\\PhpSpreadsheet\\Reader\\IReader2' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/IReader2.php', + 'PhpOffice\\PhpSpreadsheet\\Reader\\Ods' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Ods.php', + 'PhpOffice\\PhpSpreadsheet\\Reader\\Ods\\AutoFilter' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Ods/AutoFilter.php', + 'PhpOffice\\PhpSpreadsheet\\Reader\\Ods\\BaseLoader' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Ods/BaseLoader.php', + 'PhpOffice\\PhpSpreadsheet\\Reader\\Ods\\DefinedNames' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Ods/DefinedNames.php', + 'PhpOffice\\PhpSpreadsheet\\Reader\\Ods\\FormulaTranslator' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Ods/FormulaTranslator.php', + 'PhpOffice\\PhpSpreadsheet\\Reader\\Ods\\PageSettings' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Ods/PageSettings.php', + 'PhpOffice\\PhpSpreadsheet\\Reader\\Ods\\Properties' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Ods/Properties.php', + 'PhpOffice\\PhpSpreadsheet\\Reader\\Security\\XmlScanner' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Security/XmlScanner.php', + 'PhpOffice\\PhpSpreadsheet\\Reader\\Slk' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Slk.php', + 'PhpOffice\\PhpSpreadsheet\\Reader\\Xls' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Xls.php', + 'PhpOffice\\PhpSpreadsheet\\Reader\\XlsBase' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/XlsBase.php', + 'PhpOffice\\PhpSpreadsheet\\Reader\\Xls\\Biff5' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Xls/Biff5.php', + 'PhpOffice\\PhpSpreadsheet\\Reader\\Xls\\Biff8' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Xls/Biff8.php', + 'PhpOffice\\PhpSpreadsheet\\Reader\\Xls\\Color' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Xls/Color.php', + 'PhpOffice\\PhpSpreadsheet\\Reader\\Xls\\Color\\BIFF5' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Xls/Color/BIFF5.php', + 'PhpOffice\\PhpSpreadsheet\\Reader\\Xls\\Color\\BIFF8' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Xls/Color/BIFF8.php', + 'PhpOffice\\PhpSpreadsheet\\Reader\\Xls\\Color\\BuiltIn' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Xls/Color/BuiltIn.php', + 'PhpOffice\\PhpSpreadsheet\\Reader\\Xls\\ConditionalFormatting' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Xls/ConditionalFormatting.php', + 'PhpOffice\\PhpSpreadsheet\\Reader\\Xls\\DataValidationHelper' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Xls/DataValidationHelper.php', + 'PhpOffice\\PhpSpreadsheet\\Reader\\Xls\\ErrorCode' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Xls/ErrorCode.php', + 'PhpOffice\\PhpSpreadsheet\\Reader\\Xls\\Escher' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Xls/Escher.php', + 'PhpOffice\\PhpSpreadsheet\\Reader\\Xls\\ListFunctions' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Xls/ListFunctions.php', + 'PhpOffice\\PhpSpreadsheet\\Reader\\Xls\\LoadSpreadsheet' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Xls/LoadSpreadsheet.php', + 'PhpOffice\\PhpSpreadsheet\\Reader\\Xls\\MD5' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Xls/MD5.php', + 'PhpOffice\\PhpSpreadsheet\\Reader\\Xls\\Mappings' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Xls/Mappings.php', + 'PhpOffice\\PhpSpreadsheet\\Reader\\Xls\\RC4' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Xls/RC4.php', + 'PhpOffice\\PhpSpreadsheet\\Reader\\Xls\\Style\\Border' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Xls/Style/Border.php', + 'PhpOffice\\PhpSpreadsheet\\Reader\\Xls\\Style\\CellAlignment' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Xls/Style/CellAlignment.php', + 'PhpOffice\\PhpSpreadsheet\\Reader\\Xls\\Style\\CellFont' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Xls/Style/CellFont.php', + 'PhpOffice\\PhpSpreadsheet\\Reader\\Xls\\Style\\FillPattern' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Xls/Style/FillPattern.php', + 'PhpOffice\\PhpSpreadsheet\\Reader\\Xlsx' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Xlsx.php', + 'PhpOffice\\PhpSpreadsheet\\Reader\\Xlsx\\AutoFilter' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Xlsx/AutoFilter.php', + 'PhpOffice\\PhpSpreadsheet\\Reader\\Xlsx\\BaseParserClass' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Xlsx/BaseParserClass.php', + 'PhpOffice\\PhpSpreadsheet\\Reader\\Xlsx\\Chart' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Xlsx/Chart.php', + 'PhpOffice\\PhpSpreadsheet\\Reader\\Xlsx\\ColumnAndRowAttributes' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Xlsx/ColumnAndRowAttributes.php', + 'PhpOffice\\PhpSpreadsheet\\Reader\\Xlsx\\ConditionalStyles' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Xlsx/ConditionalStyles.php', + 'PhpOffice\\PhpSpreadsheet\\Reader\\Xlsx\\DataValidations' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Xlsx/DataValidations.php', + 'PhpOffice\\PhpSpreadsheet\\Reader\\Xlsx\\Hyperlinks' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Xlsx/Hyperlinks.php', + 'PhpOffice\\PhpSpreadsheet\\Reader\\Xlsx\\Namespaces' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Xlsx/Namespaces.php', + 'PhpOffice\\PhpSpreadsheet\\Reader\\Xlsx\\PageSetup' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Xlsx/PageSetup.php', + 'PhpOffice\\PhpSpreadsheet\\Reader\\Xlsx\\PivotTableReader' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Xlsx/PivotTableReader.php', + 'PhpOffice\\PhpSpreadsheet\\Reader\\Xlsx\\Properties' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Xlsx/Properties.php', + 'PhpOffice\\PhpSpreadsheet\\Reader\\Xlsx\\SharedFormula' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Xlsx/SharedFormula.php', + 'PhpOffice\\PhpSpreadsheet\\Reader\\Xlsx\\SheetViewOptions' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Xlsx/SheetViewOptions.php', + 'PhpOffice\\PhpSpreadsheet\\Reader\\Xlsx\\SheetViews' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Xlsx/SheetViews.php', + 'PhpOffice\\PhpSpreadsheet\\Reader\\Xlsx\\Sparklines' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Xlsx/Sparklines.php', + 'PhpOffice\\PhpSpreadsheet\\Reader\\Xlsx\\Styles' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Xlsx/Styles.php', + 'PhpOffice\\PhpSpreadsheet\\Reader\\Xlsx\\TableReader' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Xlsx/TableReader.php', + 'PhpOffice\\PhpSpreadsheet\\Reader\\Xlsx\\Theme' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Xlsx/Theme.php', + 'PhpOffice\\PhpSpreadsheet\\Reader\\Xlsx\\WorkbookView' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Xlsx/WorkbookView.php', + 'PhpOffice\\PhpSpreadsheet\\Reader\\Xml' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Xml.php', + 'PhpOffice\\PhpSpreadsheet\\Reader\\Xml\\DataValidations' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Xml/DataValidations.php', + 'PhpOffice\\PhpSpreadsheet\\Reader\\Xml\\PageSettings' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Xml/PageSettings.php', + 'PhpOffice\\PhpSpreadsheet\\Reader\\Xml\\Properties' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Xml/Properties.php', + 'PhpOffice\\PhpSpreadsheet\\Reader\\Xml\\Style' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Xml/Style.php', + 'PhpOffice\\PhpSpreadsheet\\Reader\\Xml\\Style\\Alignment' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Xml/Style/Alignment.php', + 'PhpOffice\\PhpSpreadsheet\\Reader\\Xml\\Style\\Border' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Xml/Style/Border.php', + 'PhpOffice\\PhpSpreadsheet\\Reader\\Xml\\Style\\Fill' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Xml/Style/Fill.php', + 'PhpOffice\\PhpSpreadsheet\\Reader\\Xml\\Style\\Font' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Xml/Style/Font.php', + 'PhpOffice\\PhpSpreadsheet\\Reader\\Xml\\Style\\NumberFormat' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Xml/Style/NumberFormat.php', + 'PhpOffice\\PhpSpreadsheet\\Reader\\Xml\\Style\\StyleBase' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Xml/Style/StyleBase.php', + 'PhpOffice\\PhpSpreadsheet\\ReferenceHelper' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/ReferenceHelper.php', + 'PhpOffice\\PhpSpreadsheet\\RichText\\ITextElement' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/RichText/ITextElement.php', + 'PhpOffice\\PhpSpreadsheet\\RichText\\RichText' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/RichText/RichText.php', + 'PhpOffice\\PhpSpreadsheet\\RichText\\Run' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/RichText/Run.php', + 'PhpOffice\\PhpSpreadsheet\\RichText\\TextElement' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/RichText/TextElement.php', + 'PhpOffice\\PhpSpreadsheet\\Settings' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Settings.php', + 'PhpOffice\\PhpSpreadsheet\\Shared\\CodePage' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Shared/CodePage.php', + 'PhpOffice\\PhpSpreadsheet\\Shared\\Date' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Shared/Date.php', + 'PhpOffice\\PhpSpreadsheet\\Shared\\Drawing' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Shared/Drawing.php', + 'PhpOffice\\PhpSpreadsheet\\Shared\\Escher' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Shared/Escher.php', + 'PhpOffice\\PhpSpreadsheet\\Shared\\Escher\\DgContainer' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Shared/Escher/DgContainer.php', + 'PhpOffice\\PhpSpreadsheet\\Shared\\Escher\\DgContainer\\SpgrContainer' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Shared/Escher/DgContainer/SpgrContainer.php', + 'PhpOffice\\PhpSpreadsheet\\Shared\\Escher\\DgContainer\\SpgrContainer\\SpContainer' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Shared/Escher/DgContainer/SpgrContainer/SpContainer.php', + 'PhpOffice\\PhpSpreadsheet\\Shared\\Escher\\DggContainer' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Shared/Escher/DggContainer.php', + 'PhpOffice\\PhpSpreadsheet\\Shared\\Escher\\DggContainer\\BstoreContainer' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Shared/Escher/DggContainer/BstoreContainer.php', + 'PhpOffice\\PhpSpreadsheet\\Shared\\Escher\\DggContainer\\BstoreContainer\\BSE' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Shared/Escher/DggContainer/BstoreContainer/BSE.php', + 'PhpOffice\\PhpSpreadsheet\\Shared\\Escher\\DggContainer\\BstoreContainer\\BSE\\Blip' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Shared/Escher/DggContainer/BstoreContainer/BSE/Blip.php', + 'PhpOffice\\PhpSpreadsheet\\Shared\\File' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Shared/File.php', + 'PhpOffice\\PhpSpreadsheet\\Shared\\Font' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Shared/Font.php', + 'PhpOffice\\PhpSpreadsheet\\Shared\\IntOrFloat' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Shared/IntOrFloat.php', + 'PhpOffice\\PhpSpreadsheet\\Shared\\OLE' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Shared/OLE.php', + 'PhpOffice\\PhpSpreadsheet\\Shared\\OLERead' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Shared/OLERead.php', + 'PhpOffice\\PhpSpreadsheet\\Shared\\OLE\\ChainedBlockStream' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Shared/OLE/ChainedBlockStream.php', + 'PhpOffice\\PhpSpreadsheet\\Shared\\OLE\\PPS' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Shared/OLE/PPS.php', + 'PhpOffice\\PhpSpreadsheet\\Shared\\OLE\\PPS\\File' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Shared/OLE/PPS/File.php', + 'PhpOffice\\PhpSpreadsheet\\Shared\\OLE\\PPS\\Root' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Shared/OLE/PPS/Root.php', + 'PhpOffice\\PhpSpreadsheet\\Shared\\PasswordHasher' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Shared/PasswordHasher.php', + 'PhpOffice\\PhpSpreadsheet\\Shared\\StringHelper' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Shared/StringHelper.php', + 'PhpOffice\\PhpSpreadsheet\\Shared\\TimeZone' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Shared/TimeZone.php', + 'PhpOffice\\PhpSpreadsheet\\Shared\\Trend\\BestFit' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Shared/Trend/BestFit.php', + 'PhpOffice\\PhpSpreadsheet\\Shared\\Trend\\ExponentialBestFit' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Shared/Trend/ExponentialBestFit.php', + 'PhpOffice\\PhpSpreadsheet\\Shared\\Trend\\LinearBestFit' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Shared/Trend/LinearBestFit.php', + 'PhpOffice\\PhpSpreadsheet\\Shared\\Trend\\LogarithmicBestFit' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Shared/Trend/LogarithmicBestFit.php', + 'PhpOffice\\PhpSpreadsheet\\Shared\\Trend\\PolynomialBestFit' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Shared/Trend/PolynomialBestFit.php', + 'PhpOffice\\PhpSpreadsheet\\Shared\\Trend\\PowerBestFit' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Shared/Trend/PowerBestFit.php', + 'PhpOffice\\PhpSpreadsheet\\Shared\\Trend\\Trend' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Shared/Trend/Trend.php', + 'PhpOffice\\PhpSpreadsheet\\Shared\\XMLWriter' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Shared/XMLWriter.php', + 'PhpOffice\\PhpSpreadsheet\\Shared\\Xls' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Shared/Xls.php', + 'PhpOffice\\PhpSpreadsheet\\Shared\\Xlsx\\AgileEncryption' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Shared/Xlsx/AgileEncryption.php', + 'PhpOffice\\PhpSpreadsheet\\Spreadsheet' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Spreadsheet.php', + 'PhpOffice\\PhpSpreadsheet\\Style\\Alignment' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Style/Alignment.php', + 'PhpOffice\\PhpSpreadsheet\\Style\\Border' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Style/Border.php', + 'PhpOffice\\PhpSpreadsheet\\Style\\Borders' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Style/Borders.php', + 'PhpOffice\\PhpSpreadsheet\\Style\\Color' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Style/Color.php', + 'PhpOffice\\PhpSpreadsheet\\Style\\Conditional' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Style/Conditional.php', + 'PhpOffice\\PhpSpreadsheet\\Style\\ConditionalFormatting\\CellMatcher' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Style/ConditionalFormatting/CellMatcher.php', + 'PhpOffice\\PhpSpreadsheet\\Style\\ConditionalFormatting\\CellStyleAssessor' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Style/ConditionalFormatting/CellStyleAssessor.php', + 'PhpOffice\\PhpSpreadsheet\\Style\\ConditionalFormatting\\ConditionalColorScale' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Style/ConditionalFormatting/ConditionalColorScale.php', + 'PhpOffice\\PhpSpreadsheet\\Style\\ConditionalFormatting\\ConditionalDataBar' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Style/ConditionalFormatting/ConditionalDataBar.php', + 'PhpOffice\\PhpSpreadsheet\\Style\\ConditionalFormatting\\ConditionalDataBarExtension' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Style/ConditionalFormatting/ConditionalDataBarExtension.php', + 'PhpOffice\\PhpSpreadsheet\\Style\\ConditionalFormatting\\ConditionalFormatValueObject' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Style/ConditionalFormatting/ConditionalFormatValueObject.php', + 'PhpOffice\\PhpSpreadsheet\\Style\\ConditionalFormatting\\ConditionalFormattingRuleExtension' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Style/ConditionalFormatting/ConditionalFormattingRuleExtension.php', + 'PhpOffice\\PhpSpreadsheet\\Style\\ConditionalFormatting\\ConditionalIconSet' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Style/ConditionalFormatting/ConditionalIconSet.php', + 'PhpOffice\\PhpSpreadsheet\\Style\\ConditionalFormatting\\IconSetValues' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Style/ConditionalFormatting/IconSetValues.php', + 'PhpOffice\\PhpSpreadsheet\\Style\\ConditionalFormatting\\MergedCellStyle' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Style/ConditionalFormatting/MergedCellStyle.php', + 'PhpOffice\\PhpSpreadsheet\\Style\\ConditionalFormatting\\StyleMerger' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Style/ConditionalFormatting/StyleMerger.php', + 'PhpOffice\\PhpSpreadsheet\\Style\\ConditionalFormatting\\Wizard' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Style/ConditionalFormatting/Wizard.php', + 'PhpOffice\\PhpSpreadsheet\\Style\\ConditionalFormatting\\Wizard\\Blanks' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Style/ConditionalFormatting/Wizard/Blanks.php', + 'PhpOffice\\PhpSpreadsheet\\Style\\ConditionalFormatting\\Wizard\\CellValue' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Style/ConditionalFormatting/Wizard/CellValue.php', + 'PhpOffice\\PhpSpreadsheet\\Style\\ConditionalFormatting\\Wizard\\DateValue' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Style/ConditionalFormatting/Wizard/DateValue.php', + 'PhpOffice\\PhpSpreadsheet\\Style\\ConditionalFormatting\\Wizard\\Duplicates' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Style/ConditionalFormatting/Wizard/Duplicates.php', + 'PhpOffice\\PhpSpreadsheet\\Style\\ConditionalFormatting\\Wizard\\Errors' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Style/ConditionalFormatting/Wizard/Errors.php', + 'PhpOffice\\PhpSpreadsheet\\Style\\ConditionalFormatting\\Wizard\\Expression' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Style/ConditionalFormatting/Wizard/Expression.php', + 'PhpOffice\\PhpSpreadsheet\\Style\\ConditionalFormatting\\Wizard\\TextValue' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Style/ConditionalFormatting/Wizard/TextValue.php', + 'PhpOffice\\PhpSpreadsheet\\Style\\ConditionalFormatting\\Wizard\\WizardAbstract' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Style/ConditionalFormatting/Wizard/WizardAbstract.php', + 'PhpOffice\\PhpSpreadsheet\\Style\\ConditionalFormatting\\Wizard\\WizardInterface' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Style/ConditionalFormatting/Wizard/WizardInterface.php', + 'PhpOffice\\PhpSpreadsheet\\Style\\Fill' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Style/Fill.php', + 'PhpOffice\\PhpSpreadsheet\\Style\\Font' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Style/Font.php', + 'PhpOffice\\PhpSpreadsheet\\Style\\NumberFormat' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Style/NumberFormat.php', + 'PhpOffice\\PhpSpreadsheet\\Style\\NumberFormat\\BaseFormatter' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Style/NumberFormat/BaseFormatter.php', + 'PhpOffice\\PhpSpreadsheet\\Style\\NumberFormat\\DateFormatter' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Style/NumberFormat/DateFormatter.php', + 'PhpOffice\\PhpSpreadsheet\\Style\\NumberFormat\\Formatter' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Style/NumberFormat/Formatter.php', + 'PhpOffice\\PhpSpreadsheet\\Style\\NumberFormat\\FractionFormatter' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Style/NumberFormat/FractionFormatter.php', + 'PhpOffice\\PhpSpreadsheet\\Style\\NumberFormat\\NumberFormatter' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Style/NumberFormat/NumberFormatter.php', + 'PhpOffice\\PhpSpreadsheet\\Style\\NumberFormat\\PercentageFormatter' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Style/NumberFormat/PercentageFormatter.php', + 'PhpOffice\\PhpSpreadsheet\\Style\\NumberFormat\\Wizard\\Accounting' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Style/NumberFormat/Wizard/Accounting.php', + 'PhpOffice\\PhpSpreadsheet\\Style\\NumberFormat\\Wizard\\Currency' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Style/NumberFormat/Wizard/Currency.php', + 'PhpOffice\\PhpSpreadsheet\\Style\\NumberFormat\\Wizard\\CurrencyBase' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Style/NumberFormat/Wizard/CurrencyBase.php', + 'PhpOffice\\PhpSpreadsheet\\Style\\NumberFormat\\Wizard\\CurrencyNegative' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Style/NumberFormat/Wizard/CurrencyNegative.php', + 'PhpOffice\\PhpSpreadsheet\\Style\\NumberFormat\\Wizard\\Date' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Style/NumberFormat/Wizard/Date.php', + 'PhpOffice\\PhpSpreadsheet\\Style\\NumberFormat\\Wizard\\DateTime' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Style/NumberFormat/Wizard/DateTime.php', + 'PhpOffice\\PhpSpreadsheet\\Style\\NumberFormat\\Wizard\\DateTimeWizard' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Style/NumberFormat/Wizard/DateTimeWizard.php', + 'PhpOffice\\PhpSpreadsheet\\Style\\NumberFormat\\Wizard\\Duration' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Style/NumberFormat/Wizard/Duration.php', + 'PhpOffice\\PhpSpreadsheet\\Style\\NumberFormat\\Wizard\\Locale' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Style/NumberFormat/Wizard/Locale.php', + 'PhpOffice\\PhpSpreadsheet\\Style\\NumberFormat\\Wizard\\Number' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Style/NumberFormat/Wizard/Number.php', + 'PhpOffice\\PhpSpreadsheet\\Style\\NumberFormat\\Wizard\\NumberBase' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Style/NumberFormat/Wizard/NumberBase.php', + 'PhpOffice\\PhpSpreadsheet\\Style\\NumberFormat\\Wizard\\Percentage' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Style/NumberFormat/Wizard/Percentage.php', + 'PhpOffice\\PhpSpreadsheet\\Style\\NumberFormat\\Wizard\\Scientific' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Style/NumberFormat/Wizard/Scientific.php', + 'PhpOffice\\PhpSpreadsheet\\Style\\NumberFormat\\Wizard\\Time' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Style/NumberFormat/Wizard/Time.php', + 'PhpOffice\\PhpSpreadsheet\\Style\\NumberFormat\\Wizard\\Wizard' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Style/NumberFormat/Wizard/Wizard.php', + 'PhpOffice\\PhpSpreadsheet\\Style\\Protection' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Style/Protection.php', + 'PhpOffice\\PhpSpreadsheet\\Style\\RgbTint' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Style/RgbTint.php', + 'PhpOffice\\PhpSpreadsheet\\Style\\Style' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Style/Style.php', + 'PhpOffice\\PhpSpreadsheet\\Style\\Supervisor' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Style/Supervisor.php', + 'PhpOffice\\PhpSpreadsheet\\Theme' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Theme.php', + 'PhpOffice\\PhpSpreadsheet\\Worksheet\\AutoFilter' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Worksheet/AutoFilter.php', + 'PhpOffice\\PhpSpreadsheet\\Worksheet\\AutoFilter\\Column' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Worksheet/AutoFilter/Column.php', + 'PhpOffice\\PhpSpreadsheet\\Worksheet\\AutoFilter\\Column\\Rule' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Worksheet/AutoFilter/Column/Rule.php', + 'PhpOffice\\PhpSpreadsheet\\Worksheet\\AutoFit' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Worksheet/AutoFit.php', + 'PhpOffice\\PhpSpreadsheet\\Worksheet\\BaseDrawing' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Worksheet/BaseDrawing.php', + 'PhpOffice\\PhpSpreadsheet\\Worksheet\\CellIterator' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Worksheet/CellIterator.php', + 'PhpOffice\\PhpSpreadsheet\\Worksheet\\Column' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Worksheet/Column.php', + 'PhpOffice\\PhpSpreadsheet\\Worksheet\\ColumnCellIterator' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Worksheet/ColumnCellIterator.php', + 'PhpOffice\\PhpSpreadsheet\\Worksheet\\ColumnDimension' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Worksheet/ColumnDimension.php', + 'PhpOffice\\PhpSpreadsheet\\Worksheet\\ColumnIterator' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Worksheet/ColumnIterator.php', + 'PhpOffice\\PhpSpreadsheet\\Worksheet\\Dimension' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Worksheet/Dimension.php', + 'PhpOffice\\PhpSpreadsheet\\Worksheet\\Drawing' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Worksheet/Drawing.php', + 'PhpOffice\\PhpSpreadsheet\\Worksheet\\Drawing\\Shadow' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Worksheet/Drawing/Shadow.php', + 'PhpOffice\\PhpSpreadsheet\\Worksheet\\HeaderFooter' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Worksheet/HeaderFooter.php', + 'PhpOffice\\PhpSpreadsheet\\Worksheet\\HeaderFooterDrawing' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Worksheet/HeaderFooterDrawing.php', + 'PhpOffice\\PhpSpreadsheet\\Worksheet\\Iterator' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Worksheet/Iterator.php', + 'PhpOffice\\PhpSpreadsheet\\Worksheet\\MemoryDrawing' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Worksheet/MemoryDrawing.php', + 'PhpOffice\\PhpSpreadsheet\\Worksheet\\PageBreak' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Worksheet/PageBreak.php', + 'PhpOffice\\PhpSpreadsheet\\Worksheet\\PageMargins' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Worksheet/PageMargins.php', + 'PhpOffice\\PhpSpreadsheet\\Worksheet\\PageSetup' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Worksheet/PageSetup.php', + 'PhpOffice\\PhpSpreadsheet\\Worksheet\\Pane' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Worksheet/Pane.php', + 'PhpOffice\\PhpSpreadsheet\\Worksheet\\PivotTable\\PivotCacheDefinition' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Worksheet/PivotTable/PivotCacheDefinition.php', + 'PhpOffice\\PhpSpreadsheet\\Worksheet\\PivotTable\\PivotField' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Worksheet/PivotTable/PivotField.php', + 'PhpOffice\\PhpSpreadsheet\\Worksheet\\PivotTable\\PivotFieldGroup' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Worksheet/PivotTable/PivotFieldGroup.php', + 'PhpOffice\\PhpSpreadsheet\\Worksheet\\PivotTable\\PivotTable' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Worksheet/PivotTable/PivotTable.php', + 'PhpOffice\\PhpSpreadsheet\\Worksheet\\PivotTable\\PivotTableBuilder' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Worksheet/PivotTable/PivotTableBuilder.php', + 'PhpOffice\\PhpSpreadsheet\\Worksheet\\ProtectedRange' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Worksheet/ProtectedRange.php', + 'PhpOffice\\PhpSpreadsheet\\Worksheet\\Protection' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Worksheet/Protection.php', + 'PhpOffice\\PhpSpreadsheet\\Worksheet\\Row' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Worksheet/Row.php', + 'PhpOffice\\PhpSpreadsheet\\Worksheet\\RowCellIterator' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Worksheet/RowCellIterator.php', + 'PhpOffice\\PhpSpreadsheet\\Worksheet\\RowDimension' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Worksheet/RowDimension.php', + 'PhpOffice\\PhpSpreadsheet\\Worksheet\\RowIterator' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Worksheet/RowIterator.php', + 'PhpOffice\\PhpSpreadsheet\\Worksheet\\SheetView' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Worksheet/SheetView.php', + 'PhpOffice\\PhpSpreadsheet\\Worksheet\\Sparkline\\Sparkline' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Worksheet/Sparkline/Sparkline.php', + 'PhpOffice\\PhpSpreadsheet\\Worksheet\\Sparkline\\SparklineGroup' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Worksheet/Sparkline/SparklineGroup.php', + 'PhpOffice\\PhpSpreadsheet\\Worksheet\\Sparkline\\SparklineType' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Worksheet/Sparkline/SparklineType.php', + 'PhpOffice\\PhpSpreadsheet\\Worksheet\\Table' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Worksheet/Table.php', + 'PhpOffice\\PhpSpreadsheet\\Worksheet\\Table\\Column' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Worksheet/Table/Column.php', + 'PhpOffice\\PhpSpreadsheet\\Worksheet\\Table\\TableDxfsStyle' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Worksheet/Table/TableDxfsStyle.php', + 'PhpOffice\\PhpSpreadsheet\\Worksheet\\Table\\TableStyle' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Worksheet/Table/TableStyle.php', + 'PhpOffice\\PhpSpreadsheet\\Worksheet\\Validations' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Worksheet/Validations.php', + 'PhpOffice\\PhpSpreadsheet\\Worksheet\\Worksheet' => $vendorDir . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Worksheet/Worksheet.php', + 'Psr\\SimpleCache\\CacheException' => $vendorDir . '/psr/simple-cache/src/CacheException.php', + 'Psr\\SimpleCache\\CacheInterface' => $vendorDir . '/psr/simple-cache/src/CacheInterface.php', + 'Psr\\SimpleCache\\InvalidArgumentException' => $vendorDir . '/psr/simple-cache/src/InvalidArgumentException.php', + 'ZipStream\\CentralDirectoryFileHeader' => $vendorDir . '/maennchen/zipstream-php/src/CentralDirectoryFileHeader.php', + 'ZipStream\\CompressionMethod' => $vendorDir . '/maennchen/zipstream-php/src/CompressionMethod.php', + 'ZipStream\\DataDescriptor' => $vendorDir . '/maennchen/zipstream-php/src/DataDescriptor.php', + 'ZipStream\\EndOfCentralDirectory' => $vendorDir . '/maennchen/zipstream-php/src/EndOfCentralDirectory.php', + 'ZipStream\\Exception' => $vendorDir . '/maennchen/zipstream-php/src/Exception.php', + 'ZipStream\\Exception\\DosTimeOverflowException' => $vendorDir . '/maennchen/zipstream-php/src/Exception/DosTimeOverflowException.php', + 'ZipStream\\Exception\\FileNotFoundException' => $vendorDir . '/maennchen/zipstream-php/src/Exception/FileNotFoundException.php', + 'ZipStream\\Exception\\FileNotReadableException' => $vendorDir . '/maennchen/zipstream-php/src/Exception/FileNotReadableException.php', + 'ZipStream\\Exception\\FileSizeIncorrectException' => $vendorDir . '/maennchen/zipstream-php/src/Exception/FileSizeIncorrectException.php', + 'ZipStream\\Exception\\OverflowException' => $vendorDir . '/maennchen/zipstream-php/src/Exception/OverflowException.php', + 'ZipStream\\Exception\\ResourceActionException' => $vendorDir . '/maennchen/zipstream-php/src/Exception/ResourceActionException.php', + 'ZipStream\\Exception\\SimulationFileUnknownException' => $vendorDir . '/maennchen/zipstream-php/src/Exception/SimulationFileUnknownException.php', + 'ZipStream\\Exception\\StreamNotReadableException' => $vendorDir . '/maennchen/zipstream-php/src/Exception/StreamNotReadableException.php', + 'ZipStream\\Exception\\StreamNotSeekableException' => $vendorDir . '/maennchen/zipstream-php/src/Exception/StreamNotSeekableException.php', + 'ZipStream\\File' => $vendorDir . '/maennchen/zipstream-php/src/File.php', + 'ZipStream\\GeneralPurposeBitFlag' => $vendorDir . '/maennchen/zipstream-php/src/GeneralPurposeBitFlag.php', + 'ZipStream\\LocalFileHeader' => $vendorDir . '/maennchen/zipstream-php/src/LocalFileHeader.php', + 'ZipStream\\OperationMode' => $vendorDir . '/maennchen/zipstream-php/src/OperationMode.php', + 'ZipStream\\PackField' => $vendorDir . '/maennchen/zipstream-php/src/PackField.php', + 'ZipStream\\Time' => $vendorDir . '/maennchen/zipstream-php/src/Time.php', + 'ZipStream\\Version' => $vendorDir . '/maennchen/zipstream-php/src/Version.php', + 'ZipStream\\Zip64\\DataDescriptor' => $vendorDir . '/maennchen/zipstream-php/src/Zip64/DataDescriptor.php', + 'ZipStream\\Zip64\\EndOfCentralDirectory' => $vendorDir . '/maennchen/zipstream-php/src/Zip64/EndOfCentralDirectory.php', + 'ZipStream\\Zip64\\EndOfCentralDirectoryLocator' => $vendorDir . '/maennchen/zipstream-php/src/Zip64/EndOfCentralDirectoryLocator.php', + 'ZipStream\\Zip64\\ExtendedInformationExtraField' => $vendorDir . '/maennchen/zipstream-php/src/Zip64/ExtendedInformationExtraField.php', + 'ZipStream\\ZipStream' => $vendorDir . '/maennchen/zipstream-php/src/ZipStream.php', + 'ZipStream\\Zs\\ExtendedInformationExtraField' => $vendorDir . '/maennchen/zipstream-php/src/Zs/ExtendedInformationExtraField.php', ); diff --git a/vendor/composer/autoload_real.php b/vendor/composer/autoload_real.php index ebb7889b..4ce4e713 100644 --- a/vendor/composer/autoload_real.php +++ b/vendor/composer/autoload_real.php @@ -2,7 +2,7 @@ // autoload_real.php @generated by Composer -class ComposerAutoloaderInit524e760e56b0620cb9bc3d8d9ad8543d +class ComposerAutoloaderInitbae58d66b0357c26ca5c29c77e2a2a8a { private static $loader; @@ -24,12 +24,12 @@ public static function getLoader() require __DIR__ . '/platform_check.php'; - spl_autoload_register(array('ComposerAutoloaderInit524e760e56b0620cb9bc3d8d9ad8543d', 'loadClassLoader'), true, true); + spl_autoload_register(array('ComposerAutoloaderInitbae58d66b0357c26ca5c29c77e2a2a8a', 'loadClassLoader'), true, true); self::$loader = $loader = new \Composer\Autoload\ClassLoader(\dirname(__DIR__)); - spl_autoload_unregister(array('ComposerAutoloaderInit524e760e56b0620cb9bc3d8d9ad8543d', 'loadClassLoader')); + spl_autoload_unregister(array('ComposerAutoloaderInitbae58d66b0357c26ca5c29c77e2a2a8a', 'loadClassLoader')); require __DIR__ . '/autoload_static.php'; - call_user_func(\Composer\Autoload\ComposerStaticInit524e760e56b0620cb9bc3d8d9ad8543d::getInitializer($loader)); + call_user_func(\Composer\Autoload\ComposerStaticInitbae58d66b0357c26ca5c29c77e2a2a8a::getInitializer($loader)); $loader->register(true); diff --git a/vendor/composer/autoload_static.php b/vendor/composer/autoload_static.php index 0fc025eb..321274d1 100644 --- a/vendor/composer/autoload_static.php +++ b/vendor/composer/autoload_static.php @@ -4,7 +4,7 @@ namespace Composer\Autoload; -class ComposerStaticInit524e760e56b0620cb9bc3d8d9ad8543d +class ComposerStaticInitbae58d66b0357c26ca5c29c77e2a2a8a { public static $prefixLengthsPsr4 = array ( 'Z' => @@ -55,15 +55,560 @@ class ComposerStaticInit524e760e56b0620cb9bc3d8d9ad8543d ); public static $classMap = array ( + 'Complex\\Complex' => __DIR__ . '/..' . '/markbaker/complex/classes/src/Complex.php', + 'Complex\\Exception' => __DIR__ . '/..' . '/markbaker/complex/classes/src/Exception.php', + 'Complex\\Functions' => __DIR__ . '/..' . '/markbaker/complex/classes/src/Functions.php', + 'Complex\\Operations' => __DIR__ . '/..' . '/markbaker/complex/classes/src/Operations.php', 'Composer\\InstalledVersions' => __DIR__ . '/..' . '/composer/InstalledVersions.php', + 'Composer\\Pcre\\MatchAllResult' => __DIR__ . '/..' . '/composer/pcre/src/MatchAllResult.php', + 'Composer\\Pcre\\MatchAllStrictGroupsResult' => __DIR__ . '/..' . '/composer/pcre/src/MatchAllStrictGroupsResult.php', + 'Composer\\Pcre\\MatchAllWithOffsetsResult' => __DIR__ . '/..' . '/composer/pcre/src/MatchAllWithOffsetsResult.php', + 'Composer\\Pcre\\MatchResult' => __DIR__ . '/..' . '/composer/pcre/src/MatchResult.php', + 'Composer\\Pcre\\MatchStrictGroupsResult' => __DIR__ . '/..' . '/composer/pcre/src/MatchStrictGroupsResult.php', + 'Composer\\Pcre\\MatchWithOffsetsResult' => __DIR__ . '/..' . '/composer/pcre/src/MatchWithOffsetsResult.php', + 'Composer\\Pcre\\PHPStan\\InvalidRegexPatternRule' => __DIR__ . '/..' . '/composer/pcre/src/PHPStan/InvalidRegexPatternRule.php', + 'Composer\\Pcre\\PHPStan\\PregMatchFlags' => __DIR__ . '/..' . '/composer/pcre/src/PHPStan/PregMatchFlags.php', + 'Composer\\Pcre\\PHPStan\\PregMatchParameterOutTypeExtension' => __DIR__ . '/..' . '/composer/pcre/src/PHPStan/PregMatchParameterOutTypeExtension.php', + 'Composer\\Pcre\\PHPStan\\PregMatchTypeSpecifyingExtension' => __DIR__ . '/..' . '/composer/pcre/src/PHPStan/PregMatchTypeSpecifyingExtension.php', + 'Composer\\Pcre\\PHPStan\\PregReplaceCallbackClosureTypeExtension' => __DIR__ . '/..' . '/composer/pcre/src/PHPStan/PregReplaceCallbackClosureTypeExtension.php', + 'Composer\\Pcre\\PHPStan\\UnsafeStrictGroupsCallRule' => __DIR__ . '/..' . '/composer/pcre/src/PHPStan/UnsafeStrictGroupsCallRule.php', + 'Composer\\Pcre\\PcreException' => __DIR__ . '/..' . '/composer/pcre/src/PcreException.php', + 'Composer\\Pcre\\Preg' => __DIR__ . '/..' . '/composer/pcre/src/Preg.php', + 'Composer\\Pcre\\Regex' => __DIR__ . '/..' . '/composer/pcre/src/Regex.php', + 'Composer\\Pcre\\ReplaceResult' => __DIR__ . '/..' . '/composer/pcre/src/ReplaceResult.php', + 'Composer\\Pcre\\UnexpectedNullMatchException' => __DIR__ . '/..' . '/composer/pcre/src/UnexpectedNullMatchException.php', + 'Matrix\\Builder' => __DIR__ . '/..' . '/markbaker/matrix/classes/src/Builder.php', + 'Matrix\\Decomposition\\Decomposition' => __DIR__ . '/..' . '/markbaker/matrix/classes/src/Decomposition/Decomposition.php', + 'Matrix\\Decomposition\\LU' => __DIR__ . '/..' . '/markbaker/matrix/classes/src/Decomposition/LU.php', + 'Matrix\\Decomposition\\QR' => __DIR__ . '/..' . '/markbaker/matrix/classes/src/Decomposition/QR.php', + 'Matrix\\Div0Exception' => __DIR__ . '/..' . '/markbaker/matrix/classes/src/Div0Exception.php', + 'Matrix\\Exception' => __DIR__ . '/..' . '/markbaker/matrix/classes/src/Exception.php', + 'Matrix\\Functions' => __DIR__ . '/..' . '/markbaker/matrix/classes/src/Functions.php', + 'Matrix\\Matrix' => __DIR__ . '/..' . '/markbaker/matrix/classes/src/Matrix.php', + 'Matrix\\Operations' => __DIR__ . '/..' . '/markbaker/matrix/classes/src/Operations.php', + 'Matrix\\Operators\\Addition' => __DIR__ . '/..' . '/markbaker/matrix/classes/src/Operators/Addition.php', + 'Matrix\\Operators\\DirectSum' => __DIR__ . '/..' . '/markbaker/matrix/classes/src/Operators/DirectSum.php', + 'Matrix\\Operators\\Division' => __DIR__ . '/..' . '/markbaker/matrix/classes/src/Operators/Division.php', + 'Matrix\\Operators\\Multiplication' => __DIR__ . '/..' . '/markbaker/matrix/classes/src/Operators/Multiplication.php', + 'Matrix\\Operators\\Operator' => __DIR__ . '/..' . '/markbaker/matrix/classes/src/Operators/Operator.php', + 'Matrix\\Operators\\Subtraction' => __DIR__ . '/..' . '/markbaker/matrix/classes/src/Operators/Subtraction.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\ArrayEnabled' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/ArrayEnabled.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\BinaryComparison' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/BinaryComparison.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Calculation' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Calculation.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\CalculationBase' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/CalculationBase.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\CalculationLocale' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/CalculationLocale.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\CalculationParserOnly' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/CalculationParserOnly.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Category' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Category.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Database\\DAverage' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Database/DAverage.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Database\\DCount' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Database/DCount.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Database\\DCountA' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Database/DCountA.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Database\\DGet' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Database/DGet.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Database\\DMax' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Database/DMax.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Database\\DMin' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Database/DMin.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Database\\DProduct' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Database/DProduct.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Database\\DStDev' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Database/DStDev.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Database\\DStDevP' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Database/DStDevP.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Database\\DSum' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Database/DSum.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Database\\DVar' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Database/DVar.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Database\\DVarP' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Database/DVarP.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Database\\DatabaseAbstract' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Database/DatabaseAbstract.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\DateTimeExcel\\Constants' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/DateTimeExcel/Constants.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\DateTimeExcel\\Current' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/DateTimeExcel/Current.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\DateTimeExcel\\Date' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/DateTimeExcel/Date.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\DateTimeExcel\\DateParts' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/DateTimeExcel/DateParts.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\DateTimeExcel\\DateValue' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/DateTimeExcel/DateValue.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\DateTimeExcel\\Days' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/DateTimeExcel/Days.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\DateTimeExcel\\Days360' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/DateTimeExcel/Days360.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\DateTimeExcel\\Difference' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/DateTimeExcel/Difference.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\DateTimeExcel\\Helpers' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/DateTimeExcel/Helpers.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\DateTimeExcel\\Month' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/DateTimeExcel/Month.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\DateTimeExcel\\NetworkDays' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/DateTimeExcel/NetworkDays.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\DateTimeExcel\\Time' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/DateTimeExcel/Time.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\DateTimeExcel\\TimeParts' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/DateTimeExcel/TimeParts.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\DateTimeExcel\\TimeValue' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/DateTimeExcel/TimeValue.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\DateTimeExcel\\Week' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/DateTimeExcel/Week.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\DateTimeExcel\\WorkDay' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/DateTimeExcel/WorkDay.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\DateTimeExcel\\YearFrac' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/DateTimeExcel/YearFrac.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Engine\\ArrayArgumentHelper' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Engine/ArrayArgumentHelper.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Engine\\ArrayArgumentProcessor' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Engine/ArrayArgumentProcessor.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Engine\\BranchPruner' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Engine/BranchPruner.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Engine\\CyclicReferenceStack' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Engine/CyclicReferenceStack.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Engine\\FormattedNumber' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Engine/FormattedNumber.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Engine\\Logger' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Engine/Logger.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Engine\\Operands\\Operand' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Engine/Operands/Operand.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Engine\\Operands\\StructuredReference' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Engine/Operands/StructuredReference.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Engineering\\BesselI' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Engineering/BesselI.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Engineering\\BesselJ' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Engineering/BesselJ.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Engineering\\BesselK' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Engineering/BesselK.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Engineering\\BesselY' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Engineering/BesselY.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Engineering\\BitWise' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Engineering/BitWise.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Engineering\\Compare' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Engineering/Compare.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Engineering\\Complex' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Engineering/Complex.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Engineering\\ComplexFunctions' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Engineering/ComplexFunctions.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Engineering\\ComplexOperations' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Engineering/ComplexOperations.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Engineering\\Constants' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Engineering/Constants.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Engineering\\ConvertBase' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Engineering/ConvertBase.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Engineering\\ConvertBinary' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Engineering/ConvertBinary.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Engineering\\ConvertDecimal' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Engineering/ConvertDecimal.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Engineering\\ConvertHex' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Engineering/ConvertHex.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Engineering\\ConvertOctal' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Engineering/ConvertOctal.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Engineering\\ConvertUOM' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Engineering/ConvertUOM.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Engineering\\EngineeringValidations' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Engineering/EngineeringValidations.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Engineering\\Erf' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Engineering/Erf.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Engineering\\ErfC' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Engineering/ErfC.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Exception' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Exception.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\ExceptionHandler' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/ExceptionHandler.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Financial\\Amortization' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Financial/Amortization.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Financial\\CashFlow\\CashFlowValidations' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Financial/CashFlow/CashFlowValidations.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Financial\\CashFlow\\Constant\\Periodic' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Financial/CashFlow/Constant/Periodic.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Financial\\CashFlow\\Constant\\Periodic\\Cumulative' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Financial/CashFlow/Constant/Periodic/Cumulative.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Financial\\CashFlow\\Constant\\Periodic\\Interest' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Financial/CashFlow/Constant/Periodic/Interest.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Financial\\CashFlow\\Constant\\Periodic\\InterestAndPrincipal' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Financial/CashFlow/Constant/Periodic/InterestAndPrincipal.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Financial\\CashFlow\\Constant\\Periodic\\Payments' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Financial/CashFlow/Constant/Periodic/Payments.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Financial\\CashFlow\\Single' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Financial/CashFlow/Single.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Financial\\CashFlow\\Variable\\NonPeriodic' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Financial/CashFlow/Variable/NonPeriodic.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Financial\\CashFlow\\Variable\\Periodic' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Financial/CashFlow/Variable/Periodic.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Financial\\Constants' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Financial/Constants.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Financial\\Coupons' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Financial/Coupons.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Financial\\Depreciation' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Financial/Depreciation.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Financial\\Dollar' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Financial/Dollar.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Financial\\FinancialValidations' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Financial/FinancialValidations.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Financial\\Helpers' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Financial/Helpers.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Financial\\InterestRate' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Financial/InterestRate.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Financial\\Securities\\AccruedInterest' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Financial/Securities/AccruedInterest.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Financial\\Securities\\Price' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Financial/Securities/Price.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Financial\\Securities\\Rates' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Financial/Securities/Rates.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Financial\\Securities\\SecurityValidations' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Financial/Securities/SecurityValidations.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Financial\\Securities\\Yields' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Financial/Securities/Yields.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Financial\\TreasuryBill' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Financial/TreasuryBill.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\FormulaParser' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/FormulaParser.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\FormulaToken' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/FormulaToken.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\FunctionArray' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/FunctionArray.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Functions' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Functions.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Information\\ErrorValue' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Information/ErrorValue.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Information\\ExcelError' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Information/ExcelError.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Information\\Info' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Information/Info.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Information\\Value' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Information/Value.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Internal\\ExcelArrayPseudoFunctions' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Internal/ExcelArrayPseudoFunctions.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Internal\\MakeMatrix' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Internal/MakeMatrix.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Internal\\WildcardMatch' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Internal/WildcardMatch.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Logical\\Boolean' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Logical/Boolean.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Logical\\Conditional' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Logical/Conditional.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Logical\\Operations' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Logical/Operations.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\LookupRef\\Address' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/LookupRef/Address.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\LookupRef\\ChooseRowsEtc' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/LookupRef/ChooseRowsEtc.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\LookupRef\\ExcelMatch' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/LookupRef/ExcelMatch.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\LookupRef\\Filter' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/LookupRef/Filter.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\LookupRef\\Formula' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/LookupRef/Formula.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\LookupRef\\HLookup' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/LookupRef/HLookup.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\LookupRef\\Helpers' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/LookupRef/Helpers.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\LookupRef\\Hstack' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/LookupRef/Hstack.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\LookupRef\\Hyperlink' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/LookupRef/Hyperlink.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\LookupRef\\Indirect' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/LookupRef/Indirect.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\LookupRef\\Lookup' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/LookupRef/Lookup.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\LookupRef\\LookupBase' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/LookupRef/LookupBase.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\LookupRef\\LookupRefValidations' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/LookupRef/LookupRefValidations.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\LookupRef\\Matrix' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/LookupRef/Matrix.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\LookupRef\\Offset' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/LookupRef/Offset.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\LookupRef\\RowColumnInformation' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/LookupRef/RowColumnInformation.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\LookupRef\\Selection' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/LookupRef/Selection.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\LookupRef\\Sort' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/LookupRef/Sort.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\LookupRef\\TorowTocol' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/LookupRef/TorowTocol.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\LookupRef\\Unique' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/LookupRef/Unique.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\LookupRef\\VLookup' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/LookupRef/VLookup.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\LookupRef\\Vstack' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/LookupRef/Vstack.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\LookupRef\\XLookup' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/LookupRef/XLookup.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\MathTrig\\Absolute' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/MathTrig/Absolute.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\MathTrig\\Angle' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/MathTrig/Angle.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\MathTrig\\Arabic' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/MathTrig/Arabic.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\MathTrig\\Base' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/MathTrig/Base.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\MathTrig\\Ceiling' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/MathTrig/Ceiling.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\MathTrig\\Combinations' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/MathTrig/Combinations.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\MathTrig\\Exp' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/MathTrig/Exp.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\MathTrig\\Factorial' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/MathTrig/Factorial.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\MathTrig\\Floor' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/MathTrig/Floor.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\MathTrig\\Gcd' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/MathTrig/Gcd.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\MathTrig\\Helpers' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/MathTrig/Helpers.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\MathTrig\\IntClass' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/MathTrig/IntClass.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\MathTrig\\Lcm' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/MathTrig/Lcm.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\MathTrig\\Logarithms' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/MathTrig/Logarithms.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\MathTrig\\MatrixFunctions' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/MathTrig/MatrixFunctions.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\MathTrig\\Operations' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/MathTrig/Operations.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\MathTrig\\Random' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/MathTrig/Random.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\MathTrig\\Roman' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/MathTrig/Roman.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\MathTrig\\Round' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/MathTrig/Round.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\MathTrig\\SeriesSum' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/MathTrig/SeriesSum.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\MathTrig\\Sign' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/MathTrig/Sign.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\MathTrig\\Sqrt' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/MathTrig/Sqrt.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\MathTrig\\Subtotal' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/MathTrig/Subtotal.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\MathTrig\\Sum' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/MathTrig/Sum.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\MathTrig\\SumSquares' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/MathTrig/SumSquares.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\MathTrig\\Trig\\Cosecant' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/MathTrig/Trig/Cosecant.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\MathTrig\\Trig\\Cosine' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/MathTrig/Trig/Cosine.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\MathTrig\\Trig\\Cotangent' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/MathTrig/Trig/Cotangent.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\MathTrig\\Trig\\Secant' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/MathTrig/Trig/Secant.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\MathTrig\\Trig\\Sine' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/MathTrig/Trig/Sine.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\MathTrig\\Trig\\Tangent' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/MathTrig/Trig/Tangent.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\MathTrig\\Trunc' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/MathTrig/Trunc.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Statistical\\AggregateBase' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Statistical/AggregateBase.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Statistical\\Averages' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Statistical/Averages.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Statistical\\Averages\\Mean' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Statistical/Averages/Mean.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Statistical\\Conditional' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Statistical/Conditional.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Statistical\\Confidence' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Statistical/Confidence.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Statistical\\Counts' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Statistical/Counts.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Statistical\\Deviations' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Statistical/Deviations.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Statistical\\Distributions\\Beta' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Statistical/Distributions/Beta.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Statistical\\Distributions\\Binomial' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Statistical/Distributions/Binomial.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Statistical\\Distributions\\ChiSquared' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Statistical/Distributions/ChiSquared.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Statistical\\Distributions\\DistributionValidations' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Statistical/Distributions/DistributionValidations.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Statistical\\Distributions\\Exponential' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Statistical/Distributions/Exponential.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Statistical\\Distributions\\F' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Statistical/Distributions/F.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Statistical\\Distributions\\Fisher' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Statistical/Distributions/Fisher.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Statistical\\Distributions\\Gamma' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Statistical/Distributions/Gamma.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Statistical\\Distributions\\GammaBase' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Statistical/Distributions/GammaBase.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Statistical\\Distributions\\HyperGeometric' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Statistical/Distributions/HyperGeometric.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Statistical\\Distributions\\LogNormal' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Statistical/Distributions/LogNormal.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Statistical\\Distributions\\NewtonRaphson' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Statistical/Distributions/NewtonRaphson.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Statistical\\Distributions\\Normal' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Statistical/Distributions/Normal.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Statistical\\Distributions\\Poisson' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Statistical/Distributions/Poisson.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Statistical\\Distributions\\StandardNormal' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Statistical/Distributions/StandardNormal.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Statistical\\Distributions\\StudentT' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Statistical/Distributions/StudentT.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Statistical\\Distributions\\Weibull' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Statistical/Distributions/Weibull.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Statistical\\MaxMinBase' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Statistical/MaxMinBase.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Statistical\\Maximum' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Statistical/Maximum.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Statistical\\Minimum' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Statistical/Minimum.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Statistical\\Percentiles' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Statistical/Percentiles.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Statistical\\Permutations' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Statistical/Permutations.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Statistical\\Size' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Statistical/Size.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Statistical\\StandardDeviations' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Statistical/StandardDeviations.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Statistical\\Standardize' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Statistical/Standardize.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Statistical\\StatisticalValidations' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Statistical/StatisticalValidations.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Statistical\\Trends' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Statistical/Trends.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Statistical\\VarianceBase' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Statistical/VarianceBase.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Statistical\\Variances' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Statistical/Variances.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\TextData\\CaseConvert' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/TextData/CaseConvert.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\TextData\\CharacterConvert' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/TextData/CharacterConvert.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\TextData\\Concatenate' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/TextData/Concatenate.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\TextData\\Extract' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/TextData/Extract.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\TextData\\Format' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/TextData/Format.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\TextData\\Helpers' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/TextData/Helpers.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\TextData\\Replace' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/TextData/Replace.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\TextData\\Search' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/TextData/Search.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\TextData\\Text' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/TextData/Text.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\TextData\\Thai' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/TextData/Thai.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\TextData\\Trim' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/TextData/Trim.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Token\\Stack' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Token/Stack.php', + 'PhpOffice\\PhpSpreadsheet\\Calculation\\Web\\Service' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Web/Service.php', + 'PhpOffice\\PhpSpreadsheet\\CellReferenceHelper' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/CellReferenceHelper.php', + 'PhpOffice\\PhpSpreadsheet\\Cell\\AddressHelper' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Cell/AddressHelper.php', + 'PhpOffice\\PhpSpreadsheet\\Cell\\AddressRange' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Cell/AddressRange.php', + 'PhpOffice\\PhpSpreadsheet\\Cell\\AdvancedValueBinder' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Cell/AdvancedValueBinder.php', + 'PhpOffice\\PhpSpreadsheet\\Cell\\Cell' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Cell/Cell.php', + 'PhpOffice\\PhpSpreadsheet\\Cell\\CellAddress' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Cell/CellAddress.php', + 'PhpOffice\\PhpSpreadsheet\\Cell\\CellRange' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Cell/CellRange.php', + 'PhpOffice\\PhpSpreadsheet\\Cell\\ColumnRange' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Cell/ColumnRange.php', + 'PhpOffice\\PhpSpreadsheet\\Cell\\Coordinate' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Cell/Coordinate.php', + 'PhpOffice\\PhpSpreadsheet\\Cell\\DataType' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Cell/DataType.php', + 'PhpOffice\\PhpSpreadsheet\\Cell\\DataValidation' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Cell/DataValidation.php', + 'PhpOffice\\PhpSpreadsheet\\Cell\\DataValidator' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Cell/DataValidator.php', + 'PhpOffice\\PhpSpreadsheet\\Cell\\DefaultValueBinder' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Cell/DefaultValueBinder.php', + 'PhpOffice\\PhpSpreadsheet\\Cell\\Hyperlink' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Cell/Hyperlink.php', + 'PhpOffice\\PhpSpreadsheet\\Cell\\IValueBinder' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Cell/IValueBinder.php', + 'PhpOffice\\PhpSpreadsheet\\Cell\\IgnoredErrors' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Cell/IgnoredErrors.php', + 'PhpOffice\\PhpSpreadsheet\\Cell\\RowRange' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Cell/RowRange.php', + 'PhpOffice\\PhpSpreadsheet\\Cell\\StringValueBinder' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Cell/StringValueBinder.php', + 'PhpOffice\\PhpSpreadsheet\\Chart\\Axis' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Chart/Axis.php', + 'PhpOffice\\PhpSpreadsheet\\Chart\\AxisText' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Chart/AxisText.php', + 'PhpOffice\\PhpSpreadsheet\\Chart\\Chart' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Chart/Chart.php', + 'PhpOffice\\PhpSpreadsheet\\Chart\\ChartColor' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Chart/ChartColor.php', + 'PhpOffice\\PhpSpreadsheet\\Chart\\DataSeries' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Chart/DataSeries.php', + 'PhpOffice\\PhpSpreadsheet\\Chart\\DataSeriesValues' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Chart/DataSeriesValues.php', + 'PhpOffice\\PhpSpreadsheet\\Chart\\DataTable' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Chart/DataTable.php', + 'PhpOffice\\PhpSpreadsheet\\Chart\\Exception' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Chart/Exception.php', + 'PhpOffice\\PhpSpreadsheet\\Chart\\GridLines' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Chart/GridLines.php', + 'PhpOffice\\PhpSpreadsheet\\Chart\\Layout' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Chart/Layout.php', + 'PhpOffice\\PhpSpreadsheet\\Chart\\Legend' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Chart/Legend.php', + 'PhpOffice\\PhpSpreadsheet\\Chart\\PlotArea' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Chart/PlotArea.php', + 'PhpOffice\\PhpSpreadsheet\\Chart\\Properties' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Chart/Properties.php', + 'PhpOffice\\PhpSpreadsheet\\Chart\\Renderer\\IRenderer' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Chart/Renderer/IRenderer.php', + 'PhpOffice\\PhpSpreadsheet\\Chart\\Renderer\\JpGraph' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Chart/Renderer/JpGraph.php', + 'PhpOffice\\PhpSpreadsheet\\Chart\\Renderer\\JpGraphRendererBase' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Chart/Renderer/JpGraphRendererBase.php', + 'PhpOffice\\PhpSpreadsheet\\Chart\\Renderer\\MtJpGraphRenderer' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Chart/Renderer/MtJpGraphRenderer.php', + 'PhpOffice\\PhpSpreadsheet\\Chart\\Title' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Chart/Title.php', + 'PhpOffice\\PhpSpreadsheet\\Chart\\TrendLine' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Chart/TrendLine.php', + 'PhpOffice\\PhpSpreadsheet\\Collection\\Cells' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Collection/Cells.php', + 'PhpOffice\\PhpSpreadsheet\\Collection\\CellsFactory' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Collection/CellsFactory.php', + 'PhpOffice\\PhpSpreadsheet\\Collection\\Memory\\SimpleCache1' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Collection/Memory/SimpleCache1.php', + 'PhpOffice\\PhpSpreadsheet\\Collection\\Memory\\SimpleCache3' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Collection/Memory/SimpleCache3.php', + 'PhpOffice\\PhpSpreadsheet\\Comment' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Comment.php', + 'PhpOffice\\PhpSpreadsheet\\DefinedName' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/DefinedName.php', + 'PhpOffice\\PhpSpreadsheet\\Document\\Properties' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Document/Properties.php', + 'PhpOffice\\PhpSpreadsheet\\Document\\Security' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Document/Security.php', + 'PhpOffice\\PhpSpreadsheet\\Exception' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Exception.php', + 'PhpOffice\\PhpSpreadsheet\\HashTable' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/HashTable.php', + 'PhpOffice\\PhpSpreadsheet\\Helper\\Dimension' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Helper/Dimension.php', + 'PhpOffice\\PhpSpreadsheet\\Helper\\Downloader' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Helper/Downloader.php', + 'PhpOffice\\PhpSpreadsheet\\Helper\\Handler' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Helper/Handler.php', + 'PhpOffice\\PhpSpreadsheet\\Helper\\Html' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Helper/Html.php', + 'PhpOffice\\PhpSpreadsheet\\Helper\\Sample' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Helper/Sample.php', + 'PhpOffice\\PhpSpreadsheet\\Helper\\Size' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Helper/Size.php', + 'PhpOffice\\PhpSpreadsheet\\Helper\\TextGrid' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Helper/TextGrid.php', + 'PhpOffice\\PhpSpreadsheet\\Helper\\TextGridRightAlign' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Helper/TextGridRightAlign.php', + 'PhpOffice\\PhpSpreadsheet\\IComparable' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/IComparable.php', + 'PhpOffice\\PhpSpreadsheet\\IOFactory' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/IOFactory.php', + 'PhpOffice\\PhpSpreadsheet\\NamedFormula' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/NamedFormula.php', + 'PhpOffice\\PhpSpreadsheet\\NamedRange' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/NamedRange.php', + 'PhpOffice\\PhpSpreadsheet\\Reader\\BaseReader' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/BaseReader.php', + 'PhpOffice\\PhpSpreadsheet\\Reader\\Csv' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Csv.php', + 'PhpOffice\\PhpSpreadsheet\\Reader\\CsvNoEscape' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/CsvNoEscape.php', + 'PhpOffice\\PhpSpreadsheet\\Reader\\Csv\\Delimiter' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Csv/Delimiter.php', + 'PhpOffice\\PhpSpreadsheet\\Reader\\DefaultReadFilter' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/DefaultReadFilter.php', + 'PhpOffice\\PhpSpreadsheet\\Reader\\EmptyWorksheetInfo' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/EmptyWorksheetInfo.php', + 'PhpOffice\\PhpSpreadsheet\\Reader\\Exception' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Exception.php', + 'PhpOffice\\PhpSpreadsheet\\Reader\\Gnumeric' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Gnumeric.php', + 'PhpOffice\\PhpSpreadsheet\\Reader\\Gnumeric\\PageSetup' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Gnumeric/PageSetup.php', + 'PhpOffice\\PhpSpreadsheet\\Reader\\Gnumeric\\Properties' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Gnumeric/Properties.php', + 'PhpOffice\\PhpSpreadsheet\\Reader\\Gnumeric\\Styles' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Gnumeric/Styles.php', + 'PhpOffice\\PhpSpreadsheet\\Reader\\Html' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Html.php', + 'PhpOffice\\PhpSpreadsheet\\Reader\\IReadFilter' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/IReadFilter.php', + 'PhpOffice\\PhpSpreadsheet\\Reader\\IReader' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/IReader.php', + 'PhpOffice\\PhpSpreadsheet\\Reader\\IReader2' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/IReader2.php', + 'PhpOffice\\PhpSpreadsheet\\Reader\\Ods' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Ods.php', + 'PhpOffice\\PhpSpreadsheet\\Reader\\Ods\\AutoFilter' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Ods/AutoFilter.php', + 'PhpOffice\\PhpSpreadsheet\\Reader\\Ods\\BaseLoader' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Ods/BaseLoader.php', + 'PhpOffice\\PhpSpreadsheet\\Reader\\Ods\\DefinedNames' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Ods/DefinedNames.php', + 'PhpOffice\\PhpSpreadsheet\\Reader\\Ods\\FormulaTranslator' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Ods/FormulaTranslator.php', + 'PhpOffice\\PhpSpreadsheet\\Reader\\Ods\\PageSettings' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Ods/PageSettings.php', + 'PhpOffice\\PhpSpreadsheet\\Reader\\Ods\\Properties' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Ods/Properties.php', + 'PhpOffice\\PhpSpreadsheet\\Reader\\Security\\XmlScanner' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Security/XmlScanner.php', + 'PhpOffice\\PhpSpreadsheet\\Reader\\Slk' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Slk.php', + 'PhpOffice\\PhpSpreadsheet\\Reader\\Xls' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Xls.php', + 'PhpOffice\\PhpSpreadsheet\\Reader\\XlsBase' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/XlsBase.php', + 'PhpOffice\\PhpSpreadsheet\\Reader\\Xls\\Biff5' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Xls/Biff5.php', + 'PhpOffice\\PhpSpreadsheet\\Reader\\Xls\\Biff8' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Xls/Biff8.php', + 'PhpOffice\\PhpSpreadsheet\\Reader\\Xls\\Color' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Xls/Color.php', + 'PhpOffice\\PhpSpreadsheet\\Reader\\Xls\\Color\\BIFF5' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Xls/Color/BIFF5.php', + 'PhpOffice\\PhpSpreadsheet\\Reader\\Xls\\Color\\BIFF8' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Xls/Color/BIFF8.php', + 'PhpOffice\\PhpSpreadsheet\\Reader\\Xls\\Color\\BuiltIn' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Xls/Color/BuiltIn.php', + 'PhpOffice\\PhpSpreadsheet\\Reader\\Xls\\ConditionalFormatting' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Xls/ConditionalFormatting.php', + 'PhpOffice\\PhpSpreadsheet\\Reader\\Xls\\DataValidationHelper' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Xls/DataValidationHelper.php', + 'PhpOffice\\PhpSpreadsheet\\Reader\\Xls\\ErrorCode' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Xls/ErrorCode.php', + 'PhpOffice\\PhpSpreadsheet\\Reader\\Xls\\Escher' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Xls/Escher.php', + 'PhpOffice\\PhpSpreadsheet\\Reader\\Xls\\ListFunctions' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Xls/ListFunctions.php', + 'PhpOffice\\PhpSpreadsheet\\Reader\\Xls\\LoadSpreadsheet' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Xls/LoadSpreadsheet.php', + 'PhpOffice\\PhpSpreadsheet\\Reader\\Xls\\MD5' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Xls/MD5.php', + 'PhpOffice\\PhpSpreadsheet\\Reader\\Xls\\Mappings' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Xls/Mappings.php', + 'PhpOffice\\PhpSpreadsheet\\Reader\\Xls\\RC4' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Xls/RC4.php', + 'PhpOffice\\PhpSpreadsheet\\Reader\\Xls\\Style\\Border' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Xls/Style/Border.php', + 'PhpOffice\\PhpSpreadsheet\\Reader\\Xls\\Style\\CellAlignment' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Xls/Style/CellAlignment.php', + 'PhpOffice\\PhpSpreadsheet\\Reader\\Xls\\Style\\CellFont' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Xls/Style/CellFont.php', + 'PhpOffice\\PhpSpreadsheet\\Reader\\Xls\\Style\\FillPattern' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Xls/Style/FillPattern.php', + 'PhpOffice\\PhpSpreadsheet\\Reader\\Xlsx' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Xlsx.php', + 'PhpOffice\\PhpSpreadsheet\\Reader\\Xlsx\\AutoFilter' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Xlsx/AutoFilter.php', + 'PhpOffice\\PhpSpreadsheet\\Reader\\Xlsx\\BaseParserClass' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Xlsx/BaseParserClass.php', + 'PhpOffice\\PhpSpreadsheet\\Reader\\Xlsx\\Chart' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Xlsx/Chart.php', + 'PhpOffice\\PhpSpreadsheet\\Reader\\Xlsx\\ColumnAndRowAttributes' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Xlsx/ColumnAndRowAttributes.php', + 'PhpOffice\\PhpSpreadsheet\\Reader\\Xlsx\\ConditionalStyles' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Xlsx/ConditionalStyles.php', + 'PhpOffice\\PhpSpreadsheet\\Reader\\Xlsx\\DataValidations' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Xlsx/DataValidations.php', + 'PhpOffice\\PhpSpreadsheet\\Reader\\Xlsx\\Hyperlinks' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Xlsx/Hyperlinks.php', + 'PhpOffice\\PhpSpreadsheet\\Reader\\Xlsx\\Namespaces' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Xlsx/Namespaces.php', + 'PhpOffice\\PhpSpreadsheet\\Reader\\Xlsx\\PageSetup' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Xlsx/PageSetup.php', + 'PhpOffice\\PhpSpreadsheet\\Reader\\Xlsx\\PivotTableReader' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Xlsx/PivotTableReader.php', + 'PhpOffice\\PhpSpreadsheet\\Reader\\Xlsx\\Properties' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Xlsx/Properties.php', + 'PhpOffice\\PhpSpreadsheet\\Reader\\Xlsx\\SharedFormula' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Xlsx/SharedFormula.php', + 'PhpOffice\\PhpSpreadsheet\\Reader\\Xlsx\\SheetViewOptions' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Xlsx/SheetViewOptions.php', + 'PhpOffice\\PhpSpreadsheet\\Reader\\Xlsx\\SheetViews' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Xlsx/SheetViews.php', + 'PhpOffice\\PhpSpreadsheet\\Reader\\Xlsx\\Sparklines' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Xlsx/Sparklines.php', + 'PhpOffice\\PhpSpreadsheet\\Reader\\Xlsx\\Styles' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Xlsx/Styles.php', + 'PhpOffice\\PhpSpreadsheet\\Reader\\Xlsx\\TableReader' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Xlsx/TableReader.php', + 'PhpOffice\\PhpSpreadsheet\\Reader\\Xlsx\\Theme' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Xlsx/Theme.php', + 'PhpOffice\\PhpSpreadsheet\\Reader\\Xlsx\\WorkbookView' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Xlsx/WorkbookView.php', + 'PhpOffice\\PhpSpreadsheet\\Reader\\Xml' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Xml.php', + 'PhpOffice\\PhpSpreadsheet\\Reader\\Xml\\DataValidations' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Xml/DataValidations.php', + 'PhpOffice\\PhpSpreadsheet\\Reader\\Xml\\PageSettings' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Xml/PageSettings.php', + 'PhpOffice\\PhpSpreadsheet\\Reader\\Xml\\Properties' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Xml/Properties.php', + 'PhpOffice\\PhpSpreadsheet\\Reader\\Xml\\Style' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Xml/Style.php', + 'PhpOffice\\PhpSpreadsheet\\Reader\\Xml\\Style\\Alignment' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Xml/Style/Alignment.php', + 'PhpOffice\\PhpSpreadsheet\\Reader\\Xml\\Style\\Border' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Xml/Style/Border.php', + 'PhpOffice\\PhpSpreadsheet\\Reader\\Xml\\Style\\Fill' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Xml/Style/Fill.php', + 'PhpOffice\\PhpSpreadsheet\\Reader\\Xml\\Style\\Font' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Xml/Style/Font.php', + 'PhpOffice\\PhpSpreadsheet\\Reader\\Xml\\Style\\NumberFormat' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Xml/Style/NumberFormat.php', + 'PhpOffice\\PhpSpreadsheet\\Reader\\Xml\\Style\\StyleBase' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Xml/Style/StyleBase.php', + 'PhpOffice\\PhpSpreadsheet\\ReferenceHelper' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/ReferenceHelper.php', + 'PhpOffice\\PhpSpreadsheet\\RichText\\ITextElement' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/RichText/ITextElement.php', + 'PhpOffice\\PhpSpreadsheet\\RichText\\RichText' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/RichText/RichText.php', + 'PhpOffice\\PhpSpreadsheet\\RichText\\Run' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/RichText/Run.php', + 'PhpOffice\\PhpSpreadsheet\\RichText\\TextElement' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/RichText/TextElement.php', + 'PhpOffice\\PhpSpreadsheet\\Settings' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Settings.php', + 'PhpOffice\\PhpSpreadsheet\\Shared\\CodePage' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Shared/CodePage.php', + 'PhpOffice\\PhpSpreadsheet\\Shared\\Date' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Shared/Date.php', + 'PhpOffice\\PhpSpreadsheet\\Shared\\Drawing' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Shared/Drawing.php', + 'PhpOffice\\PhpSpreadsheet\\Shared\\Escher' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Shared/Escher.php', + 'PhpOffice\\PhpSpreadsheet\\Shared\\Escher\\DgContainer' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Shared/Escher/DgContainer.php', + 'PhpOffice\\PhpSpreadsheet\\Shared\\Escher\\DgContainer\\SpgrContainer' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Shared/Escher/DgContainer/SpgrContainer.php', + 'PhpOffice\\PhpSpreadsheet\\Shared\\Escher\\DgContainer\\SpgrContainer\\SpContainer' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Shared/Escher/DgContainer/SpgrContainer/SpContainer.php', + 'PhpOffice\\PhpSpreadsheet\\Shared\\Escher\\DggContainer' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Shared/Escher/DggContainer.php', + 'PhpOffice\\PhpSpreadsheet\\Shared\\Escher\\DggContainer\\BstoreContainer' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Shared/Escher/DggContainer/BstoreContainer.php', + 'PhpOffice\\PhpSpreadsheet\\Shared\\Escher\\DggContainer\\BstoreContainer\\BSE' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Shared/Escher/DggContainer/BstoreContainer/BSE.php', + 'PhpOffice\\PhpSpreadsheet\\Shared\\Escher\\DggContainer\\BstoreContainer\\BSE\\Blip' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Shared/Escher/DggContainer/BstoreContainer/BSE/Blip.php', + 'PhpOffice\\PhpSpreadsheet\\Shared\\File' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Shared/File.php', + 'PhpOffice\\PhpSpreadsheet\\Shared\\Font' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Shared/Font.php', + 'PhpOffice\\PhpSpreadsheet\\Shared\\IntOrFloat' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Shared/IntOrFloat.php', + 'PhpOffice\\PhpSpreadsheet\\Shared\\OLE' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Shared/OLE.php', + 'PhpOffice\\PhpSpreadsheet\\Shared\\OLERead' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Shared/OLERead.php', + 'PhpOffice\\PhpSpreadsheet\\Shared\\OLE\\ChainedBlockStream' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Shared/OLE/ChainedBlockStream.php', + 'PhpOffice\\PhpSpreadsheet\\Shared\\OLE\\PPS' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Shared/OLE/PPS.php', + 'PhpOffice\\PhpSpreadsheet\\Shared\\OLE\\PPS\\File' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Shared/OLE/PPS/File.php', + 'PhpOffice\\PhpSpreadsheet\\Shared\\OLE\\PPS\\Root' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Shared/OLE/PPS/Root.php', + 'PhpOffice\\PhpSpreadsheet\\Shared\\PasswordHasher' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Shared/PasswordHasher.php', + 'PhpOffice\\PhpSpreadsheet\\Shared\\StringHelper' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Shared/StringHelper.php', + 'PhpOffice\\PhpSpreadsheet\\Shared\\TimeZone' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Shared/TimeZone.php', + 'PhpOffice\\PhpSpreadsheet\\Shared\\Trend\\BestFit' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Shared/Trend/BestFit.php', + 'PhpOffice\\PhpSpreadsheet\\Shared\\Trend\\ExponentialBestFit' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Shared/Trend/ExponentialBestFit.php', + 'PhpOffice\\PhpSpreadsheet\\Shared\\Trend\\LinearBestFit' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Shared/Trend/LinearBestFit.php', + 'PhpOffice\\PhpSpreadsheet\\Shared\\Trend\\LogarithmicBestFit' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Shared/Trend/LogarithmicBestFit.php', + 'PhpOffice\\PhpSpreadsheet\\Shared\\Trend\\PolynomialBestFit' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Shared/Trend/PolynomialBestFit.php', + 'PhpOffice\\PhpSpreadsheet\\Shared\\Trend\\PowerBestFit' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Shared/Trend/PowerBestFit.php', + 'PhpOffice\\PhpSpreadsheet\\Shared\\Trend\\Trend' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Shared/Trend/Trend.php', + 'PhpOffice\\PhpSpreadsheet\\Shared\\XMLWriter' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Shared/XMLWriter.php', + 'PhpOffice\\PhpSpreadsheet\\Shared\\Xls' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Shared/Xls.php', + 'PhpOffice\\PhpSpreadsheet\\Shared\\Xlsx\\AgileEncryption' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Shared/Xlsx/AgileEncryption.php', + 'PhpOffice\\PhpSpreadsheet\\Spreadsheet' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Spreadsheet.php', + 'PhpOffice\\PhpSpreadsheet\\Style\\Alignment' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Style/Alignment.php', + 'PhpOffice\\PhpSpreadsheet\\Style\\Border' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Style/Border.php', + 'PhpOffice\\PhpSpreadsheet\\Style\\Borders' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Style/Borders.php', + 'PhpOffice\\PhpSpreadsheet\\Style\\Color' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Style/Color.php', + 'PhpOffice\\PhpSpreadsheet\\Style\\Conditional' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Style/Conditional.php', + 'PhpOffice\\PhpSpreadsheet\\Style\\ConditionalFormatting\\CellMatcher' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Style/ConditionalFormatting/CellMatcher.php', + 'PhpOffice\\PhpSpreadsheet\\Style\\ConditionalFormatting\\CellStyleAssessor' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Style/ConditionalFormatting/CellStyleAssessor.php', + 'PhpOffice\\PhpSpreadsheet\\Style\\ConditionalFormatting\\ConditionalColorScale' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Style/ConditionalFormatting/ConditionalColorScale.php', + 'PhpOffice\\PhpSpreadsheet\\Style\\ConditionalFormatting\\ConditionalDataBar' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Style/ConditionalFormatting/ConditionalDataBar.php', + 'PhpOffice\\PhpSpreadsheet\\Style\\ConditionalFormatting\\ConditionalDataBarExtension' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Style/ConditionalFormatting/ConditionalDataBarExtension.php', + 'PhpOffice\\PhpSpreadsheet\\Style\\ConditionalFormatting\\ConditionalFormatValueObject' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Style/ConditionalFormatting/ConditionalFormatValueObject.php', + 'PhpOffice\\PhpSpreadsheet\\Style\\ConditionalFormatting\\ConditionalFormattingRuleExtension' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Style/ConditionalFormatting/ConditionalFormattingRuleExtension.php', + 'PhpOffice\\PhpSpreadsheet\\Style\\ConditionalFormatting\\ConditionalIconSet' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Style/ConditionalFormatting/ConditionalIconSet.php', + 'PhpOffice\\PhpSpreadsheet\\Style\\ConditionalFormatting\\IconSetValues' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Style/ConditionalFormatting/IconSetValues.php', + 'PhpOffice\\PhpSpreadsheet\\Style\\ConditionalFormatting\\MergedCellStyle' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Style/ConditionalFormatting/MergedCellStyle.php', + 'PhpOffice\\PhpSpreadsheet\\Style\\ConditionalFormatting\\StyleMerger' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Style/ConditionalFormatting/StyleMerger.php', + 'PhpOffice\\PhpSpreadsheet\\Style\\ConditionalFormatting\\Wizard' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Style/ConditionalFormatting/Wizard.php', + 'PhpOffice\\PhpSpreadsheet\\Style\\ConditionalFormatting\\Wizard\\Blanks' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Style/ConditionalFormatting/Wizard/Blanks.php', + 'PhpOffice\\PhpSpreadsheet\\Style\\ConditionalFormatting\\Wizard\\CellValue' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Style/ConditionalFormatting/Wizard/CellValue.php', + 'PhpOffice\\PhpSpreadsheet\\Style\\ConditionalFormatting\\Wizard\\DateValue' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Style/ConditionalFormatting/Wizard/DateValue.php', + 'PhpOffice\\PhpSpreadsheet\\Style\\ConditionalFormatting\\Wizard\\Duplicates' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Style/ConditionalFormatting/Wizard/Duplicates.php', + 'PhpOffice\\PhpSpreadsheet\\Style\\ConditionalFormatting\\Wizard\\Errors' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Style/ConditionalFormatting/Wizard/Errors.php', + 'PhpOffice\\PhpSpreadsheet\\Style\\ConditionalFormatting\\Wizard\\Expression' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Style/ConditionalFormatting/Wizard/Expression.php', + 'PhpOffice\\PhpSpreadsheet\\Style\\ConditionalFormatting\\Wizard\\TextValue' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Style/ConditionalFormatting/Wizard/TextValue.php', + 'PhpOffice\\PhpSpreadsheet\\Style\\ConditionalFormatting\\Wizard\\WizardAbstract' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Style/ConditionalFormatting/Wizard/WizardAbstract.php', + 'PhpOffice\\PhpSpreadsheet\\Style\\ConditionalFormatting\\Wizard\\WizardInterface' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Style/ConditionalFormatting/Wizard/WizardInterface.php', + 'PhpOffice\\PhpSpreadsheet\\Style\\Fill' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Style/Fill.php', + 'PhpOffice\\PhpSpreadsheet\\Style\\Font' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Style/Font.php', + 'PhpOffice\\PhpSpreadsheet\\Style\\NumberFormat' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Style/NumberFormat.php', + 'PhpOffice\\PhpSpreadsheet\\Style\\NumberFormat\\BaseFormatter' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Style/NumberFormat/BaseFormatter.php', + 'PhpOffice\\PhpSpreadsheet\\Style\\NumberFormat\\DateFormatter' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Style/NumberFormat/DateFormatter.php', + 'PhpOffice\\PhpSpreadsheet\\Style\\NumberFormat\\Formatter' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Style/NumberFormat/Formatter.php', + 'PhpOffice\\PhpSpreadsheet\\Style\\NumberFormat\\FractionFormatter' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Style/NumberFormat/FractionFormatter.php', + 'PhpOffice\\PhpSpreadsheet\\Style\\NumberFormat\\NumberFormatter' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Style/NumberFormat/NumberFormatter.php', + 'PhpOffice\\PhpSpreadsheet\\Style\\NumberFormat\\PercentageFormatter' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Style/NumberFormat/PercentageFormatter.php', + 'PhpOffice\\PhpSpreadsheet\\Style\\NumberFormat\\Wizard\\Accounting' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Style/NumberFormat/Wizard/Accounting.php', + 'PhpOffice\\PhpSpreadsheet\\Style\\NumberFormat\\Wizard\\Currency' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Style/NumberFormat/Wizard/Currency.php', + 'PhpOffice\\PhpSpreadsheet\\Style\\NumberFormat\\Wizard\\CurrencyBase' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Style/NumberFormat/Wizard/CurrencyBase.php', + 'PhpOffice\\PhpSpreadsheet\\Style\\NumberFormat\\Wizard\\CurrencyNegative' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Style/NumberFormat/Wizard/CurrencyNegative.php', + 'PhpOffice\\PhpSpreadsheet\\Style\\NumberFormat\\Wizard\\Date' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Style/NumberFormat/Wizard/Date.php', + 'PhpOffice\\PhpSpreadsheet\\Style\\NumberFormat\\Wizard\\DateTime' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Style/NumberFormat/Wizard/DateTime.php', + 'PhpOffice\\PhpSpreadsheet\\Style\\NumberFormat\\Wizard\\DateTimeWizard' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Style/NumberFormat/Wizard/DateTimeWizard.php', + 'PhpOffice\\PhpSpreadsheet\\Style\\NumberFormat\\Wizard\\Duration' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Style/NumberFormat/Wizard/Duration.php', + 'PhpOffice\\PhpSpreadsheet\\Style\\NumberFormat\\Wizard\\Locale' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Style/NumberFormat/Wizard/Locale.php', + 'PhpOffice\\PhpSpreadsheet\\Style\\NumberFormat\\Wizard\\Number' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Style/NumberFormat/Wizard/Number.php', + 'PhpOffice\\PhpSpreadsheet\\Style\\NumberFormat\\Wizard\\NumberBase' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Style/NumberFormat/Wizard/NumberBase.php', + 'PhpOffice\\PhpSpreadsheet\\Style\\NumberFormat\\Wizard\\Percentage' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Style/NumberFormat/Wizard/Percentage.php', + 'PhpOffice\\PhpSpreadsheet\\Style\\NumberFormat\\Wizard\\Scientific' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Style/NumberFormat/Wizard/Scientific.php', + 'PhpOffice\\PhpSpreadsheet\\Style\\NumberFormat\\Wizard\\Time' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Style/NumberFormat/Wizard/Time.php', + 'PhpOffice\\PhpSpreadsheet\\Style\\NumberFormat\\Wizard\\Wizard' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Style/NumberFormat/Wizard/Wizard.php', + 'PhpOffice\\PhpSpreadsheet\\Style\\Protection' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Style/Protection.php', + 'PhpOffice\\PhpSpreadsheet\\Style\\RgbTint' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Style/RgbTint.php', + 'PhpOffice\\PhpSpreadsheet\\Style\\Style' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Style/Style.php', + 'PhpOffice\\PhpSpreadsheet\\Style\\Supervisor' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Style/Supervisor.php', + 'PhpOffice\\PhpSpreadsheet\\Theme' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Theme.php', + 'PhpOffice\\PhpSpreadsheet\\Worksheet\\AutoFilter' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Worksheet/AutoFilter.php', + 'PhpOffice\\PhpSpreadsheet\\Worksheet\\AutoFilter\\Column' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Worksheet/AutoFilter/Column.php', + 'PhpOffice\\PhpSpreadsheet\\Worksheet\\AutoFilter\\Column\\Rule' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Worksheet/AutoFilter/Column/Rule.php', + 'PhpOffice\\PhpSpreadsheet\\Worksheet\\AutoFit' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Worksheet/AutoFit.php', + 'PhpOffice\\PhpSpreadsheet\\Worksheet\\BaseDrawing' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Worksheet/BaseDrawing.php', + 'PhpOffice\\PhpSpreadsheet\\Worksheet\\CellIterator' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Worksheet/CellIterator.php', + 'PhpOffice\\PhpSpreadsheet\\Worksheet\\Column' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Worksheet/Column.php', + 'PhpOffice\\PhpSpreadsheet\\Worksheet\\ColumnCellIterator' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Worksheet/ColumnCellIterator.php', + 'PhpOffice\\PhpSpreadsheet\\Worksheet\\ColumnDimension' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Worksheet/ColumnDimension.php', + 'PhpOffice\\PhpSpreadsheet\\Worksheet\\ColumnIterator' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Worksheet/ColumnIterator.php', + 'PhpOffice\\PhpSpreadsheet\\Worksheet\\Dimension' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Worksheet/Dimension.php', + 'PhpOffice\\PhpSpreadsheet\\Worksheet\\Drawing' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Worksheet/Drawing.php', + 'PhpOffice\\PhpSpreadsheet\\Worksheet\\Drawing\\Shadow' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Worksheet/Drawing/Shadow.php', + 'PhpOffice\\PhpSpreadsheet\\Worksheet\\HeaderFooter' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Worksheet/HeaderFooter.php', + 'PhpOffice\\PhpSpreadsheet\\Worksheet\\HeaderFooterDrawing' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Worksheet/HeaderFooterDrawing.php', + 'PhpOffice\\PhpSpreadsheet\\Worksheet\\Iterator' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Worksheet/Iterator.php', + 'PhpOffice\\PhpSpreadsheet\\Worksheet\\MemoryDrawing' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Worksheet/MemoryDrawing.php', + 'PhpOffice\\PhpSpreadsheet\\Worksheet\\PageBreak' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Worksheet/PageBreak.php', + 'PhpOffice\\PhpSpreadsheet\\Worksheet\\PageMargins' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Worksheet/PageMargins.php', + 'PhpOffice\\PhpSpreadsheet\\Worksheet\\PageSetup' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Worksheet/PageSetup.php', + 'PhpOffice\\PhpSpreadsheet\\Worksheet\\Pane' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Worksheet/Pane.php', + 'PhpOffice\\PhpSpreadsheet\\Worksheet\\PivotTable\\PivotCacheDefinition' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Worksheet/PivotTable/PivotCacheDefinition.php', + 'PhpOffice\\PhpSpreadsheet\\Worksheet\\PivotTable\\PivotField' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Worksheet/PivotTable/PivotField.php', + 'PhpOffice\\PhpSpreadsheet\\Worksheet\\PivotTable\\PivotFieldGroup' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Worksheet/PivotTable/PivotFieldGroup.php', + 'PhpOffice\\PhpSpreadsheet\\Worksheet\\PivotTable\\PivotTable' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Worksheet/PivotTable/PivotTable.php', + 'PhpOffice\\PhpSpreadsheet\\Worksheet\\PivotTable\\PivotTableBuilder' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Worksheet/PivotTable/PivotTableBuilder.php', + 'PhpOffice\\PhpSpreadsheet\\Worksheet\\ProtectedRange' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Worksheet/ProtectedRange.php', + 'PhpOffice\\PhpSpreadsheet\\Worksheet\\Protection' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Worksheet/Protection.php', + 'PhpOffice\\PhpSpreadsheet\\Worksheet\\Row' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Worksheet/Row.php', + 'PhpOffice\\PhpSpreadsheet\\Worksheet\\RowCellIterator' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Worksheet/RowCellIterator.php', + 'PhpOffice\\PhpSpreadsheet\\Worksheet\\RowDimension' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Worksheet/RowDimension.php', + 'PhpOffice\\PhpSpreadsheet\\Worksheet\\RowIterator' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Worksheet/RowIterator.php', + 'PhpOffice\\PhpSpreadsheet\\Worksheet\\SheetView' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Worksheet/SheetView.php', + 'PhpOffice\\PhpSpreadsheet\\Worksheet\\Sparkline\\Sparkline' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Worksheet/Sparkline/Sparkline.php', + 'PhpOffice\\PhpSpreadsheet\\Worksheet\\Sparkline\\SparklineGroup' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Worksheet/Sparkline/SparklineGroup.php', + 'PhpOffice\\PhpSpreadsheet\\Worksheet\\Sparkline\\SparklineType' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Worksheet/Sparkline/SparklineType.php', + 'PhpOffice\\PhpSpreadsheet\\Worksheet\\Table' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Worksheet/Table.php', + 'PhpOffice\\PhpSpreadsheet\\Worksheet\\Table\\Column' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Worksheet/Table/Column.php', + 'PhpOffice\\PhpSpreadsheet\\Worksheet\\Table\\TableDxfsStyle' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Worksheet/Table/TableDxfsStyle.php', + 'PhpOffice\\PhpSpreadsheet\\Worksheet\\Table\\TableStyle' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Worksheet/Table/TableStyle.php', + 'PhpOffice\\PhpSpreadsheet\\Worksheet\\Validations' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Worksheet/Validations.php', + 'PhpOffice\\PhpSpreadsheet\\Worksheet\\Worksheet' => __DIR__ . '/..' . '/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Worksheet/Worksheet.php', + 'Psr\\SimpleCache\\CacheException' => __DIR__ . '/..' . '/psr/simple-cache/src/CacheException.php', + 'Psr\\SimpleCache\\CacheInterface' => __DIR__ . '/..' . '/psr/simple-cache/src/CacheInterface.php', + 'Psr\\SimpleCache\\InvalidArgumentException' => __DIR__ . '/..' . '/psr/simple-cache/src/InvalidArgumentException.php', + 'ZipStream\\CentralDirectoryFileHeader' => __DIR__ . '/..' . '/maennchen/zipstream-php/src/CentralDirectoryFileHeader.php', + 'ZipStream\\CompressionMethod' => __DIR__ . '/..' . '/maennchen/zipstream-php/src/CompressionMethod.php', + 'ZipStream\\DataDescriptor' => __DIR__ . '/..' . '/maennchen/zipstream-php/src/DataDescriptor.php', + 'ZipStream\\EndOfCentralDirectory' => __DIR__ . '/..' . '/maennchen/zipstream-php/src/EndOfCentralDirectory.php', + 'ZipStream\\Exception' => __DIR__ . '/..' . '/maennchen/zipstream-php/src/Exception.php', + 'ZipStream\\Exception\\DosTimeOverflowException' => __DIR__ . '/..' . '/maennchen/zipstream-php/src/Exception/DosTimeOverflowException.php', + 'ZipStream\\Exception\\FileNotFoundException' => __DIR__ . '/..' . '/maennchen/zipstream-php/src/Exception/FileNotFoundException.php', + 'ZipStream\\Exception\\FileNotReadableException' => __DIR__ . '/..' . '/maennchen/zipstream-php/src/Exception/FileNotReadableException.php', + 'ZipStream\\Exception\\FileSizeIncorrectException' => __DIR__ . '/..' . '/maennchen/zipstream-php/src/Exception/FileSizeIncorrectException.php', + 'ZipStream\\Exception\\OverflowException' => __DIR__ . '/..' . '/maennchen/zipstream-php/src/Exception/OverflowException.php', + 'ZipStream\\Exception\\ResourceActionException' => __DIR__ . '/..' . '/maennchen/zipstream-php/src/Exception/ResourceActionException.php', + 'ZipStream\\Exception\\SimulationFileUnknownException' => __DIR__ . '/..' . '/maennchen/zipstream-php/src/Exception/SimulationFileUnknownException.php', + 'ZipStream\\Exception\\StreamNotReadableException' => __DIR__ . '/..' . '/maennchen/zipstream-php/src/Exception/StreamNotReadableException.php', + 'ZipStream\\Exception\\StreamNotSeekableException' => __DIR__ . '/..' . '/maennchen/zipstream-php/src/Exception/StreamNotSeekableException.php', + 'ZipStream\\File' => __DIR__ . '/..' . '/maennchen/zipstream-php/src/File.php', + 'ZipStream\\GeneralPurposeBitFlag' => __DIR__ . '/..' . '/maennchen/zipstream-php/src/GeneralPurposeBitFlag.php', + 'ZipStream\\LocalFileHeader' => __DIR__ . '/..' . '/maennchen/zipstream-php/src/LocalFileHeader.php', + 'ZipStream\\OperationMode' => __DIR__ . '/..' . '/maennchen/zipstream-php/src/OperationMode.php', + 'ZipStream\\PackField' => __DIR__ . '/..' . '/maennchen/zipstream-php/src/PackField.php', + 'ZipStream\\Time' => __DIR__ . '/..' . '/maennchen/zipstream-php/src/Time.php', + 'ZipStream\\Version' => __DIR__ . '/..' . '/maennchen/zipstream-php/src/Version.php', + 'ZipStream\\Zip64\\DataDescriptor' => __DIR__ . '/..' . '/maennchen/zipstream-php/src/Zip64/DataDescriptor.php', + 'ZipStream\\Zip64\\EndOfCentralDirectory' => __DIR__ . '/..' . '/maennchen/zipstream-php/src/Zip64/EndOfCentralDirectory.php', + 'ZipStream\\Zip64\\EndOfCentralDirectoryLocator' => __DIR__ . '/..' . '/maennchen/zipstream-php/src/Zip64/EndOfCentralDirectoryLocator.php', + 'ZipStream\\Zip64\\ExtendedInformationExtraField' => __DIR__ . '/..' . '/maennchen/zipstream-php/src/Zip64/ExtendedInformationExtraField.php', + 'ZipStream\\ZipStream' => __DIR__ . '/..' . '/maennchen/zipstream-php/src/ZipStream.php', + 'ZipStream\\Zs\\ExtendedInformationExtraField' => __DIR__ . '/..' . '/maennchen/zipstream-php/src/Zs/ExtendedInformationExtraField.php', ); public static function getInitializer(ClassLoader $loader) { return \Closure::bind(function () use ($loader) { - $loader->prefixLengthsPsr4 = ComposerStaticInit524e760e56b0620cb9bc3d8d9ad8543d::$prefixLengthsPsr4; - $loader->prefixDirsPsr4 = ComposerStaticInit524e760e56b0620cb9bc3d8d9ad8543d::$prefixDirsPsr4; - $loader->classMap = ComposerStaticInit524e760e56b0620cb9bc3d8d9ad8543d::$classMap; + $loader->prefixLengthsPsr4 = ComposerStaticInitbae58d66b0357c26ca5c29c77e2a2a8a::$prefixLengthsPsr4; + $loader->prefixDirsPsr4 = ComposerStaticInitbae58d66b0357c26ca5c29c77e2a2a8a::$prefixDirsPsr4; + $loader->classMap = ComposerStaticInitbae58d66b0357c26ca5c29c77e2a2a8a::$classMap; }, null, ClassLoader::class); } diff --git a/vendor/composer/installed.json b/vendor/composer/installed.json index 954276f0..c4974de5 100644 --- a/vendor/composer/installed.json +++ b/vendor/composer/installed.json @@ -1,445 +1,447 @@ { - "packages": [ + "packages": [ + { + "name": "composer/pcre", + "version": "3.4.0", + "version_normalized": "3.4.0.0", + "source": { + "type": "git", + "url": "https://github.com/composer/pcre.git", + "reference": "d5a341b3fb61f3001970940afb1d332968a183ed" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/composer/pcre/zipball/d5a341b3fb61f3001970940afb1d332968a183ed", + "reference": "d5a341b3fb61f3001970940afb1d332968a183ed", + "shasum": "" + }, + "require": { + "php": "^7.4 || ^8.0" + }, + "conflict": { + "phpstan/phpstan": "<2.2.2" + }, + "require-dev": { + "phpstan/phpstan": "^2", + "phpstan/phpstan-deprecation-rules": "^2", + "phpstan/phpstan-strict-rules": "^2", + "phpunit/phpunit": "^9" + }, + "time": "2026-06-07T11:47:49+00:00", + "type": "library", + "extra": { + "phpstan": { + "includes": [ + "extension.neon" + ] + }, + "branch-alias": { + "dev-main": "3.x-dev" + } + }, + "installation-source": "dist", + "autoload": { + "psr-4": { + "Composer\\Pcre\\": "src" + } + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "MIT" + ], + "authors": [ + { + "name": "Jordi Boggiano", + "email": "j.boggiano@seld.be", + "homepage": "http://seld.be" + } + ], + "description": "PCRE wrapping library that offers type-safe preg_* replacements.", + "keywords": [ + "PCRE", + "preg", + "regex", + "regular expression" + ], + "support": { + "issues": "https://github.com/composer/pcre/issues", + "source": "https://github.com/composer/pcre/tree/3.4.0" + }, + "funding": [ { - "name": "composer/pcre", - "version": "3.4.0", - "version_normalized": "3.4.0.0", - "source": { - "type": "git", - "url": "https://github.com/composer/pcre.git", - "reference": "d5a341b3fb61f3001970940afb1d332968a183ed" - }, - "dist": { - "type": "zip", - "url": "https://api.github.com/repos/composer/pcre/zipball/d5a341b3fb61f3001970940afb1d332968a183ed", - "reference": "d5a341b3fb61f3001970940afb1d332968a183ed", - "shasum": "" - }, - "require": { - "php": "^7.4 || ^8.0" - }, - "conflict": { - "phpstan/phpstan": "<2.2.2" - }, - "require-dev": { - "phpstan/phpstan": "^2", - "phpstan/phpstan-deprecation-rules": "^2", - "phpstan/phpstan-strict-rules": "^2", - "phpunit/phpunit": "^9" - }, - "time": "2026-06-07T11:47:49+00:00", - "type": "library", - "extra": { - "phpstan": { - "includes": [ - "extension.neon" - ] - }, - "branch-alias": { - "dev-main": "3.x-dev" - } - }, - "installation-source": "dist", - "autoload": { - "psr-4": { - "Composer\\Pcre\\": "src" - } - }, - "notification-url": "https://packagist.org/downloads/", - "license": [ - "MIT" - ], - "authors": [ - { - "name": "Jordi Boggiano", - "email": "j.boggiano@seld.be", - "homepage": "http://seld.be" - } - ], - "description": "PCRE wrapping library that offers type-safe preg_* replacements.", - "keywords": [ - "PCRE", - "preg", - "regex", - "regular expression" - ], - "support": { - "issues": "https://github.com/composer/pcre/issues", - "source": "https://github.com/composer/pcre/tree/3.4.0" - }, - "funding": [ - { - "url": "https://packagist.com", - "type": "custom" - }, - { - "url": "https://github.com/composer", - "type": "github" - } - ], - "install-path": "./pcre" + "url": "https://packagist.com", + "type": "custom" }, { - "name": "maennchen/zipstream-php", - "version": "3.1.2", - "version_normalized": "3.1.2.0", - "source": { - "type": "git", - "url": "https://github.com/maennchen/ZipStream-PHP.git", - "reference": "aeadcf5c412332eb426c0f9b4485f6accba2a99f" - }, - "dist": { - "type": "zip", - "url": "https://api.github.com/repos/maennchen/ZipStream-PHP/zipball/aeadcf5c412332eb426c0f9b4485f6accba2a99f", - "reference": "aeadcf5c412332eb426c0f9b4485f6accba2a99f", - "shasum": "" - }, - "require": { - "ext-mbstring": "*", - "ext-zlib": "*", - "php-64bit": "^8.2" - }, - "require-dev": { - "brianium/paratest": "^7.7", - "ext-zip": "*", - "friendsofphp/php-cs-fixer": "^3.16", - "guzzlehttp/guzzle": "^7.5", - "mikey179/vfsstream": "^1.6", - "php-coveralls/php-coveralls": "^2.5", - "phpunit/phpunit": "^11.0", - "vimeo/psalm": "^6.0" - }, - "suggest": { - "guzzlehttp/psr7": "^2.4", - "psr/http-message": "^2.0" - }, - "time": "2025-01-27T12:07:53+00:00", - "type": "library", - "installation-source": "dist", - "autoload": { - "psr-4": { - "ZipStream\\": "src/" - } - }, - "notification-url": "https://packagist.org/downloads/", - "license": [ - "MIT" - ], - "authors": [ - { - "name": "Paul Duncan", - "email": "pabs@pablotron.org" - }, - { - "name": "Jonatan Männchen", - "email": "jonatan@maennchen.ch" - }, - { - "name": "Jesse Donat", - "email": "donatj@gmail.com" - }, - { - "name": "András Kolesár", - "email": "kolesar@kolesar.hu" - } - ], - "description": "ZipStream is a library for dynamically streaming dynamic zip files from PHP without writing to the disk at all on the server.", - "keywords": [ - "stream", - "zip" - ], - "support": { - "issues": "https://github.com/maennchen/ZipStream-PHP/issues", - "source": "https://github.com/maennchen/ZipStream-PHP/tree/3.1.2" - }, - "funding": [ - { - "url": "https://github.com/maennchen", - "type": "github" - } - ], - "install-path": "../maennchen/zipstream-php" + "url": "https://github.com/composer", + "type": "github" + } + ], + "install-path": "./pcre" + }, + { + "name": "maennchen/zipstream-php", + "version": "3.1.2", + "version_normalized": "3.1.2.0", + "source": { + "type": "git", + "url": "https://github.com/maennchen/ZipStream-PHP.git", + "reference": "aeadcf5c412332eb426c0f9b4485f6accba2a99f" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/maennchen/ZipStream-PHP/zipball/aeadcf5c412332eb426c0f9b4485f6accba2a99f", + "reference": "aeadcf5c412332eb426c0f9b4485f6accba2a99f", + "shasum": "" + }, + "require": { + "ext-mbstring": "*", + "ext-zlib": "*", + "php-64bit": "^8.2" + }, + "require-dev": { + "brianium/paratest": "^7.7", + "ext-zip": "*", + "friendsofphp/php-cs-fixer": "^3.16", + "guzzlehttp/guzzle": "^7.5", + "mikey179/vfsstream": "^1.6", + "php-coveralls/php-coveralls": "^2.5", + "phpunit/phpunit": "^11.0", + "vimeo/psalm": "^6.0" + }, + "suggest": { + "guzzlehttp/psr7": "^2.4", + "psr/http-message": "^2.0" + }, + "time": "2025-01-27T12:07:53+00:00", + "type": "library", + "installation-source": "dist", + "autoload": { + "psr-4": { + "ZipStream\\": "src/" + } + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "MIT" + ], + "authors": [ + { + "name": "Paul Duncan", + "email": "pabs@pablotron.org" }, { - "name": "markbaker/complex", - "version": "3.0.2", - "version_normalized": "3.0.2.0", - "source": { - "type": "git", - "url": "https://github.com/MarkBaker/PHPComplex.git", - "reference": "95c56caa1cf5c766ad6d65b6344b807c1e8405b9" - }, - "dist": { - "type": "zip", - "url": "https://api.github.com/repos/MarkBaker/PHPComplex/zipball/95c56caa1cf5c766ad6d65b6344b807c1e8405b9", - "reference": "95c56caa1cf5c766ad6d65b6344b807c1e8405b9", - "shasum": "" - }, - "require": { - "php": "^7.2 || ^8.0" - }, - "require-dev": { - "dealerdirect/phpcodesniffer-composer-installer": "dev-master", - "phpcompatibility/php-compatibility": "^9.3", - "phpunit/phpunit": "^7.0 || ^8.0 || ^9.0", - "squizlabs/php_codesniffer": "^3.7" - }, - "time": "2022-12-06T16:21:08+00:00", - "type": "library", - "installation-source": "dist", - "autoload": { - "psr-4": { - "Complex\\": "classes/src/" - } - }, - "notification-url": "https://packagist.org/downloads/", - "license": [ - "MIT" - ], - "authors": [ - { - "name": "Mark Baker", - "email": "mark@lange.demon.co.uk" - } - ], - "description": "PHP Class for working with complex numbers", - "homepage": "https://github.com/MarkBaker/PHPComplex", - "keywords": [ - "complex", - "mathematics" - ], - "support": { - "issues": "https://github.com/MarkBaker/PHPComplex/issues", - "source": "https://github.com/MarkBaker/PHPComplex/tree/3.0.2" - }, - "install-path": "../markbaker/complex" + "name": "Jonatan Männchen", + "email": "jonatan@maennchen.ch" }, { - "name": "markbaker/matrix", - "version": "3.0.1", - "version_normalized": "3.0.1.0", - "source": { - "type": "git", - "url": "https://github.com/MarkBaker/PHPMatrix.git", - "reference": "728434227fe21be27ff6d86621a1b13107a2562c" - }, - "dist": { - "type": "zip", - "url": "https://api.github.com/repos/MarkBaker/PHPMatrix/zipball/728434227fe21be27ff6d86621a1b13107a2562c", - "reference": "728434227fe21be27ff6d86621a1b13107a2562c", - "shasum": "" - }, - "require": { - "php": "^7.1 || ^8.0" - }, - "require-dev": { - "dealerdirect/phpcodesniffer-composer-installer": "dev-master", - "phpcompatibility/php-compatibility": "^9.3", - "phpdocumentor/phpdocumentor": "2.*", - "phploc/phploc": "^4.0", - "phpmd/phpmd": "2.*", - "phpunit/phpunit": "^7.0 || ^8.0 || ^9.0", - "sebastian/phpcpd": "^4.0", - "squizlabs/php_codesniffer": "^3.7" - }, - "time": "2022-12-02T22:17:43+00:00", - "type": "library", - "installation-source": "dist", - "autoload": { - "psr-4": { - "Matrix\\": "classes/src/" - } - }, - "notification-url": "https://packagist.org/downloads/", - "license": [ - "MIT" - ], - "authors": [ - { - "name": "Mark Baker", - "email": "mark@demon-angel.eu" - } - ], - "description": "PHP Class for working with matrices", - "homepage": "https://github.com/MarkBaker/PHPMatrix", - "keywords": [ - "mathematics", - "matrix", - "vector" - ], - "support": { - "issues": "https://github.com/MarkBaker/PHPMatrix/issues", - "source": "https://github.com/MarkBaker/PHPMatrix/tree/3.0.1" - }, - "install-path": "../markbaker/matrix" + "name": "Jesse Donat", + "email": "donatj@gmail.com" }, { - "name": "phpoffice/phpspreadsheet", - "version": "5.8.0", - "version_normalized": "5.8.0.0", - "source": { - "type": "git", - "url": "https://github.com/PHPOffice/PhpSpreadsheet.git", - "reference": "01964d92536edf1a3a874b9580a52824bebf6fbb" - }, - "dist": { - "type": "zip", - "url": "https://api.github.com/repos/PHPOffice/PhpSpreadsheet/zipball/01964d92536edf1a3a874b9580a52824bebf6fbb", - "reference": "01964d92536edf1a3a874b9580a52824bebf6fbb", - "shasum": "" - }, - "require": { - "composer/pcre": "^1||^2||^3", - "ext-ctype": "*", - "ext-dom": "*", - "ext-fileinfo": "*", - "ext-filter": "*", - "ext-gd": "*", - "ext-iconv": "*", - "ext-libxml": "*", - "ext-mbstring": "*", - "ext-simplexml": "*", - "ext-xml": "*", - "ext-xmlreader": "*", - "ext-xmlwriter": "*", - "ext-zip": "*", - "ext-zlib": "*", - "maennchen/zipstream-php": "^2.1 || ^3.0", - "markbaker/complex": "^3.0", - "markbaker/matrix": "^3.0", - "php": "^8.1", - "psr/simple-cache": "^1.0 || ^2.0 || ^3.0" - }, - "require-dev": { - "dealerdirect/phpcodesniffer-composer-installer": "dev-main", - "dompdf/dompdf": "^2.0 || ^3.0", - "ext-intl": "*", - "friendsofphp/php-cs-fixer": "^3.2", - "mitoteam/jpgraph": "^10.5", - "mpdf/mpdf": "^8.1.1", - "phpcompatibility/php-compatibility": "^9.3", - "phpstan/phpstan": "^1.1 || ^2.0", - "phpstan/phpstan-deprecation-rules": "^1.0 || ^2.0", - "phpstan/phpstan-phpunit": "^1.0 || ^2.0", - "phpunit/phpunit": "^10.5", - "squizlabs/php_codesniffer": "^3.7", - "tecnickcom/tcpdf": "^6.5" - }, - "suggest": { - "dompdf/dompdf": "Option for rendering PDF with PDF Writer", - "ext-intl": "PHP Internationalization Functions, required for NumberFormat Wizard and StringHelper::setLocale()", - "mitoteam/jpgraph": "Option for rendering charts, or including charts with PDF or HTML Writers", - "mpdf/mpdf": "Option for rendering PDF with PDF Writer", - "tecnickcom/tcpdf": "Option for rendering PDF with PDF Writer" - }, - "time": "2026-06-07T03:51:10+00:00", - "type": "library", - "installation-source": "dist", - "autoload": { - "psr-4": { - "PhpOffice\\PhpSpreadsheet\\": "src/PhpSpreadsheet" - } - }, - "notification-url": "https://packagist.org/downloads/", - "license": [ - "MIT" - ], - "authors": [ - { - "name": "Maarten Balliauw", - "homepage": "https://blog.maartenballiauw.be" - }, - { - "name": "Mark Baker", - "homepage": "https://markbakeruk.net" - }, - { - "name": "Franck Lefevre", - "homepage": "https://rootslabs.net" - }, - { - "name": "Erik Tilt" - }, - { - "name": "Adrien Crivelli" - }, - { - "name": "Owen Leibman" - } - ], - "description": "PHPSpreadsheet - Read, Create and Write Spreadsheet documents in PHP - Spreadsheet engine", - "homepage": "https://github.com/PHPOffice/PhpSpreadsheet", - "keywords": [ - "OpenXML", - "excel", - "gnumeric", - "ods", - "php", - "spreadsheet", - "xls", - "xlsx" - ], - "support": { - "issues": "https://github.com/PHPOffice/PhpSpreadsheet/issues", - "source": "https://github.com/PHPOffice/PhpSpreadsheet/tree/5.8.0" - }, - "install-path": "../phpoffice/phpspreadsheet" + "name": "András Kolesár", + "email": "kolesar@kolesar.hu" + } + ], + "description": "ZipStream is a library for dynamically streaming dynamic zip files from PHP without writing to the disk at all on the server.", + "keywords": [ + "stream", + "zip" + ], + "support": { + "issues": "https://github.com/maennchen/ZipStream-PHP/issues", + "source": "https://github.com/maennchen/ZipStream-PHP/tree/3.1.2" + }, + "funding": [ + { + "url": "https://github.com/maennchen", + "type": "github" + } + ], + "install-path": "../maennchen/zipstream-php" + }, + { + "name": "markbaker/complex", + "version": "3.0.2", + "version_normalized": "3.0.2.0", + "source": { + "type": "git", + "url": "https://github.com/MarkBaker/PHPComplex.git", + "reference": "95c56caa1cf5c766ad6d65b6344b807c1e8405b9" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/MarkBaker/PHPComplex/zipball/95c56caa1cf5c766ad6d65b6344b807c1e8405b9", + "reference": "95c56caa1cf5c766ad6d65b6344b807c1e8405b9", + "shasum": "" + }, + "require": { + "php": "^7.2 || ^8.0" + }, + "require-dev": { + "dealerdirect/phpcodesniffer-composer-installer": "dev-master", + "phpcompatibility/php-compatibility": "^9.3", + "phpunit/phpunit": "^7.0 || ^8.0 || ^9.0", + "squizlabs/php_codesniffer": "^3.7" + }, + "time": "2022-12-06T16:21:08+00:00", + "type": "library", + "installation-source": "dist", + "autoload": { + "psr-4": { + "Complex\\": "classes/src/" + } + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "MIT" + ], + "authors": [ + { + "name": "Mark Baker", + "email": "mark@lange.demon.co.uk" + } + ], + "description": "PHP Class for working with complex numbers", + "homepage": "https://github.com/MarkBaker/PHPComplex", + "keywords": [ + "complex", + "mathematics" + ], + "support": { + "issues": "https://github.com/MarkBaker/PHPComplex/issues", + "source": "https://github.com/MarkBaker/PHPComplex/tree/3.0.2" + }, + "install-path": "../markbaker/complex" + }, + { + "name": "markbaker/matrix", + "version": "3.0.1", + "version_normalized": "3.0.1.0", + "source": { + "type": "git", + "url": "https://github.com/MarkBaker/PHPMatrix.git", + "reference": "728434227fe21be27ff6d86621a1b13107a2562c" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/MarkBaker/PHPMatrix/zipball/728434227fe21be27ff6d86621a1b13107a2562c", + "reference": "728434227fe21be27ff6d86621a1b13107a2562c", + "shasum": "" + }, + "require": { + "php": "^7.1 || ^8.0" + }, + "require-dev": { + "dealerdirect/phpcodesniffer-composer-installer": "dev-master", + "phpcompatibility/php-compatibility": "^9.3", + "phpdocumentor/phpdocumentor": "2.*", + "phploc/phploc": "^4.0", + "phpmd/phpmd": "2.*", + "phpunit/phpunit": "^7.0 || ^8.0 || ^9.0", + "sebastian/phpcpd": "^4.0", + "squizlabs/php_codesniffer": "^3.7" + }, + "time": "2022-12-02T22:17:43+00:00", + "type": "library", + "installation-source": "dist", + "autoload": { + "psr-4": { + "Matrix\\": "classes/src/" + } + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "MIT" + ], + "authors": [ + { + "name": "Mark Baker", + "email": "mark@demon-angel.eu" + } + ], + "description": "PHP Class for working with matrices", + "homepage": "https://github.com/MarkBaker/PHPMatrix", + "keywords": [ + "mathematics", + "matrix", + "vector" + ], + "support": { + "issues": "https://github.com/MarkBaker/PHPMatrix/issues", + "source": "https://github.com/MarkBaker/PHPMatrix/tree/3.0.1" + }, + "install-path": "../markbaker/matrix" + }, + { + "name": "phpoffice/phpspreadsheet", + "version": "5.10.0", + "version_normalized": "5.10.0.0", + "source": { + "type": "git", + "url": "https://github.com/PHPOffice/PhpSpreadsheet.git", + "reference": "eb18727acf6b1f4cc67145a52ab04f9fd4c28d53" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/PHPOffice/PhpSpreadsheet/zipball/eb18727acf6b1f4cc67145a52ab04f9fd4c28d53", + "reference": "eb18727acf6b1f4cc67145a52ab04f9fd4c28d53", + "shasum": "" + }, + "require": { + "composer/pcre": "^1||^2||^3", + "ext-ctype": "*", + "ext-dom": "*", + "ext-fileinfo": "*", + "ext-filter": "*", + "ext-gd": "*", + "ext-iconv": "*", + "ext-libxml": "*", + "ext-mbstring": "*", + "ext-simplexml": "*", + "ext-xml": "*", + "ext-xmlreader": "*", + "ext-xmlwriter": "*", + "ext-zip": "*", + "ext-zlib": "*", + "maennchen/zipstream-php": "^2.1 || ^3.0", + "markbaker/complex": "^3.0", + "markbaker/matrix": "^3.0", + "php": "^8.2", + "psr/simple-cache": "^1.0 || ^2.0 || ^3.0" + }, + "require-dev": { + "dealerdirect/phpcodesniffer-composer-installer": "dev-main", + "dompdf/dompdf": "^2.0 || ^3.0", + "ext-intl": "*", + "ext-openssl": "*", + "friendsofphp/php-cs-fixer": "^3.2", + "mitoteam/jpgraph": "^10.5", + "mpdf/mpdf": "^8.1.1", + "phpcompatibility/php-compatibility": "^9.3", + "phpstan/phpstan": "^1.1 || ^2.0", + "phpstan/phpstan-deprecation-rules": "^1.0 || ^2.0", + "phpstan/phpstan-phpunit": "^1.0 || ^2.0", + "phpunit/phpunit": "^10.5 || ^11.0", + "squizlabs/php_codesniffer": "^3.7", + "tecnickcom/tcpdf": ">=6.8.0 <7.0.0" + }, + "suggest": { + "dompdf/dompdf": "Option for rendering PDF with PDF Writer", + "ext-intl": "PHP Internationalization Functions, required for NumberFormat Wizard and StringHelper::setLocale()", + "ext-openssl": "Handline Agile-encrypted Xlsx spreadsheets", + "mitoteam/jpgraph": "Option for rendering charts, or including charts with PDF or HTML Writers", + "mpdf/mpdf": "Option for rendering PDF with PDF Writer", + "tecnickcom/tcpdf": "Option for rendering PDF with PDF Writer" + }, + "time": "2026-09-17T03:54:50+00:00", + "type": "library", + "installation-source": "dist", + "autoload": { + "psr-4": { + "PhpOffice\\PhpSpreadsheet\\": "src/PhpSpreadsheet" + } + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "MIT" + ], + "authors": [ + { + "name": "Maarten Balliauw", + "homepage": "https://blog.maartenballiauw.be" + }, + { + "name": "Mark Baker", + "homepage": "https://markbakeruk.net" + }, + { + "name": "Franck Lefevre", + "homepage": "https://rootslabs.net" }, { - "name": "psr/simple-cache", - "version": "3.0.0", - "version_normalized": "3.0.0.0", - "source": { - "type": "git", - "url": "https://github.com/php-fig/simple-cache.git", - "reference": "764e0b3939f5ca87cb904f570ef9be2d78a07865" - }, - "dist": { - "type": "zip", - "url": "https://api.github.com/repos/php-fig/simple-cache/zipball/764e0b3939f5ca87cb904f570ef9be2d78a07865", - "reference": "764e0b3939f5ca87cb904f570ef9be2d78a07865", - "shasum": "" - }, - "require": { - "php": ">=8.0.0" - }, - "time": "2021-10-29T13:26:27+00:00", - "type": "library", - "extra": { - "branch-alias": { - "dev-master": "3.0.x-dev" - } - }, - "installation-source": "dist", - "autoload": { - "psr-4": { - "Psr\\SimpleCache\\": "src/" - } - }, - "notification-url": "https://packagist.org/downloads/", - "license": [ - "MIT" - ], - "authors": [ - { - "name": "PHP-FIG", - "homepage": "https://www.php-fig.org/" - } - ], - "description": "Common interfaces for simple caching", - "keywords": [ - "cache", - "caching", - "psr", - "psr-16", - "simple-cache" - ], - "support": { - "source": "https://github.com/php-fig/simple-cache/tree/3.0.0" - }, - "install-path": "../psr/simple-cache" + "name": "Erik Tilt" + }, + { + "name": "Adrien Crivelli" + }, + { + "name": "Owen Leibman" + } + ], + "description": "PHPSpreadsheet - Read, Create and Write Spreadsheet documents in PHP - Spreadsheet engine", + "homepage": "https://github.com/PHPOffice/PhpSpreadsheet", + "keywords": [ + "OpenXML", + "excel", + "gnumeric", + "ods", + "php", + "spreadsheet", + "xls", + "xlsx" + ], + "support": { + "issues": "https://github.com/PHPOffice/PhpSpreadsheet/issues", + "source": "https://github.com/PHPOffice/PhpSpreadsheet/tree/5.10.0" + }, + "install-path": "../phpoffice/phpspreadsheet" + }, + { + "name": "psr/simple-cache", + "version": "3.0.0", + "version_normalized": "3.0.0.0", + "source": { + "type": "git", + "url": "https://github.com/php-fig/simple-cache.git", + "reference": "764e0b3939f5ca87cb904f570ef9be2d78a07865" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/php-fig/simple-cache/zipball/764e0b3939f5ca87cb904f570ef9be2d78a07865", + "reference": "764e0b3939f5ca87cb904f570ef9be2d78a07865", + "shasum": "" + }, + "require": { + "php": ">=8.0.0" + }, + "time": "2021-10-29T13:26:27+00:00", + "type": "library", + "extra": { + "branch-alias": { + "dev-master": "3.0.x-dev" + } + }, + "installation-source": "dist", + "autoload": { + "psr-4": { + "Psr\\SimpleCache\\": "src/" + } + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "MIT" + ], + "authors": [ + { + "name": "PHP-FIG", + "homepage": "https://www.php-fig.org/" } - ], - "dev": true, - "dev-package-names": [] + ], + "description": "Common interfaces for simple caching", + "keywords": [ + "cache", + "caching", + "psr", + "psr-16", + "simple-cache" + ], + "support": { + "source": "https://github.com/php-fig/simple-cache/tree/3.0.0" + }, + "install-path": "../psr/simple-cache" + } + ], + "dev": false, + "dev-package-names": [] } diff --git a/vendor/composer/installed.php b/vendor/composer/installed.php index dbb12392..084f788b 100644 --- a/vendor/composer/installed.php +++ b/vendor/composer/installed.php @@ -3,17 +3,17 @@ 'name' => '__root__', 'pretty_version' => 'dev-master', 'version' => 'dev-master', - 'reference' => '98b2bc3a78ba746076a6e597f1a8efc32f7c9343', + 'reference' => null, 'type' => 'library', 'install_path' => __DIR__ . '/../../', 'aliases' => array(), - 'dev' => true, + 'dev' => false, ), 'versions' => array( '__root__' => array( 'pretty_version' => 'dev-master', 'version' => 'dev-master', - 'reference' => '98b2bc3a78ba746076a6e597f1a8efc32f7c9343', + 'reference' => null, 'type' => 'library', 'install_path' => __DIR__ . '/../../', 'aliases' => array(), @@ -56,9 +56,9 @@ 'dev_requirement' => false, ), 'phpoffice/phpspreadsheet' => array( - 'pretty_version' => '5.8.0', - 'version' => '5.8.0.0', - 'reference' => '01964d92536edf1a3a874b9580a52824bebf6fbb', + 'pretty_version' => '5.10.0', + 'version' => '5.10.0.0', + 'reference' => 'eb18727acf6b1f4cc67145a52ab04f9fd4c28d53', 'type' => 'library', 'install_path' => __DIR__ . '/../phpoffice/phpspreadsheet', 'aliases' => array(), diff --git a/vendor/phpoffice/phpspreadsheet/CHANGELOG.md b/vendor/phpoffice/phpspreadsheet/CHANGELOG.md index 148625aa..049eefd9 100644 --- a/vendor/phpoffice/phpspreadsheet/CHANGELOG.md +++ b/vendor/phpoffice/phpspreadsheet/CHANGELOG.md @@ -3,9 +3,13 @@ All notable changes to this project will be documented in this file. The format is based on [Keep a Changelog](https://keepachangelog.com) -and this project adheres to [Semantic Versioning](https://semver.org). Thia is always true of the master branch. Some earlier branches remain supported and security fixes are applied to them; if the security fix represents a breaking change, it may have to be applied as a minor or patch version. +and this project adheres to [Semantic Versioning](https://semver.org). This is always true of the master branch. +Dropping support for EOL versions of PHP will not be considered +a breaking change. -## TBD - 5.9.0 +Some earlier branches remain supported and security fixes are applied to them; if the security fix represents a breaking change, it may have to be applied as a minor or patch version. + +## TBD - 5.11.0 ### Added @@ -31,6 +35,61 @@ and this project adheres to [Semantic Versioning](https://semver.org). Thia is a - Nothing yet. +## 2026-09-15 - 5.10.0 + +### Added + +- XLSX password-to-open encryption and decryption using Office Agile encryption. [Issue #3878](https://github.com/PHPOffice/PhpSpreadsheet/issues/3878) [PR #4975](https://github.com/PHPOffice/PhpSpreadsheet/pull/4975) [PR #4988](https://github.com/PHPOffice/PhpSpreadsheet/pull/4988) +- Support for Excel sparklines (line, column, and win/loss) in Xlsx reader and writer. [Issue #4941](https://github.com/PHPOffice/PhpSpreadsheet/issues/4941) +- Read-only object model for Pivot Tables. Existing pivot tables in an Xlsx file are now parsed into `Worksheet\PivotTable\PivotTable` objects (name, location, source cache definition, and row/column/page/data field layout), accessible via `Worksheet::getPivotTableCollection()` / `getPivotTableByName()`. Pivot tables (their tables, caches and records) are now also preserved through an Xlsx load/save round-trip instead of being silently dropped. [Issue #4534](https://github.com/PHPOffice/PhpSpreadsheet/issues/4534) + +### Changed + +- Performance: avoid `Worksheet::getStyle()` on every `Cell::setValueExplicit()` unless quote-prefix must change. On a dense 40k-cell populate+save microbenchmark this cut wall time by ~5%. [PR #4958](https://github.com/PHPOffice/PhpSpreadsheet/pull/4958) +- Infrastructure changes for documentation. [PR #4973](https://github.com/PHPOffice/PhpSpreadsheet/pull/4973) + +### Fixed + +- Security patches. +- Xls Writer now creates conformant CFB/DIFAT metadata at FAT-sector boundaries. [Issue #4811](https://github.com/PHPOffice/PhpSpreadsheet/issues/4811) [PR #4983](https://github.com/PHPOffice/PhpSpreadsheet/pull/4983) +- Ods Reader/Writer Drawings. [Issue #4809](https://github.com/PHPOffice/PhpSpreadsheet/issues/4809) [PR #4956](https://github.com/PHPOffice/PhpSpreadsheet/pull/4956) +- Ods Writer no longer converts cell references or commas inside string literals, so `="THIS IS E1"` is written unchanged instead of as `="THIS IS [.E1]"`. [Issue #4454](https://github.com/PHPOffice/PhpSpreadsheet/issues/4454) [PR #4962](https://github.com/PHPOffice/PhpSpreadsheet/pull/4962) +- Ods Reader/Writer slight improvement for Date styles. [PR #4960](https://github.com/PHPOffice/PhpSpreadsheet/pull/4960) +- BETAINV/BETA.INV no longer abandons its search when the Beta CDF underflows to zero (wrong results for alpha above about 1080). [PR #4954](https://github.com/PHPOffice/PhpSpreadsheet/pull/4954) +- GAMMA.INV, the GAMMA.DIST/CHISQ.DIST/F.DIST densities, and GAMMALN no longer fail or return wrong results for large shape parameters / degrees of freedom. [PR #4953](https://github.com/PHPOffice/PhpSpreadsheet/pull/4953) +- GAMMAINV/GAMMA.INV no longer clamps upper-tail quantiles beyond alpha*beta*5. [PR #4946](https://github.com/PHPOffice/PhpSpreadsheet/pull/4946) +- Correct incomplete gamma convergence for GAMMA.DIST/CHISQ.DIST family (wrong once the series argument reached ~32). [PR #4945](https://github.com/PHPOffice/PhpSpreadsheet/pull/4945) +- Fix problem with VLOOKUP and whole-column ranges. [Issue #4969](https://github.com/PHPOffice/PhpSpreadsheet/issues/4969) [PR #4967](https://github.com/PHPOffice/PhpSpreadsheet/pull/4967) +- Problem with Xlsx Writer and header-row table. [PR #4968](https://github.com/PHPOffice/PhpSpreadsheet/pull/4968) +- Throw when Ods Reader encounters invalid Xml. [PR #4986](https://github.com/PHPOffice/PhpSpreadsheet/pull/4986) +- Update Sheetname in Charts when Sheetname changes. [Issue #744](https://github.com/PHPOffice/PhpSpreadsheet/issues/744) [PR #4984](https://github.com/PHPOffice/PhpSpreadsheet/pull/4984) + +## 2026-07-12 - 5.9.0 + +### Removed + +- **Drop support for PHP 8.1**, according to [our published guidelines](https://phpspreadsheet.readthedocs.io/en/latest/#php-version-support). [PR #4907](https://github.com/PHPOffice/PhpSpreadsheet/pull/4907) + +### Added + +- Navigate Cell as Cursor. [Issue #863](https://github.com/PHPOffice/PhpSpreadsheet/issues/863) [PR #4909](https://github.com/PHPOffice/PhpSpreadsheet/pull/4909) +- Chart DataTables. [Issue #413](https://github.com/PHPOffice/PhpSpreadsheet/issues/413) [PR #4911](https://github.com/PHPOffice/PhpSpreadsheet/pull/4911) +- Permit Ignoring "Misleading Format" Tag. [PR #4914](https://github.com/PHPOffice/PhpSpreadsheet/pull/4914) + +### Changed + +- Restructure parsing logic in Reader/Xlsx. [PR #4830](https://github.com/PHPOffice/PhpSpreadsheet/pull/4830) + +### Fixed + +- Small improvement for Radar Charts. [Issue #661](https://github.com/PHPOffice/PhpSpreadsheet/issues/661) [PR #4908](https://github.com/PHPOffice/PhpSpreadsheet/pull/4908) +- Allow Use of Multiple Ranges When Setting Styles. [Issue #411](https://github.com/PHPOffice/PhpSpreadsheet/issues/411) [PR #4910](https://github.com/PHPOffice/PhpSpreadsheet/pull/4910) +- Small change to Writer Html. [Issue #434](https://github.com/PHPOffice/PhpSpreadsheet/issues/434) [PR #4912](https://github.com/PHPOffice/PhpSpreadsheet/pull/4912) +- Avoid hard-coding some chart Xml attributes. [PR #4915](https://github.com/PHPOffice/PhpSpreadsheet/pull/4915) +- Readers should directly access readFilter. [PR #4919](https://github.com/PHPOffice/PhpSpreadsheet/pull/4919) +- Very minor changes to Worksheet, Reader/Xlsx, and Worksheet/AutoFilter. [Issue #4917](https://github.com/PHPOffice/PhpSpreadsheet/issues/4917) [PR #4926](https://github.com/PHPOffice/PhpSpreadsheet/pull/4926) +- Consistent HighestRow/Column after row/columnDelete. [Issue #943](https://github.com/PHPOffice/PhpSpreadsheet/issues/943) [PR #4925](https://github.com/PHPOffice/PhpSpreadsheet/pull/4925) + ## 2026-06-06 - 5.8.0 ### Security Note @@ -69,18 +128,6 @@ and this project adheres to [Semantic Versioning](https://semver.org). Thia is a - XLOOKUP function. [Issue #1453](https://github.com/PHPOffice/PhpSpreadsheet/issues/1453) [PR #4844](https://github.com/PHPOffice/PhpSpreadsheet/pull/4844) - Introduction of a benchmark test suite, independent of the default unit test suite. Users can use it as a template for experimenting and making decisions concerning performance. [PR #4824](https://github.com/PHPOffice/PhpSpreadsheet/pull/4824) -### Removed - -- Nothing yet. - -### Changed - -- Nothing yet. - -### Moved - -- Nothing yet. - ### Deprecated - Collection/Cells::MAX_COLUMN_ID - use Cell/AddressRange::MAX_COLUMN_INT. @@ -411,18 +458,6 @@ and this project adheres to [Semantic Versioning](https://semver.org). Thia is a - Worksheet::getProtectedCells - use getProtectedCellRanges instead. - Writer/Html::isMpdf property - use instanceof Mpdf instead. -### Changed - -- Nothing yet. - -### Moved - -- Nothing yet. - -### Deprecated - -- Nothing yet. - ### Fixed - Xls writer Parser Mishandling True/False Argument. [Issue #4331](https://github.com/PHPOffice/PhpSpreadsheet/issues/4331) [PR #4333](https://github.com/PHPOffice/PhpSpreadsheet/pull/4333) @@ -475,22 +510,6 @@ and this project adheres to [Semantic Versioning](https://semver.org). Thia is a ## 2024-12-08 - 3.6.0 -### Added - -- Nothing yet. - -### Changed - -- Nothing yet. - -### Moved - -- Nothing yet. - -### Deprecated - -- Nothing yet. - ### Fixed - Html Reader/Writer Better Handling of Booleans. [PR #4257](https://github.com/PHPOffice/PhpSpreadsheet/pull/4257) @@ -503,18 +522,10 @@ and this project adheres to [Semantic Versioning](https://semver.org). Thia is a ## 2024-11-22 - 3.5.0 -### Added - -- Nothing yet. - ### Changed - Settings::libXmlLoaderOptions is ignored. [PR #4233](https://github.com/PHPOffice/PhpSpreadsheet/pull/4233) -### Moved - -- Nothing yet. - ### Deprecated - Settings::setLibXmlLoaderOptions() and Settings::getLibXmlLoaderOptions() are no longer needed - no replacement. @@ -547,10 +558,6 @@ and this project adheres to [Semantic Versioning](https://semver.org). Thia is a - Worksheet::getProtectedCells was deprecated in release 2, but was not properly documented, and not removed in release 3. Use getProtectedCellRanges instead. - Writer/Html::isMpdf property was deprecated in release 2, but was not properly documented, and not removed in release 3. Use instanceof Mpdf instead. -### Moved - -- Nothing yet. - ### Fixed - Xls Writer Condtional Rules Applied to Whole Rows or Columns. [Issue #3185](https://github.com/PHPOffice/PhpSpreadsheet/issues/3185) [PR #4152](https://github.com/PHPOffice/PhpSpreadsheet/pull/4152) @@ -582,10 +589,6 @@ and this project adheres to [Semantic Versioning](https://semver.org). Thia is a - Currency and Accounting Wizards are changed to act like Excel, and a new CurrencyBase Wizard is added for for non-Excel formats. [Issue #4125](https://github.com/PHPOffice/PhpSpreadsheet/issues/4125) [Issue #4124](https://github.com/PHPOffice/PhpSpreadsheet/issues/4124) [PR #4127](https://github.com/PHPOffice/PhpSpreadsheet/pull/4127) - Images will not be added to spreadsheet if they cannot be validated as images. -### Deprecated - -- Nothing yet. - ### Removed - The following items were deprecated in release 2 and are now removed. @@ -594,10 +597,6 @@ and this project adheres to [Semantic Versioning](https://semver.org). Thia is a - Calculation\Calculation::_translateFormulaToLocale (use method name translateFormulaToLocale without leading underscore). - Calculation\Calculation::_translateFormulaToEnglish (use method name translateFormulaToEnglish without leading underscore). -### Moved - -- Nothing yet. - ### Fixed - Several security patches. @@ -607,22 +606,6 @@ and this project adheres to [Semantic Versioning](https://semver.org). Thia is a ## 2024-08-07 - 2.2.2 -### Added - -- Nothing yet. - -### Changed - -- Nothing yet. - -### Deprecated - -- Nothing yet. - -### Moved - -- Nothing yet. - ### Fixed - Html Reader Preserve Unicode Whitespace. [Issue #1284](https://github.com/PHPOffice/PhpSpreadsheet/issues/1284) [PR #4106](https://github.com/PHPOffice/PhpSpreadsheet/pull/4106) @@ -661,10 +644,6 @@ and this project adheres to [Semantic Versioning](https://semver.org). Thia is a - Writer\Xls\Style\ColorMap is no longer needed. -### Moved - -- Nothing - ### Fixed - Incorrect Reader CSV with BOM. [Issue #4028](https://github.com/PHPOffice/PhpSpreadsheet/issues/4028) [PR #4029](https://github.com/PHPOffice/PhpSpreadsheet/pull/4029) @@ -699,18 +678,10 @@ and this project adheres to [Semantic Versioning](https://semver.org). Thia is a - Default Style Alignment Property (workaround for bug in non-Excel spreadsheet apps) [Issue #3918](https://github.com/PHPOffice/PhpSpreadsheet/issues/3918) [PR #3924](https://github.com/PHPOffice/PhpSpreadsheet/pull/3924) - Additional Support for Date/Time Styles [PR #3939](https://github.com/PHPOffice/PhpSpreadsheet/pull/3939) -### Changed - -- Nothing - ### Deprecated - Reader/Xml trySimpleXMLLoadString should not have had public visibility, and will be removed. -### Removed - -- Nothing - ### Fixed - IF Empty Arguments. [Issue #3875](https://github.com/PHPOffice/PhpSpreadsheet/issues/3875) [Issue #2146](https://github.com/PHPOffice/PhpSpreadsheet/issues/2146) [PR #3879](https://github.com/PHPOffice/PhpSpreadsheet/pull/3879) @@ -772,10 +743,6 @@ and this project adheres to [Semantic Versioning](https://semver.org). Thia is a - Functions `_translateFormulaToLocale` and `_translateFormulaEnglish` are replaced by versions without leading underscore. [PR #3828](https://github.com/PHPOffice/PhpSpreadsheet/pull/3828) -### Removed - -- Nothing - ### Fixed - Take advantage of mitoteam/jpgraph Extended mode to enable rendering of more graphs. [PR #3603](https://github.com/PHPOffice/PhpSpreadsheet/pull/3603) @@ -843,14 +810,6 @@ and this project adheres to [Semantic Versioning](https://semver.org). Thia is a - Allow `CellRange` and `CellAddress` objects for the `range` argument in the `rangeToArray()` method. [PR #3494](https://github.com/PHPOffice/PhpSpreadsheet/pull/3494) - Stock charts will now read and reproduce `upDownBars` and subsidiary tags; these were previously ignored on read and hard-coded on write. [PR #3515](https://github.com/PHPOffice/PhpSpreadsheet/pull/3515) -### Deprecated - -- Nothing - -### Removed - -- Nothing - ### Fixed - Updates Cell formula absolute ranges/references, and Defined Name absolute ranges/references when inserting/deleting rows/columns. [Issue #3368](https://github.com/PHPOffice/PhpSpreadsheet/issues/3368) [PR #3402](https://github.com/PHPOffice/PhpSpreadsheet/pull/3402) @@ -908,10 +867,6 @@ and this project adheres to [Semantic Versioning](https://semver.org). Thia is a - Rationalisation of Pre-defined Currency Format Masks [PR #3377](https://github.com/PHPOffice/PhpSpreadsheet/pull/3377) -### Removed - -- Nothing - ### Fixed - Calculation Engine doesn't evaluate Defined Name when default cell A1 is quote-prefixed [Issue #3335](https://github.com/PHPOffice/PhpSpreadsheet/issues/3335) [PR #3336](https://github.com/PHPOffice/PhpSpreadsheet/pull/3336) @@ -925,22 +880,6 @@ and this project adheres to [Semantic Versioning](https://semver.org). Thia is a ## 1.27.1 - 2023-02-08 -### Added - -- Nothing - -### Changed - -- Nothing - -### Deprecated - -- Nothing - -### Removed - -- Nothing - ### Fixed - Fix Composer --dev dependency issue with dealerdirect/phpcodesniffer-composer-installer renaming their `master` branch to `main` @@ -955,14 +894,6 @@ and this project adheres to [Semantic Versioning](https://semver.org). Thia is a - Support for Structured References in the Calculation Engine [PR #3261](https://github.com/PHPOffice/PhpSpreadsheet/pull/3261) - Limited Support for Form Controls [PR #3130](https://github.com/PHPOffice/PhpSpreadsheet/pull/3130) [Issue #2396](https://github.com/PHPOffice/PhpSpreadsheet/issues/2396) [Issue #1770](https://github.com/PHPOffice/PhpSpreadsheet/issues/1770) [Issue #2388](https://github.com/PHPOffice/PhpSpreadsheet/issues/2388) [Issue #2904](https://github.com/PHPOffice/PhpSpreadsheet/issues/2904) [Issue #2661](https://github.com/PHPOffice/PhpSpreadsheet/issues/2661) -### Changed - -- Nothing - -### Deprecated - -- Nothing - ### Removed - Shared/JAMA is removed. [PR #3260](https://github.com/PHPOffice/PhpSpreadsheet/pull/3260) @@ -988,10 +919,6 @@ and this project adheres to [Semantic Versioning](https://semver.org). Thia is a - Xlsx Reader support for Pivot Tables [PR #2829](https://github.com/PHPOffice/PhpSpreadsheet/pull/2829) - Permit Date/Time Entered on Spreadsheet to be calculated as Float [Issue #1416](https://github.com/PHPOffice/PhpSpreadsheet/issues/1416) [PR #3121](https://github.com/PHPOffice/PhpSpreadsheet/pull/3121) -### Changed - -- Nothing - ### Deprecated - Direct update of Calculation::suppressFormulaErrors is replaced with setter. @@ -999,10 +926,6 @@ and this project adheres to [Semantic Versioning](https://semver.org). Thia is a - ExcelError public static variable errorCodes replaced with constant ERROR_CODES. - NumberFormat constant FORMAT_DATE_YYYYMMDD2 replaced with existing identical FORMAT_DATE_YYYYMMDD. -### Removed - -- Nothing - ### Fixed - Fixed handling for `_xlws` prefixed functions from Office365 [Issue #3245](https://github.com/PHPOffice/PhpSpreadsheet/issues/3245) [PR #3247](https://github.com/PHPOffice/PhpSpreadsheet/pull/3247) @@ -1031,22 +954,6 @@ and this project adheres to [Semantic Versioning](https://semver.org). Thia is a ## 1.25.2 - 2022-09-25 -### Added - -- Nothing - -### Changed - -- Nothing - -### Deprecated - -- Nothing - -### Removed - -- Nothing - ### Fixed - Composer dependency clash with ezyang/htmlpurifier @@ -1079,10 +986,6 @@ and this project adheres to [Semantic Versioning](https://semver.org). Thia is a - Misspelled Properties::LINE_STYLE_DASH_SQUERE_DOT deprecated in favor of LINE_STYLE_DASH_SQUARE_DOT. - Clone not permitted for Spreadsheet. Spreadsheet->copy() can be used instead. -### Removed - -- Nothing - ### Fixed - Fix update to defined names when inserting/deleting rows/columns [Issue #3076](https://github.com/PHPOffice/PhpSpreadsheet/issues/3076) [PR #3077](https://github.com/PHPOffice/PhpSpreadsheet/pull/3077) @@ -1111,18 +1014,6 @@ and this project adheres to [Semantic Versioning](https://semver.org). Thia is a - Support for SimpleCache Interface versions 1.0, 2.0 and 3.0 - Add Chart Axis Option textRotation [Issue #2705](https://github.com/PHPOffice/PhpSpreadsheet/issues/2705) [PR #2940](https://github.com/PHPOffice/PhpSpreadsheet/pull/2940) -### Changed - -- Nothing - -### Deprecated - -- Nothing - -### Removed - -- Nothing - ### Fixed - Fix Encoding issue with Html reader (PHP 8.2 deprecation for mb_convert_encoding) [Issue #2942](https://github.com/PHPOffice/PhpSpreadsheet/issues/2942) [PR #2943](https://github.com/PHPOffice/PhpSpreadsheet/pull/2943) @@ -1163,14 +1054,6 @@ Note that this will be the last 1.x branch release before the 2.x release. We wi See [the Discussion section on github](https://github.com/PHPOffice/PhpSpreadsheet/discussions/2821) for details of performance across versions - Improved performance for removing rows/columns from a worksheet -### Deprecated - -- Nothing - -### Removed - -- Nothing - ### Fixed - Xls Reader resolving absolute named ranges to relative ranges [Issue #2826](https://github.com/PHPOffice/PhpSpreadsheet/issues/2826) [PR #2827](https://github.com/PHPOffice/PhpSpreadsheet/pull/2827) @@ -1250,10 +1133,6 @@ Note that this will be the last 1.x branch release before the 2.x release. We wi This change provides more consistency in the methods (not every "by cell address" method has an equivalent "byColumnAndRow" method); and the "by cell address" methods often provide more flexibility, such as allowing a range of cells, or referencing them by passing the defined name of a named range as the argument. -### Removed - -- Nothing - ### Fixed - Make allowance for the AutoFilter dropdown icon in the first row of an Autofilter range when using Autosize columns. [Issue #2413](https://github.com/PHPOffice/PhpSpreadsheet/issues/2413) [PR #2754](https://github.com/PHPOffice/PhpSpreadsheet/pull/2754) @@ -1321,14 +1200,6 @@ Note that this will be the last 1.x branch release before the 2.x release. We wi - Extract some methods from the Calculation Engine into dedicated classes [#2537](https://github.com/PHPOffice/PhpSpreadsheet/issues/2537) - Eliminate calls to `flattenSingleValue()` that are no longer required when we're checking for array values as arguments [#2590](https://github.com/PHPOffice/PhpSpreadsheet/issues/2590) -### Deprecated - -- Nothing - -### Removed - -- Nothing - ### Fixed - Fixed `ReferenceHelper@insertNewBefore` behavior when removing column before last column with null value [PR #2541](https://github.com/PHPOffice/PhpSpreadsheet/pull/2541) @@ -1363,14 +1234,6 @@ Note that this will be the last 1.x branch release before the 2.x release. We wi - Xlsx Writer will evaluate AutoFilter only if it is as yet unevaluated, or has changed since it was last evaluated [PR #2414](https://github.com/PHPOffice/PhpSpreadsheet/pull/2414) -### Deprecated - -- Nothing - -### Removed - -- Nothing - ### Fixed - Rounding in `NumberFormatter` [Issue #2385](https://github.com/PHPOffice/PhpSpreadsheet/issues/2385) [PR #2399](https://github.com/PHPOffice/PhpSpreadsheet/pull/2399) @@ -1401,14 +1264,6 @@ Note that this will be the last 1.x branch release before the 2.x release. We wi - Drop support for PHP 7.2, according to https://phpspreadsheet.readthedocs.io/en/latest/#php-version-support - Use native typing for objects that were already documented as such -### Deprecated - -- Nothing - -### Removed - -- Nothing - ### Fixed - Fixed null conversation for strToUpper [#2292](https://github.com/PHPOffice/PhpSpreadsheet/issues/2292) @@ -1442,18 +1297,10 @@ Note that this will be the last 1.x branch release before the 2.x release. We wi - Ability to stream to an Amazon S3 bucket [Issue #2249](https://github.com/PHPOffice/PhpSpreadsheet/issues/2249) - Provided a Size Helper class to validate size values (pt, px, em) [PR #1694](https://github.com/PHPOffice/PhpSpreadsheet/pull/1694) -### Changed - -- Nothing. - ### Deprecated - PHP 8.1 will deprecate auto_detect_line_endings. As a result of this change, Csv Reader using some release after PHP8.1 will no longer be able to handle a Csv with Mac line endings. -### Removed - -- Nothing. - ### Fixed - Unexpected format in Xlsx Timestamp [Issue #2331](https://github.com/PHPOffice/PhpSpreadsheet/issues/2331) [PR #2332](https://github.com/PHPOffice/PhpSpreadsheet/pull/2332) @@ -1576,10 +1423,6 @@ Note that this will be the last 1.x branch release before the 2.x release. We wi This makes the logic in these classes easier to maintain; and will reduce the memory footprint required to execute formulae when calling these functions. -### Removed - -- Nothing. - ### Fixed - Avoid Duplicate Titles When Reading Multiple HTML Files.[Issue #1823](https://github.com/PHPOffice/PhpSpreadsheet/issues/1823) [PR #1829](https://github.com/PHPOffice/PhpSpreadsheet/pull/1829) @@ -1609,10 +1452,6 @@ Note that this will be the last 1.x branch release before the 2.x release. We wi - All Excel Function implementations in `Calculation\Database`, `Calculation\DateTime`, `Calculation\Engineering`, `Calculation\Financial`, `Calculation\Logical`, `Calculation\LookupRef`, `Calculation\MathTrig`, `Calculation\Statistical`, `Calculation\TextData` and `Calculation\Web` have been moved to dedicated classes for individual functions or groups of related functions. See the docblocks against all the deprecated methods for details of the new methods to call instead. At some point, these old classes will be deleted. -### Removed - -- Nothing. - ### Fixed - Fixed issue with absolute path in worksheets' Target [PR #1769](https://github.com/PHPOffice/PhpSpreadsheet/pull/1769) @@ -1672,10 +1511,6 @@ Note that this will be the last 1.x branch release before the 2.x release. We wi - **IMPORTANT NOTE:** This Introduces a **BC break** in the handling of named ranges. Previously, a named range cell reference of `B2` would be treated identically to a named range cell reference of `$B2` or `B$2` or `$B$2` because the calculation engine treated then all as absolute references. These changes "fix" that, so the calculation engine now handles relative references in named ranges correctly. This change that resolves previously incorrect behaviour in the calculation may affect users who have dynamically defined named ranges using relative references when they should have used absolute references. -### Removed - -- Nothing. - ### Fixed - PrintArea causes exception [#1544](https://github.com/phpoffice/phpspreadsheet/pull/1544) @@ -1686,10 +1521,6 @@ Note that this will be the last 1.x branch release before the 2.x release. We wi ## 1.14.1 - 2020-07-19 -### Added - -- nothing - ### Fixed - WEBSERVICE is HTTP client agnostic and must be configured via `Settings::setHttpClient()` [#1562](https://github.com/PHPOffice/PhpSpreadsheet/issues/1562) diff --git a/vendor/phpoffice/phpspreadsheet/CONTRIBUTING.md b/vendor/phpoffice/phpspreadsheet/CONTRIBUTING.md index d7d33996..a8d92371 100644 --- a/vendor/phpoffice/phpspreadsheet/CONTRIBUTING.md +++ b/vendor/phpoffice/phpspreadsheet/CONTRIBUTING.md @@ -45,5 +45,5 @@ This makes it easier to see exactly what is being tested when reviewing the PR. > **Note:** Tagged releases are made from the `master` branch. Only in an emergency should a tagged release be made from the `release` branch. (i.e. cherry-picked hot-fixes.) However, there are 4 branches which have been updated to apply security patches, and those may be tagged if future security updates are needed. - 1.30.x (no further updates aside from security patches, including code changes needed for Php 8.5 compatibility) - 2.1.x (no further updates aside from security patches, including code changes needed for Php 8.5 compatibility) -- 2.4.x +- 2.4.x (no further updates aside from security patches) - 3.10.x diff --git a/vendor/phpoffice/phpspreadsheet/README.md b/vendor/phpoffice/phpspreadsheet/README.md index 7685ba94..1a7488ff 100644 --- a/vendor/phpoffice/phpspreadsheet/README.md +++ b/vendor/phpoffice/phpspreadsheet/README.md @@ -16,8 +16,9 @@ This is the master branch, and is maintained for security and bug fixes. LTS: For maintained branches, support for PHP versions will only be maintained for a period of six months beyond the [end of life](https://www.php.net/supported-versions) of that PHP version. +Dropping support for versions after that date will not be considered a breaking change. -Currently the required PHP minimum version is PHP __8.1__, and we [will support that version](https://www.php.net/supported-versions.php) until 30th June 2026. +Currently the required PHP minimum version is PHP __8.2__, and we [will support that version](https://www.php.net/supported-versions.php) until 30th June 2027. See the `composer.json` for other requirements. diff --git a/vendor/phpoffice/phpspreadsheet/composer.json b/vendor/phpoffice/phpspreadsheet/composer.json index 0825a5b8..19cbcc0b 100644 --- a/vendor/phpoffice/phpspreadsheet/composer.json +++ b/vendor/phpoffice/phpspreadsheet/composer.json @@ -13,7 +13,7 @@ ], "config": { "platform": { - "php": "8.1.99" + "php": "8.2.99" }, "process-timeout": 600, "sort-packages": true, @@ -69,7 +69,7 @@ ] }, "require": { - "php": "^8.1", + "php": "^8.2", "ext-ctype": "*", "ext-dom": "*", "ext-fileinfo": "*", @@ -92,6 +92,7 @@ }, "require-dev": { "ext-intl": "*", + "ext-openssl": "*", "dealerdirect/phpcodesniffer-composer-installer": "dev-main", "dompdf/dompdf": "^2.0 || ^3.0", "friendsofphp/php-cs-fixer": "^3.2", @@ -101,12 +102,13 @@ "phpstan/phpstan": "^1.1 || ^2.0", "phpstan/phpstan-deprecation-rules": "^1.0 || ^2.0", "phpstan/phpstan-phpunit": "^1.0 || ^2.0", - "phpunit/phpunit": "^10.5", + "phpunit/phpunit": "^10.5 || ^11.0", "squizlabs/php_codesniffer": "^3.7", - "tecnickcom/tcpdf": "^6.5" + "tecnickcom/tcpdf": ">=6.8.0 <7.0.0" }, "suggest": { "ext-intl": "PHP Internationalization Functions, required for NumberFormat Wizard and StringHelper::setLocale()", + "ext-openssl": "Handline Agile-encrypted Xlsx spreadsheets", "mpdf/mpdf": "Option for rendering PDF with PDF Writer", "dompdf/dompdf": "Option for rendering PDF with PDF Writer", "tecnickcom/tcpdf": "Option for rendering PDF with PDF Writer", diff --git a/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Calculation.php b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Calculation.php index 3ac8d334..faaf4407 100644 --- a/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Calculation.php +++ b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Calculation.php @@ -554,7 +554,7 @@ public function calculateCellValue(?Cell $cell = null, bool $resetLog = true): m $value ); } - $result = self::unwrapResult($this->_calculateFormulaValue($value, $cell->getCoordinate(), $cell)); //* @phpstan-ignore-line + $result = self::unwrapResult($this->_calculateFormulaValue($value, $cell->getCoordinate(), $cell)); //* @phpstan-ignore argument.type ($value can be mixed not string) if ($this->spreadsheet === null) { throw new Exception('null spreadsheet in calculateCellValue'); } @@ -574,7 +574,7 @@ public function calculateCellValue(?Cell $cell = null, bool $resetLog = true): m $cellAddress = array_pop($this->cellStack); } if ($this->spreadsheet !== null && is_array($cellAddress) && array_key_exists('sheet', $cellAddress)) { - $sheetName = $cellAddress['sheet'] ?? null; + $sheetName = $cellAddress['sheet']; $testSheet = is_string($sheetName) ? $this->spreadsheet->getSheetByName($sheetName) : null; if ($testSheet !== null && array_key_exists('cell', $cellAddress)) { /** @var array{cell: string} $cellAddress */ @@ -638,6 +638,8 @@ public function parseFormula(string $formula): array|bool // Cache the result when caching is enabled (clear cache if it exceeds the maximum size) if ($this->formulaTokenCacheMaxSize > 0) { + // Phpstan says if condition is always false, + // but coverage report says next statement is covered. if (count($this->formulaTokenCache) >= $this->formulaTokenCacheMaxSize) { $this->formulaTokenCache = []; } @@ -987,7 +989,7 @@ private function showValue(mixed $value): mixed $pad = $rpad = ', '; foreach ($value as $row) { if (is_array($row)) { - $returnMatrix[] = implode($pad, array_map([$this, 'showValue'], $row)); // @phpstan-ignore-line + $returnMatrix[] = implode($pad, array_map([$this, 'showValue'], $row)); // @phpstan-ignore argument.type (array_map can theoretically return array not array) $rpad = '; '; } else { $returnMatrix[] = $this->showValue($row); @@ -1389,7 +1391,7 @@ private function internalParseFormula(string $formula, ?Cell $cell = null): bool // do we now have a function/variable/number? $expectingOperator = true; $expectingOperand = false; - $val = $match[1] ?? ''; //* @phpstan-ignore-line + $val = $match[1] ?? ''; $length = strlen($val); if (preg_match('/^' . self::CALCULATION_REGEXP_FUNCTION . '$/miu', $val, $matches)) { @@ -1542,7 +1544,7 @@ private function internalParseFormula(string $formula, ?Cell $cell = null): bool } elseif (ctype_alpha($val) && strlen($val) <= 3) { // Column range $stackItemType = 'Column Reference'; - $endRowColRef = ($refSheet !== null) ? $refSheet->getHighestDataRow($val) : AddressRange::MAX_ROW; // Max 1,048,576 rows for Excel2007 + $endRowColRef = ($refSheet !== null) ? $refSheet->getHighestDataRow() : AddressRange::MAX_ROW; // Max 1,048,576 rows for Excel2007 $val = "{$rangeWS2}{$val}{$endRowColRef}"; } $stackItemReference = $val; @@ -1568,7 +1570,7 @@ private function internalParseFormula(string $formula, ?Cell $cell = null): bool // unescape any apostrophes or double quotes in worksheet name $val = str_replace(["''", '""'], ["'", '"'], $val); $column = 'A'; - if (($testPrevOp !== null && $testPrevOp['value'] === ':') && $pCellParent !== null) { // @phpstan-ignore-line + if (($testPrevOp !== null && $testPrevOp['value'] === ':') && $pCellParent !== null) { // @phpstan-ignore booleanAnd.alwaysFalse (testPrevop must be non-null), booleanAnd.alwaysFalse (ditto), identical.alwaysFalse (ditto) $column = $pCellParent->getHighestDataColumn($val); } $val = "{$rowRangeReference[2]}{$column}{$rowRangeReference[7]}"; @@ -1582,7 +1584,7 @@ private function internalParseFormula(string $formula, ?Cell $cell = null): bool // unescape any apostrophes or double quotes in worksheet name $val = str_replace(["''", '""'], ["'", '"'], $val); $row = '1'; - if (($testPrevOp !== null && $testPrevOp['value'] === ':') && $pCellParent !== null) { // @phpstan-ignore-line + if (($testPrevOp !== null && $testPrevOp['value'] === ':') && $pCellParent !== null) { // @phpstan-ignore booleanAnd.alwaysFalse (testPrevOp must be non-null?), booleanAnd.alwaysFalse (ditto), identical.alwaysFalse (ditto) $row = $pCellParent->getHighestDataRow($val); } $val = "{$val}{$row}"; @@ -1733,7 +1735,7 @@ private function processTokenStack(false|array $tokens, ?string $cellID = null, foreach ($tokens as $tokenIdx => $tokenData) { /** @var mixed[] $tokenData */ $this->processingAnchorArray = false; - if ($tokenData['type'] === 'Cell Reference' && isset($tokens[$tokenIdx + 1]) && $tokens[$tokenIdx + 1]['type'] === 'Operand Count for Function ANCHORARRAY()') { //* @phpstan-ignore-line + if ($tokenData['type'] === 'Cell Reference' && isset($tokens[$tokenIdx + 1]) && $tokens[$tokenIdx + 1]['type'] === 'Operand Count for Function ANCHORARRAY()') { //* @phpstan-ignore offsetAccess.nonOffsetAccessible ($tokens might be mixed not array) $this->processingAnchorArray = true; } $token = $tokenData['value']; @@ -1835,7 +1837,7 @@ private function processTokenStack(false|array $tokens, ?string $cellID = null, return $this->raiseFormulaError($e->getMessage(), $e->getCode(), $e); } } - } elseif (!is_numeric($token) && !is_object($token) && isset($token, self::BINARY_OPERATORS[$token])) { //* @phpstan-ignore-line + } elseif (!is_numeric($token) && !is_object($token) && isset($token, self::BINARY_OPERATORS[$token])) { //* @phpstan-ignore offsetAccess.invalidOffset ($token is mixed) // if the token is a binary operator, pop the top two values off the stack, do the operation, and push the result back on the stack // We must have two operands, error if we don't $operand2Data = $stack->pop(); @@ -1953,7 +1955,7 @@ private function processTokenStack(false|array $tokens, ?string $cellID = null, if ($breakNeeded) { break; } - $cellRef = Coordinate::stringFromColumnIndex(min($oCol) + 1) . min($oRow) . ':' . Coordinate::stringFromColumnIndex(max($oCol) + 1) . max($oRow); // @phpstan-ignore-line + $cellRef = Coordinate::stringFromColumnIndex(min($oCol) + 1) . min($oRow) . ':' . Coordinate::stringFromColumnIndex(max($oCol) + 1) . max($oRow); if ($pCellParent !== null && $this->spreadsheet !== null) { $cellValue = $this->extractCellRange($cellRef, $this->spreadsheet->getSheetByName($sheet1), false); } else { @@ -2024,7 +2026,7 @@ private function processTokenStack(false|array $tokens, ?string $cellID = null, } elseif (Information\ErrorValue::isError($operand2)) { $result = $operand2; } else { - $result = str_replace('""', self::FORMULA_STRING_QUOTE, self::unwrapResult($operand1) . self::unwrapResult($operand2)); //* @phpstan-ignore-line + $result = str_replace('""', self::FORMULA_STRING_QUOTE, self::unwrapResult($operand1) . self::unwrapResult($operand2)); //* @phpstan-ignore binaryOp.invalid (unwrapresult can return mixed rather than string) $result = StringHelper::substring( $result, 0, @@ -2057,8 +2059,8 @@ private function processTokenStack(false|array $tokens, ?string $cellID = null, $this->debugLog->writeDebugLog('Evaluation Result is %s', $this->showTypeDetails($cellIntersect)); $stack->push('Error', ExcelError::null(), null); } else { - $cellRef = Coordinate::stringFromColumnIndex(min($oCol) + 1) . min($oRow) . ':' // @phpstan-ignore-line - . Coordinate::stringFromColumnIndex(max($oCol) + 1) . max($oRow); // @phpstan-ignore-line + $cellRef = Coordinate::stringFromColumnIndex(min($oCol) + 1) . min($oRow) . ':' // @phpstan-ignore argument.type ($oCol or $oRow might be empty), argument.type (ditto) + . Coordinate::stringFromColumnIndex(max($oCol) + 1) . max($oRow); // @phpstan-ignore argument.type ($oCol or $oRow might be empty), argument.type (ditto) $this->debugLog->writeDebugLog('Evaluation Result is %s', $this->showTypeDetails($cellIntersect)); $stack->push('Value', $cellIntersect, $cellRef); } @@ -2073,13 +2075,13 @@ private function processTokenStack(false|array $tokens, ?string $cellID = null, break; } - } elseif (($token === '~') || ($token === '%')) { // @phpstan-ignore-line + } elseif (($token === '~') || ($token === '%')) { // @phpstan-ignore booleanOr.alwaysFalse (phpstan says token can't be plain string), identical.alwaysFalse (ditto), identical.alwaysFalse (ditto) // if the token is a unary operator, pop one value off the stack, do the operation, and push it back on if (($arg = $stack->pop()) === null) { return $this->raiseFormulaError('Internal error - Operand value missing from stack'); } $arg = $arg['value']; - if ($token === '~') { // @phpstan-ignore-line + if ($token === '~') { // @phpstan-ignore identical.alwaysFalse (phpstan says token can't be plain string) $this->debugLog->writeDebugLog('Evaluating Negation of %s', $this->showValue($arg)); $multiplier = -1; } else { @@ -2253,7 +2255,7 @@ private function processTokenStack(false|array $tokens, ?string $cellID = null, $a = $argCount - $i - 1; if ( ($passByReference) - && (isset($phpSpreadsheetFunctions[$functionName]['passByReference'][$a])) //* @phpstan-ignore-line + && (isset($phpSpreadsheetFunctions[$functionName]['passByReference'][$a])) //* @phpstan-ignore offsetAccess.nonOffsetAccessible (possibly need to pass 2 arguments to isset) && ($phpSpreadsheetFunctions[$functionName]['passByReference'][$a]) ) { /** @var mixed[] $arg */ @@ -2320,7 +2322,7 @@ private function processTokenStack(false|array $tokens, ?string $cellID = null, if ($functionName !== 'MKMATRIX') { if ($this->debugLog->getWriteDebugLog()) { krsort($argArrayVals); - $this->debugLog->writeDebugLog('Evaluating %s ( %s )', self::localeFunc($functionName), implode(self::$localeArgumentSeparator . ' ', Functions::flattenArray($argArrayVals))); // @phpstan-ignore-line + $this->debugLog->writeDebugLog('Evaluating %s ( %s )', self::localeFunc($functionName), implode(self::$localeArgumentSeparator . ' ', Functions::flattenArray($argArrayVals))); // @phpstan-ignore argument.type (flattenArray returns array rather than array) } } @@ -2365,7 +2367,7 @@ private function processTokenStack(false|array $tokens, ?string $cellID = null, $branchStore[$storeKey] = self::EXCEL_CONSTANTS[$excelConstant]; } $this->debugLog->writeDebugLog('Evaluating Constant %s as %s', $excelConstant, $this->showTypeDetails(self::EXCEL_CONSTANTS[$excelConstant])); - } elseif ((is_numeric($token)) || ($token === null) || (is_bool($token)) || ($token == '') || ($token[0] == self::FORMULA_STRING_QUOTE) || ($token[0] == '#')) { //* @phpstan-ignore-line + } elseif ((is_numeric($token)) || ($token === null) || (is_bool($token)) || ($token == '') || ($token[0] == self::FORMULA_STRING_QUOTE) || ($token[0] == '#')) { //* @phpstan-ignore function.alreadyNarrowedType (phpstan says is_bool has argument of *NEVER*?), equal.alwaysFalse (ditto) /** @var array{type: string, reference: ?string} $tokenData */ $stack->push($tokenData['type'], $token, $tokenData['reference']); if (isset($storeKey)) { @@ -2491,7 +2493,7 @@ private function executeArrayComparison(mixed $operand1, mixed $operand2, string $r = $stack->pop(); $result[$x] = $r['value']; } - } elseif (is_array($operand2) && is_array($operand1)) { + } elseif (is_array($operand2) /*&& is_array($operand1)*/) { // Operand 1 and Operand 2 are both arrays if (!$recursingArrays) { self::checkMatrixOperands($operand1, $operand2, 2); @@ -2504,7 +2506,7 @@ private function executeArrayComparison(mixed $operand1, mixed $operand2, string $result[$x] = $r['value']; } } else { - throw new Exception('Neither operand is an arra'); + throw new Exception('Neither operand is an array'); } // Log the result details $this->debugLog->writeDebugLog('Comparison Evaluation Result is %s', $this->showTypeDetails($result)); diff --git a/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Database/DatabaseAbstract.php b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Database/DatabaseAbstract.php index 052b9f55..389464c4 100644 --- a/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Database/DatabaseAbstract.php +++ b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Database/DatabaseAbstract.php @@ -53,7 +53,7 @@ protected static function fieldExtract(array $database, mixed $field): ?int /** @var callable */ $callable = 'strtoupper'; - $fieldNames = array_map($callable, array_shift($database)); //* @phpstan-ignore-line + $fieldNames = array_map($callable, array_shift($database)); //* @phpstan-ignore argument.type (array_shift can return mixed not array?) if (is_numeric($field)) { $field = (int) $field - 1; if ($field < 0 || $field >= count($fieldNames)) { @@ -143,7 +143,7 @@ private static function buildQuery(array $criteriaNames, array $criteria): strin } $rowQuery = array_map( - fn ($rowValue): string => (count($rowValue) > 1) ? 'AND(' . implode(',', $rowValue) . ')' : ($rowValue[0] ?? ''), // @phpstan-ignore-line + fn ($rowValue): string => (count($rowValue) > 1) ? 'AND(' . implode(',', $rowValue) . ')' : ($rowValue[0] ?? ''), // @phpstan-ignore nullCoalesce.offset ($rowValue[0] always exists?) $baseQuery ); diff --git a/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/DateTimeExcel/DateValue.php b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/DateTimeExcel/DateValue.php index db757e57..74f189e0 100644 --- a/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/DateTimeExcel/DateValue.php +++ b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/DateTimeExcel/DateValue.php @@ -46,13 +46,22 @@ public static function fromString(null|array|string|int|bool|float $dateValue): return self::evaluateSingleArgumentArray([self::class, __FUNCTION__], $dateValue); } + return self::fromString2($dateValue, null); + } + + /** + * @return array|DateTime|float|int|string Excel date/time serial value, PHP date/time serial value or PHP date/time object, + * depending on the value of the ReturnDateType flag + */ + public static function fromString2(null|string|int|bool|float $dateValue, ?int $calendar = null): array|string|float|int|DateTime + { // try to parse as date iff there is at least one digit if (is_string($dateValue) && preg_match('/\d/', $dateValue) !== 1) { return ExcelError::VALUE(); } $dti = new DateTimeImmutable(); - $baseYear = SharedDateHelper::getExcelCalendar(); + $baseYear = $calendar ?? SharedDateHelper::getExcelCalendar(); $dateValue = trim((string) $dateValue, '"'); // Strip any ordinals because they're allowed in Excel (English only) $dateValue = (string) preg_replace('/(\d)(st|nd|rd|th)([ -\/])/Ui', '$1$3', $dateValue); @@ -160,9 +169,9 @@ private static function finalResults(array $PHPDateArray, DateTimeImmutable $dti $day = self::getInt($PHPDateArray, 'day'); $year = self::getInt($PHPDateArray, 'year'); if (!checkdate($month, $day, $year)) { - return ($year === 1900 && $month === 2 && $day === 29) ? Helpers::returnIn3FormatsFloat(60.0) : ExcelError::VALUE(); + return ($year === 1900 && $month === 2 && $day === 29) ? Helpers::returnIn3FormatsFloat(60.0, calendar: $baseYear) : ExcelError::VALUE(); } - $retValue = Helpers::returnIn3FormatsArray($PHPDateArray, true); + $retValue = Helpers::returnIn3FormatsArray($PHPDateArray, true, calendar: $baseYear); } return $retValue; diff --git a/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/DateTimeExcel/Helpers.php b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/DateTimeExcel/Helpers.php index 492447dd..5fc951c8 100644 --- a/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/DateTimeExcel/Helpers.php +++ b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/DateTimeExcel/Helpers.php @@ -30,10 +30,10 @@ public static function isLeapYear(int|string $year): bool * * @return float Excel date/time serial value */ - public static function getDateValue(mixed $dateValue, bool $allowBool = true): float + public static function getDateValue(mixed $dateValue, bool $allowBool = true, ?int $calendar = null): float { if (is_object($dateValue)) { - $retval = SharedDateHelper::PHPToExcel($dateValue); + $retval = SharedDateHelper::PHPToExcel($dateValue, calendar: $calendar); if (is_bool($retval)) { throw new Exception(ExcelError::VALUE()); } @@ -41,7 +41,7 @@ public static function getDateValue(mixed $dateValue, bool $allowBool = true): f return $retval; } - self::nullFalseTrueToNumber($dateValue, $allowBool); + self::nullFalseTrueToNumber($dateValue, $allowBool, $calendar); if (!is_numeric($dateValue)) { $saveReturnDateType = Functions::getReturnDateType(); Functions::setReturnDateType(Functions::RETURNDATE_EXCEL); @@ -58,7 +58,7 @@ public static function getDateValue(mixed $dateValue, bool $allowBool = true): f } try { - SharedDateHelper::excelToDateTimeObject((float) $dateValue); + SharedDateHelper::excelToDateTimeObject((float) $dateValue, calendar: $calendar); } catch (Throwable) { throw new Exception(ExcelError::NAN()); } @@ -87,10 +87,10 @@ public static function getTimeValue(string $timeValue): string|float * * @param float|int $dateValue date to be adjusted */ - public static function adjustDateByMonths($dateValue = 0, float $adjustmentMonths = 0): DateTime + public static function adjustDateByMonths($dateValue = 0, float $adjustmentMonths = 0, ?int $calendar = null): DateTime { // Execute function - $PHPDateObject = SharedDateHelper::excelToDateTimeObject($dateValue); + $PHPDateObject = SharedDateHelper::excelToDateTimeObject($dateValue, calendar: $calendar); $oMonth = (int) $PHPDateObject->format('m'); $oYear = (int) $PHPDateObject->format('Y'); @@ -141,7 +141,7 @@ public static function adjustYear(string $testVal1, string $testVal2, string &$t * * @param array{year: int, month: int, day: int, hour: int, minute: int, second: int} $dateArray */ - public static function returnIn3FormatsArray(array $dateArray, bool $noFrac = false): DateTime|float|int + public static function returnIn3FormatsArray(array $dateArray, bool $noFrac = false, ?int $calendar = null): DateTime|float|int { $retType = Functions::getReturnDateType(); if ($retType === Functions::RETURNDATE_PHP_DATETIME_OBJECT) { @@ -161,58 +161,60 @@ public static function returnIn3FormatsArray(array $dateArray, bool $noFrac = fa $dateArray['day'], $dateArray['hour'], $dateArray['minute'], - $dateArray['second'] + $dateArray['second'], + calendar: $calendar ); if ($retType === Functions::RETURNDATE_EXCEL) { return $noFrac ? floor($excelDateValue) : $excelDateValue; } // RETURNDATE_UNIX_TIMESTAMP) - return SharedDateHelper::excelToTimestamp($excelDateValue); + return SharedDateHelper::excelToTimestamp($excelDateValue, calendar: $calendar); } /** * Return result in one of three formats. */ - public static function returnIn3FormatsFloat(float $excelDateValue): float|int|DateTime + public static function returnIn3FormatsFloat(float $excelDateValue, ?int $calendar = null): float|int|DateTime { $retType = Functions::getReturnDateType(); if ($retType === Functions::RETURNDATE_EXCEL) { return $excelDateValue; } if ($retType === Functions::RETURNDATE_UNIX_TIMESTAMP) { - return SharedDateHelper::excelToTimestamp($excelDateValue); + return SharedDateHelper::excelToTimestamp($excelDateValue, calendar: $calendar); } // RETURNDATE_PHP_DATETIME_OBJECT - return SharedDateHelper::excelToDateTimeObject($excelDateValue); + return SharedDateHelper::excelToDateTimeObject($excelDateValue, calendar: $calendar); } /** * Return result in one of three formats. */ - public static function returnIn3FormatsObject(DateTime $PHPDateObject): DateTime|float|int + public static function returnIn3FormatsObject(DateTime $PHPDateObject, ?int $calendar = null): DateTime|float|int { $retType = Functions::getReturnDateType(); if ($retType === Functions::RETURNDATE_PHP_DATETIME_OBJECT) { return $PHPDateObject; } if ($retType === Functions::RETURNDATE_EXCEL) { - return (float) SharedDateHelper::PHPToExcel($PHPDateObject); + return (float) SharedDateHelper::PHPToExcel($PHPDateObject, calendar: $calendar); } // RETURNDATE_UNIX_TIMESTAMP - $stamp = SharedDateHelper::PHPToExcel($PHPDateObject); + $stamp = SharedDateHelper::PHPToExcel($PHPDateObject, calendar: $calendar); $stamp = is_bool($stamp) ? ((int) $stamp) : $stamp; - return SharedDateHelper::excelToTimestamp($stamp); + return SharedDateHelper::excelToTimestamp($stamp, calendar: $calendar); } - private static function baseDate(): int + private static function baseDate(?int $calendar): int { if (Functions::getCompatibilityMode() === Functions::COMPATIBILITY_OPENOFFICE) { return 0; } - if (SharedDateHelper::getExcelCalendar() === SharedDateHelper::CALENDAR_MAC_1904) { + $calendar ??= SharedDateHelper::getExcelCalendar(); + if ($calendar === SharedDateHelper::CALENDAR_MAC_1904) { return 0; } @@ -222,10 +224,10 @@ private static function baseDate(): int /** * Many functions accept null/false/true argument treated as 0/0/1. */ - public static function nullFalseTrueToNumber(mixed &$number, bool $allowBool = true): void + public static function nullFalseTrueToNumber(mixed &$number, bool $allowBool = true, ?int $calendar = null): void { $number = Functions::flattenSingleValue($number); - $nullVal = self::baseDate(); + $nullVal = self::baseDate($calendar); if ($number === null) { $number = $nullVal; } elseif ($allowBool && is_bool($number)) { diff --git a/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Engine/Logger.php b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Engine/Logger.php index c67849ec..d917320e 100644 --- a/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Engine/Logger.php +++ b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Engine/Logger.php @@ -78,8 +78,8 @@ public function writeDebugLog(string $message, mixed ...$args): void { // Only write the debug log if logging is enabled if ($this->writeDebugLog) { - $message = sprintf($message, ...$args); //* @phpstan-ignore-line - $cellReference = implode(' -> ', $this->cellStack->showStack()); //* @phpstan-ignore-line + $message = sprintf($message, ...$args); //* @phpstan-ignore argument.type (...$args could contain items that sprintf can't handle) + $cellReference = implode(' -> ', $this->cellStack->showStack()); //* @phpstan-ignore argument.type (showStack can return array not array) if ($this->echoDebugLog) { echo $cellReference, ($this->cellStack->count() > 0 ? ' => ' : ''), diff --git a/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Engine/Operands/StructuredReference.php b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Engine/Operands/StructuredReference.php index 9c4cf726..0b1f0eb5 100644 --- a/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Engine/Operands/StructuredReference.php +++ b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Engine/Operands/StructuredReference.php @@ -204,8 +204,9 @@ private function getRowReference(Cell $cell): string /** @var string $reference */ $reference = str_replace('[' . self::ITEM_SPECIFIER_THIS_ROW . '],', '', $reference); - foreach ($this->columns as $columnId => $columnName) { - $columnName = str_replace("\u{a0}", ' ', $columnName); //* @phpstan-ignore-line + foreach ($this->columns as $columnId => $columnNamex) { + /** @var string $columnNamex */ + $columnName = str_replace("\u{a0}", ' ', $columnNamex); $reference = $this->adjustRowReference($columnName, $reference, $cell, $columnId); } @@ -338,8 +339,9 @@ private function getRowsForColumnReference(string &$reference, int $startRow, in private function getColumnsForColumnReference(string $reference, int $startRow, int $endRow): string { $columnsSelected = false; - foreach ($this->columns as $columnId => $columnName) { - $columnName = str_replace("\u{a0}", ' ', $columnName ?? ''); //* @phpstan-ignore-line + foreach ($this->columns as $columnId => $columnNamex) { + /** @var ?string $columnNamex */ + $columnName = str_replace("\u{a0}", ' ', $columnNamex ?? ''); $cellFrom = "{$columnId}{$startRow}"; $cellTo = "{$columnId}{$endRow}"; $cellReference = ($cellFrom === $cellTo) ? $cellFrom : "{$cellFrom}:{$cellTo}"; diff --git a/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Financial/CashFlow/Variable/NonPeriodic.php b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Financial/CashFlow/Variable/NonPeriodic.php index 53668d13..130e4c10 100644 --- a/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Financial/CashFlow/Variable/NonPeriodic.php +++ b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Financial/CashFlow/Variable/NonPeriodic.php @@ -166,7 +166,7 @@ private static function xirrPart2(array &$values): string $foundneg = false; for ($i = 0; $i < $valCount; ++$i) { $fld = $values[$i]; - if (!is_numeric($fld)) { //* @phpstan-ignore-line + if (!is_numeric($fld)) { return ExcelError::VALUE(); } elseif ($fld > 0) { $foundpos = true; diff --git a/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/FunctionArray.php b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/FunctionArray.php index 96f2518a..8f1de755 100644 --- a/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/FunctionArray.php +++ b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/FunctionArray.php @@ -9,7 +9,7 @@ class FunctionArray extends CalculationBase * * @var array */ - protected static array $phpSpreadsheetFunctions = [ // @phpstan-ignore-line + protected static array $phpSpreadsheetFunctions = [ // @phpstan-ignore property.defaultValue (Phpstan is wrong) 'ABS' => [ 'category' => Category::CATEGORY_MATH_AND_TRIG, 'functionCall' => [MathTrig\Absolute::class, 'evaluate'], diff --git a/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Information/Value.php b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Information/Value.php index 8280bc5e..56620852 100644 --- a/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Information/Value.php +++ b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Information/Value.php @@ -54,7 +54,7 @@ public static function isRef(mixed $value, ?Cell $cell = null): bool } try { - [$column, $row] = Coordinate::indexesFromString($cellValue ?? ''); + [$column, $row] = Coordinate::indexesFromString($cellValue ?? ''); //* @phpstan-ignore nullCoalesce.variable (Not sure whether Phpstan is correct) } catch (SpreadsheetException) { return false; } diff --git a/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/LookupRef/ChooseRowsEtc.php b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/LookupRef/ChooseRowsEtc.php index 944675e7..b268de86 100644 --- a/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/LookupRef/ChooseRowsEtc.php +++ b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/LookupRef/ChooseRowsEtc.php @@ -18,7 +18,7 @@ class ChooseRowsEtc */ public static function transpose(array $array): array { - return empty($array) ? [] : (array_map((count($array) === 1) ? (fn ($x) => [$x]) : null, ...$array)); // @phpstan-ignore-line + return empty($array) ? [] : (array_map((count($array) === 1) ? (fn ($x) => [$x]) : null, ...$array)); // @phpstan-ignore argument.type (phstan is wrong), argument.type (phpstan is wrong) } /** @return mixed[] */ diff --git a/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/LookupRef/ExcelMatch.php b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/LookupRef/ExcelMatch.php index b7e0f9de..4346037b 100644 --- a/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/LookupRef/ExcelMatch.php +++ b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/LookupRef/ExcelMatch.php @@ -70,7 +70,7 @@ public static function MATCH(mixed $lookupValue, mixed $lookupArray, mixed $matc }; if ($valueKey !== null) { - return ++$valueKey; //* @phpstan-ignore-line + return ++$valueKey; //* @phpstan-ignore preInc.type ($valueKey can be mixed not numeric) } // Unsuccessful in finding a match, return #N/A error value diff --git a/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/LookupRef/Filter.php b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/LookupRef/Filter.php index 486194e4..3106d4e7 100644 --- a/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/LookupRef/Filter.php +++ b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/LookupRef/Filter.php @@ -58,7 +58,7 @@ function (&$columns): void { */ private static function filterByRow(array $lookupArray, array $matchArray): array { - $matchArray = array_values(array_column($matchArray, 0)); // @phpstan-ignore-line + $matchArray = array_values(array_column($matchArray, 0)); return array_filter( array_values($lookupArray), diff --git a/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/LookupRef/Hstack.php b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/LookupRef/Hstack.php index 9be77e5c..5d4938b1 100644 --- a/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/LookupRef/Hstack.php +++ b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/LookupRef/Hstack.php @@ -37,7 +37,7 @@ public static function hstack(mixed ...$inputData): array|string } } - $transpose = array_map(null, ...$inputData); //* @phpstan-ignore-line + $transpose = array_map(null, ...$inputData); //* @phpstan-ignore argument.type (inputData is mixed not array) $returnMatrix = []; foreach ($transpose as $array) { $returnMatrix[] = Functions::flattenArray($array); diff --git a/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/LookupRef/Lookup.php b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/LookupRef/Lookup.php index 36472c26..f3b6ad99 100644 --- a/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/LookupRef/Lookup.php +++ b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/LookupRef/Lookup.php @@ -40,7 +40,7 @@ public static function lookup(mixed $lookupValue, mixed $lookupVector, $resultVe $lookupColumns = self::columnCount($lookupVector); } - $resultVector = self::verifyResultVector($resultVector ?? $lookupVector); //* @phpstan-ignore-line + $resultVector = self::verifyResultVector($resultVector ?? $lookupVector); //* @phpstan-ignore argument.type (resultVector can be mixed not array>) if ($lookupRows === 2 && !$hasResultVector) { $resultVector = array_pop($lookupVector); diff --git a/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/LookupRef/Matrix.php b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/LookupRef/Matrix.php index 722e644a..a916af5f 100644 --- a/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/LookupRef/Matrix.php +++ b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/LookupRef/Matrix.php @@ -125,7 +125,7 @@ public static function index(mixed $matrix, mixed $rowNum = 0, mixed $columnNum } $rowKeys = array_keys($matrix); - $columnKeys = @array_keys($matrix[$rowKeys[0]]); //* @phpstan-ignore-line + $columnKeys = @array_keys($matrix[$rowKeys[0]]); //* @phpstan-ignore argument.type (argument 1 of array_keys may be mixed not array) if ($columnNum > count($columnKeys)) { return ExcelError::REF(); @@ -135,14 +135,14 @@ public static function index(mixed $matrix, mixed $rowNum = 0, mixed $columnNum return self::extractRowValue($matrix, $rowKeys, $rowNum); } - $columnNum = $columnKeys[--$columnNum]; //* @phpstan-ignore-line + $columnNum = $columnKeys[--$columnNum]; //* @phpstan-ignore offsetAccess.notFound (perhaps index --$columnNum does not exist) if ($rowNum === 0) { return array_map( fn ($value): array => [$value], array_column($matrix, $columnNum) ); } - $rowNum = $rowKeys[--$rowNum]; //* @phpstan-ignore-line + $rowNum = $rowKeys[--$rowNum]; //* @phpstan-ignore offsetAccess.notFound (perhaps index --$rowNum does not exist) /** @var mixed[][] $matrix */ return $matrix[$rowNum][$columnNum]; diff --git a/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/LookupRef/Unique.php b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/LookupRef/Unique.php index 40a9df70..aec06a0c 100644 --- a/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/LookupRef/Unique.php +++ b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/LookupRef/Unique.php @@ -40,7 +40,7 @@ private static function uniqueByRow(array $lookupVector, bool $exactlyOnce): mix // so implode each row into a single string value array_walk( $lookupVector, - //* @phpstan-ignore-next-line + // @phpstan-ignore argument.type (not sure what is needed) function (array &$value): void { $valuex = ''; $separator = ''; @@ -79,7 +79,7 @@ function (string &$value): void { if (str_ends_with($stringValue, "\x01")) { // x01 should only end a string which is otherwise a float or int, // so phpstan is technically correct but what it fears should not happen. - $stringValue = 0 + substr($stringValue, 0, -1); //@phpstan-ignore-line + $stringValue = 0 + substr($stringValue, 0, -1); //@phpstan-ignore binaryOp.invalid (stringValue might not be numeric?) } } } diff --git a/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/LookupRef/Vstack.php b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/LookupRef/Vstack.php index 919c262a..ce2fe638 100644 --- a/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/LookupRef/Vstack.php +++ b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/LookupRef/Vstack.php @@ -20,7 +20,7 @@ public static function vstack(mixed ...$inputData): array|string if (!is_array($matrix)) { $count = 1; } else { - $count = count(reset($matrix)); //* @phpstan-ignore-line + $count = count(reset($matrix)); //* @phpstan-ignore argument.type (reset can theoretically return mixed not array) } $columns = max($columns, $count); } diff --git a/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/MathTrig/Round.php b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/MathTrig/Round.php index 0d3f83cc..130636f6 100644 --- a/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/MathTrig/Round.php +++ b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/MathTrig/Round.php @@ -73,7 +73,7 @@ public static function up($number, $digits): array|string|float return round( (float) (string) $number, $digits, - RoundingMode::AwayFromZero //* @phpstan-ignore-line + RoundingMode::AwayFromZero //* @phpstan-ignore argument.type (phpstan error till we no longer support Php < 8.4) ); } diff --git a/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/MathTrig/Subtotal.php b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/MathTrig/Subtotal.php index d873c16b..cec1ff1e 100644 --- a/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/MathTrig/Subtotal.php +++ b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/MathTrig/Subtotal.php @@ -152,7 +152,10 @@ public static function evaluate(mixed $functionType, ...$args): float|int|string if (array_key_exists($subtotal, self::CALL_FUNCTIONS)) { $call = self::CALL_FUNCTIONS[$subtotal]; - return call_user_func_array($call, $aArgs); //* @phpstan-ignore-line + /** @var float|int|string */ + $temp = call_user_func_array($call, $aArgs); + + return $temp; } return ExcelError::VALUE(); diff --git a/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Statistical/Averages.php b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Statistical/Averages.php index 58809827..e9e7bd29 100644 --- a/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Statistical/Averages.php +++ b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Statistical/Averages.php @@ -163,7 +163,8 @@ public static function median(mixed ...$args): float|string sort($aArgs, SORT_NUMERIC); $valueCount = $valueCount / 2; if ($valueCount == floor($valueCount)) { - $returnValue = ($aArgs[$valueCount--] + $aArgs[$valueCount]) / 2; //* @phpstan-ignore-line + $valueCount = (int) $valueCount; + $returnValue = ($aArgs[$valueCount--] + $aArgs[$valueCount]) / 2; } else { $valueCount = (int) floor($valueCount); $returnValue = $aArgs[$valueCount]; @@ -243,7 +244,7 @@ private static function modeCalc(array $data): float|string $maxfreqkey = $key; $maxfreqdatum = $datum; } elseif ($freq == $maxfreq) { - if ($frequencyArray[$key]['index'] < $frequencyArray[$maxfreqkey]['index']) { //* @phpstan-ignore-line + if ($frequencyArray[$key]['index'] < $frequencyArray[$maxfreqkey]['index']) { //* @phpstan-ignore offsetAccess.notFound (not sure what phpstan wants) $maxfreqkey = $key; $maxfreqdatum = $datum; } diff --git a/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Statistical/Conditional.php b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Statistical/Conditional.php index 818d9dba..7ac5ec10 100644 --- a/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Statistical/Conditional.php +++ b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Statistical/Conditional.php @@ -10,6 +10,7 @@ use PhpOffice\PhpSpreadsheet\Calculation\Exception as CalcException; use PhpOffice\PhpSpreadsheet\Calculation\Functions; use PhpOffice\PhpSpreadsheet\Calculation\Information\ExcelError; +use PhpOffice\PhpSpreadsheet\Shared\StringHelper; class Conditional { @@ -26,11 +27,14 @@ class Conditional * AVERAGEIF(range,condition[, average_range]) * * @param mixed $range Data values, expect array - * @param null|mixed[]|string $condition the criteria that defines which cells will be checked + * @param mixed $condition the criteria that defines which cells will be checked, expect null|mixed[]|string * @param mixed $averageRange Data values */ - public static function AVERAGEIF(mixed $range, null|array|string $condition, mixed $averageRange = []): null|int|float|string + public static function AVERAGEIF(mixed $range, mixed $condition, mixed $averageRange = []): null|int|float|string { + if ($condition !== null && !is_array($condition)) { + $condition = StringHelper::convertToString($condition); + } if (!is_array($range) || !is_array($averageRange) || array_key_exists(0, $range) || array_key_exists(0, $averageRange)) { $refError = ExcelError::REF(); if (in_array($refError, [$range, $averageRange], true)) { @@ -62,7 +66,7 @@ public static function AVERAGEIFS(mixed ...$args): null|int|float|string return 0.0; } if (count($args) === 3) { - return self::AVERAGEIF($args[1], $args[2], $args[0]); //* @phpstan-ignore-line + return self::AVERAGEIF($args[1], $args[2], $args[0]); } foreach ($args as $arg) { if (is_array($arg) && array_key_exists(0, $arg)) { diff --git a/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Statistical/Distributions/Beta.php b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Statistical/Distributions/Beta.php index b53f15c4..dbe64d3f 100644 --- a/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Statistical/Distributions/Beta.php +++ b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Statistical/Distributions/Beta.php @@ -116,6 +116,11 @@ public static function inverse(mixed $probability, mixed $alpha, mixed $beta, mi if (($alpha <= 0) || ($beta <= 0) || ($rMin == $rMax) || ($probability <= 0.0)) { return ExcelError::NAN(); } + if (($alpha + $beta) > self::LOG_GAMMA_X_MAX_VALUE) { + // incompleteBeta declines to evaluate here and returns 0 for every x, + // so there is no quantile to search for. + return ExcelError::NAN(); + } return self::calculateInverse($probability, $alpha, $beta, $rMin, $rMax); } @@ -130,7 +135,7 @@ private static function calculateInverse(float $probability, float $alpha, float while ((($b - $a) > Functions::PRECISION) && (++$i <= self::MAX_ITERATIONS)) { $guess = ($a + $b) / 2; $result = self::distribution($guess, $alpha, $beta); - if (($result === $probability) || ($result === 0.0)) { + if ($result === $probability) { $b = $a; } elseif ($result > $probability) { $b = $guess; diff --git a/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Statistical/Distributions/ChiSquared.php b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Statistical/Distributions/ChiSquared.php index b1324849..0ce15478 100644 --- a/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Statistical/Distributions/ChiSquared.php +++ b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Statistical/Distributions/ChiSquared.php @@ -50,7 +50,7 @@ public static function distributionRightTail(mixed $value, mixed $degrees): arra return ExcelError::NAN(); } - return 1 - (Gamma::incompleteGamma($degrees / 2, $value / 2) / Gamma::gammaValue($degrees / 2)); + return Gamma::regularizedGammaQ($degrees / 2, $value / 2); } /** @@ -99,8 +99,16 @@ public static function distributionLeftTail(mixed $value, mixed $degrees, mixed return 1 - (is_numeric($temp) ? $temp : 0); } - return ($value ** (($degrees / 2) - 1) * exp(-$value / 2)) - / ((2 ** ($degrees / 2)) * Gamma::gammaValue($degrees / 2)); + if ($value == 0.0) { + if ($degrees === 2) { + return 0.5; + } + + return ($degrees === 1) ? INF : 0.0; + } + + // Log domain, so large degrees of freedom cannot overflow Gamma(d/2). + return exp((($degrees / 2) - 1) * log($value) - $value / 2 - ($degrees / 2) * M_LN2 - Gamma::logGamma($degrees / 2)); } /** @@ -133,8 +141,7 @@ public static function inverseRightTail(mixed $probability, mixed $degrees) return ExcelError::NAN(); } - $callback = fn (float $value): float => 1 - (Gamma::incompleteGamma($degrees / 2, $value / 2) - / Gamma::gammaValue($degrees / 2)); + $callback = fn (float $value): float => Gamma::regularizedGammaQ($degrees / 2, $value / 2); $newtonRaphson = new NewtonRaphson($callback); @@ -258,75 +265,6 @@ private static function inverseLeftTailCalculation(float $probability, int $degr private static function pchisq(float $chi2, int $degrees): float { - return self::gammp($degrees, 0.5 * $chi2); - } - - private static function gammp(int $n, float $x): float - { - if ($x < 0.5 * $n + 1) { - return self::gser($n, $x); - } - - return 1 - self::gcf($n, $x); - } - - // Return the incomplete gamma function P(n/2,x) evaluated by - // series representation. Algorithm from numerical recipe. - // Assume that n is a positive integer and x>0, won't check arguments. - // Relative error controlled by the eps parameter - private static function gser(int $n, float $x): float - { - /** @var float $gln */ - $gln = Gamma::ln($n / 2); - $a = 0.5 * $n; - $ap = $a; - $sum = 1.0 / $a; - $del = $sum; - for ($i = 1; $i < 101; ++$i) { - ++$ap; - $del = $del * $x / $ap; - $sum += $del; - if ($del < $sum * self::EPS) { - break; - } - } - - return $sum * exp(-$x + $a * log($x) - $gln); - } - - // Return the incomplete gamma function Q(n/2,x) evaluated by - // its continued fraction representation. Algorithm from numerical recipe. - // Assume that n is a postive integer and x>0, won't check arguments. - // Relative error controlled by the eps parameter - private static function gcf(int $n, float $x): float - { - /** @var float $gln */ - $gln = Gamma::ln($n / 2); - $a = 0.5 * $n; - $b = $x + 1 - $a; - $fpmin = 1.e-300; - $c = 1 / $fpmin; - $d = 1 / $b; - $h = $d; - for ($i = 1; $i < 101; ++$i) { - $an = -$i * ($i - $a); - $b += 2; - $d = $an * $d + $b; - if (abs($d) < $fpmin) { - $d = $fpmin; - } - $c = $b + $an / $c; - if (abs($c) < $fpmin) { - $c = $fpmin; - } - $d = 1 / $d; - $del = $d * $c; - $h = $h * $del; - if (abs($del - 1) < self::EPS) { - break; - } - } - - return $h * exp(-$x + $a * log($x) - $gln); + return Gamma::regularizedGammaP($degrees / 2, 0.5 * $chi2); } } diff --git a/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Statistical/Distributions/F.php b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Statistical/Distributions/F.php index 01275657..e6153556 100644 --- a/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Statistical/Distributions/F.php +++ b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Statistical/Distributions/F.php @@ -55,9 +55,20 @@ public static function distribution(mixed $value, mixed $u, mixed $v, mixed $cum return Beta::incompleteBeta($adjustedValue, $u / 2, $v / 2); } - return (Gamma::gammaValue(($v + $u) / 2) - / (Gamma::gammaValue($u / 2) * Gamma::gammaValue($v / 2))) - * (($u / $v) ** ($u / 2)) - * (($value ** (($u - 2) / 2)) / ((1 + ($u / $v) * $value) ** (($u + $v) / 2))); + if ($value == 0.0) { + if ($u === 2) { + return 1.0; + } + + return ($u === 1) ? INF : 0.0; + } + + // Log domain, so large degrees of freedom cannot overflow the Gamma ratio. + return exp( + Gamma::logGamma(($v + $u) / 2) - Gamma::logGamma($u / 2) - Gamma::logGamma($v / 2) + + ($u / 2) * log($u / $v) + + (($u - 2) / 2) * log($value) + - (($u + $v) / 2) * log(1 + ($u / $v) * $value) + ); } } diff --git a/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Statistical/Distributions/Gamma.php b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Statistical/Distributions/Gamma.php index 60f5309a..284c89da 100644 --- a/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Statistical/Distributions/Gamma.php +++ b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Statistical/Distributions/Gamma.php @@ -85,6 +85,10 @@ public static function distribution(mixed $value, mixed $a, mixed $b, mixed $cum * * Returns the inverse of the Gamma distribution. * + * For a probability so far into the upper tail that the forward-CDF series + * approximation plateaus below it, the root cannot be bracketed; the result + * is capped at the alpha*beta*5 search ceiling rather than diverging. + * * @param mixed $probability Float probability at which you want to evaluate the distribution * Or can be an array of values * @param mixed $alpha Parameter to the distribution as a float @@ -143,6 +147,9 @@ public static function ln(mixed $value): array|string|float return ExcelError::NAN(); } - return log(self::gammaValue($value)); + $result = self::logGamma($value); + + // logGamma returns its MAX_VALUE sentinel when the result would overflow. + return ($result >= self::MAX_VALUE) ? ExcelError::NAN() : $result; } } diff --git a/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Statistical/Distributions/GammaBase.php b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Statistical/Distributions/GammaBase.php index 4ae6075a..e1d5539d 100644 --- a/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Statistical/Distributions/GammaBase.php +++ b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Statistical/Distributions/GammaBase.php @@ -11,7 +11,7 @@ abstract class GammaBase private const EPS = 2.22e-16; - private const MAX_VALUE = 1.2e308; + protected const MAX_VALUE = 1.2e308; private const SQRT2PI = 2.5066282746310005024157652848110452530069867406099; @@ -20,10 +20,19 @@ abstract class GammaBase protected static function calculateDistribution(float $value, float $a, float $b, bool $cumulative): float { if ($cumulative) { - return self::incompleteGamma($a, $value / $b) / self::gammaValue($a); + return self::regularizedGammaP($a, $value / $b); } - return (1 / ($b ** $a * self::gammaValue($a))) * $value ** ($a - 1) * exp(0 - ($value / $b)); + if ($value == 0.0) { + if ($a == 1.0) { + return 1.0 / $b; + } + + return ($a < 1.0) ? INF : 0.0; + } + + // Log domain, so large shape parameters cannot overflow Gamma(a). + return exp(($a - 1.0) * log($value) - $value / $b - $a * log($b) - self::logGamma($a)); } /** @return float|string */ @@ -32,6 +41,24 @@ protected static function calculateInverse(float $probability, float $alpha, flo $xLo = 0; $xHi = $alpha * $beta * 5; + // Extend the upper bound while it does not yet bracket the root, so a + // tail quantile beyond alpha*beta*5 is no longer clamped to it. Stop if + // the CDF stops increasing (series approximation past its usable range) + // and keep the original bound rather than expanding into that region. + $xHiBase = $xHi; + $cdfHi = self::calculateDistribution($xHi, $alpha, $beta, true); + while ($cdfHi < $probability) { + $xHiNext = $xHi * 2; + $cdfNext = self::calculateDistribution($xHiNext, $alpha, $beta, true); + if ($cdfNext <= $cdfHi) { + $xHi = $xHiBase; + + break; + } + $xHi = $xHiNext; + $cdfHi = $cdfNext; + } + $dx = 1024; $x = $xNew = 1; $i = 0; @@ -78,17 +105,98 @@ protected static function calculateInverse(float $probability, float $alpha, flo // public static function incompleteGamma(float $a, float $x): float { - static $max = 32; - $summer = 0; - for ($n = 0; $n <= $max; ++$n) { - $divisor = $a; - for ($i = 1; $i <= $n; ++$i) { - $divisor *= ($a + $i); + // Unregularized lower incomplete gamma; kept for backward compatibility. + return self::regularizedGammaP($a, $x) * self::gammaValue($a); + } + + /** + * Regularized lower incomplete gamma P(a,x) = gamma(a,x) / Gamma(a). + * Series for x < a+1, else the complement of the continued fraction. + */ + public static function regularizedGammaP(float $a, float $x): float + { + if ($x <= 0.0 || $a <= 0.0) { + return 0.0; + } + if ($x < $a + 1.0) { + return self::gammaSeries($a, $x); + } + + return 1.0 - self::gammaContinuedFraction($a, $x); + } + + /** + * Regularized upper incomplete gamma Q(a,x) = 1 - P(a,x). + * Continued fraction for x >= a+1 keeps the right tail free of cancellation. + */ + public static function regularizedGammaQ(float $a, float $x): float + { + if ($x <= 0.0 || $a <= 0.0) { + return 1.0; + } + if ($x < $a + 1.0) { + return 1.0 - self::gammaSeries($a, $x); + } + + return self::gammaContinuedFraction($a, $x); + } + + // Near x ~ a both expansions need O(sqrt(a)) terms to reach EPS. + private static function incompleteGammaIterations(float $a): int + { + return max(self::MAX_ITERATIONS, (int) ceil(10.0 * sqrt($a))); + } + + // P(a,x) by its series representation (Numerical Recipes gser). + private static function gammaSeries(float $a, float $x): float + { + $maxIterations = self::incompleteGammaIterations($a); + $gln = self::logGamma($a); + $ap = $a; + $sum = 1.0 / $a; + $del = $sum; + for ($i = 1; $i <= $maxIterations; ++$i) { + ++$ap; + $del *= $x / $ap; + $sum += $del; + if (abs($del) < abs($sum) * self::EPS) { + break; + } + } + + return $sum * exp(-$x + $a * log($x) - $gln); + } + + // Q(a,x) by its continued fraction representation (Numerical Recipes gcf). + private static function gammaContinuedFraction(float $a, float $x): float + { + $maxIterations = self::incompleteGammaIterations($a); + $fpMin = 1.0e-300; + $gln = self::logGamma($a); + $b = $x + 1.0 - $a; + $c = 1.0 / $fpMin; + $d = 1.0 / $b; + $h = $d; + for ($i = 1; $i <= $maxIterations; ++$i) { + $an = -$i * ($i - $a); + $b += 2.0; + $d = $an * $d + $b; + if (abs($d) < $fpMin) { + $d = $fpMin; + } + $c = $b + $an / $c; + if (abs($c) < $fpMin) { + $c = $fpMin; + } + $d = 1.0 / $d; + $del = $d * $c; + $h *= $del; + if (abs($del - 1.0) < self::EPS) { + break; } - $summer += ($x ** $n / $divisor); } - return $x ** $a * exp(0 - $x) * $summer; + return $h * exp(-$x + $a * log($x) - $gln); } private const GAMMA_VALUE_P0 = 1.000000000190015; diff --git a/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/TextData/Format.php b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/TextData/Format.php index ff5c83fe..c6e37f40 100644 --- a/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/TextData/Format.php +++ b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/TextData/Format.php @@ -206,18 +206,20 @@ public static function VALUE(mixed $value = '') Functions::setReturnDateType(Functions::RETURNDATE_EXCEL); if (str_contains($value, ':')) { + /** @var DateTimeInterface|float|int|string */ $timeValue = Functions::scalar(DateTimeExcel\TimeValue::fromString($value)); if ($timeValue !== ExcelError::VALUE()) { Functions::setReturnDateType($dateSetting); - return $timeValue; //* @phpstan-ignore-line + return $timeValue; } } + /** @var DateTimeInterface|float|int|string */ $dateValue = Functions::scalar(DateTimeExcel\DateValue::fromString($value)); if ($dateValue !== ExcelError::VALUE()) { Functions::setReturnDateType($dateSetting); - return $dateValue; //* @phpstan-ignore-line + return $dateValue; } Functions::setReturnDateType($dateSetting); diff --git a/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/TextData/Text.php b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/TextData/Text.php index a4cc14f1..40e3a173 100644 --- a/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/TextData/Text.php +++ b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/TextData/Text.php @@ -171,12 +171,12 @@ private static function applyPadding(array $rows, mixed $padding): array { $columnCount = array_reduce( $rows, - fn (int $counter, array $row): int => max($counter, count($row)), //* @phpstan-ignore-line + fn (int $counter, array $row): int => max($counter, count($row)), //* @phpstan-ignore argument.type (I don't know) 0 ); return array_map( - fn (array $row): array => (count($row) < $columnCount) //* @phpstan-ignore-line + fn (array $row): array => (count($row) < $columnCount) //* @phpstan-ignore argument.type (I don't know) ? array_merge($row, array_fill(0, $columnCount - count($row), $padding)) : $row, $rows diff --git a/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Web/Service.php b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Web/Service.php index ab8357ad..02684008 100644 --- a/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Web/Service.php +++ b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Calculation/Web/Service.php @@ -42,6 +42,7 @@ public static function webService(mixed $url, ?Cell $cell = null): ?string // Get results from the webservice $ctxArray = [ 'http' => [ + 'follow_location' => 0, 'user_agent' => 'Mozilla/5.0 (Macintosh; Intel Mac OS X 10_15_7) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/131.0.0.0 Safari/537.36', ], ]; @@ -54,7 +55,7 @@ public static function webService(mixed $url, ?Cell $cell = null): ?string return ExcelError::VALUE(); // Output not a string or too long } - return $output; + return ($output === '') ? Functions::NOT_YET_IMPLEMENTED : $output; } /** diff --git a/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Cell/AddressHelper.php b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Cell/AddressHelper.php index 9b48f596..15920f55 100644 --- a/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Cell/AddressHelper.php +++ b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Cell/AddressHelper.php @@ -58,7 +58,7 @@ public static function convertToA1( $columnReference = (string) $currentColumnNumber; } // Bracketed C references are relative to the current column - if (is_string($columnReference) && $columnReference[0] === '[') { // @phpstan-ignore-line + if ($columnReference[0] === '[') { $columnReference = $currentColumnNumber + (int) trim($columnReference, '[]'); } $columnReference = (int) $columnReference; diff --git a/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Cell/AdvancedValueBinder.php b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Cell/AdvancedValueBinder.php index 1db0c0f5..a0edb8a8 100644 --- a/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Cell/AdvancedValueBinder.php +++ b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Cell/AdvancedValueBinder.php @@ -60,7 +60,7 @@ public function bindValue(Cell $cell, mixed $value = null): bool // Check for currency if (preg_match(FormattedNumber::currencyMatcherRegexp(), (string) preg_replace('/(\d)' . $thousandsSeparator . '(\d)/u', '$1$2', $value), $matches, PREG_UNMATCHED_AS_NULL)) { // Convert value to number - $sign = ($matches['PrefixedSign'] ?? $matches['PrefixedSign2'] ?? $matches['PostfixedSign']) ?? null; + $sign = ($matches['PrefixedSign'] ?? $matches['PrefixedSign2'] ?? $matches['PostfixedSign']) ?? null; //* @phpstan-ignore nullCoalesce.unnecessary (Not sure whether Phpstan is correct) $currencyCode = $matches['PrefixedCurrency'] ?? $matches['PostfixedCurrency'] ?? ''; /** @var string */ $temp = str_replace([$decimalSeparatorNoPreg, $currencyCode, ' ', '-'], ['.', '', '', ''], (string) preg_replace('/(\d)' . $thousandsSeparator . '(\d)/u', '$1$2', $value)); diff --git a/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Cell/Cell.php b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Cell/Cell.php index 2b0da2fa..dd9b5331 100644 --- a/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Cell/Cell.php +++ b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Cell/Cell.php @@ -191,12 +191,22 @@ public function getValueString(): string public function getFormattedValue(): string { $currentCalendar = SharedDate::getExcelCalendar(); - SharedDate::setExcelCalendar($this->getWorksheet()->getParent()?->getExcelCalendar()); - $formattedValue = (string) NumberFormat::toFormattedString( - $this->getCalculatedValueString(), - (string) $this->getStyle()->getNumberFormat()->getFormatCode(true) + SharedDate::setExcelCalendar( + $this->getWorksheet() + ->getParent() + ?->getExcelCalendar() ); - SharedDate::setExcelCalendar($currentCalendar); + + try { + $formattedValue = NumberFormat::toFormattedString( + $this->getCalculatedValueString(), + (string) $this->getStyle() + ->getNumberFormat() + ->getFormatCode(true) + ); + } finally { + SharedDate::setExcelCalendar($currentCalendar); + } return $formattedValue; } @@ -360,16 +370,16 @@ public function setValueExplicit(mixed $value, string $dataType = DataType::TYPE $worksheet = $this->getWorksheet(); $spreadsheet = $worksheet->getParent(); if (isset($spreadsheet) && $spreadsheet->getIndex($worksheet, true) >= 0) { - $originalSelected = $worksheet->getSelectedCells(); - $activeSheetIndex = $spreadsheet->getActiveSheetIndex(); - $style = $this->getStyle(); - $oldQuotePrefix = $style->getQuotePrefix(); + // Avoid Worksheet::getStyle() (selection + validation) unless quotePrefix must change. + $oldQuotePrefix = $spreadsheet->getCellXfByIndex($this->getXfIndex())->getQuotePrefix(); if ($oldQuotePrefix !== $quotePrefix) { - $style->setQuotePrefix($quotePrefix); - } - $worksheet->setSelectedCells($originalSelected); - if ($activeSheetIndex >= 0) { - $spreadsheet->setActiveSheetIndex($activeSheetIndex); + $originalSelected = $worksheet->getSelectedCells(); + $activeSheetIndex = $spreadsheet->getActiveSheetIndex(); + $this->getStyle()->setQuotePrefix($quotePrefix); + $worksheet->setSelectedCells($originalSelected); + if ($activeSheetIndex >= 0) { + $spreadsheet->setActiveSheetIndex($activeSheetIndex); + } } } @@ -1010,6 +1020,19 @@ public function setXfIndex(int $indexValue): self return $this->updateInCollection(); } + /** + * Set the XF index without triggering updateInCollection(). + * + * This is intended for use by readers that will immediately follow with + * setValueExplicit(), avoiding a redundant cache write. + * + * @internal + */ + public function setXfIndexNoUpdate(int $indexValue): void + { + $this->xfIndex = $indexValue; + } + /** * Set the formula attributes. * @@ -1071,4 +1094,96 @@ public function isHiddenOnFormulaBar(): bool return $hidden !== Protection::PROTECTION_UNPROTECTED; } + + /** + * Return cell $right positions to the right of this one. + */ + public function cursorRight(int $right = 1): self + { + $row = $this->getRow(); + $col = $this->getColumn(); + $colIndex = Coordinate::columnIndexFromString($col); + $newCol = max( + 1, + min($colIndex + $right, AddressRange::MAX_COLUMN_INT) + ); + $newColStr = Coordinate::stringFromColumnIndex($newCol); + + return $this->getWorksheet()->getCell("$newColStr$row"); + } + + /** + * Return cell $left positions to the left of this one. + */ + public function cursorLeft(int $left = 1): self + { + return $this->cursorRight(-$left); + } + + /** + * Return cell $down positions below this one. + */ + public function cursorDown(int $down = 1): self + { + $row = $this->getRow(); + $col = $this->getColumn(); + $newRow = max( + 1, + min($row + $down, AddressRange::MAX_ROW) + ); + + return $this->getWorksheet()->getCell("$col$newRow"); + } + + /** + * Return cell $up positions above this one. + */ + public function cursorUp(int $up = 1): self + { + return $this->cursorDown(-$up); + } + + /** + * Return cell at row $row in current column. + */ + public function cursorRow(int $row = 1): self + { + $col = $this->getColumn(); + $newRow = max( + 1, + min($row, AddressRange::MAX_ROW) + ); + + return $this->getWorksheet()->getCell("$col$newRow"); + } + + /** + * Return cell at column $column in current row. + */ + public function cursorColumn(string $column = 'A'): self + { + $row = $this->getRow(); + $colIndex = Coordinate::columnIndexFromString($column); + $newCol = max( + 1, + min($colIndex, AddressRange::MAX_COLUMN_INT) + ); + $newColStr = Coordinate::stringFromColumnIndex($newCol); + + return $this->getWorksheet()->getCell("$newColStr$row"); + } + + /** + * Return cell adjusted for Xls limits if applicable. + */ + public function cursorXlsLimits(): self + { + $row = min($this->getRow(), AddressRange::MAX_ROW_XLS); + $column = $this->getColumn(); + $colIndex = Coordinate::columnIndexFromString($column); + $newCol = min($colIndex, AddressRange::MAX_COLUMN_INT_XLS); + $newColStr = Coordinate::stringFromColumnIndex($newCol); + + return $this->getWorksheet()->getCell("$newColStr$row"); + } } diff --git a/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Cell/Coordinate.php b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Cell/Coordinate.php index f7daa9d9..02e1d9eb 100644 --- a/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Cell/Coordinate.php +++ b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Cell/Coordinate.php @@ -522,8 +522,7 @@ public static function extractAllCellReferencesInRange(string $cellRange): array } /** @var string[] */ - $cellList = array_merge(...$cells); //* @phpstan-ignore-line - // Unsure how to satisfy phpstan in line above + $cellList = array_merge(...$cells); //* @phpstan-ignore argument.type (Unsure how to satisfy phpstan) $retVal = array_map( fn (string $cellAddress) => ($worksheet !== '') ? "{$quoted}{$worksheet}{$quoted}!{$cellAddress}" : $cellAddress, @@ -647,10 +646,8 @@ private static function getReferencesForCellBlock(string $cellBlock): array // Range... [$rangeStart, $rangeEnd] = $range; - [$startColumn, $startRow] = self::coordinateFromString($rangeStart); - [$endColumn, $endRow] = self::coordinateFromString($rangeEnd); - $startColumnIndex = self::columnIndexFromString($startColumn); - $endColumnIndex = self::columnIndexFromString($endColumn); + [$startColumnIndex, $startRow, $startColumn] = self::indexesFromString($rangeStart); + [$endColumnIndex, $endRow, $endColumn] = self::indexesFromString($rangeEnd); ++$endColumnIndex; // Current data @@ -661,8 +658,6 @@ private static function getReferencesForCellBlock(string $cellBlock): array // Loop cells while ($currentColumnIndex < $endColumnIndex) { - /** @var int $currentRow */ - /** @var int $endRow */ while ($currentRow <= $endRow) { $returnValue[] = self::stringFromColumnIndex($currentColumnIndex) . $currentRow; ++$currentRow; @@ -745,7 +740,7 @@ public static function mergeRangesInCollection(array $coordinateCollection): arr } } - if ($rowStart !== null) { // @phpstan-ignore-line + if ($rowStart !== null) { if ($rowStart == $rowEnd) { $ranges[] = $hashedValue->col . $rowStart; } else { diff --git a/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Cell/IgnoredErrors.php b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Cell/IgnoredErrors.php index 0d88fe34..37b4de47 100644 --- a/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Cell/IgnoredErrors.php +++ b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Cell/IgnoredErrors.php @@ -14,6 +14,8 @@ class IgnoredErrors private bool $evalError = false; + private bool $misleadingFormat = false; + public function setNumberStoredAsText(bool $value): self { $this->numberStoredAsText = $value; @@ -73,4 +75,16 @@ public function getEvalError(): bool { return $this->evalError; } + + public function setMisleadingFormat(bool $value): self + { + $this->misleadingFormat = $value; + + return $this; + } + + public function getMisleadingFormat(): bool + { + return $this->misleadingFormat; + } } diff --git a/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Chart/Axis.php b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Chart/Axis.php index dc1fca4f..243c11f1 100644 --- a/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Chart/Axis.php +++ b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Chart/Axis.php @@ -336,7 +336,7 @@ public function __clone() { parent::__clone(); $this->majorGridlines = ($this->majorGridlines === null) ? null : clone $this->majorGridlines; - $this->majorGridlines = ($this->minorGridlines === null) ? null : clone $this->minorGridlines; + $this->minorGridlines = ($this->minorGridlines === null) ? null : clone $this->minorGridlines; $this->axisText = ($this->axisText === null) ? null : clone $this->axisText; $this->dispUnitsTitle = ($this->dispUnitsTitle === null) ? null : clone $this->dispUnitsTitle; $this->fillColor = clone $this->fillColor; diff --git a/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Chart/Chart.php b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Chart/Chart.php index e750edc2..6288ea1d 100644 --- a/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Chart/Chart.php +++ b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Chart/Chart.php @@ -110,6 +110,37 @@ class Chart private bool $roundedCorners = false; + private bool $date1904 = false; + + private string $lang = 'en-GB'; + + /** @var array{ + * b?: numeric-string, + * l?: numeric-string, + * r?: numeric-string, + * t?: numeric-string, + * header?: numeric-string, + * footer?: numeric-string, + * } + */ + private array $pageMargins = [ + 'b' => '0.75', + 'l' => '0.7', + 'r' => '0.7', + 't' => '0.75', + 'header' => '0.3', + 'footer' => '0.3', + ]; + + /** @var array{ + * paperSize?: string, + * orientation?: string, + * } + */ + private array $pageSetup = [ + 'orientation' => 'portrait', + ]; + private GridLines $borderLines; private ChartColor $fillColor; @@ -680,9 +711,11 @@ public function getAutoTitleDeleted(): bool return $this->autoTitleDeleted; } - public function setAutoTitleDeleted(bool $autoTitleDeleted): self + public function setAutoTitleDeleted(?bool $autoTitleDeleted): self { - $this->autoTitleDeleted = $autoTitleDeleted; + if (is_bool($autoTitleDeleted)) { + $this->autoTitleDeleted = $autoTitleDeleted; + } return $this; } @@ -725,6 +758,34 @@ public function setRoundedCorners(?bool $roundedCorners): self return $this; } + public function getDate1904(): bool + { + return $this->date1904; + } + + public function setDate1904(?bool $date1904): self + { + if ($date1904 !== null) { + $this->date1904 = $date1904; + } + + return $this; + } + + public function getLang(): string + { + return $this->lang; + } + + public function setLang(?string $lang): self + { + if ($lang !== null && $lang !== '') { + $this->lang = $lang; + } + + return $this; + } + public function getBorderLines(): GridLines { return $this->borderLines; @@ -782,4 +843,58 @@ public function __clone() $this->borderLines = clone $this->borderLines; $this->fillColor = clone $this->fillColor; } + + /** @return array{ + * b?: numeric-string, + * l?: numeric-string, + * r?: numeric-string, + * t?: numeric-string, + * header?: numeric-string, + * footer?: numeric-string, + * } + */ + public function getPageMargins(): array + { + return $this->pageMargins; + } + + /** @param mixed $pageMargins expecting array matching $this->pageMargins */ + public function setPageMargins(mixed $pageMargins): self + { + if (is_array($pageMargins)) { + foreach (['b', 'l', 'r', 't', 'header', 'footer'] as $key) { + $value = $pageMargins[$key] ?? null; + if (is_string($value) && is_numeric($value)) { + $this->pageMargins[$key] = "$value"; + } + } + } + + return $this; + } + + /** @return array{ + * paperSize?: string, + * orientation?: string, + * } + */ + public function getPageSetup(): array + { + return $this->pageSetup; + } + + /** @param mixed $pageSetup expecting array matching $this->pageSetup */ + public function setPageSetup(mixed $pageSetup): self + { + if (is_array($pageSetup)) { + foreach (['paperSize', 'orientation'] as $key) { + $value = $pageSetup[$key] ?? null; + if (is_string($value)) { + $this->pageSetup[$key] = "$value"; + } + } + } + + return $this; + } } diff --git a/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Chart/ChartColor.php b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Chart/ChartColor.php index 6ac4b5ac..a1381634 100644 --- a/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Chart/ChartColor.php +++ b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Chart/ChartColor.php @@ -114,7 +114,7 @@ public function setColorProperties(?string $color, null|float|int|string $alpha return $this; } - /** @param array{value: ?string, alpha: null|int|string, brightness?: null|int|string, type: ?string} $color */ + /** @param array{value: ?string, alpha?: null|int|string, brightness?: null|int|string, type?: null|string} $color */ public function setColorPropertiesArray(array $color): self { return $this->setColorProperties( diff --git a/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Chart/DataSeries.php b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Chart/DataSeries.php index 06f1c3c7..972a3855 100644 --- a/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Chart/DataSeries.php +++ b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Chart/DataSeries.php @@ -387,7 +387,7 @@ public function __clone() $plotLabels = $this->plotLabel; $this->plotLabel = []; foreach ($plotLabels as $plotLabel) { - $this->plotLabel[] = $plotLabel; + $this->plotLabel[] = clone $plotLabel; } $plotCategories = $this->plotCategory; $this->plotCategory = []; diff --git a/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Chart/DataTable.php b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Chart/DataTable.php new file mode 100644 index 00000000..71c18fe7 --- /dev/null +++ b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Chart/DataTable.php @@ -0,0 +1,62 @@ +showHorizontalBorder; + } + + public function getShowVerticalBorder(): bool + { + return $this->showVerticalBorder; + } + + public function getShowOutline(): bool + { + return $this->showOutline; + } + + public function getShowKeys(): bool + { + return $this->showKeys; + } + + public function setShowHorizontalBorder(bool $showHorizontalBorder): self + { + $this->showHorizontalBorder = $showHorizontalBorder; + + return $this; + } + + public function setShowVerticalBorder(bool $showVerticalBorder): self + { + $this->showVerticalBorder = $showVerticalBorder; + + return $this; + } + + public function setShowOutline(bool $showOutline): self + { + $this->showOutline = $showOutline; + + return $this; + } + + public function setShowKeys(bool $showKeys): self + { + $this->showKeys = $showKeys; + + return $this; + } +} diff --git a/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Chart/Layout.php b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Chart/Layout.php index 95e113d5..dbf9f75f 100644 --- a/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Chart/Layout.php +++ b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Chart/Layout.php @@ -99,6 +99,26 @@ class Layout private ?Properties $labelEffects = null; + /** @var array{ + * vertOverflow?: string, + * horzOverflow?: string, + * wrap?: string, + * lIns?: numeric-string, + * tIns?: numeric-string, + * rIns?: numeric-string, + * bIns?: numeric-string, + * anchor?: string, + * } + */ + private array $bodyPr = [ + 'wrap' => 'square', + 'lIns' => '38100', + 'tIns' => '19050', + 'rIns' => '38100', + 'bIns' => '19050', + 'anchor' => 'ctr', + ]; + /** * Create a new Layout. * @@ -106,7 +126,22 @@ class Layout */ public function __construct(array $layout = []) { - /** @var array{layoutTarget?: string, xMode?: string, yMode?: string, x?: float, y?: float, w?:float, h?:float, dLblPos?: string, labelFont?: ?mixed, labelFontColor?: ?mixed, labelEffects?: ?mixed, numFmtCode?: string} $layout */ + /** @var array{ + * layoutTarget?: string, + * xMode?: string, + * yMode?: string, + * x?: float, + * y?: float, + * w?:float, + * h?:float, + * dLblPos?: string, + * labelFont?: ?mixed, + * labelFontColor?: ?mixed, + * labelEffects?: ?mixed, + * numFmtCode?: string, + * bodyPr?: mixed, + * } $layout + */ if (isset($layout['layoutTarget'])) { $this->layoutTarget = $layout['layoutTarget']; } @@ -156,6 +191,10 @@ public function __construct(array $layout = []) if ($labelEffects instanceof Properties) { $this->labelEffects = $labelEffects; } + $bodyPr = $layout['bodyPr'] ?? null; + if (is_array($bodyPr)) { + $this->setBodyPr($bodyPr); + } } /** @param mixed[] $layout */ @@ -469,11 +508,7 @@ public function getLabelEffects(): ?Properties public function getLabelFontColor(): ?ChartColor { - if ($this->labelFont === null) { - return null; - } - - return $this->labelFont->getChartColor(); + return $this->labelFont?->getChartColor(); } public function setLabelFontColor(?ChartColor $chartColor): self @@ -523,6 +558,45 @@ public function setNumFmtLinked(bool $numFmtLinked): self return $this; } + /** @return array{ + * vertOverflow?: string, + * horzOverflow?: string, + * wrap?: string, + * lIns?: numeric-string, + * tIns?: numeric-string, + * rIns?: numeric-string, + * bIns?: numeric-string, + * anchor?: string, + * } + */ + public function getBodyPr(): array + { + return $this->bodyPr; + } + + /** + * @param mixed $bodyPr expect array matching $this->bodyPr + */ + public function setBodyPr(mixed $bodyPr): self + { + if (is_array($bodyPr)) { + foreach (['vertOverflow', 'horzOverflow', 'wrap', 'anchor'] as $key) { + $value = $bodyPr[$key] ?? null; + if (is_string($value)) { + $this->bodyPr[$key] = "$value"; + } + } + foreach (['lIns', 'tIns', 'rIns', 'bIns'] as $key) { + $value = $bodyPr[$key] ?? null; + if (is_string($value) && is_numeric($value)) { + $this->bodyPr[$key] = "$value"; + } + } + } + + return $this; + } + /** * Implement PHP __clone to create a deep clone, not just a shallow copy. */ diff --git a/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Chart/PlotArea.php b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Chart/PlotArea.php index e5e39078..f23febca 100644 --- a/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Chart/PlotArea.php +++ b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Chart/PlotArea.php @@ -38,6 +38,8 @@ class PlotArea */ private array $plotSeries; + private ?DataTable $dataTable = null; + /** * Create a new PlotArea. * @@ -195,16 +197,34 @@ public function setUseDownBars(bool $useDownBars): self return $this; } + public function setDataTable(DataTable $dataTable): self + { + $this->dataTable = $dataTable; + + return $this; + } + + public function getDataTable(): ?DataTable + { + return $this->dataTable; + } + /** * Implement PHP __clone to create a deep clone, not just a shallow copy. */ public function __clone() { $this->layout = ($this->layout === null) ? null : clone $this->layout; + $this->dataTable = ($this->dataTable === null) ? null : clone $this->dataTable; $plotSeries = $this->plotSeries; $this->plotSeries = []; foreach ($plotSeries as $series) { $this->plotSeries[] = clone $series; } + $gradientFillStops = $this->gradientFillStops; + $this->gradientFillStops = []; + foreach ($gradientFillStops as $gradientFillStop) { + $this->gradientFillStops[] = [$gradientFillStop[0], clone $gradientFillStop[1]]; + } } } diff --git a/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Chart/Properties.php b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Chart/Properties.php index 9d5fc015..9bf15999 100644 --- a/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Chart/Properties.php +++ b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Chart/Properties.php @@ -419,7 +419,7 @@ protected function getArrayElementsValue(array $properties, array|int|string $el } foreach ($elements as $keys) { - $reference = &$reference[$keys]; //* @phpstan-ignore-line + $reference = &$reference[$keys]; //* @phpstan-ignore offsetAccess.nonOffsetAccessible (I'm not sure what this is doing) } return $reference; @@ -855,7 +855,7 @@ public function setLineStyleArray(array $lineStyleProperties = []): self public function setLineStyleProperty(string $propertyName, mixed $value): self { $this->activateObject(); - $this->lineStyleProperties[$propertyName] = $value; //* @phpstan-ignore-line + $this->lineStyleProperties[$propertyName] = $value; //* @phpstan-ignore assign.propertyType (Too complicated) return $this; } diff --git a/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Helper/Handler.php b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Helper/Handler.php index 8100df5d..514b7d7a 100644 --- a/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Helper/Handler.php +++ b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Helper/Handler.php @@ -9,7 +9,7 @@ final class Handler // A bunch of methods to show that we continue // to capture messages even using PhpUnit 10. - public static function suppressed(): bool + public static function suppressed(): true { return @trigger_error('hello'); } @@ -29,17 +29,17 @@ public static function warning(): bool return file_get_contents(__FILE__ . 'noexist') !== false; } - public static function userDeprecated(): bool + public static function userDeprecated(): true { return trigger_error('hello', E_USER_DEPRECATED); } - public static function userNotice(): bool + public static function userNotice(): true { return trigger_error('userNotice', E_USER_NOTICE); } - public static function userWarning(): bool + public static function userWarning(): true { return trigger_error('userWarning', E_USER_WARNING); } diff --git a/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/IOFactory.php b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/IOFactory.php index 7444aa87..7e4010f6 100644 --- a/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/IOFactory.php +++ b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/IOFactory.php @@ -265,8 +265,7 @@ private static function getReaderTypeFromExtension(string $filename): ?string */ public static function registerWriter(string $writerType, string $writerClass): void { - // We want phpstan to validate caller, but still need this test - if (!is_a($writerClass, IWriter::class, true)) { //* @phpstan-ignore-line + if (!is_a($writerClass, IWriter::class, true)) { throw new Writer\Exception('Registered writers must implement ' . IWriter::class); } @@ -280,8 +279,7 @@ public static function registerWriter(string $writerType, string $writerClass): */ public static function registerReader(string $readerType, string $readerClass): void { - // We want phpstan to validate caller, but still need this test - if (!is_a($readerClass, IReader::class, true)) { //* @phpstan-ignore-line + if (!is_a($readerClass, IReader::class, true)) { throw new Reader\Exception('Registered readers must implement ' . IReader::class); } diff --git a/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Gnumeric.php b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Gnumeric.php index 85f8404b..67cbba99 100644 --- a/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Gnumeric.php +++ b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Gnumeric.php @@ -50,8 +50,14 @@ class Gnumeric extends BaseReader private ReferenceHelper $referenceHelper; - /** @var array{'dataType': string[]} */ - public static array $mappings = [ + /** + * @deprecated 5.10.0 No longer used, replaced by const which is not user-accessible. + * + * @var array{'dataType': string[]} + */ + public static array $mappings = self::MAPPINGS; + + private const MAPPINGS = [ 'dataType' => [ '10' => DataType::TYPE_NULL, '20' => DataType::TYPE_BOOL, @@ -64,6 +70,14 @@ class Gnumeric extends BaseReader ], ]; + protected int $maxLength; + + private const LENGTH_MULTIPLIER = [ + 'G' => 1024 * 1024 * 1024, + 'M' => 1024 * 1024, + 'K' => 1024, + ]; + /** * Create a new Gnumeric. */ @@ -72,6 +86,20 @@ public function __construct() parent::__construct(); $this->referenceHelper = ReferenceHelper::getInstance(); $this->securityScanner = XmlScanner::getInstance($this); + $limit = ini_get('memory_limit') ?: '128M'; + $limit = trim(str_replace('-1', '128M', $limit)); + $unit = strtoupper(substr($limit, -1)); + $limit = (int) $limit; + $multiplier = self::LENGTH_MULTIPLIER[$unit] ?? 1; + $limit *= $multiplier; + $this->maxLength = intdiv($limit, 4); + } + + public function setMaxLength(int $maxLength): self + { + $this->maxLength = $maxLength; + + return $this; } /** @@ -192,7 +220,7 @@ private function gzfileGetContents(string $filename): string if (str_starts_with($contents, "\x1f\x8b")) { // Check if gzlib functions are available if (function_exists('gzdecode')) { - $contents = @gzdecode($contents); + $contents = @gzdecode($contents, $this->maxLength); if ($contents !== false) { $data = $contents; } @@ -208,10 +236,14 @@ private function gzfileGetContents(string $filename): string return $data; } - /** @return mixed[] */ + /** + * @return mixed[] + * + * @internal + */ public static function gnumericMappings(): array { - return array_merge(self::$mappings, Styles::$mappings); + return array_merge(self::MAPPINGS, Styles::MAPPINGS); } private function processComments(SimpleXMLElement $sheet): void @@ -260,8 +292,7 @@ public function loadIntoExisting(string $filename, Spreadsheet $spreadsheet): Sp $gFileData = $this->gzfileGetContents($filename); - /** @var XmlScanner */ - $securityScanner = $this->securityScanner; + $securityScanner = $this->getSecurityScannerOrThrow(); $xml2 = simplexml_load_string($securityScanner->scan($gFileData)); $xml = self::testSimpleXml($xml2); @@ -311,7 +342,7 @@ public function loadIntoExisting(string $filename, Spreadsheet $spreadsheet): Sp $column = Coordinate::stringFromColumnIndex($column + 1); // Read cell? - if (!$this->getReadFilter()->readCell($column, $row, $worksheetName)) { + if (!$this->readFilter->readCell($column, $row, $worksheetName)) { continue; } @@ -589,8 +620,8 @@ private function loadCell( $type = DataType::TYPE_FORMULA; } elseif ($isArrayFormula === false) { $vtype = (string) $ValueType; - if (array_key_exists($vtype, self::$mappings['dataType'])) { - $type = self::$mappings['dataType'][$vtype]; + if (array_key_exists($vtype, self::MAPPINGS['dataType'])) { + $type = self::MAPPINGS['dataType'][$vtype]; } if ($vtype === '20') { // Boolean $cell = $cell == 'TRUE'; diff --git a/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Gnumeric/Styles.php b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Gnumeric/Styles.php index 0729f2ef..07f8a70d 100644 --- a/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Gnumeric/Styles.php +++ b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Gnumeric/Styles.php @@ -18,8 +18,15 @@ class Styles protected bool $readDataOnly; - /** @var array */ - public static array $mappings = [ + /** + * @deprecated 5.10.0 No longer used, replaced by const which is not user-accessible. + * + * @var array + */ + public static array $mappings = self::MAPPINGS; + + /** @internal */ + public const MAPPINGS = [ 'borderStyle' => [ '0' => Border::BORDER_NONE, '1' => Border::BORDER_THIN, @@ -143,6 +150,7 @@ private function addBorderStyle(SimpleXMLElement $srssb, array &$styleArray, str { $ucDirection = ucfirst($direction); if (isset($srssb->$ucDirection)) { + // https://github.com/phpstan/phpstan/issues/14925 /** @var SimpleXMLElement */ $temp = $srssb->$ucDirection; $styleArray['borders'][$direction] = self::parseBorderAttributes($temp->attributes()); @@ -160,19 +168,19 @@ private function calcRotation(SimpleXMLElement $styleAttributes): int return $rotation; } - /** @param mixed[][] $styleArray */ + /** @param array|string> $styleArray */ private static function addStyle(array &$styleArray, string $key, string $value): void { - if (array_key_exists($value, self::$mappings[$key])) { - $styleArray[$key] = self::$mappings[$key][$value]; //* @phpstan-ignore-line + if (array_key_exists($value, self::MAPPINGS[$key])) { + $styleArray[$key] = self::MAPPINGS[$key][$value]; } } /** @param mixed[][] $styleArray */ private static function addStyle2(array &$styleArray, string $key1, string $key, string $value): void { - if (array_key_exists($value, self::$mappings[$key])) { - $styleArray[$key1][$key] = self::$mappings[$key][$value]; + if (array_key_exists($value, self::MAPPINGS[$key])) { + $styleArray[$key1][$key] = self::MAPPINGS[$key][$value]; } } diff --git a/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Html.php b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Html.php index 3c157936..5135ba7f 100644 --- a/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Html.php +++ b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Html.php @@ -203,7 +203,7 @@ private function readEnding(): string { $meta = stream_get_meta_data($this->fileHandle); // Phpstan incorrectly flags following line for Php8.2-, corrected in 8.3 - $filename = $meta['uri']; //@phpstan-ignore-line + $filename = $meta['uri']; //@phpstan-ignore offsetAccess.notFound (fixable when Php < 8.3 is no longer possible) clearstatcache(true, $filename); $size = (int) filesize($filename); @@ -369,13 +369,13 @@ protected function flushCell(Worksheet $sheet, string $column, int|string $row, $sheet->setCellValue($column . $row, $attributeArray['data-value'] ?? $cellContent); $sheet->setHyperlink($column . $row, $hyperlink); } - $this->dataArray[$row][$column] = $cellContent; // @phpstan-ignore-line + $this->dataArray[$row][$column] = $cellContent; // @phpstan-ignore property.deprecated (fixable when $this.data is removed) } } else { // We have a Rich Text run. // I don't actually see any way to reach this line. // TODO - // @phpstan-ignore-next-line + // @phpstan-ignore property.deprecated (fixable when $this->data is removed) $this->dataArray[$row][$column] = 'RICH TEXT: ' . StringHelper::convertToString($cellContent); // @codeCoverageIgnore } $cellContentx = ''; diff --git a/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Ods.php b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Ods.php index 818753a7..bb4b7b1e 100644 --- a/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Ods.php +++ b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Ods.php @@ -31,6 +31,7 @@ use PhpOffice\PhpSpreadsheet\Style\Fill; use PhpOffice\PhpSpreadsheet\Style\NumberFormat; use PhpOffice\PhpSpreadsheet\Style\Protection; +use PhpOffice\PhpSpreadsheet\Worksheet\Drawing; use PhpOffice\PhpSpreadsheet\Worksheet\Worksheet; use Throwable; use XMLReader; @@ -40,6 +41,10 @@ class Ods extends BaseReader { const INITIAL_FILE = 'content.xml'; + private ZipArchive $zip; + + private string $filename; + /** * Create a new Ods Reader instance. */ @@ -209,6 +214,7 @@ public function listWorksheetInfo(string $filename): array if ($xml->name == 'table:table-row' && $xml->nodeType == XMLReader::ELEMENT) { $rowspan = $xml->getAttribute('table:number-rows-repeated'); $rowspan = empty($rowspan) ? 1 : (int) $rowspan; + self::checkRowsRepeated($currRow, $rowspan); $currRow += $rowspan; $currCol = 0; // Step into the row @@ -218,6 +224,10 @@ public function listWorksheetInfo(string $filename): array if ($xml->name == 'table:table-cell' && $xml->nodeType == XMLReader::ELEMENT) { $mergeSize = $xml->getAttribute('table:number-columns-repeated'); $mergeSize = empty($mergeSize) ? 1 : (int) $mergeSize; + self::checkColumnsRepeatedInt( + $currCol, + $mergeSize + ); $currCol += $mergeSize; if (!$xml->isEmptyElement) { $tmpInfo['totalColumns'] = max($tmpInfo['totalColumns'], $currCol); @@ -227,6 +237,11 @@ public function listWorksheetInfo(string $filename): array } } elseif ($xml->name == 'table:covered-table-cell' && $xml->nodeType == XMLReader::ELEMENT) { $mergeSize = $xml->getAttribute('table:number-columns-repeated'); + $mergeSize = empty($mergeSize) ? 1 : (int) $mergeSize; + self::checkColumnsRepeatedInt( + $currCol, + $mergeSize + ); $currCol += (int) $mergeSize; } if ($doread) { @@ -312,7 +327,8 @@ public function loadIntoExisting(string $filename, Spreadsheet $spreadsheet): Sp { File::assertFile($filename, self::INITIAL_FILE); - $zip = new ZipArchive(); + $this->zip = $zip = new ZipArchive(); + $this->filename = $filename; $zip->open($filename); // Meta @@ -322,7 +338,7 @@ public function loadIntoExisting(string $filename, Spreadsheet $spreadsheet): Sp ->scan($zip->getFromName('meta.xml')) ); if ($xml === false) { - throw new Exception('Unable to read data from {$pFilename}'); + throw new Exception("Unable to read data from {$filename}"); } /** @var array{meta?: string, office?: string, dc?: string} */ @@ -333,11 +349,7 @@ public function loadIntoExisting(string $filename, Spreadsheet $spreadsheet): Sp // Styles $this->allStyles = $this->numberFormats = []; - $dom = new DOMDocument('1.01', 'UTF-8'); - $dom->loadXML( - $this->getSecurityScannerOrThrow() - ->scan($zip->getFromName('styles.xml')) - ); + $dom = $this->loadDom('styles.xml', $zip); $officeNs = (string) $dom->lookupNamespaceUri('office'); $styleNs = (string) $dom->lookupNamespaceUri('style'); $fontNs = (string) $dom->lookupNamespaceUri('fo'); @@ -403,11 +415,7 @@ public function loadIntoExisting(string $filename, Spreadsheet $spreadsheet): Sp // Main Content - $dom = new DOMDocument('1.01', 'UTF-8'); - $dom->loadXML( - $this->getSecurityScannerOrThrow() - ->scan($zip->getFromName(self::INITIAL_FILE)) - ); + $dom = $this->loadDom(self::INITIAL_FILE, $zip); $pageSettings->readStyleCrossReferences($dom); @@ -817,6 +825,7 @@ private function processTableRow( } else { $rowRepeats = 1; } + self::checkRowsRepeated($rowID, $rowRepeats); $worksheet = $spreadsheet->getSheetByName($worksheetName); $columnID = 'A'; @@ -830,6 +839,8 @@ private function processTableRow( } else { $colRepeats = 1; } + $columnIndex = Coordinate::columnIndexFromString($columnID); + self::checkColumnsRepeated($columnID, $colRepeats); $styleName = $cellData->getAttributeNS($tableNs, 'style-name'); if ($styleName === '') { if ($worksheet === null || !$worksheet->columnDimensionExists($columnID)) { @@ -851,7 +862,7 @@ private function processTableRow( // repeated range passes the read filter. If not, skip the entire group. // If some columns pass, we need to fall through to the processing block // which will handle per-column filtering. - if (!$this->getReadFilter()->readCell($columnID, $rowID, $worksheetName)) { + if (!$this->readFilter->readCell($columnID, $rowID, $worksheetName)) { if ($colRepeats <= 1) { StringHelper::stringIncrement($columnID); @@ -865,7 +876,7 @@ private function processTableRow( if ($i > 0) { StringHelper::stringIncrement($tempCol); } - if ($this->getReadFilter()->readCell($tempCol, $rowID, $worksheetName)) { + if ($this->readFilter->readCell($tempCol, $rowID, $worksheetName)) { $anyColumnPasses = true; break; @@ -881,6 +892,8 @@ private function processTableRow( } // Fall through to process the cell, with per-column filter checks } + $tempSpannedRange = "$columnID$rowID"; + $spannedRange = ''; if ($worksheet !== null && ($cellData->hasChildNodes() || ($cellData->nextSibling !== null)) && isset($this->allStyles[$styleName])) { $spannedRange = "$columnID$rowID"; // the following is sufficient for ods, @@ -977,6 +990,8 @@ private function processTableRow( // Filter text:p elements if ($item->nodeName == 'text:p') { $paragraphs[] = $item; + } elseif ($item->nodeName === 'draw:frame' && $worksheet !== null) { + $this->processDrawFrame($spannedRange ?: $tempSpannedRange, $item, $worksheet); } } @@ -1081,17 +1096,20 @@ private function processTableRow( $type = DataType::TYPE_NUMERIC; $value = $cellData->getAttributeNS($officeNs, 'date-value'); $dataValue = Date::convertIsoDate($value); + $format15 = Preg::isMatch('/\d\d\d\d/', $allCellDataText) ? NumberFormat::FORMAT_DATE_XLSX15_YYYY : NumberFormat::FORMAT_DATE_XLSX15; if (Preg::isMatch('/^\d\d\d\d-\d\d-\d\d$/', $allCellDataText)) { $formatting = 'yyyy-mm-dd'; + } elseif (Preg::isMatch('/^\d\d\d\d-\d\d-\d\d \d\d:\d\d(:\d\d)?$/', $allCellDataText)) { + $formatting = NumberFormat::FORMAT_DATE_DATETIME_BETTER; } elseif (Preg::isMatch('/^\d\d?-[a-zA-Z]+-\d\d\d\d$/', $allCellDataText)) { $formatting = 'd-mmm-yyyy'; - } elseif ($dataValue != floor($dataValue)) { - $formatting = NumberFormat::FORMAT_DATE_XLSX15 + } elseif ($dataValue != floor($dataValue) || str_contains($allCellDataText, ':')) { + $formatting = $format15 . ' ' . NumberFormat::FORMAT_DATE_TIME4; } else { - $formatting = NumberFormat::FORMAT_DATE_XLSX15; + $formatting = $format15; } break; @@ -1143,7 +1161,7 @@ private function processTableRow( StringHelper::stringIncrement($columnID); } - if (!$this->getReadFilter()->readCell($columnID, $rowID, $worksheetName)) { + if (!$this->readFilter->readCell($columnID, $rowID, $worksheetName)) { continue; } @@ -1200,6 +1218,61 @@ private function processTableRow( $rowID += $rowRepeats; } + private function processDrawFrame(string $spannedRange, DOMElement $item, Worksheet $worksheet): void + { + $drawName = $item->getAttribute('draw:name'); + $svgWidth = $item->getAttribute('svg:width'); + $svgHeight = $item->getAttribute('svg:height'); + $styleName = $item->getAttribute('draw:style-name'); + $drawImage = null; + foreach ($item->childNodes as $node) { + // Check if the node is a standard element tag + if ($node->nodeType === XML_ELEMENT_NODE && $node->nodeName === 'draw:image') { + /** @var DOMElement */ + $drawImage = $node; + + break; + } + } + + $xlinkHref = $xlinkType = $xlinkShow = ''; + if ($drawImage !== null) { + $xlinkHref = $drawImage->getAttribute('xlink:href'); + $xlinkType = $drawImage->getAttribute('xlink:type'); + $xlinkShow = $drawImage->getAttribute('xlink:show'); + } + if ( + $drawName !== '' + && Preg::isMatch('/(\d+([.]\d+)?)(cm|in)/', $svgWidth, $matchWidth) + && Preg::isMatch('/(\d+([.]\d+)?)(cm|in)/', $svgHeight, $matchHeight) + //&& $styleName === 'gr1' + && (str_starts_with($xlinkHref, 'Pictures/') || str_starts_with($xlinkHref, 'media/')) + && $xlinkType === 'simple' + && $xlinkShow === 'embed' + ) { + $drawing = new Drawing(); + $drawing->setPath( + "zip://{$this->filename}#$xlinkHref", + true, + $this->zip, + false + ); + $unit = [ + 'cm' => HelperDimension::ABSOLUTE_UNITS[HelperDimension::UOM_CENTIMETERS], + 'in' => HelperDimension::ABSOLUTE_UNITS[HelperDimension::UOM_INCHES], + ]; + $width = ((float) $matchWidth[1]) * $unit[$matchWidth[3]]; + $height = ((float) $matchHeight[1]) * $unit[$matchHeight[3]]; + if ($drawing->getPath()) { + $drawing->setCoordinates($spannedRange) + ->setWidth((int) $width) + ->setHeight((int) $height) + ->setName($drawName) + ->setWorksheet($worksheet); + } + } + } + private static function extractNodeName(string $key): string { // Remove ns from node name @@ -1313,17 +1386,19 @@ private function processTableColumn( bool $processStyles = true ): void { if ($childNode->hasAttributeNS($tableNs, 'number-columns-repeated')) { - $rowRepeats = (int) $childNode->getAttributeNS($tableNs, 'number-columns-repeated'); + $colRepeats = (int) $childNode->getAttributeNS($tableNs, 'number-columns-repeated'); } else { - $rowRepeats = 1; + $colRepeats = 1; } + // called routine expects index to be 1 less than it is + self::checkColumnsRepeatedInt($tableColumnIndex - 1, $colRepeats); $tableStyleName = $childNode->getAttributeNS($tableNs, 'style-name'); if ($processWidths) { if (isset($columnWidths[$tableStyleName])) { $columnWidth = new HelperDimension($columnWidths[$tableStyleName]); $tableColumnIndex2 = $tableColumnIndex; $tableColumnString = Coordinate::stringFromColumnIndex($tableColumnIndex2); - for ($rowRepeats2 = $rowRepeats; $rowRepeats2 > 0 && $tableColumnIndex2 <= AddressRange::MAX_COLUMN_INT; --$rowRepeats2) { + for ($colRepeats2 = $colRepeats; $colRepeats2 > 0 && $tableColumnIndex2 <= AddressRange::MAX_COLUMN_INT; --$colRepeats2) { if (!$this->readEmptyCells && $tableColumnIndex2 > $this->highestDataIndex) { break; } @@ -1342,7 +1417,7 @@ private function processTableColumn( if ($defaultStyleName !== 'Default' && isset($this->allStyles[$defaultStyleName])) { $tableColumnIndex2 = $tableColumnIndex; $tableColumnString = Coordinate::stringFromColumnIndex($tableColumnIndex2); - for ($rowRepeats2 = $rowRepeats; $rowRepeats2 > 0 && $tableColumnIndex2 <= AddressRange::MAX_COLUMN_INT; --$rowRepeats2) { + for ($colRepeats2 = $colRepeats; $colRepeats2 > 0 && $tableColumnIndex2 <= AddressRange::MAX_COLUMN_INT; --$colRepeats2) { $spreadsheet->getActiveSheet() ->getStyle($tableColumnString) ->applyFromArray( @@ -1355,16 +1430,12 @@ private function processTableColumn( } } } - $tableColumnIndex += $rowRepeats; + $tableColumnIndex += $colRepeats; } private function processSettings(ZipArchive $zip, Spreadsheet $spreadsheet): void { - $dom = new DOMDocument('1.01', 'UTF-8'); - $dom->loadXML( - $this->getSecurityScannerOrThrow() - ->scan($zip->getFromName('settings.xml')) - ); + $dom = $this->loadDom('settings.xml', $zip); $configNs = (string) $dom->lookupNamespaceUri('config'); $officeNs = (string) $dom->lookupNamespaceUri('office'); $settings = $dom->getElementsByTagNameNS($officeNs, 'settings') @@ -1751,7 +1822,7 @@ protected function getBorderStyles(DOMElement $tableCellProperties, string $font $temp = $tableCellProperties->getAttributeNs($fontNs, 'border'); $diagonalIndex = Borders::DIAGONAL_NONE; foreach (['bottom', 'left', 'right', 'top', 'diagonal-tl-br', 'diagonal-bl-tr'] as $direction) { - if (str_starts_with($direction, 'diagonal')) { + if ($direction === 'diagonal-tl-br' || $direction === 'diagonal-bl-tr') { $directionIndex = 'diagonal'; $temp = $tableCellProperties->getAttributeNs($styleNs, $direction); } else { @@ -1779,7 +1850,7 @@ protected function getBorderStyles(DOMElement $tableCellProperties, string $font $borders['diagonalDirection'] = $diagonalIndex; } - return $borders; // @phpstan-ignore-line + return $borders; } protected function processSomeNumberFormats(?DOMElement $automaticStyle0, string $numberNs, string $styleNs): void @@ -1801,4 +1872,55 @@ protected function processNumberNumber(DOMElement $automaticStyle, string $numbe } } } + + private static function checkRowsRepeated(int $rowID, int $rowRepeats): void + { + if ($rowRepeats < 1 || $rowID + $rowRepeats - 1 > AddressRange::MAX_ROW) { + throw new Exception("Invalid number-rows-repeated $rowRepeats following row $rowID"); + } + } + + private static function checkColumnsRepeated(string $colID, int $colRepeats): void + { + $colIndex = Coordinate::columnIndexFromString($colID); + if ($colRepeats < 1 || $colIndex + $colRepeats - 1 > AddressRange::MAX_COLUMN_INT) { + throw new Exception("Invalid number-columns-repeated $colRepeats following column $colID"); + } + } + + private static function checkColumnsRepeatedInt(int $colIndex, int $colRepeats): void + { + // We don't have column string at this point, + // and colIndex is actually 1 less than it should be. + if ($colRepeats < 1 || $colIndex + $colRepeats > AddressRange::MAX_COLUMN_INT) { + throw new Exception("Invalid number-columns-repeated $colRepeats following column index $colIndex"); + } + } + + private function loadDom(string $file, ZipArchive $zip): DOMDocument + { + $dom = new DOMDocument('1.01', 'UTF-8'); + $orig = false; + + try { + $orig = libxml_use_internal_errors(true); + $result = $dom->loadXML( + $this->getSecurityScannerOrThrow() + ->scan($zip->getFromName($file)) + ); + if ($result === false) { + $fatal = false; + foreach (libxml_get_errors() as $err) { + if ($err->level === LIBXML_ERR_FATAL) { + throw new Exception($err->message); + } + } + } + } finally { + libxml_clear_errors(); + libxml_use_internal_errors($orig); + } + + return $dom; + } } diff --git a/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Security/XmlScanner.php b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Security/XmlScanner.php index 7b4e1043..5d238a80 100644 --- a/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Security/XmlScanner.php +++ b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Security/XmlScanner.php @@ -56,6 +56,11 @@ private function toUtf8(string $xml): string throw new Reader\Exception('UTF-7 encoding not permitted'); } if (substr($xml, 0, Reader\Csv::UTF8_BOM_LEN) === Reader\Csv::UTF8_BOM) { + if (preg_match(self::ENCODING_PATTERN, $xml, $matches) === 1) { + if (strtolower($matches[2]) !== 'utf-8') { + throw new Reader\Exception("BOM says UTF-8 but encoding says {$matches[2]}"); + } + } $xml = substr($xml, Reader\Csv::UTF8_BOM_LEN); } diff --git a/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Slk.php b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Slk.php index 4a460fe6..f0e81897 100644 --- a/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Slk.php +++ b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Slk.php @@ -371,7 +371,7 @@ private function styleSettings(string $rowDatum, array &$styleData, string &$fon if (array_key_exists($char, self::STYLE_SETTINGS_FONT)) { $styleData['font'][self::STYLE_SETTINGS_FONT[$char]] = true; } elseif (array_key_exists($char, self::STYLE_SETTINGS_BORDER)) { - $styleData['borders'][self::STYLE_SETTINGS_BORDER[$char]]['borderStyle'] = Border::BORDER_THIN; //* @phpstan-ignore-line + $styleData['borders'][self::STYLE_SETTINGS_BORDER[$char]]['borderStyle'] = Border::BORDER_THIN; //* @phpstan-ignore offsetAccess.nonOffsetAccessible (I don't know how to fix this) } elseif ($char == 'S') { $styleData['fill']['fillType'] = Fill::FILL_PATTERN_GRAY125; } elseif ($char == 'M') { diff --git a/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Xls.php b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Xls.php index 453d74ea..9c9397de 100644 --- a/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Xls.php +++ b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Xls.php @@ -99,6 +99,12 @@ class Xls extends XlsBase */ protected Worksheet $phpSheet; + /** + * Cached sheet title for the current sheet being parsed. + * Avoids repeated getTitle() calls in per-cell read filter checks. + */ + protected string $phpSheetTitle = ''; + /** * BIFF version. */ @@ -380,7 +386,7 @@ protected function loadOLE(string $filename): void // get excel data, $ole->read($filename); // Get workbook data: workbook stream + sheet streams - $this->data = $ole->getStream($ole->wrkbook); // @phpstan-ignore-line + $this->data = $ole->getStream($ole->wrkbook) ?? ''; // Get summary information data $this->summaryInformation = $ole->getStream($ole->summaryInformation); // Get additional document summary information data @@ -1944,7 +1950,7 @@ protected function readSst(): void $nm = self::getInt4d($recordData, 4); $pos += 4; - // look up limit position + // look up limit position (last splice offset where pos fits) foreach ($spliceOffsets as $spliceOffset) { // it can happen that the string is empty, therefore we need // <= and not just < @@ -1992,7 +1998,7 @@ protected function readSst(): void // expected byte length of character array if not split $len = ($isCompressed) ? $numChars : $numChars * 2; - // look up limit position - Check it again to be sure that no error occurs when parsing SST structure + // look up limit position - find the first splice offset at or beyond current pos $limitpos = null; foreach ($spliceOffsets as $spliceOffset) { // it can happen that the string is empty, therefore we need @@ -2025,7 +2031,7 @@ protected function readSst(): void // keep reading the characters while ($charsLeft > 0) { - // look up next limit position, in case the string span more than one continue record + // look up next limit position, in case the string spans more than one continue record foreach ($spliceOffsets as $spliceOffset) { if ($pos < $spliceOffset) { $limitpos = $spliceOffset; @@ -2057,25 +2063,19 @@ protected function readSst(): void $retstr .= substr($recordData, $pos, $len); $charsLeft -= $len / 2; $isCompressed = false; - } elseif (!$isCompressed && ($option == 0)) { + } elseif (!$isCompressed /*&& ($option == 0)*/) { // 1st fragment uncompressed // this fragment compressed - $len = min($charsLeft, $limitpos - $pos); - for ($j = 0; $j < $len; ++$j) { - $retstr .= $recordData[$pos + $j] - . chr(0); - } + $len = (int) min($charsLeft, $limitpos - $pos); + // Pad each byte with a null byte to expand to UTF-16LE + $retstr .= chunk_split(substr($recordData, $pos, $len), 1, "\x00"); $charsLeft -= $len; $isCompressed = false; } else { // 1st fragment compressed // this fragment uncompressed - $newstr = ''; - $jMax = strlen($retstr); - for ($j = 0; $j < $jMax; ++$j) { - $newstr .= $retstr[$j] . chr(0); - } - $retstr = $newstr; + // Pad existing compressed string bytes with null bytes + $retstr = chunk_split($retstr, 1, "\x00"); /** @var int */ $len = min($charsLeft * 2, $limitpos - $pos); $retstr .= substr($recordData, $pos, $len); @@ -2726,9 +2726,10 @@ protected function readRk(): void // offset: 2; size: 2; index to column $column = self::getUInt2d($recordData, 2); $columnString = Coordinate::stringFromColumnIndex($column + 1); + $cellCoordinate = $columnString . ($row + 1); // Read cell? - if ($this->getReadFilter()->readCell($columnString, $row + 1, $this->phpSheet->getTitle())) { + if ($this->readFilter->readCell($columnString, $row + 1, $this->phpSheetTitle)) { // offset: 4; size: 2; index to XF record $xfIndex = self::getUInt2d($recordData, 4); @@ -2736,10 +2737,10 @@ protected function readRk(): void $rknum = self::getInt4d($recordData, 6); $numValue = self::getIEEE754($rknum); - $cell = $this->phpSheet->getCell($columnString . ($row + 1)); + $cell = $this->phpSheet->getCell($cellCoordinate); if (!$this->readDataOnly && isset($this->mapCellXfIndex[$xfIndex])) { // add style information - $cell->setXfIndex($this->mapCellXfIndex[$xfIndex]); + $cell->setXfIndexNoUpdate($this->mapCellXfIndex[$xfIndex]); } // add cell @@ -2770,22 +2771,28 @@ protected function readLabelSst(): void // offset: 2; size: 2; index to column $column = self::getUInt2d($recordData, 2); $columnString = Coordinate::stringFromColumnIndex($column + 1); + $cellCoordinate = $columnString . ($row + 1); - $cell = null; // Read cell? - if ($this->getReadFilter()->readCell($columnString, $row + 1, $this->phpSheet->getTitle())) { + if ($this->readFilter->readCell($columnString, $row + 1, $this->phpSheetTitle)) { // offset: 4; size: 2; index to XF record $xfIndex = self::getUInt2d($recordData, 4); // offset: 6; size: 4; index to SST record $index = self::getInt4d($recordData, 6); + // cache SST entry locally to avoid repeated array lookups + $sstValue = $this->sst[$index]['value']; + $fmtRuns = $this->sst[$index]['fmtRuns']; + // add cell - if (($fmtRuns = $this->sst[$index]['fmtRuns']) && !$this->readDataOnly) { + if ($fmtRuns && !$this->readDataOnly) { // then we should treat as rich text $richText = new RichText(); $charPos = 0; - $sstCount = count($this->sst[$index]['fmtRuns']); + $sstCount = count($fmtRuns); + $sstValueLength = StringHelper::countCharacters($sstValue); + $lastFontIndex = count($this->objFonts) - 1; for ($i = 0; $i <= $sstCount; ++$i) { /** @var mixed[][] $fmtRuns */ if (isset($fmtRuns[$i])) { @@ -2793,10 +2800,10 @@ protected function readLabelSst(): void $temp = $fmtRuns[$i]; $temp = $temp['charPos']; /** @var int $charPos */ - $text = StringHelper::substring($this->sst[$index]['value'], $charPos, $temp - $charPos); + $text = StringHelper::substring($sstValue, $charPos, $temp - $charPos); $charPos = $temp; } else { - $text = StringHelper::substring($this->sst[$index]['value'], $charPos, StringHelper::countCharacters($this->sst[$index]['value'])); + $text = StringHelper::substring($sstValue, $charPos, $sstValueLength); } if (StringHelper::countCharacters($text) > 0) { @@ -2815,8 +2822,8 @@ protected function readLabelSst(): void $temp = $fmtRuns[$i - 1]['fontIndex']; $fontIndex = $temp - 1; } - if (array_key_exists($fontIndex, $this->objFonts) === false) { - $fontIndex = count($this->objFonts) - 1; + if ($fontIndex > $lastFontIndex) { + $fontIndex = $lastFontIndex; } $textRun->setFont(clone $this->objFonts[$fontIndex]); } @@ -2824,20 +2831,21 @@ protected function readLabelSst(): void } } if ($this->readEmptyCells || trim($richText->getPlainText()) !== '') { - $cell = $this->phpSheet->getCell($columnString . ($row + 1)); + $cell = $this->phpSheet->getCell($cellCoordinate); + if (isset($this->mapCellXfIndex[$xfIndex])) { + $cell->setXfIndexNoUpdate($this->mapCellXfIndex[$xfIndex]); + } $cell->setValueExplicit($richText, DataType::TYPE_STRING); } } else { - if ($this->readEmptyCells || trim($this->sst[$index]['value']) !== '') { - $cell = $this->phpSheet->getCell($columnString . ($row + 1)); - $cell->setValueExplicit($this->sst[$index]['value'], DataType::TYPE_STRING); + if ($this->readEmptyCells || trim($sstValue) !== '') { + $cell = $this->phpSheet->getCell($cellCoordinate); + if (!$this->readDataOnly && isset($this->mapCellXfIndex[$xfIndex])) { + $cell->setXfIndexNoUpdate($this->mapCellXfIndex[$xfIndex]); + } + $cell->setValueExplicit($sstValue, DataType::TYPE_STRING); } } - - if (!$this->readDataOnly && $cell !== null && isset($this->mapCellXfIndex[$xfIndex])) { - // add style information - $cell->setXfIndex($this->mapCellXfIndex[$xfIndex]); - } } } @@ -2870,20 +2878,21 @@ protected function readMulRk(): void // offset within record data $offset = 4; + $rowIndex = $row + 1; for ($i = 1; $i <= $columns; ++$i) { $columnString = Coordinate::stringFromColumnIndex($colFirst + $i); // Read cell? - if ($this->getReadFilter()->readCell($columnString, $row + 1, $this->phpSheet->getTitle())) { + if ($this->readFilter->readCell($columnString, $rowIndex, $this->phpSheetTitle)) { // offset: var; size: 2; index to XF record $xfIndex = self::getUInt2d($recordData, $offset); // offset: var; size: 4; RK value $numValue = self::getIEEE754(self::getInt4d($recordData, $offset + 2)); - $cell = $this->phpSheet->getCell($columnString . ($row + 1)); + $cell = $this->phpSheet->getCell($columnString . $rowIndex); if (!$this->readDataOnly && isset($this->mapCellXfIndex[$xfIndex])) { // add style - $cell->setXfIndex($this->mapCellXfIndex[$xfIndex]); + $cell->setXfIndexNoUpdate($this->mapCellXfIndex[$xfIndex]); } // add cell value @@ -2916,18 +2925,19 @@ protected function readNumber(): void // offset: 2; size 2; index to column $column = self::getUInt2d($recordData, 2); $columnString = Coordinate::stringFromColumnIndex($column + 1); + $cellCoordinate = $columnString . ($row + 1); // Read cell? - if ($this->getReadFilter()->readCell($columnString, $row + 1, $this->phpSheet->getTitle())) { + if ($this->readFilter->readCell($columnString, $row + 1, $this->phpSheetTitle)) { // offset 4; size: 2; index to XF record $xfIndex = self::getUInt2d($recordData, 4); $numValue = self::extractNumber(substr($recordData, 6, 8)); - $cell = $this->phpSheet->getCell($columnString . ($row + 1)); + $cell = $this->phpSheet->getCell($cellCoordinate); if (!$this->readDataOnly && isset($this->mapCellXfIndex[$xfIndex])) { // add cell style - $cell->setXfIndex($this->mapCellXfIndex[$xfIndex]); + $cell->setXfIndexNoUpdate($this->mapCellXfIndex[$xfIndex]); } // add cell value @@ -2957,6 +2967,7 @@ protected function readFormula(): void // offset: 2; size: 2; col index $column = self::getUInt2d($recordData, 2); $columnString = Coordinate::stringFromColumnIndex($column + 1); + $cellCoordinate = $columnString . ($row + 1); // offset: 20: size: variable; formula structure $formulaStructure = substr($recordData, 20); @@ -2984,10 +2995,10 @@ protected function readFormula(): void } // Read cell? - if ($this->getReadFilter()->readCell($columnString, $row + 1, $this->phpSheet->getTitle())) { + if ($this->readFilter->readCell($columnString, $row + 1, $this->phpSheetTitle)) { if ($isPartOfSharedFormula) { // formula is added to this cell after the sheet has been read - $this->sharedFormulaParts[$columnString . ($row + 1)] = $this->baseCell; + $this->sharedFormulaParts[$cellCoordinate] = $this->baseCell; } // offset: 16: size: 4; not used @@ -2996,7 +3007,9 @@ protected function readFormula(): void $xfIndex = self::getUInt2d($recordData, 4); // offset: 6; size: 8; result of the formula - if ((ord($recordData[6]) == 0) && (ord($recordData[12]) == 255) && (ord($recordData[13]) == 255)) { + $resultType = ord($recordData[6]); + $isSpecialResult = (ord($recordData[12]) == 255) && (ord($recordData[13]) == 255); + if (($resultType == 0) && $isSpecialResult) { // String formula. Result follows in appended STRING record $dataType = DataType::TYPE_STRING; @@ -3008,27 +3021,15 @@ protected function readFormula(): void // read STRING record $value = $this->readString(); - } elseif ( - (ord($recordData[6]) == 1) - && (ord($recordData[12]) == 255) - && (ord($recordData[13]) == 255) - ) { + } elseif (($resultType == 1) && $isSpecialResult) { // Boolean formula. Result is in +2; 0=false, 1=true $dataType = DataType::TYPE_BOOL; $value = (bool) ord($recordData[8]); - } elseif ( - (ord($recordData[6]) == 2) - && (ord($recordData[12]) == 255) - && (ord($recordData[13]) == 255) - ) { + } elseif (($resultType == 2) && $isSpecialResult) { // Error formula. Error code is in +2 $dataType = DataType::TYPE_ERROR; $value = Xls\ErrorCode::lookup(ord($recordData[8])); - } elseif ( - (ord($recordData[6]) == 3) - && (ord($recordData[12]) == 255) - && (ord($recordData[13]) == 255) - ) { + } elseif (($resultType == 3) && $isSpecialResult) { // Formula result is a null string $dataType = DataType::TYPE_NULL; $value = ''; @@ -3038,10 +3039,12 @@ protected function readFormula(): void $value = self::extractNumber(substr($recordData, 6, 8)); } - $cell = $this->phpSheet->getCell($columnString . ($row + 1)); + $cell = $this->phpSheet->getCell($cellCoordinate); if (!$this->readDataOnly && isset($this->mapCellXfIndex[$xfIndex])) { - // add cell style - $cell->setXfIndex($this->mapCellXfIndex[$xfIndex]); + // add cell style; skipping the collection update is safe here + // because every path below ends in setCalculatedValue(), which + // performs the update + $cell->setXfIndexNoUpdate($this->mapCellXfIndex[$xfIndex]); } // store the formula @@ -3148,9 +3151,10 @@ protected function readBoolErr(): void // offset: 2; size: 2; column index $column = self::getUInt2d($recordData, 2); $columnString = Coordinate::stringFromColumnIndex($column + 1); + $cellCoordinate = $columnString . ($row + 1); // Read cell? - if ($this->getReadFilter()->readCell($columnString, $row + 1, $this->phpSheet->getTitle())) { + if ($this->readFilter->readCell($columnString, $row + 1, $this->phpSheetTitle)) { // offset: 4; size: 2; index to XF record $xfIndex = self::getUInt2d($recordData, 4); @@ -3160,7 +3164,12 @@ protected function readBoolErr(): void // offset: 7; size: 1; 0=boolean; 1=error $isError = ord($recordData[7]); - $cell = $this->phpSheet->getCell($columnString . ($row + 1)); + $cell = $this->phpSheet->getCell($cellCoordinate); + if (!$this->readDataOnly && isset($this->mapCellXfIndex[$xfIndex])) { + // add cell style; a value write does not follow on every path, + // so use the updating setter to guarantee persistence + $cell->setXfIndex($this->mapCellXfIndex[$xfIndex]); + } switch ($isError) { case 0: // boolean $value = (bool) $boolErr; @@ -3177,11 +3186,6 @@ protected function readBoolErr(): void break; } - - if (!$this->readDataOnly && isset($this->mapCellXfIndex[$xfIndex])) { - // add cell style - $cell->setXfIndex($this->mapCellXfIndex[$xfIndex]); - } } } @@ -3210,14 +3214,17 @@ protected function readMulBlank(): void // offset: 4; size: 2 x nc; list of indexes to XF records // add style information if (!$this->readDataOnly && $this->readEmptyCells) { + $rowIndex = $row + 1; for ($i = 0; $i < $length / 2 - 3; ++$i) { $columnString = Coordinate::stringFromColumnIndex($fc + $i + 1); // Read cell? - if ($this->getReadFilter()->readCell($columnString, $row + 1, $this->phpSheet->getTitle())) { + if ($this->readFilter->readCell($columnString, $rowIndex, $this->phpSheetTitle)) { $xfIndex = self::getUInt2d($recordData, 4 + 2 * $i); if (isset($this->mapCellXfIndex[$xfIndex])) { - $this->phpSheet->getCell($columnString . ($row + 1))->setXfIndex($this->mapCellXfIndex[$xfIndex]); + // blank cells never receive a value write, so use the + // updating setter to guarantee persistence + $this->phpSheet->getCell($columnString . $rowIndex)->setXfIndex($this->mapCellXfIndex[$xfIndex]); } } } @@ -3250,9 +3257,10 @@ protected function readLabel(): void // offset: 2; size: 2; index to column $column = self::getUInt2d($recordData, 2); $columnString = Coordinate::stringFromColumnIndex($column + 1); + $cellCoordinate = $columnString . ($row + 1); // Read cell? - if ($this->getReadFilter()->readCell($columnString, $row + 1, $this->phpSheet->getTitle())) { + if ($this->readFilter->readCell($columnString, $row + 1, $this->phpSheetTitle)) { // offset: 4; size: 2; XF index $xfIndex = self::getUInt2d($recordData, 4); @@ -3267,13 +3275,12 @@ protected function readLabel(): void } /** @var string $value */ if ($this->readEmptyCells || trim($value) !== '') { - $cell = $this->phpSheet->getCell($columnString . ($row + 1)); - $cell->setValueExplicit($value, DataType::TYPE_STRING); - + $cell = $this->phpSheet->getCell($cellCoordinate); if (!$this->readDataOnly && isset($this->mapCellXfIndex[$xfIndex])) { // add cell style - $cell->setXfIndex($this->mapCellXfIndex[$xfIndex]); + $cell->setXfIndexNoUpdate($this->mapCellXfIndex[$xfIndex]); } + $cell->setValueExplicit($value, DataType::TYPE_STRING); } } } @@ -3296,14 +3303,17 @@ protected function readBlank(): void $col = self::getUInt2d($recordData, 2); $columnString = Coordinate::stringFromColumnIndex($col + 1); + $rowIndex = $row + 1; + // Read cell? - if ($this->getReadFilter()->readCell($columnString, $row + 1, $this->phpSheet->getTitle())) { + if ($this->readFilter->readCell($columnString, $rowIndex, $this->phpSheetTitle)) { // offset: 4; size: 2; XF index $xfIndex = self::getUInt2d($recordData, 4); - // add style information + // add style information; blank cells never receive a value write, + // so use the updating setter to guarantee persistence if (!$this->readDataOnly && $this->readEmptyCells && isset($this->mapCellXfIndex[$xfIndex])) { - $this->phpSheet->getCell($columnString . ($row + 1))->setXfIndex($this->mapCellXfIndex[$xfIndex]); + $this->phpSheet->getCell($columnString . $rowIndex)->setXfIndex($this->mapCellXfIndex[$xfIndex]); } } } @@ -3605,7 +3615,7 @@ private function includeCellRangeFiltered(string $cellRangeAddress): bool StringHelper::stringIncrement($rangeBoundaries[1][0]); for ($row = $rangeBoundaries[0][1]; $row <= $rangeBoundaries[1][1]; ++$row) { for ($column = $rangeBoundaries[0][0]; $column != $rangeBoundaries[1][0]; StringHelper::stringIncrement($column)) { - if ($this->getReadFilter()->readCell($column, $row, $this->phpSheet->getTitle())) { + if ($this->readFilter->readCell($column, $row, $this->phpSheetTitle)) { $includeCellRange = true; break 2; diff --git a/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Xls/LoadSpreadsheet.php b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Xls/LoadSpreadsheet.php index 402b9f59..10a2e5e6 100644 --- a/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Xls/LoadSpreadsheet.php +++ b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Xls/LoadSpreadsheet.php @@ -175,6 +175,7 @@ protected function loadSpreadsheetFromFile2(string $filename, Xls $xls): Spreads // name in line with the formula, not the reverse $xls->phpSheet->setTitle($sheet['name'], false, false); $xls->phpSheet->setSheetState($sheet['sheetState']); + $xls->phpSheetTitle = $sheet['name']; $xls->pos = $sheet['offset']; @@ -451,10 +452,8 @@ protected function loadSpreadsheetFromFile2(string $filename, Xls $xls): Spreads } // calculate the width and height of the shape - /** @var int $startRow */ - [$startColumn, $startRow] = Coordinate::coordinateFromString($spContainer->getStartCoordinates()); - /** @var int $endRow */ - [$endColumn, $endRow] = Coordinate::coordinateFromString($spContainer->getEndCoordinates()); + [, $startRow, $startColumn] = Coordinate::indexesFromString($spContainer->getStartCoordinates()); + [, $endRow, $endColumn] = Coordinate::indexesFromString($spContainer->getEndCoordinates()); $startOffsetX = $spContainer->getStartOffsetX(); $startOffsetY = $spContainer->getStartOffsetY(); @@ -477,7 +476,7 @@ protected function loadSpreadsheetFromFile2(string $filename, Xls $xls): Spreads if (isset($xls->textObjects[$obj['idObjID']])) { $textObject = $xls->textObjects[$obj['idObjID']]; - $xls->cellNotes[$obj['idObjID']]['objTextData'] = $textObject; //* @phpstan-ignore-line + $xls->cellNotes[$obj['idObjID']]['objTextData'] = $textObject; //* @phpstan-ignore offsetAccess.nonOffsetAccessible (I don't know to fix this) } } @@ -548,10 +547,9 @@ protected function loadSpreadsheetFromFile2(string $filename, Xls $xls): Spreads // treat SHAREDFMLA records if ($xls->version == self::XLS_BIFF8) { foreach ($xls->sharedFormulaParts as $cell => $baseCell) { - /** @var int $row */ - [$column, $row] = Coordinate::coordinateFromString($cell); + [, $row, $column] = Coordinate::indexesFromString($cell); /** @var string $baseCell */ - if ($xls->getReadFilter()->readCell($column, $row, $xls->phpSheet->getTitle())) { + if ($xls->readFilter->readCell($column, $row, $xls->phpSheet->getTitle())) { /** @var string */ $temp = $xls->sharedFormulas[$baseCell]; $formula = $xls->getFormulaFromStructure($temp, $cell); diff --git a/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/XlsBase.php b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/XlsBase.php index eedd185d..454f0f22 100644 --- a/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/XlsBase.php +++ b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/XlsBase.php @@ -392,7 +392,7 @@ public static function getInt2d(string $data, int $pos): int { self::confirmPos($data, $pos + 1); - return unpack('s', $data[$pos] . $data[$pos + 1])[1]; // @phpstan-ignore-line + return unpack('s', $data[$pos] . $data[$pos + 1])[1]; // @phpstan-ignore offsetAccess.nonOffsetAccessible (I don't know how this statement works), return.type (ditto) } /** diff --git a/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Xlsx.php b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Xlsx.php index db1a87d8..b1de05a5 100644 --- a/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Xlsx.php +++ b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Xlsx.php @@ -3,6 +3,7 @@ namespace PhpOffice\PhpSpreadsheet\Reader; use Composer\Pcre\Preg; +use InvalidArgumentException; use PhpOffice\PhpSpreadsheet\Calculation\Information\ExcelError; use PhpOffice\PhpSpreadsheet\Cell\Coordinate; use PhpOffice\PhpSpreadsheet\Cell\DataType; @@ -18,10 +19,12 @@ use PhpOffice\PhpSpreadsheet\Reader\Xlsx\Hyperlinks; use PhpOffice\PhpSpreadsheet\Reader\Xlsx\Namespaces; use PhpOffice\PhpSpreadsheet\Reader\Xlsx\PageSetup; +use PhpOffice\PhpSpreadsheet\Reader\Xlsx\PivotTableReader; use PhpOffice\PhpSpreadsheet\Reader\Xlsx\Properties as PropertyReader; use PhpOffice\PhpSpreadsheet\Reader\Xlsx\SharedFormula; use PhpOffice\PhpSpreadsheet\Reader\Xlsx\SheetViewOptions; use PhpOffice\PhpSpreadsheet\Reader\Xlsx\SheetViews; +use PhpOffice\PhpSpreadsheet\Reader\Xlsx\Sparklines; use PhpOffice\PhpSpreadsheet\Reader\Xlsx\Styles; use PhpOffice\PhpSpreadsheet\Reader\Xlsx\TableReader; use PhpOffice\PhpSpreadsheet\Reader\Xlsx\Theme; @@ -32,7 +35,9 @@ use PhpOffice\PhpSpreadsheet\Shared\Drawing; use PhpOffice\PhpSpreadsheet\Shared\File; use PhpOffice\PhpSpreadsheet\Shared\Font; +use PhpOffice\PhpSpreadsheet\Shared\OLE; use PhpOffice\PhpSpreadsheet\Shared\StringHelper; +use PhpOffice\PhpSpreadsheet\Shared\Xlsx\AgileEncryption; use PhpOffice\PhpSpreadsheet\Spreadsheet; use PhpOffice\PhpSpreadsheet\Style\Color; use PhpOffice\PhpSpreadsheet\Style\Font as StyleFont; @@ -53,16 +58,37 @@ class Xlsx extends BaseReader /** * ReferenceHelper instance. */ - private ReferenceHelper $referenceHelper; + protected ReferenceHelper $referenceHelper; - private ZipArchive $zip; + protected ZipArchive $zip; private Styles $styleReader; /** @var SharedFormula[] */ - private array $sharedFormulae = []; + protected array $sharedFormulae = []; - private bool $parseHuge = false; + protected bool $parseHuge = false; + + private string $encryptionPassword = ''; + + private int $maxEncryptionSpinCount = AgileEncryption::MAX_SPIN_COUNT; + + public function setEncryptionPassword(string $encryptionPassword): self + { + $this->encryptionPassword = $encryptionPassword; + + return $this; + } + + public function setMaxEncryptionSpinCount(int $maxEncryptionSpinCount): self + { + if ($maxEncryptionSpinCount < 0 || $maxEncryptionSpinCount > AgileEncryption::MAX_SPIN_COUNT) { + throw new InvalidArgumentException('Maximum encryption spin count must be between 0 and ' . AgileEncryption::MAX_SPIN_COUNT . '.'); + } + $this->maxEncryptionSpinCount = $maxEncryptionSpinCount; + + return $this; + } /** * Allow use of LIBXML_PARSEHUGE. @@ -91,7 +117,7 @@ public function __construct() public function canRead(string $filename): bool { if (!File::testFileNoThrow($filename, self::INITIAL_FILE)) { - return false; + return $this->hasEncryptedPackage($filename); } $result = false; @@ -107,6 +133,75 @@ public function canRead(string $filename): bool return $result; } + public function load(string $filename, int $flags = 0): Spreadsheet + { + $temporaryFilename = $this->decryptToTemporaryFile($filename); + if ($temporaryFilename === null) { + return parent::load($filename, $flags); + } + + try { + return parent::load($temporaryFilename, $flags); + } finally { + @unlink($temporaryFilename); + } + } + + private function hasEncryptedPackage(string $filename): bool + { + try { + $ole = new OLE(); + $ole->read($filename); + + return $ole->hasDataByName('EncryptionInfo') && $ole->hasDataByName('EncryptedPackage'); + } catch (Throwable) { + return false; + } + } + + private function decryptToTemporaryFile(string $filename): ?string + { + if (File::testFileNoThrow($filename, self::INITIAL_FILE)) { + return null; + } + + try { + $ole = new OLE(); + $ole->read($filename); + $encryptionInfo = $ole->getDataByName('EncryptionInfo'); + } catch (Throwable) { + return null; + } + + $temporaryFilename = File::temporaryFilename(); + $encryptedPackageFilename = File::temporaryFilename(); + $encryptedPackage = fopen($encryptedPackageFilename, 'wb'); + if ($encryptedPackage === false) { + @unlink($temporaryFilename); + @unlink($encryptedPackageFilename); + + throw new Exception('Could not create decrypted XLSX package.'); + } + + try { + $ole->copyDataByName('EncryptedPackage', $encryptedPackage); + fclose($encryptedPackage); + $encryptedPackage = null; + AgileEncryption::decryptFile(AgileEncryption::parse($encryptionInfo, $this->maxEncryptionSpinCount), $encryptedPackageFilename, $temporaryFilename, $this->encryptionPassword); + } catch (Throwable $e) { + if ($encryptedPackage !== null) { + fclose($encryptedPackage); + } + @unlink($temporaryFilename); + + throw $e; + } finally { + @unlink($encryptedPackageFilename); + } + + return $temporaryFilename; + } + public static function testSimpleXml(mixed $value): SimpleXMLElement { return ($value instanceof SimpleXMLElement) ? $value : new SimpleXMLElement(''); @@ -180,6 +275,21 @@ private function loadZipNonamespace(string $filename, string $ns): SimpleXMLElem * @return string[] */ public function listWorksheetNames(string $filename): array + { + $temporaryFilename = $this->decryptToTemporaryFile($filename); + if ($temporaryFilename === null) { + return $this->listWorksheetNamesFromFile($filename); + } + + try { + return $this->listWorksheetNamesFromFile($temporaryFilename); + } finally { + @unlink($temporaryFilename); + } + } + + /** @return string[] */ + private function listWorksheetNamesFromFile(string $filename): array { File::assertFile($filename, self::INITIAL_FILE); @@ -217,6 +327,23 @@ public function listWorksheetNames(string $filename): array * @return array */ public function listWorksheetInfo(string $filename): array + { + $temporaryFilename = $this->decryptToTemporaryFile($filename); + if ($temporaryFilename === null) { + return $this->listWorksheetInfoFromFile($filename); + } + + try { + return $this->listWorksheetInfoFromFile($temporaryFilename); + } finally { + @unlink($temporaryFilename); + } + } + + /** + * @return array + */ + private function listWorksheetInfoFromFile(string $filename): array { File::assertFile($filename, self::INITIAL_FILE); @@ -319,7 +446,7 @@ public function listWorksheetInfo(string $filename): array return $worksheetInfo; } - private static function castToBoolean(SimpleXMLElement $c): bool + protected static function castToBoolean(SimpleXMLElement $c): bool { $value = isset($c->v) ? (string) $c->v : null; if ($value == '0') { @@ -331,12 +458,12 @@ private static function castToBoolean(SimpleXMLElement $c): bool return (bool) $c->v; } - private static function castToError(?SimpleXMLElement $c): ?string + protected static function castToError(?SimpleXMLElement $c): ?string { return isset($c, $c->v) ? (string) $c->v : null; } - private static function castToString(?SimpleXMLElement $c): ?string + protected static function castToString(?SimpleXMLElement $c): ?string { return isset($c, $c->v) ? (string) $c->v : null; } @@ -346,7 +473,7 @@ public static function replacePrefixes(string $formula): string return str_replace(['_xlfn.', '_xlws.'], '', $formula); } - private function castToFormula(?SimpleXMLElement $c, string $r, string &$cellDataType, mixed &$value, mixed &$calculatedValue, string $castBaseType, bool $updateSharedCells = true): void + protected function castToFormula(?SimpleXMLElement $c, string $r, string &$cellDataType, mixed &$value, mixed &$calculatedValue, string $castBaseType, bool $updateSharedCells = true): void { if ($c === null) { return; @@ -398,7 +525,7 @@ private function fileExistsInArchive(ZipArchive $archive, string $fileName = '') return $contents !== false; } - private function getFromZipArchive(ZipArchive $archive, string $fileName = ''): string + protected function getFromZipArchive(ZipArchive $archive, string $fileName = ''): string { // Root-relative paths if (str_contains($fileName, '//')) { @@ -579,6 +706,7 @@ protected function loadSpreadsheetFromFile(string $filename): Spreadsheet $relsWorkbook->registerXPathNamespace('rel', Namespaces::RELATIONSHIPS); $worksheets = []; + $pivotCacheRels = []; $macros = $customUI = null; foreach ($relsWorkbook->Relationship as $elex) { $ele = self::getAttributes($elex); @@ -593,6 +721,10 @@ protected function loadSpreadsheetFromFile(string $filename): Spreadsheet $worksheets[(string) $ele['Id']] = $ele['Target']; } + break; + case Namespaces::RELATIONSHIPS_PIVOT_CACHE_DEFINITION: + $pivotCacheRels[(string) $ele['Id']] = File::realpath("$dir/" . (string) $ele['Target']); + break; // a vbaProject ? (: some macros) case Namespaces::VBA: @@ -890,188 +1022,26 @@ protected function loadSpreadsheetFromFile(string $filename): Spreadsheet $sheetViewOptions->load($this->readDataOnly, $this->styleReader); (new ColumnAndRowAttributes($docSheet, $xmlSheetNS)) - ->load($this->getReadFilter(), $this->readDataOnly, $this->ignoreRowsWithNoCells); + ->load($this->readFilter, $this->readDataOnly, $this->ignoreRowsWithNoCells); } $holdSelectedCells = $docSheet->getSelectedCells(); - if ($xmlSheetNS && $xmlSheetNS->sheetData && $xmlSheetNS->sheetData->row) { - $cIndex = 1; // Cell Start from 1 - foreach ($xmlSheetNS->sheetData->row as $row) { - $rowIndex = 1; - foreach ($row->c as $c) { - $cAttr = self::getAttributes($c); - $r = (string) $cAttr['r']; - if ($r == '') { - $r = Coordinate::stringFromColumnIndex($rowIndex) . $cIndex; - } - $cellDataType = (string) $cAttr['t']; - $originalCellDataTypeNumeric = $cellDataType === ''; - $value = null; - $calculatedValue = null; - - // Read cell? - $coordinates = Coordinate::coordinateFromString($r); - - if (!$this->getReadFilter()->readCell($coordinates[0], (int) $coordinates[1], $docSheet->getTitle())) { - // Normally, just testing for the f attribute should identify this cell as containing a formula - // that we need to read, even though it is outside of the filter range, in case it is a shared formula. - // But in some cases, this attribute isn't set; so we need to delve a level deeper and look at - // whether or not the cell has a child formula element that is shared. - if (isset($cAttr->f) || (isset($c->f, $c->f->attributes()['t']) && strtolower((string) $c->f->attributes()['t']) === 'shared')) { - $this->castToFormula($c, $r, $cellDataType, $value, $calculatedValue, 'castToError', false); - } - ++$rowIndex; - - continue; - } - - // Read cell! - $useFormula = isset($c->f) - && ((string) $c->f !== '' || (isset($c->f->attributes()['t']) && strtolower((string) $c->f->attributes()['t']) === 'shared')); - switch ($cellDataType) { - case DataType::TYPE_STRING: - if ((string) $c->v != '') { - $value = $sharedStrings[(int) ($c->v)]; - - if ($value instanceof RichText) { - $value = clone $value; - } - } else { - $value = ''; - } - - break; - case DataType::TYPE_BOOL: - if (!$useFormula) { - if (isset($c->v)) { - $value = self::castToBoolean($c); - } else { - $value = null; - $cellDataType = DataType::TYPE_NULL; - } - } else { - // Formula - $this->castToFormula($c, $r, $cellDataType, $value, $calculatedValue, 'castToBoolean'); - self::storeFormulaAttributes($c->f, $docSheet, $r); - } - - break; - case DataType::TYPE_STRING2: - if ($useFormula) { - $this->castToFormula($c, $r, $cellDataType, $value, $calculatedValue, 'castToString'); - self::storeFormulaAttributes($c->f, $docSheet, $r); - } else { - $value = self::castToString($c); - } - - break; - case DataType::TYPE_INLINE: - if ($useFormula) { - $this->castToFormula($c, $r, $cellDataType, $value, $calculatedValue, 'castToError'); - self::storeFormulaAttributes($c->f, $docSheet, $r); - } else { - $value = $this->parseRichText($c->is); - } - - break; - case DataType::TYPE_ERROR: - if (isset($cAttr->vm, $richData['image']['rId' . $cAttr->vm]) && !$useFormula) { - $imagePath = $dir . '/' . str_replace('../', '', $richData['image']['rId' . $cAttr->vm]); - $objDrawing = new \PhpOffice\PhpSpreadsheet\Worksheet\Drawing(); - $objDrawing->setPath( - 'zip://' . File::realpath($filename) . '#' . $imagePath, - false, - $zip - ); - - $objDrawing->setCoordinates($r); - $objDrawing->setResizeProportional(false); - $objDrawing->setInCell(true); - $objDrawing->setWorksheet($docSheet); - - $value = $objDrawing; - $cellDataType = DataType::TYPE_DRAWING_IN_CELL; - $c->t = DataType::TYPE_ERROR; - - break; - } - - if (!$useFormula) { - $value = self::castToError($c); - } else { - // Formula - $this->castToFormula($c, $r, $cellDataType, $value, $calculatedValue, 'castToError'); - $eattr = $c->attributes(); - if (isset($eattr['vm'])) { - if ($calculatedValue === ExcelError::VALUE()) { - $calculatedValue = ExcelError::SPILL(); - } - } - } - - break; - default: - if (!$useFormula) { - $value = self::castToString($c); - if (is_numeric($value)) { - $value += 0; - $cellDataType = DataType::TYPE_NUMERIC; - } - } else { - // Formula - $this->castToFormula($c, $r, $cellDataType, $value, $calculatedValue, 'castToString'); - if (is_numeric($calculatedValue)) { - $calculatedValue += 0; - } - self::storeFormulaAttributes($c->f, $docSheet, $r); - } + /** @var array $styles */ + $this->loadSheetData( + $xmlSheetNS, + $filename, + $dir, + $richData, + $docSheet, + $sharedStrings, + $styles, + [ + // this array can be expanded with additional entries to make it easier to extend + 'mainNS' => $mainNS, + 'fileWorksheetPath' => "$dir/$fileWorksheet", + ], + ); - break; - } - - // read empty cells or the cells are not empty - if ($this->readEmptyCells || ($value !== null && $value !== '')) { - // Rich text? - if ($value instanceof RichText && $this->readDataOnly) { - $value = $value->getPlainText(); - } - - $cell = $docSheet->getCell($r); - // Assign value - if ($cellDataType != '') { - // it is possible, that datatype is numeric but with an empty string, which result in an error - if ($cellDataType === DataType::TYPE_NUMERIC && ($value === '' || $value === null)) { - $cellDataType = DataType::TYPE_NULL; - } - if ($cellDataType !== DataType::TYPE_NULL) { - $cell->setValueExplicit($value, $cellDataType); - } - } else { - $cell->setValue($value); - } - if ($calculatedValue !== null) { - $cell->setCalculatedValue($calculatedValue, $originalCellDataTypeNumeric); - } - - // Style information? - if (!$this->readDataOnly) { - $cAttrS = (int) ($cAttr['s'] ?? 0); - // no style index means 0, it seems - $cAttrS = isset($styles[$cAttrS]) ? $cAttrS : 0; - $cell->setXfIndex($cAttrS); - // issue 3495 - if ($cellDataType === DataType::TYPE_FORMULA && $styles[$cAttrS]->quotePrefix === true) { //* @phpstan-ignore-line - $holdSelected = $docSheet->getSelectedCells(); - $cell->getStyle()->setQuotePrefix(false); - $docSheet->setSelectedCells($holdSelected); - } - } - } - ++$rowIndex; - } - ++$cIndex; - } - } $docSheet->setSelectedCells($holdSelectedCells); if (!$this->readDataOnly && $xmlSheetNS && $xmlSheetNS->ignoredErrors) { foreach ($xmlSheetNS->ignoredErrors->ignoredError as $ignoredError) { @@ -1098,6 +1068,10 @@ protected function loadSpreadsheetFromFile(string $filename): Spreadsheet $this->readTables($xmlSheetNS, $docSheet, $dir, $fileWorksheet, $zip, $mainNS, $tableStyles, $dxfs); + if ($this->readDataOnly === false) { + $this->readPivotTables($docSheet, $dir, $fileWorksheet, $zip, $unparsedLoadedData); + } + if ($xmlSheetNS && $xmlSheetNS->mergeCells && $xmlSheetNS->mergeCells->mergeCell && !$this->readDataOnly) { foreach ($xmlSheetNS->mergeCells->mergeCell as $mergeCellx) { $mergeCell = $mergeCellx->attributes(); @@ -1147,6 +1121,10 @@ protected function loadSpreadsheetFromFile(string $filename): Spreadsheet (new DataValidations($docSheet, $xmlSheet))->load(); } + if ($xmlSheet && !$this->readDataOnly) { + (new Sparklines($docSheet, $xmlSheet))->load(); + } + // unparsed sheet AlternateContent if ($xmlSheet && !$this->readDataOnly) { $mc = $xmlSheet->children(Namespaces::COMPATIBILITY); @@ -1980,6 +1958,22 @@ protected function loadSpreadsheetFromFile(string $filename): Spreadsheet } } } + + // Preserve the workbook registry (cacheId + // -> cache definition part) so pivot tables survive a + // load/save round-trip. + if (!$this->readDataOnly && $xmlWorkbook->pivotCaches && $xmlWorkbook->pivotCaches->pivotCache) { + foreach ($xmlWorkbook->pivotCaches->pivotCache as $pivotCache) { + $pivotCacheAttributes = self::getAttributes($pivotCache); + $relId = (string) self::getAttributes($pivotCache, Namespaces::SCHEMA_OFFICE_DOCUMENT)['id']; + if (isset($pivotCacheRels[$relId])) { + $unparsedLoadedData['workbookPivotCaches'][] = [ + 'cacheId' => (string) $pivotCacheAttributes['cacheId'], + 'cacheDefinitionPath' => $pivotCacheRels[$relId], + ]; + } + } + } } if ($this->createBlankSheetIfNoneRead && !$sheetCreated) { $excel->createSheet(); @@ -2040,6 +2034,9 @@ protected function loadSpreadsheetFromFile(string $filename): Spreadsheet // unparsed case 'application/vnd.ms-excel.controlproperties+xml': + case 'application/vnd.openxmlformats-officedocument.spreadsheetml.pivotTable+xml': + case 'application/vnd.openxmlformats-officedocument.spreadsheetml.pivotCacheDefinition+xml': + case 'application/vnd.openxmlformats-officedocument.spreadsheetml.pivotCacheRecords+xml': $unparsedLoadedData['override_content_types'][(string) $contentType['PartName']] = (string) $contentType['ContentType']; break; @@ -2055,7 +2052,206 @@ protected function loadSpreadsheetFromFile(string $filename): Spreadsheet return $excel; } - private function parseRichText(?SimpleXMLElement $is): RichText + /** + * @param string[][] $richData + * @param Worksheet $docSheet the worksheet to populate + * @param array $sharedStrings shared string table + * @param object[] $styles style objects array + * @param mixed[] $extraParameters maybe make it a little easier to extend + */ + protected function loadSheetData( + ?SimpleXMLElement $xmlSheetNS, + string $filename, + string $dir, + array $richData, + Worksheet $docSheet, + array $sharedStrings, + array $styles, + array $extraParameters = [], + ): void { + if (!($xmlSheetNS && $xmlSheetNS->sheetData && $xmlSheetNS->sheetData->row)) { + return; // @codeCoverageIgnore + } + + $cIndex = 1; // Cell Start from 1 + foreach ($xmlSheetNS->sheetData->row as $row) { + $rowIndex = 1; + foreach ($row->c as $c) { + $cAttr = self::getAttributes($c); + $r = (string) $cAttr['r']; + if ($r == '') { + $r = Coordinate::stringFromColumnIndex($rowIndex) . $cIndex; + } + $cellDataType = (string) $cAttr['t']; + $originalCellDataTypeNumeric = $cellDataType === ''; + $value = null; + $calculatedValue = null; + + // Read cell? + $coordinates = Coordinate::coordinateFromString($r); + + if (!$this->readFilter->readCell($coordinates[0], (int) $coordinates[1], $docSheet->getTitle())) { + // Normally, just testing for the f attribute should identify this cell as containing a formula + // that we need to read, even though it is outside of the filter range, in case it is a shared formula. + // But in some cases, this attribute isn't set; so we need to delve a level deeper and look at + // whether or not the cell has a child formula element that is shared. + if (isset($cAttr->f) || (isset($c->f, $c->f->attributes()['t']) && strtolower((string) $c->f->attributes()['t']) === 'shared')) { + $this->castToFormula($c, $r, $cellDataType, $value, $calculatedValue, 'castToError', false); + } + ++$rowIndex; + + continue; + } + + // Read cell! + $useFormula = isset($c->f) + && ((string) $c->f !== '' || (isset($c->f->attributes()['t']) && strtolower((string) $c->f->attributes()['t']) === 'shared')); + switch ($cellDataType) { + case DataType::TYPE_STRING: + if ((string) $c->v != '') { + $value = $sharedStrings[(int) ($c->v)]; + + if ($value instanceof RichText) { + $value = clone $value; + } + } else { + $value = ''; + } + + break; + case DataType::TYPE_BOOL: + if (!$useFormula) { + if (isset($c->v)) { + $value = self::castToBoolean($c); + } else { + $value = null; + $cellDataType = DataType::TYPE_NULL; + } + } else { + // Formula + $this->castToFormula($c, $r, $cellDataType, $value, $calculatedValue, 'castToBoolean'); + self::storeFormulaAttributes($c->f, $docSheet, $r); + } + + break; + case DataType::TYPE_STRING2: + if ($useFormula) { + $this->castToFormula($c, $r, $cellDataType, $value, $calculatedValue, 'castToString'); + self::storeFormulaAttributes($c->f, $docSheet, $r); + } else { + $value = self::castToString($c); + } + + break; + case DataType::TYPE_INLINE: + if ($useFormula) { + $this->castToFormula($c, $r, $cellDataType, $value, $calculatedValue, 'castToError'); + self::storeFormulaAttributes($c->f, $docSheet, $r); + } else { + $value = $this->parseRichText($c->is); + } + + break; + case DataType::TYPE_ERROR: + if (isset($cAttr->vm, $richData['image']['rId' . $cAttr->vm]) && !$useFormula) { + $imagePath = $dir . '/' . str_replace('../', '', $richData['image']['rId' . $cAttr->vm]); + $objDrawing = new \PhpOffice\PhpSpreadsheet\Worksheet\Drawing(); + $objDrawing->setPath( + 'zip://' . File::realpath($filename) . '#' . $imagePath, + false, + $this->zip + ); + + $objDrawing->setCoordinates($r); + $objDrawing->setResizeProportional(false); + $objDrawing->setInCell(true); + $objDrawing->setWorksheet($docSheet); + + $value = $objDrawing; + $cellDataType = DataType::TYPE_DRAWING_IN_CELL; + $c->t = DataType::TYPE_ERROR; + + break; + } + + if (!$useFormula) { + $value = self::castToError($c); + } else { + // Formula + $this->castToFormula($c, $r, $cellDataType, $value, $calculatedValue, 'castToError'); + $eattr = $c->attributes(); + if (isset($eattr['vm'])) { + if ($calculatedValue === ExcelError::VALUE()) { + $calculatedValue = ExcelError::SPILL(); + } + } + } + + break; + default: + if (!$useFormula) { + $value = self::castToString($c); + if (is_numeric($value)) { + $value += 0; + $cellDataType = DataType::TYPE_NUMERIC; + } + } else { + // Formula + $this->castToFormula($c, $r, $cellDataType, $value, $calculatedValue, 'castToString'); + if (is_numeric($calculatedValue)) { + $calculatedValue += 0; + } + self::storeFormulaAttributes($c->f, $docSheet, $r); + } + + break; + } + + // read empty cells or the cells are not empty + if ($this->readEmptyCells || ($value !== null && $value !== '')) { + // Rich text? + if ($value instanceof RichText && $this->readDataOnly) { + $value = $value->getPlainText(); + } + + $cell = $docSheet->getCell($r); + // Assign value + if ($cellDataType != '') { + // it is possible, that datatype is numeric but with an empty string, which result in an error + if ($cellDataType === DataType::TYPE_NUMERIC && ($value === '' || $value === null)) { + $cellDataType = DataType::TYPE_NULL; + } + if ($cellDataType !== DataType::TYPE_NULL) { + $cell->setValueExplicit($value, $cellDataType); + } + } else { + $cell->setValue($value); + } + if ($calculatedValue !== null) { + $cell->setCalculatedValue($calculatedValue, $originalCellDataTypeNumeric); + } + + // Style information? + if (!$this->readDataOnly) { + $cAttrS = (int) ($cAttr['s'] ?? 0); + // no style index means 0, it seems + $cAttrS = isset($styles[$cAttrS]) ? $cAttrS : 0; + $cell->setXfIndex($cAttrS); + // issue 3495 + if ($cellDataType === DataType::TYPE_FORMULA && $styles[$cAttrS]->quotePrefix === true) { //* @phpstan-ignore property.notFound (quotePrefix does exist) + $holdSelected = $docSheet->getSelectedCells(); + $cell->getStyle()->setQuotePrefix(false); + $docSheet->setSelectedCells($holdSelected); + } + } + } + ++$rowIndex; + } + ++$cIndex; + } + } + + protected function parseRichText(?SimpleXMLElement $is): RichText { $value = new RichText(); @@ -2366,7 +2562,7 @@ private static function getLockValue(SimpleXMLElement $protection, string $key): { $returnValue = null; $protectKey = $protection[$key]; - if (!empty($protectKey)) { + if (isset($protectKey)) { $protectKey = (string) $protectKey; $returnValue = $protectKey !== 'false' && (bool) $protectKey; } @@ -2583,6 +2779,166 @@ private function readTablesInTablesFile( } } + /** + * Discover the pivot table parts referenced by a worksheet, parse them into + * the read-only PivotTable object model, and preserve every associated raw + * XML part (pivot table, cache definition, cache records and their rels) in + * the unparsed loaded data so they can be written back unchanged. + * + * @param mixed[] $unparsedLoadedData + */ + private function readPivotTables( + Worksheet $docSheet, + string $dir, + string $fileWorksheet, + ZipArchive $zip, + array &$unparsedLoadedData + ): void { + $relationsFileName = dirname("$dir/$fileWorksheet") . '/_rels/' . basename($fileWorksheet) . '.rels'; + if ($zip->locateName($relationsFileName) === false) { + return; + } + + $relsWorksheet = $this->loadZip($relationsFileName, Namespaces::RELATIONSHIPS); + foreach ($relsWorksheet->Relationship as $relationship) { + $relAttributes = self::getAttributes($relationship, ''); + if ((string) $relAttributes['Type'] !== Namespaces::RELATIONSHIPS_PIVOT_TABLE) { + continue; + } + + $relTarget = (string) $relAttributes['Target']; + $pivotTablePath = File::realpath(dirname("$dir/$fileWorksheet") . '/' . $relTarget); + if (!$this->fileExistsInArchive($this->zip, $pivotTablePath)) { + continue; + } + + $pivotTableXml = $this->loadZip($pivotTablePath, Namespaces::MAIN); + $cacheDefinitionXml = $this->readPivotCacheDefinition($pivotTablePath, $zip, $unparsedLoadedData); + + (new PivotTableReader($docSheet, $pivotTableXml, $cacheDefinitionXml))->load(); + + // Preserve the raw pivot table part (and its rels) for write-back. + $sheetCodeName = $docSheet->getCodeName(); + if (!isset($unparsedLoadedData['sheets']) || !is_array($unparsedLoadedData['sheets'])) { + $unparsedLoadedData['sheets'] = []; + } + if (!isset($unparsedLoadedData['sheets'][$sheetCodeName]) || !is_array($unparsedLoadedData['sheets'][$sheetCodeName])) { + $unparsedLoadedData['sheets'][$sheetCodeName] = []; + } + /** @var array $sheetUnparsedData */ + $sheetUnparsedData = &$unparsedLoadedData['sheets'][$sheetCodeName]; + if (!isset($sheetUnparsedData['pivotTables']) || !is_array($sheetUnparsedData['pivotTables'])) { + $sheetUnparsedData['pivotTables'] = []; + } + /** @var array> $sheetPivotTables */ + $sheetPivotTables = &$sheetUnparsedData['pivotTables']; + $sheetPivotTables[] = [ + 'relFilePath' => $relTarget, + 'path' => $pivotTablePath, + 'content' => $this->getSecurityScannerOrThrow()->scan($this->getFromZipArchive($this->zip, $pivotTablePath)), + ]; + unset($sheetPivotTables, $sheetUnparsedData); + $this->preserveRawPart( + dirname($pivotTablePath) . '/_rels/' . basename($pivotTablePath) . '.rels', + $unparsedLoadedData + ); + } + } + + /** + * Follow a pivot table part's relationships to load its cache definition + * part, preserving the cache definition, its records and all of their rels + * as raw parts. Returns the parsed cache definition XML, or null. + * + * @param mixed[] $unparsedLoadedData + */ + private function readPivotCacheDefinition(string $pivotTablePath, ZipArchive $zip, array &$unparsedLoadedData): ?SimpleXMLElement + { + $relsFileName = dirname($pivotTablePath) . '/_rels/' . basename($pivotTablePath) . '.rels'; + if ($zip->locateName($relsFileName) === false) { + return null; + } + + $rels = $this->loadZip($relsFileName, Namespaces::RELATIONSHIPS); + foreach ($rels->Relationship as $relationship) { + $relAttributes = self::getAttributes($relationship, ''); + if ((string) $relAttributes['Type'] === Namespaces::RELATIONSHIPS_PIVOT_CACHE_DEFINITION) { + $cachePath = File::realpath( + dirname($pivotTablePath) . '/' . (string) $relAttributes['Target'] + ); + if (!$this->fileExistsInArchive($this->zip, $cachePath)) { + return null; + } + + $cacheDefinitionXml = $this->loadZip($cachePath, Namespaces::MAIN); + $this->preservePivotCache($cachePath, $unparsedLoadedData); + + return $cacheDefinitionXml; + } + } + + return null; + } + + /** + * Preserve a pivot cache definition (keyed by its zip path so a workbook + * relationship can be recreated), along with its rels and any parts they + * reference (typically the cache records). + * + * @param mixed[] $unparsedLoadedData + */ + private function preservePivotCache(string $cachePath, array &$unparsedLoadedData): void + { + if (!isset($unparsedLoadedData['pivotCacheDefinitions']) || !is_array($unparsedLoadedData['pivotCacheDefinitions'])) { + $unparsedLoadedData['pivotCacheDefinitions'] = []; + } + /** @var array> $cacheDefinitions */ + $cacheDefinitions = &$unparsedLoadedData['pivotCacheDefinitions']; + if (!isset($cacheDefinitions[$cachePath])) { + $cacheDefinitions[$cachePath] = [ + 'path' => $cachePath, + 'content' => $this->getSecurityScannerOrThrow()->scan($this->getFromZipArchive($this->zip, $cachePath)), + ]; + unset($cacheDefinitions); + + $relsFileName = dirname($cachePath) . '/_rels/' . basename($cachePath) . '.rels'; + if ($this->zip->locateName($relsFileName) !== false) { + $this->preserveRawPart($relsFileName, $unparsedLoadedData); + + $rels = $this->loadZip($relsFileName, Namespaces::RELATIONSHIPS); + foreach ($rels->Relationship as $relationship) { + $relAttributes = self::getAttributes($relationship, ''); + $target = File::realpath(dirname($cachePath) . '/' . (string) $relAttributes['Target']); + if ($this->fileExistsInArchive($this->zip, $target)) { + $this->preserveRawPart($target, $unparsedLoadedData); + } + } + } + } + } + + /** + * Store a single part verbatim (keyed by its zip path) so the writer can + * re-add it to the archive without modification. + * + * @param mixed[] $unparsedLoadedData + */ + private function preserveRawPart(string $path, array &$unparsedLoadedData): void + { + if ($this->zip->locateName($path) === false) { + return; + } + if (!isset($unparsedLoadedData['pivotCacheParts']) || !is_array($unparsedLoadedData['pivotCacheParts'])) { + $unparsedLoadedData['pivotCacheParts'] = []; + } + /** @var array $pivotCacheParts */ + $pivotCacheParts = &$unparsedLoadedData['pivotCacheParts']; + $pivotCacheParts[$path] = $this->getSecurityScannerOrThrow()->scan( + $this->getFromZipArchive($this->zip, $path) + ); + unset($pivotCacheParts); + } + /** @return mixed[] */ private static function extractStyles(?SimpleXMLElement $sxml, string $node1, string $node2): array { @@ -2624,6 +2980,8 @@ private function processIgnoredErrors(SimpleXMLElement $xml, Worksheet $sheet): $formulaRange = (string) ($attributes['formulaRange'] ?? ''); $twoDigitTextYear = (string) ($attributes['twoDigitTextYear'] ?? ''); $evalError = (string) ($attributes['evalError'] ?? ''); + $attributes2 = self::getAttributes($xml, Namespaces::MISLEADING_FORMAT); + $misleadingFormat = (string) ($attributes2['misleadingFormat'] ?? ''); if (!empty($sqref)) { $explodedSqref = explode(' ', $sqref); $pattern1 = '/^([A-Z]{1,3})([0-9]{1,7})(:([A-Z]{1,3})([0-9]{1,7}))?$/'; @@ -2645,19 +3003,34 @@ private function processIgnoredErrors(SimpleXMLElement $xml, Worksheet $sheet): continue; } if ($numberStoredAsText === '1') { - $sheet->getCell("$col$row")->getIgnoredErrors()->setNumberStoredAsText(true); + $sheet->getCell("$col$row") + ->getIgnoredErrors() + ->setNumberStoredAsText(true); } if ($formula === '1') { - $sheet->getCell("$col$row")->getIgnoredErrors()->setFormula(true); + $sheet->getCell("$col$row") + ->getIgnoredErrors() + ->setFormula(true); } if ($formulaRange === '1') { - $sheet->getCell("$col$row")->getIgnoredErrors()->setFormulaRange(true); + $sheet->getCell("$col$row") + ->getIgnoredErrors() + ->setFormulaRange(true); } if ($twoDigitTextYear === '1') { - $sheet->getCell("$col$row")->getIgnoredErrors()->setTwoDigitTextYear(true); + $sheet->getCell("$col$row") + ->getIgnoredErrors() + ->setTwoDigitTextYear(true); } if ($evalError === '1') { - $sheet->getCell("$col$row")->getIgnoredErrors()->setEvalError(true); + $sheet->getCell("$col$row") + ->getIgnoredErrors() + ->setEvalError(true); + } + if ($misleadingFormat === '1') { + $sheet->getCell("$col$row") + ->getIgnoredErrors() + ->setMisleadingFormat(true); } } } @@ -2666,7 +3039,7 @@ private function processIgnoredErrors(SimpleXMLElement $xml, Worksheet $sheet): } } - private static function storeFormulaAttributes(SimpleXMLElement $f, Worksheet $docSheet, string $r): void + protected static function storeFormulaAttributes(SimpleXMLElement $f, Worksheet $docSheet, string $r): void { $formulaAttributes = []; $attributes = $f->attributes(); diff --git a/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Xlsx/Chart.php b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Xlsx/Chart.php index 4ae3fd4e..d00a7aed 100644 --- a/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Xlsx/Chart.php +++ b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Xlsx/Chart.php @@ -8,6 +8,7 @@ use PhpOffice\PhpSpreadsheet\Chart\ChartColor; use PhpOffice\PhpSpreadsheet\Chart\DataSeries; use PhpOffice\PhpSpreadsheet\Chart\DataSeriesValues; +use PhpOffice\PhpSpreadsheet\Chart\DataTable; use PhpOffice\PhpSpreadsheet\Chart\GridLines; use PhpOffice\PhpSpreadsheet\Chart\Layout; use PhpOffice\PhpSpreadsheet\Chart\Legend; @@ -91,13 +92,26 @@ public function readChart(SimpleXMLElement $chartElements, string $chartName): \ $chartFillColor = null; $gradientArray = []; $gradientLin = null; - $roundedCorners = false; + $roundedCorners = null; + $date1904 = null; + $lang = null; $gapWidth = null; $useUpBars = null; $useDownBars = null; $noBorder = false; + $pageMargins = []; + $pageSetup = []; foreach ($chartElementsC as $chartElementKey => $chartElement) { switch ($chartElementKey) { + case 'printSettings': + if (isset($chartElement->pageMargins)) { + $pageMargins = current((array) $chartElement->pageMargins->attributes()); + } + if (isset($chartElement->pageSetup)) { + $pageSetup = current((array) $chartElement->pageSetup->attributes()); + } + + break; case 'spPr': $children = $chartElementsC->spPr->children($this->aNamespace); if (isset($children->noFill)) { @@ -116,16 +130,22 @@ public function readChart(SimpleXMLElement $chartElements, string $chartName): \ break; case 'roundedCorners': - /** @var bool $roundedCorners */ $roundedCorners = self::getAttributeBoolean($chartElementsC->roundedCorners, 'val'); + break; + case 'date1904': + $date1904 = self::getAttributeBoolean($chartElementsC->date1904, 'val'); + + break; + case 'lang': + $lang = self::getAttributeString($chartElementsC->lang, 'val'); + break; case 'chart': foreach ($chartElement as $chartDetailsKey => $chartDetails) { $chartDetails = Xlsx::testSimpleXml($chartDetails); switch ($chartDetailsKey) { case 'autoTitleDeleted': - /** @var bool $autoTitleDeleted */ $autoTitleDeleted = self::getAttributeBoolean($chartElementsC->chart->autoTitleDeleted, 'val'); break; @@ -137,7 +157,7 @@ public function readChart(SimpleXMLElement $chartElements, string $chartName): \ break; case 'plotArea': - $plotAreaLayout = $XaxisLabel = $YaxisLabel = null; + $plotAreaLayout = $XaxisLabel = $YaxisLabel = $dataTable = null; $plotSeries = $plotAttributes = []; $catAxRead = false; $plotNoFill = false; @@ -358,6 +378,10 @@ public function readChart(SimpleXMLElement $chartElements, string $chartName): \ } $plotAttributes = $this->readChartAttributes($chartDetail); + break; + case 'dTable': + $dataTable = $this->readDataTable($chartDetail); + break; } } @@ -365,6 +389,11 @@ public function readChart(SimpleXMLElement $chartElements, string $chartName): \ $plotAreaLayout = new Layout(); } $plotArea = new PlotArea($plotAreaLayout, $plotSeries); + if ($dataTable !== null) { + $plotArea->setDataTable( + $dataTable + ); + } $this->setChartAttributes($plotAreaLayout, $plotAttributes); if ($plotNoFill) { $plotArea->setNoFill(true); @@ -472,23 +501,18 @@ public function readChart(SimpleXMLElement $chartElements, string $chartName): \ if ($chartBorderLines !== null) { $chart->setBorderLines($chartBorderLines); } - $chart->setNoBorder($noBorder); - $chart->setRoundedCorners($roundedCorners); - if (is_bool($autoTitleDeleted)) { - $chart->setAutoTitleDeleted($autoTitleDeleted); - } - if (is_int($rotX)) { - $chart->setRotX($rotX); - } - if (is_int($rotY)) { - $chart->setRotY($rotY); - } - if (is_int($rAngAx)) { - $chart->setRAngAx($rAngAx); - } - if (is_int($perspective)) { - $chart->setPerspective($perspective); - } + $chart + ->setNoBorder($noBorder) + ->setRoundedCorners($roundedCorners) + ->setDate1904($date1904) + ->setLang($lang) + ->setPageMargins($pageMargins) + ->setPageSetup($pageSetup) + ->setAutoTitleDeleted($autoTitleDeleted) + ->setRotX($rotX) + ->setRotY($rotY) + ->setRAngAx($rAngAx) + ->setPerspective($perspective); return $chart; } @@ -1289,12 +1313,38 @@ private function readChartAttributes(?SimpleXMLElement $chartDetail): array $plotAttributes['labelEffects'] = $labelEffects; } } + if (isset($txpr->bodyPr)) { + $plotAttributes['bodyPr'] = current((array) $txpr->bodyPr->attributes()); + } } } return $plotAttributes; } + private function readDataTable(SimpleXMLElement $chartDetail): DataTable + { + $dataTable = new DataTable(); + $temp = self::getAttributeBoolean($chartDetail->showHorzBorder, 'val'); + if ($temp !== null) { + $dataTable->setShowHorizontalBorder($temp); + } + $temp = self::getAttributeBoolean($chartDetail->showVertBorder, 'val'); + if ($temp !== null) { + $dataTable->setShowVerticalBorder($temp); + } + $temp = self::getAttributeBoolean($chartDetail->showOutline, 'val'); + if ($temp !== null) { + $dataTable->setShowOutline($temp); + } + $temp = self::getAttributeBoolean($chartDetail->showKeys, 'val'); + if ($temp !== null) { + $dataTable->setShowKeys($temp); + } + + return $dataTable; + } + /** @param array $plotAttributes */ private function setChartAttributes(Layout $plotArea, array $plotAttributes): void { @@ -1333,6 +1383,11 @@ private function setChartAttributes(Layout $plotArea, array $plotAttributes): vo /** @var ?Font $plotAttributeValue */ $plotArea->setLabelFont($plotAttributeValue); + break; + case 'bodyPr': + /** @var mixed $plotAttributeValue */ + $plotArea->setBodyPr($plotAttributeValue); + break; } } diff --git a/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Xlsx/ConditionalStyles.php b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Xlsx/ConditionalStyles.php index dda02793..e41806ea 100644 --- a/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Xlsx/ConditionalStyles.php +++ b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Xlsx/ConditionalStyles.php @@ -302,7 +302,7 @@ private function readDataBarOfConditionalRule(SimpleXMLElement $cfRule, array $c //conditionalFormatValueObjects $cfvoXml = $cfRule->dataBar->cfvo; $cfvoIndex = 0; - foreach ((count($cfvoXml) > 1 ? $cfvoXml : [$cfvoXml]) as $cfvo) { //* @phpstan-ignore-line + foreach ((count($cfvoXml) > 1 ? $cfvoXml : [$cfvoXml]) as $cfvo) { //* @phpstan-ignore foreach.nonIterable (I don't know how to fix this) /** @var SimpleXMLElement $cfvo */ if ($cfvoIndex === 0) { $dataBar->setMinimumConditionalFormatValueObject(new ConditionalFormatValueObject((string) $cfvo['type'], (string) $cfvo['val'])); @@ -405,7 +405,7 @@ private function readDataBarExtLstOfConditionalRule(ConditionalDataBar $dataBar, { if (isset($cfRule->extLst)) { $ns = $cfRule->extLst->getNamespaces(true); - foreach ((count($cfRule->extLst) > 0 ? $cfRule->extLst->ext : [$cfRule->extLst->ext]) as $ext) { //* @phpstan-ignore-line + foreach ((count($cfRule->extLst) > 0 ? $cfRule->extLst->ext : [$cfRule->extLst->ext]) as $ext) { //* @phpstan-ignore foreach.nonIterable (I don't know how to fix this) /** @var SimpleXMLElement $ext */ $extId = (string) $ext->children($ns['x14'])->id; if (isset($conditionalFormattingRuleExtensions[$extId]) && (string) $ext['uri'] === '{B025F937-C7B1-47D3-B67F-A62EFF666E3E}') { diff --git a/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Xlsx/Namespaces.php b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Xlsx/Namespaces.php index 5d94f2fd..c414c09f 100644 --- a/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Xlsx/Namespaces.php +++ b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Xlsx/Namespaces.php @@ -88,6 +88,12 @@ class Namespaces const RELATIONSHIPS_TABLE = 'http://schemas.openxmlformats.org/officeDocument/2006/relationships/table'; + const RELATIONSHIPS_PIVOT_TABLE = 'http://schemas.openxmlformats.org/officeDocument/2006/relationships/pivotTable'; + + const RELATIONSHIPS_PIVOT_CACHE_DEFINITION = 'http://schemas.openxmlformats.org/officeDocument/2006/relationships/pivotCacheDefinition'; + + const RELATIONSHIPS_PIVOT_CACHE_RECORDS = 'http://schemas.openxmlformats.org/officeDocument/2006/relationships/pivotCacheRecords'; + const SPREADSHEETML_AC = 'http://schemas.microsoft.com/office/spreadsheetml/2009/9/ac'; const DC_ELEMENTS = 'http://purl.org/dc/elements/1.1/'; @@ -133,4 +139,8 @@ class Namespaces const FEATURE_PROPERTY_BAG = 'http://schemas.microsoft.com/office/spreadsheetml/2022/featurepropertybag'; const RELATIONSHIPS_FEATURE_PROPERTY_BAG = 'http://schemas.microsoft.com/office/2022/11/relationships/FeaturePropertyBag'; const STYLE_CHECKBOX_URI = '{C7286773-470A-42A8-94C5-96B5CB345126}'; + + const SPARKLINE_URI = '{05C60535-1F16-4fd2-B633-F4F36F0B64E0}'; + + const MISLEADING_FORMAT = 'http://schemas.microsoft.com/office/spreadsheetml/2018/08/main'; } diff --git a/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Xlsx/PivotTableReader.php b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Xlsx/PivotTableReader.php new file mode 100644 index 00000000..d3e2e3c9 --- /dev/null +++ b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Xlsx/PivotTableReader.php @@ -0,0 +1,141 @@ +worksheet = $worksheet; + $this->pivotTableXml = $pivotTableXml; + $this->cacheDefinitionXml = $cacheDefinitionXml; + } + + /** + * Parse the pivot table definition and add it to the worksheet. + */ + public function load(): void + { + $attributes = $this->pivotTableXml->attributes(); + + $pivotTable = new PivotTable((string) ($attributes['name'] ?? '')); + + if (isset($this->pivotTableXml->location)) { + $locationAttributes = $this->pivotTableXml->location->attributes(); + $pivotTable->setLocation((string) ($locationAttributes['ref'] ?? '')); + } + + $cacheDefinition = $this->readCacheDefinition( + isset($attributes['cacheId']) ? (int) $attributes['cacheId'] : null + ); + $pivotTable->setCacheDefinition($cacheDefinition); + + if (isset($this->pivotTableXml->pivotFields)) { + $this->readFields($pivotTable, $cacheDefinition); + } + + $this->worksheet->addPivotTable($pivotTable); + } + + /** + * Build the cache definition (source range + field names) if we have it. + */ + private function readCacheDefinition(?int $cacheId): PivotCacheDefinition + { + $cacheDefinition = new PivotCacheDefinition($cacheId); + + if ($this->cacheDefinitionXml !== null) { + $source = $this->cacheDefinitionXml->cacheSource; + if (isset($source->worksheetSource)) { + $sourceAttributes = $source->worksheetSource->attributes(); + if (isset($sourceAttributes['sheet'])) { + $cacheDefinition->setSourceWorksheet((string) $sourceAttributes['sheet']); + } + if (isset($sourceAttributes['ref'])) { + $cacheDefinition->setSourceRange((string) $sourceAttributes['ref']); + } + } + + if (isset($this->cacheDefinitionXml->cacheFields)) { + foreach ($this->cacheDefinitionXml->cacheFields->cacheField as $cacheField) { + $fieldAttributes = $cacheField->attributes(); + $cacheDefinition->addCacheField((string) ($fieldAttributes['name'] ?? '')); + } + } + } + + return $cacheDefinition; + } + + /** + * Read the pivotFields and the axis/data placement sections into fields. + */ + private function readFields(PivotTable $pivotTable, PivotCacheDefinition $cacheDefinition): void + { + $index = 0; + /** @var PivotField[] $fields */ + $fields = []; + foreach ($this->pivotTableXml->pivotFields->pivotField as $pivotFieldXml) { + $field = new PivotField($index, (string) ($cacheDefinition->getCacheFieldName($index) ?? '')); + + $fieldAttributes = $pivotFieldXml->attributes(); + if (isset($fieldAttributes['axis'])) { + $field->setAxis((string) $fieldAttributes['axis']); + } + + $fields[$index] = $field; + $pivotTable->addField($field); + ++$index; + } + + $this->markDataFields($fields); + } + + /** + * Flag the fields referenced by as value fields, and record + * their aggregation function. + * + * @param PivotField[] $fields keyed by field index + */ + private function markDataFields(array $fields): void + { + if (isset($this->pivotTableXml->dataFields)) { + foreach ($this->pivotTableXml->dataFields->dataField as $dataFieldXml) { + $dataAttributes = $dataFieldXml->attributes(); + if (isset($dataAttributes['fld'])) { + $fieldIndex = (int) $dataAttributes['fld']; + if (isset($fields[$fieldIndex])) { + $fields[$fieldIndex]->setDataField(true); + // "sum" is the default subtotal when the attribute is absent. + $fields[$fieldIndex]->setSubtotal( + isset($dataAttributes['subtotal']) ? (string) $dataAttributes['subtotal'] : 'sum' + ); + } + } + } + } + } +} diff --git a/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Xlsx/Sparklines.php b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Xlsx/Sparklines.php new file mode 100644 index 00000000..04d1c3b7 --- /dev/null +++ b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Xlsx/Sparklines.php @@ -0,0 +1,163 @@ +worksheet = $workSheet; + $this->worksheetXml = $worksheetXml; + } + + public function load(): void + { + if (!isset($this->worksheetXml->extLst->ext)) { + return; + } + + foreach ($this->worksheetXml->extLst->ext as $ext) { + $extAttrs = $ext->attributes() ?? []; + if ((string) ($extAttrs['uri'] ?? '') !== Namespaces::SPARKLINE_URI) { + continue; + } + + $groups = $ext->children(Namespaces::DATA_VALIDATIONS1)->sparklineGroups; + if (!isset($groups)) { + continue; + } + + $groupList = $groups->children(Namespaces::DATA_VALIDATIONS1)->sparklineGroup ?? null; + if ($groupList === null) { + continue; + } + + foreach ($groupList as $groupXml) { + $group = $this->readGroup($groupXml); + if ($group !== null) { + $this->worksheet->addSparklineGroup($group); + } + } + } + } + + private function readGroup(SimpleXMLElement $groupXml): ?SparklineGroup + { + $group = new SparklineGroup(); + $attributes = $groupXml->attributes() ?? []; + + $typeValue = isset($attributes['type']) ? (string) $attributes['type'] : SparklineType::Line->value; + $group->setType(SparklineType::tryFrom($typeValue) ?? SparklineType::Line); + + if (isset($attributes['lineWeight'])) { + $group->setLineWeight((float) $attributes['lineWeight']); + } + if (isset($attributes['displayEmptyCellsAs'])) { + $group->setDisplayEmptyCellsAs((string) $attributes['displayEmptyCellsAs']); + } + if (isset($attributes['minAxisType'])) { + $group->setMinAxisType((string) $attributes['minAxisType']); + } + if (isset($attributes['maxAxisType'])) { + $group->setMaxAxisType((string) $attributes['maxAxisType']); + } + if (isset($attributes['manualMin'])) { + $group->setManualMin((float) $attributes['manualMin']); + } + if (isset($attributes['manualMax'])) { + $group->setManualMax((float) $attributes['manualMax']); + } + + $group->setDisplayMarkers(self::boolAttr($attributes, 'markers')); + $group->setDisplayHigh(self::boolAttr($attributes, 'high')); + $group->setDisplayLow(self::boolAttr($attributes, 'low')); + $group->setDisplayFirst(self::boolAttr($attributes, 'first')); + $group->setDisplayLast(self::boolAttr($attributes, 'last')); + $group->setDisplayNegative(self::boolAttr($attributes, 'negative')); + $group->setDisplayXAxis(self::boolAttr($attributes, 'displayXAxis')); + $group->setDisplayHidden(self::boolAttr($attributes, 'displayHidden')); + $group->setRightToLeft(self::boolAttr($attributes, 'rightToLeft')); + + $this->readColors($group, $groupXml); + $this->readSparklines($group, $groupXml); + + // A group with no sparklines carries no useful information. + return $group->getSparklines() === [] ? null : $group; + } + + private function readColors(SparklineGroup $group, SimpleXMLElement $groupXml): void + { + $children = $groupXml->children(Namespaces::DATA_VALIDATIONS1); + $group->setColorSeries(self::color($children->colorSeries)); + $group->setColorNegative(self::color($children->colorNegative)); + $group->setColorAxis(self::color($children->colorAxis)); + $group->setColorMarkers(self::color($children->colorMarkers)); + $group->setColorFirst(self::color($children->colorFirst)); + $group->setColorLast(self::color($children->colorLast)); + $group->setColorHigh(self::color($children->colorHigh)); + $group->setColorLow(self::color($children->colorLow)); + } + + private function readSparklines(SparklineGroup $group, SimpleXMLElement $groupXml): void + { + $sparklinesXml = $groupXml->children(Namespaces::DATA_VALIDATIONS1)->sparklines; + if (!isset($sparklinesXml)) { + return; + } + + $sparklineList = $sparklinesXml->children(Namespaces::DATA_VALIDATIONS1)->sparkline ?? null; + if ($sparklineList === null) { + return; + } + + foreach ($sparklineList as $sparklineXml) { + $xm = $sparklineXml->children(Namespaces::DATA_VALIDATIONS2); + $dataRange = isset($xm->f) ? (string) $xm->f : ''; + $location = isset($xm->sqref) ? (string) $xm->sqref : ''; + if ($location === '') { + continue; + } + $group->addSparkline(new Sparkline($location, $dataRange)); + } + } + + /** + * @param iterable|SimpleXMLElement $attributes + */ + private static function boolAttr(mixed $attributes, string $name): bool + { + if (!($attributes instanceof SimpleXMLElement)) { + return false; + } + $attrs = $attributes; + + return isset($attrs[$name]) && self::boolean((string) $attrs[$name]); + } + + /** + * Extract an ARGB colour from an `x14:color*` element's `rgb` attribute. + */ + private static function color(?SimpleXMLElement $colorXml): ?string + { + if ($colorXml === null || !isset($colorXml[0])) { + return null; + } + $attrs = $colorXml->attributes() ?? []; + + return isset($attrs['rgb']) ? (string) $attrs['rgb'] : null; + } +} diff --git a/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Xlsx/Styles.php b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Xlsx/Styles.php index 54e26e7c..1ef14591 100644 --- a/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Xlsx/Styles.php +++ b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Xlsx/Styles.php @@ -184,8 +184,8 @@ public function readFillStyle(Fill $fillStyle, SimpleXMLElement $fillStyleXml): } $fillStyle->setRotation((float) ($attr['degree'])); $gradientFill->registerXPathNamespace('sml', Namespaces::MAIN); - $fillStyle->getStartColor()->setARGB($this->readColor(self::getArrayItem($gradientFill->xpath('sml:stop[@position=0]'))->color)); //* @phpstan-ignore-line - $fillStyle->getEndColor()->setARGB($this->readColor(self::getArrayItem($gradientFill->xpath('sml:stop[@position=1]'))->color)); //* @phpstan-ignore-line + $fillStyle->getStartColor()->setARGB($this->readColor(self::getArrayItem($gradientFill->xpath('sml:stop[@position=0]'))->color)); //* @phpstan-ignore property.nonObject (xpath may return null) + $fillStyle->getEndColor()->setARGB($this->readColor(self::getArrayItem($gradientFill->xpath('sml:stop[@position=1]'))->color)); //* @phpstan-ignore property.nonObject (xpath may return null) } elseif ($fillStyleXml->patternFill) { $defaultFillStyle = ($fillStyle->getFillType() !== null) ? Fill::FILL_NONE : ''; $fgFound = false; @@ -549,10 +549,10 @@ public function styles(): array /** * Get array item. * - * @param false|mixed[] $array (usually array, in theory can be false) + * @param null|false|SimpleXMLElement[] $array (usually array, in theory can be false) */ private static function getArrayItem(mixed $array): ?SimpleXMLElement { - return is_array($array) ? ($array[0] ?? null) : null; // @phpstan-ignore-line + return is_array($array) ? ($array[0] ?? null) : null; } } diff --git a/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Xml.php b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Xml.php index 4fba7dcd..9e5bd997 100644 --- a/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Xml.php +++ b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Xml.php @@ -2,6 +2,7 @@ namespace PhpOffice\PhpSpreadsheet\Reader; +use Composer\Pcre\Preg; use DateTime; use DateTimeZone; use PhpOffice\PhpSpreadsheet\Cell\AddressHelper; @@ -53,9 +54,14 @@ public function __construct() public static function unentity(string $contents): string { - $contents = preg_replace('/&(amp|lt|gt|quot|apos);/', "\u{fffe}\u{feff}\$1;", trim($contents)) ?? $contents; + // fffe is invalid, replace with replacement char + $contents = str_replace("\u{fffe}", "\u{fffd}", $contents); + // use positive lookahead to "protect" valid xml entities + $contents = Preg::replace('/&(?=(?:amp|lt|gt|quot|apos|#[0-9]+|#x[0-9a-fA-F]+);)/', "\u{fffe}", trim($contents)); + // now decode remaining html entities $contents = html_entity_decode($contents, ENT_NOQUOTES | ENT_SUBSTITUTE | ENT_HTML401, 'UTF-8'); - $contents = str_replace("\u{fffe}\u{feff}", '&', $contents); + // Escape remaining ampersands, restore those which were replaced with fffe + $contents = str_replace(['&', "\u{fffe}"], ['&', '&'], $contents); return $contents; } @@ -432,7 +438,7 @@ public function loadIntoExisting(string $filename, Spreadsheet $spreadsheet, boo $arrayRef = AddressHelper::convertFormulaToA1($arrayRange, $rowID, $columnIndex); } - if (!$this->getReadFilter()->readCell($columnID, $rowID, $worksheetName)) { + if (!$this->readFilter->readCell($columnID, $rowID, $worksheetName)) { continue; } @@ -651,7 +657,7 @@ public function loadIntoExisting(string $filename, Spreadsheet $spreadsheet, boo } $rangeCalculated = false; if (isset($xmlX->WorksheetOptions->Panes->Pane->RangeSelection)) { - if (1 === preg_match('/^R(\d+)C(\d+):R(\d+)C(\d+)$/', (string) $xmlX->WorksheetOptions->Panes->Pane->RangeSelection, $selectionMatches)) { + if (Preg::isMatch('/^R(\d+)C(\d+):R(\d+)C(\d+)$/', (string) $xmlX->WorksheetOptions->Panes->Pane->RangeSelection, $selectionMatches)) { $selectedCell = Coordinate::stringFromColumnIndex((int) $selectionMatches[2]) . $selectionMatches[1] . ':' diff --git a/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Xml/PageSettings.php b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Xml/PageSettings.php index 2434e86a..e74f045b 100644 --- a/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Xml/PageSettings.php +++ b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Reader/Xml/PageSettings.php @@ -10,16 +10,27 @@ class PageSettings { - /** @var (object{orientation: string, scale: ?int, printOrder: ?string, - * paperSize: int, - * horizontalCentered: bool, verticalCentered: bool, leftMargin: float, rightMargin: float, topMargin: float, - * bottomMargin: float, headerMargin: float, footerMargin: float}&stdClass) */ + /** @var (object{ + * orientation: string, + * scale: ?int, + * printOrder: ?string, + * paperSize: int, + * horizontalCentered: bool, + * verticalCentered: bool, + * leftMargin: float, + * rightMargin: float, + * topMargin: float, + * bottomMargin: float, + * headerMargin: float, + * footerMargin: float, + * } &stdClass) + */ private stdClass $printSettings; public function __construct(SimpleXMLElement $xmlX) { $printSettings = $this->pageSetup($xmlX, $this->getPrintDefaults()); - $this->printSettings = $this->printSetup($xmlX, $printSettings); //* @phpstan-ignore-line + $this->printSettings = $this->printSetup($xmlX, $printSettings); //* @phpstan-ignore assign.propertyType (I don't know what Phpstan wants) } public function loadPageSettings(Spreadsheet $spreadsheet): void diff --git a/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Settings.php b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Settings.php index 9c2beaa0..7759d925 100644 --- a/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Settings.php +++ b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Settings.php @@ -52,8 +52,7 @@ public static function getLocale(): string */ public static function setChartRenderer(string $rendererClassName): void { - // We want phpstan to validate caller, but still need this test - if (!is_a($rendererClassName, IRenderer::class, true)) { //* @phpstan-ignore-line + if (!is_a($rendererClassName, IRenderer::class, true)) { throw new Exception('Chart renderer must implement ' . IRenderer::class); } diff --git a/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Shared/Date.php b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Shared/Date.php index 2e2df9ad..fbb48c92 100644 --- a/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Shared/Date.php +++ b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Shared/Date.php @@ -160,7 +160,7 @@ private static function validateTimeZone($timeZone): ?DateTimeZone * serialized timestamp. * See https://en.wikipedia.org/wiki/ISO_8601 for details of the ISO-8601 standard format. */ - public static function convertIsoDate(mixed $value): float|int + public static function convertIsoDate(mixed $value, ?int $calendar = null): float|int { if (!is_string($value)) { throw new Exception('Non-string value supplied for Iso Date conversion'); @@ -173,7 +173,7 @@ public static function convertIsoDate(mixed $value): float|int throw new Exception("Invalid string $value supplied for datatype Date"); } - $newValue = self::dateTimeToExcel($date); + $newValue = self::dateTimeToExcel($date, $calendar); if (preg_match('/^\s*\d?\d:\d\d(:\d\d([.]\d+)?)?\s*(am|pm)?\s*$/i', $value) == 1) { $newValue = fmod($newValue, 1.0); @@ -194,16 +194,17 @@ public static function convertIsoDate(mixed $value): float|int * * @return DateTime PHP date/time object */ - public static function excelToDateTimeObject(float|int $excelTimestamp, null|DateTimeZone|string $timeZone = null): DateTime + public static function excelToDateTimeObject(float|int $excelTimestamp, null|DateTimeZone|string $timeZone = null, ?int $calendar = null): DateTime { + $calendar ??= self::$excelCalendar; $timeZone = ($timeZone === null) ? self::getDefaultTimezone() : self::validateTimeZone($timeZone); if (Functions::getCompatibilityMode() == Functions::COMPATIBILITY_EXCEL) { - if ($excelTimestamp < 1 && self::$excelCalendar === self::CALENDAR_WINDOWS_1900) { + if ($excelTimestamp < 1 && $calendar === self::CALENDAR_WINDOWS_1900) { // Unix timestamp base date $baseDate = new DateTime('1970-01-01', $timeZone); } else { // MS Excel calendar base dates - if (self::$excelCalendar == self::CALENDAR_WINDOWS_1900) { + if ($calendar == self::CALENDAR_WINDOWS_1900) { // Allow adjustment for 1900 Leap Year in MS Excel $baseDate = ($excelTimestamp < 60) ? new DateTime('1899-12-31', $timeZone) : new DateTime('1899-12-30', $timeZone); } else { @@ -252,9 +253,9 @@ public static function excelToDateTimeObject(float|int $excelTimestamp, null|Dat * * @return int Unix timetamp for this date/time */ - public static function excelToTimestamp($excelTimestamp, $timeZone = null): int + public static function excelToTimestamp($excelTimestamp, $timeZone = null, ?int $calendar = null): int { - $dto = self::excelToDateTimeObject($excelTimestamp, $timeZone); + $dto = self::excelToDateTimeObject($excelTimestamp, $timeZone, $calendar); self::roundMicroseconds($dto); return (int) $dto->format('U'); @@ -269,14 +270,16 @@ public static function excelToTimestamp($excelTimestamp, $timeZone = null): int * @return false|float Excel date/time value * or boolean FALSE on failure */ - public static function PHPToExcel(mixed $dateValue) + public static function PHPToExcel(mixed $dateValue, ?int $calendar = null) { if ((is_object($dateValue)) && ($dateValue instanceof DateTimeInterface)) { - return self::dateTimeToExcel($dateValue); - } elseif (is_numeric($dateValue)) { - return self::timestampToExcel($dateValue); - } elseif (is_string($dateValue)) { - return self::stringToExcel($dateValue); + return self::dateTimeToExcel($dateValue, $calendar); + } + if (is_numeric($dateValue)) { + return self::timestampToExcel($dateValue, $calendar); + } + if (is_string($dateValue)) { + return self::stringToExcel($dateValue, $calendar); } return false; @@ -289,7 +292,7 @@ public static function PHPToExcel(mixed $dateValue) * * @return float MS Excel serialized date/time value */ - public static function dateTimeToExcel(DateTimeInterface $dateValue): float + public static function dateTimeToExcel(DateTimeInterface $dateValue, ?int $calendar = null): float { $seconds = (float) sprintf('%d.%06d', $dateValue->format('s'), $dateValue->format('u')); @@ -299,7 +302,8 @@ public static function dateTimeToExcel(DateTimeInterface $dateValue): float (int) $dateValue->format('d'), (int) $dateValue->format('H'), (int) $dateValue->format('i'), - $seconds + $seconds, + $calendar ); } @@ -312,13 +316,13 @@ public static function dateTimeToExcel(DateTimeInterface $dateValue): float * * @return false|float MS Excel serialized date/time value */ - public static function timestampToExcel($unixTimestamp): bool|float + public static function timestampToExcel($unixTimestamp, ?int $calendar = null): bool|float { if (!is_numeric($unixTimestamp)) { return false; } - return self::dateTimeToExcel(new DateTime('@' . $unixTimestamp)); + return self::dateTimeToExcel(new DateTime('@' . $unixTimestamp), $calendar); } /** @@ -326,9 +330,10 @@ public static function timestampToExcel($unixTimestamp): bool|float * * @return float Excel date/time value */ - public static function formattedPHPToExcel(int $year, int $month, int $day, int $hours = 0, int $minutes = 0, float|int $seconds = 0): float + public static function formattedPHPToExcel(int $year, int $month, int $day, int $hours = 0, int $minutes = 0, float|int $seconds = 0, ?int $calendar = null): float { - if (self::$excelCalendar == self::CALENDAR_WINDOWS_1900) { + $calendar ??= self::$excelCalendar; + if ($calendar === self::CALENDAR_WINDOWS_1900) { // // Fudge factor for the erroneous fact that the year 1900 is treated as a Leap Year in MS Excel // This affects every date following 28th February 1900 @@ -474,7 +479,7 @@ public static function isDateTimeFormatCode(string $excelFormatCode, bool $dateW * * @return false|float Excel date/time serial value */ - public static function stringToExcel(string $dateValue): bool|float + public static function stringToExcel(string $dateValue, ?int $calendar = null): bool|float { if (strlen($dateValue) < 2) { return false; @@ -483,7 +488,7 @@ public static function stringToExcel(string $dateValue): bool|float return false; } - $dateValueNew = DateTimeExcel\DateValue::fromString($dateValue); + $dateValueNew = DateTimeExcel\DateValue::fromString2($dateValue, $calendar); if (!is_float($dateValueNew)) { return false; diff --git a/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Shared/OLE.php b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Shared/OLE.php index 652d32f4..61c12708 100644 --- a/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Shared/OLE.php +++ b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Shared/OLE.php @@ -221,14 +221,17 @@ public function getStream($blockIdOrPps) // Store current instance in global array, so that it can be accessed // in OLE_ChainedBlockStream::stream_open(). // Object is removed from self::$instances in OLE_Stream::close(). - $GLOBALS['_OLE_INSTANCES'][] = $this; //* @phpstan-ignore-line - $keys = array_keys($GLOBALS['_OLE_INSTANCES']); //* @phpstan-ignore-line + $GLOBALS['_OLE_INSTANCES'][] = $this; //* @phpstan-ignore offsetAccess.nonOffsetAccessible (I don't know how to fix this) + $keys = array_keys($GLOBALS['_OLE_INSTANCES']); //* @phpstan-ignore argument.type (I don't know how to fix this) $instanceId = end($keys); $path = 'ole-chainedblockstream://oleInstanceId=' . $instanceId; if ($blockIdOrPps instanceof OLE\PPS) { $path .= '&blockId=' . $blockIdOrPps->startBlock; $path .= '&size=' . $blockIdOrPps->Size; + if ($blockIdOrPps instanceof Root) { + $path .= '&isRoot=1'; + } } else { $path .= '&blockId=' . $blockIdOrPps; } @@ -472,6 +475,86 @@ public function getDataLength(int $index): int return 0; } + /** + * Get the complete contents of a named file stream. + * + * @throws ReaderException if no file stream has the requested name + */ + public function getDataByName(string $name): string + { + foreach ($this->_list as $index => $pps) { + if ($pps->Type === self::OLE_PPS_TYPE_FILE && $pps->Name === $name) { + return $this->getData($index, 0, $pps->Size); + } + } + + throw new ReaderException("OLE stream '$name' was not found."); + } + + /** + * Check whether a named file stream exists without reading its contents. + */ + public function hasDataByName(string $name): bool + { + foreach ($this->_list as $pps) { + if ($pps->Type === self::OLE_PPS_TYPE_FILE && $pps->Name === $name) { + return true; + } + } + + return false; + } + + /** + * Copy a named file stream to an open output handle without loading a + * large stream into memory. + * + * @param resource $output + * + * @throws ReaderException if no file stream has the requested name + */ + public function copyDataByName(string $name, $output): void + { + foreach ($this->_list as $pps) { + if ($pps->Type !== self::OLE_PPS_TYPE_FILE || $pps->Name !== $name) { + continue; + } + if ($pps->Size < $this->bigBlockThreshold) { + $data = $this->getData($pps->No, 0, $pps->Size); + if (fwrite($output, $data) !== strlen($data)) { + throw new ReaderException("Could not write OLE stream '$name'."); + } + + return; + } + + $remaining = $pps->Size; + $blockId = $pps->startBlock; + $blocks = []; + while ($remaining > 0) { + if (!is_int($blockId) || $blockId === -2 || isset($blocks[$blockId], $this->bbat[$blockId])) { + throw new ReaderException("Invalid OLE stream '$name'."); + } + $blocks[$blockId] = true; + fseek($this->_file_handle, $this->getBlockOffset($blockId)); + $length = min($remaining, $this->bigBlockSize); + $data = fread($this->_file_handle, $length); + if ($data === false || strlen($data) !== $length || fwrite($output, $data) !== $length) { + throw new ReaderException("Could not copy OLE stream '$name'."); + } + $remaining -= $length; + $blockId = $this->bbat[$blockId] ?? null; + if (!is_int($blockId)) { + throw new ReaderException("Invalid OLE stream '$name'."); + } + } + + return; + } + + throw new ReaderException("OLE stream '$name' was not found."); + } + /** * Utility function to transform ASCII text to Unicode. * diff --git a/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Shared/OLE/ChainedBlockStream.php b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Shared/OLE/ChainedBlockStream.php index 76f1be71..21cc896b 100644 --- a/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Shared/OLE/ChainedBlockStream.php +++ b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Shared/OLE/ChainedBlockStream.php @@ -58,42 +58,66 @@ public function stream_open(string $path, string $mode, int $options, ?string &$ // 25 is length of "ole-chainedblockstream://" parse_str(substr($path, 25), $this->params); - if (!isset($this->params['oleInstanceId'], $this->params['blockId'], $GLOBALS['_OLE_INSTANCES'][$this->params['oleInstanceId']])) { //* @phpstan-ignore-line + if (!isset($this->params['oleInstanceId'], $this->params['blockId'], $GLOBALS['_OLE_INSTANCES'][$this->params['oleInstanceId']])) { //* @phpstan-ignore offsetAccess.nonOffsetAccessible (I don't know how to fix this) if ($options & STREAM_REPORT_ERRORS) { trigger_error('OLE stream not found', E_USER_WARNING); } return false; } - $this->ole = $GLOBALS['_OLE_INSTANCES'][$this->params['oleInstanceId']]; //* @phpstan-ignore-line - if (!($this->ole instanceof OLE)) { //* @phpstan-ignore-line + $this->ole = $GLOBALS['_OLE_INSTANCES'][$this->params['oleInstanceId']]; //* @phpstan-ignore assign.propertyType (I don't know how to fix this) + if (!($this->ole instanceof OLE)) { //* @phpstan-ignore instanceof.alwaysTrue (I don't know how to fix this) throw new Exception('class is not OLE'); } - $blockId = $this->params['blockId']; + $blockId = (int) $this->params['blockId']; + $size = isset($this->params['size']) ? (int) $this->params['size'] : null; + $isRoot = isset($this->params['isRoot']) && $this->params['isRoot'] === '1'; $this->data = ''; - if (isset($this->params['size']) && $this->params['size'] < $this->ole->bigBlockThreshold && $blockId != $this->ole->root->startBlock) { + if ($size !== null && $size < $this->ole->bigBlockThreshold && !$isRoot) { // Block id refers to small blocks - $rootPos = $this->ole->getBlockOffset((int) $this->ole->root->startBlock); + $rootData = ''; + if ($this->ole->root->startBlock === null) { + throw new Exception('Invalid OLE root mini-stream chain.'); + } + $rootBlockId = (int) $this->ole->root->startBlock; + $rootBlocks = []; + while ($rootBlockId !== -2) { + if (isset($rootBlocks[$rootBlockId], $this->ole->bbat[$rootBlockId])) { + throw new Exception('Invalid OLE root mini-stream chain.'); + } + $rootBlocks[$rootBlockId] = true; + fseek($this->ole->_file_handle, $this->ole->getBlockOffset($rootBlockId)); + $rootData .= fread($this->ole->_file_handle, $this->ole->bigBlockSize); + $rootBlockId = self::nextBlock($this->ole->bbat, $rootBlockId, 'Invalid OLE root mini-stream chain.'); + } + + $smallBlocks = []; while ($blockId != -2) { - /** @var int $blockId */ - $pos = $rootPos + $blockId * $this->ole->bigBlockSize; - $blockId = $this->ole->sbat[$blockId]; - fseek($this->ole->_file_handle, $pos); - $this->data .= fread($this->ole->_file_handle, $this->ole->bigBlockSize); + if (isset($smallBlocks[$blockId], $this->ole->sbat[$blockId])) { + throw new Exception('Invalid OLE mini-stream chain.'); + } + $smallBlocks[$blockId] = true; + $pos = $blockId * $this->ole->smallBlockSize; + $this->data .= substr($rootData, $pos, $this->ole->smallBlockSize); + $blockId = self::nextBlock($this->ole->sbat, $blockId, 'Invalid OLE mini-stream chain.'); } } else { // Block id refers to big blocks + $bigBlocks = []; while ($blockId != -2) { - /** @var int $blockId */ + if (isset($bigBlocks[$blockId], $this->ole->bbat[$blockId])) { + throw new Exception('Invalid OLE stream chain.'); + } + $bigBlocks[$blockId] = true; $pos = $this->ole->getBlockOffset($blockId); fseek($this->ole->_file_handle, $pos); $this->data .= fread($this->ole->_file_handle, $this->ole->bigBlockSize); - $blockId = $this->ole->bbat[$blockId]; + $blockId = self::nextBlock($this->ole->bbat, $blockId, 'Invalid OLE stream chain.'); } } - if (isset($this->params['size'])) { - $this->data = substr($this->data, 0, $this->params['size']); //* @phpstan-ignore-line + if ($size !== null) { + $this->data = substr($this->data, 0, $size); } if ($options & STREAM_USE_PATH) { @@ -103,6 +127,17 @@ public function stream_open(string $path, string $mode, int $options, ?string &$ return true; } + /** @param mixed[] $allocationTable */ + private static function nextBlock(array $allocationTable, int $blockId, string $message): int + { + $nextBlockId = $allocationTable[$blockId] ?? null; + if (!is_int($nextBlockId)) { + throw new Exception($message); + } + + return $nextBlockId; + } + /** * Implements support for fclose(). */ @@ -151,6 +186,10 @@ public function stream_tell(): int // @codingStandardsIgnoreLine /** * Implements support for fseek(). + * Note that the first condition is always true, at least in + * the unit test suite. One consequence is that Phpstan's + * correct flagging of count($this->data) below is never + * executed, and would fail should it be executed. * * @param int $offset byte offset * @param int $whence SEEK_SET, SEEK_CUR or SEEK_END @@ -161,7 +200,7 @@ public function stream_seek(int $offset, int $whence): bool // @codingStandardsI $this->pos = $offset; } elseif ($whence == SEEK_CUR && -$offset <= $this->pos) { $this->pos += $offset; - } elseif ($whence == SEEK_END && -$offset <= count($this->data)) { // @phpstan-ignore-line + } elseif ($whence == SEEK_END && -$offset <= count($this->data)) { // @phpstan-ignore argument.type (phpstan is correct - see docBlock above) $this->pos = strlen($this->data) + $offset; } else { return false; diff --git a/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Shared/OLE/PPS/Root.php b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Shared/OLE/PPS/Root.php index c92deb5a..9dca5067 100644 --- a/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Shared/OLE/PPS/Root.php +++ b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Shared/OLE/PPS/Root.php @@ -20,6 +20,7 @@ // | Based on OLE::Storage_Lite by Kawai, Takanori | // +----------------------------------------------------------------------+ // +use PhpOffice\PhpSpreadsheet\Exception; use PhpOffice\PhpSpreadsheet\Shared\OLE; use PhpOffice\PhpSpreadsheet\Shared\OLE\PPS; @@ -30,14 +31,22 @@ */ class Root extends PPS { + private const BIG_BLOCK_SIZE = 512; + + private const SMALL_BLOCK_SIZE = 64; + + private const MAX_VERSION_3_STREAM_SIZE = 0x80000000; + + private const MAX_REGULAR_SECTOR_COUNT = 0xFFFFFFFB; + /** * @var resource */ private $fileHandle; - private ?int $smallBlockSize = null; + private int $smallBlockSize = self::SMALL_BLOCK_SIZE; - private ?int $bigBlockSize = null; + private int $bigBlockSize = self::BIG_BLOCK_SIZE; /** * @param null|float|int $time_1st A timestamp @@ -64,13 +73,9 @@ public function save($fileHandle): bool { $this->fileHandle = $fileHandle; - // Initial Setting for saving - $this->bigBlockSize = (int) (2 ** ( - (isset($this->bigBlockSize)) ? self::adjust2($this->bigBlockSize) : 9 - )); - $this->smallBlockSize = (int) (2 ** ( - (isset($this->smallBlockSize)) ? self::adjust2($this->smallBlockSize) : 6 - )); + // This writer implements the version-3 CFB profile only. + $this->bigBlockSize = self::BIG_BLOCK_SIZE; + $this->smallBlockSize = self::SMALL_BLOCK_SIZE; // Make an array of PPS's (for Save) $aList = []; @@ -82,6 +87,7 @@ public function save($fileHandle): bool // Make Small Data string (write SBD) $this->_data = $this->makeSmallData($aList); + $this->assertVersion3StreamSize(strlen($this->_data)); // Write BB $this->saveBigData((int) $iSBDcnt, $aList); @@ -109,6 +115,7 @@ private function calcSize(array &$raList): array for ($i = 0; $i < $iCount; ++$i) { if ($raList[$i]->Type == OLE::OLE_PPS_TYPE_FILE) { $raList[$i]->Size = $raList[$i]->getDataLen(); + $this->assertVersion3StreamSize($raList[$i]->Size); if ($raList[$i]->Size < OLE::OLE_DATA_SIZE_SMALL) { $iSBcnt += floor($raList[$i]->Size / $this->smallBlockSize) + (($raList[$i]->Size % $this->smallBlockSize) ? 1 : 0); @@ -118,6 +125,7 @@ private function calcSize(array &$raList): array } } } + $this->assertVersion3MiniStreamSize((int) $iSBcnt); $iSmallLen = $iSBcnt * $this->smallBlockSize; $iSlCnt = floor($this->bigBlockSize / OLE::OLE_LONG_INT_SIZE); $iSBDcnt = floor($iSBcnt / $iSlCnt) + (($iSBcnt % $iSlCnt) ? 1 : 0); @@ -130,18 +138,16 @@ private function calcSize(array &$raList): array return [$iSBDcnt, $iBBcnt, $iPPScnt]; } - /** - * Helper function for calculating a magic value for block sizes. - * - * @param int $i2 The argument - * - * @see save() - */ - private static function adjust2(int $i2): float + private function assertVersion3StreamSize(int $size): void { - $iWk = log($i2) / log(2); + if ($size > self::MAX_VERSION_3_STREAM_SIZE) { + throw new Exception('OLE version-3 streams cannot exceed 2 GiB.'); + } + } - return ($iWk > floor($iWk)) ? floor($iWk) + 1 : $iWk; + private function assertVersion3MiniStreamSize(int $smallBlockCount): void + { + $this->assertVersion3StreamSize($smallBlockCount * self::SMALL_BLOCK_SIZE); } /** @@ -168,12 +174,16 @@ private function saveHeader(int $iSBDcnt, int $iBBcnt, int $iPPScnt): void ++$iAllW; $iBdCntW = floor($iAllW / $iBlCnt) + (($iAllW % $iBlCnt) ? 1 : 0); $iBdCnt = floor(($iAllW + $iBdCntW) / $iBlCnt) + ((($iAllW + $iBdCntW) % $iBlCnt) ? 1 : 0); - if ($iBdCnt <= ($iBdExL * $iBlCnt + $i1stBdL)) { + if ($iBdCnt <= ($iBdExL * ($iBlCnt - 1) + $i1stBdL)) { break; } } } + if ($iAllW + $iBdCnt > self::MAX_REGULAR_SECTOR_COUNT) { + throw new Exception('OLE version-3 output exceeds the maximum sector count.'); + } + // Save Header fwrite( $FILE, @@ -182,7 +192,7 @@ private function saveHeader(int $iSBDcnt, int $iBBcnt, int $iPPScnt): void . "\x00\x00\x00\x00" . "\x00\x00\x00\x00" . "\x00\x00\x00\x00" - . pack('v', 0x3B) + . pack('v', 0x3E) . pack('v', 0x03) . pack('v', -2) . pack('v', 9) @@ -198,7 +208,7 @@ private function saveHeader(int $iSBDcnt, int $iBBcnt, int $iPPScnt): void . pack('V', $iSBDcnt) ); // Extra BDList Start, Count - if ($iBdCnt < $i1stBdL) { + if ($iBdCnt <= $i1stBdL) { fwrite( $FILE, pack('V', -2) // Extra BDList Start @@ -342,7 +352,7 @@ private function saveBbd(int $iSbdSize, int $iBsize, int $iPpsCnt): void ++$iAllW; $iBdCntW = floor($iAllW / $iBbCnt) + (($iAllW % $iBbCnt) ? 1 : 0); $iBdCnt = floor(($iAllW + $iBdCntW) / $iBbCnt) + ((($iAllW + $iBdCntW) % $iBbCnt) ? 1 : 0); - if ($iBdCnt <= ($iBdExL * $iBbCnt + $i1stBdL)) { + if ($iBdCnt <= ($iBdExL * ($iBbCnt - 1) + $i1stBdL)) { break; } } diff --git a/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Shared/OLERead.php b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Shared/OLERead.php index 5d38e956..9ed4ba4f 100644 --- a/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Shared/OLERead.php +++ b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Shared/OLERead.php @@ -61,6 +61,9 @@ class OLERead /** @var mixed[][] */ private array $props = []; + /** @var int[] */ + private array $possibleLoop = []; + /** * Read the file. */ @@ -137,7 +140,9 @@ public function read(string $filename): void $sbdBlock = $this->sbdStartBlock; $this->smallBlockChain = ''; + $this->possibleLoop = []; while ($sbdBlock != -2) { + $this->catchLoop($sbdBlock); $pos = ($sbdBlock + 1) * self::BIG_BLOCK_SIZE; $this->smallBlockChain .= substr($this->data, $pos, 4 * $bbs); @@ -153,6 +158,14 @@ public function read(string $filename): void $this->readPropertySets(); } + private function catchLoop(int $sbdBlock): void + { + if (in_array($sbdBlock, $this->possibleLoop, true)) { + throw new ReaderException('Detected loop while iterating blocks'); + } + $this->possibleLoop[] = $sbdBlock; + } + /** * Extract binary stream data. */ @@ -172,7 +185,9 @@ public function getStream(?int $stream): ?string /** @var int */ $block = $this->props[$stream]['startBlock']; + $this->possibleLoop = []; while ($block != -2) { + $this->catchLoop($block); $pos = $block * self::SMALL_BLOCK_SIZE; $streamData .= substr($rootdata, $pos, self::SMALL_BLOCK_SIZE); @@ -195,7 +210,9 @@ public function getStream(?int $stream): ?string /** @var int */ $block = $this->props[$stream]['startBlock']; + $this->possibleLoop = []; while ($block != -2) { + $this->catchLoop($block); $pos = ($block + 1) * self::BIG_BLOCK_SIZE; $streamData .= substr($this->data, $pos, self::BIG_BLOCK_SIZE); $block = self::getInt4d($this->bigBlockChain, $block * 4); @@ -215,7 +232,9 @@ private function readData(int $block): string { $data = ''; + $this->possibleLoop = []; while ($block != -2) { + $this->catchLoop($block); $pos = ($block + 1) * self::BIG_BLOCK_SIZE; $data .= substr($this->data, $pos, self::BIG_BLOCK_SIZE); $block = self::getInt4d($this->bigBlockChain, $block * 4); diff --git a/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Shared/StringHelper.php b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Shared/StringHelper.php index 8717c1be..fe732887 100644 --- a/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Shared/StringHelper.php +++ b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Shared/StringHelper.php @@ -787,17 +787,34 @@ public static function convertPostToString(string $index, string $default = ''): * Php introduced str_increment with Php8.3, * but didn't issue deprecation notices till 8.5. * + * @param-out string $str + * * @codeCoverageIgnore */ public static function stringIncrement(string &$str): string { if (function_exists('str_increment')) { - $str = str_increment($str); // @phpstan-ignore-line + /** @var non-empty-string $str */ + $str2 = str_increment($str); } else { - ++$str; // @phpstan-ignore-line + $str1 = $str; + /** + * This is an outright lie, but I don't know how else to satisfy Phpstan for Php8.5+. + * + * @var numeric-string $str1 + */ + ++$str1; + $str2 = "$str1"; } - return $str; // @phpstan-ignore-line + /** + * This is demonstrably the case. I don't know why Phpstan thinks $str2 is mixed at this point. + * + * @var string $str2 set above by str_increment or ="..." + */ + $str = $str2; + + return $str; } /** @internal */ diff --git a/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Shared/Trend/PolynomialBestFit.php b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Shared/Trend/PolynomialBestFit.php index 0fc66717..a40f43bb 100644 --- a/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Shared/Trend/PolynomialBestFit.php +++ b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Shared/Trend/PolynomialBestFit.php @@ -24,7 +24,7 @@ class PolynomialBestFit extends BestFit */ protected int $order = 0; - private bool $implemented = false; + protected bool $implemented = false; /** * Return the order of this polynomial. @@ -45,9 +45,7 @@ public function getValueOfYForX(float $xValue): float { $retVal = $this->getIntersect(); $slope = $this->getSlope(); - // Phpstan and Scrutinizer are both correct - getSlope returns float, not array. - // @phpstan-ignore-next-line - foreach ($slope as $key => $value) { + foreach ($slope as $key => $value) { //* @phpstan-ignore foreach.nonIterable (this whole class is a mess) /** @var float $value */ if ($value != 0.0) { /** @var int $key */ @@ -82,8 +80,7 @@ public function getEquation(int $dp = 0): string $equation = 'Y = ' . $intersect; // Phpstan and Scrutinizer are both correct - getSlope returns float, not array. - // @phpstan-ignore-next-line - foreach ($slope as $key => $value) { + foreach ($slope as $key => $value) { //* @phpstan-ignore foreach.nonIterable (this whole class is a mess) /** @var float|int $value */ if ($value != 0.0) { $equation .= ' + ' . $value . ' * X'; @@ -106,14 +103,12 @@ public function getSlope(int $dp = 0): float { if ($dp != 0) { $coefficients = []; - //* @phpstan-ignore-next-line - foreach ($this->slope as $coefficient) { + foreach ($this->slope as $coefficient) { //* @phpstan-ignore foreach.nonIterable (this whole class is a mess) /** @var float|int $coefficient */ $coefficients[] = round($coefficient, $dp); } - // @phpstan-ignore-next-line - return $coefficients; + return $coefficients; //* @phpstan-ignore return.type (this whole class is a mess) } return $this->slope; @@ -122,9 +117,7 @@ public function getSlope(int $dp = 0): float /** @return array */ public function getCoefficients(int $dp = 0): array { - // Phpstan and Scrutinizer are both correct - getSlope returns float, not array. - // @phpstan-ignore-next-line - return array_merge([$this->getIntersect($dp)], $this->getSlope($dp)); + return array_merge([$this->getIntersect($dp)], $this->getSlope($dp)); //* @phpstan-ignore return.type (this whole class is a mess), argument.type (ditto) } /** @@ -179,9 +172,7 @@ private function polynomialRegression(int $order, array $yValues, array $xValues } $this->intersect = (float) array_shift($coefficients); - // Phpstan is correct - //* @phpstan-ignore-next-line - $this->slope = $coefficients; + $this->slope = $coefficients; //* @phpstan-ignore assign.propertyType (this whole class is a mess) $this->calculateGoodnessOfFit($x_sum, $y_sum, $xx_sum, $yy_sum, $xy_sum, 0, 0, 0); foreach ($this->xValues as $xKey => $xValue) { diff --git a/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Shared/XMLWriter.php b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Shared/XMLWriter.php index 17b1ee61..9cde153c 100644 --- a/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Shared/XMLWriter.php +++ b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Shared/XMLWriter.php @@ -64,7 +64,15 @@ public function __destruct() } } - /** @param mixed[] $data */ + /** + * Unserialization is not allowed. This needs to be enforced + * in the class before Php8.6, but, with that release, + * this method is no longer needed and will not be executed. + * + * @see https://github.com/php/php-src/pull/21694 + * + * @param mixed[] $data + */ public function __unserialize(array $data): void { $this->tempFileName = ''; diff --git a/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Shared/Xlsx/AgileEncryption.php b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Shared/Xlsx/AgileEncryption.php new file mode 100644 index 00000000..f41c4071 --- /dev/null +++ b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Shared/Xlsx/AgileEncryption.php @@ -0,0 +1,842 @@ +> 2; + + private const CFB_DIFAT_ENTRIES_IN_HEADER = 109; + + private const CFB_DIFAT_ENTRIES_PER_SECTOR = self::CFB_FAT_ENTRIES_PER_SECTOR - 1; + + private const CFB_DIRECTORY_ENTRIES_PER_SECTOR = self::CFB_SECTOR_SIZE >> 7; + + private const CFB_MINI_SECTORS_PER_SECTOR = self::CFB_SECTOR_SIZE >> 6; + + private const DIRECTORY_ENCRYPTED_PACKAGE = 1; + + private const DIRECTORY_DATA_SPACES = 2; + + private const DIRECTORY_VERSION = 3; + + private const DIRECTORY_DATA_SPACE_MAP = 4; + + private const DIRECTORY_DATA_SPACE_INFO = 5; + + private const DIRECTORY_STRONG_ENCRYPTION_DATA_SPACE = 6; + + private const DIRECTORY_TRANSFORM_INFO = 7; + + private const DIRECTORY_STRONG_ENCRYPTION_TRANSFORM = 8; + + private const DIRECTORY_PRIMARY = 9; + + private const DIRECTORY_ENCRYPTION_INFO = 10; + + private const CFB_DIRECTORY_ENTRY_COUNT = self::DIRECTORY_ENCRYPTION_INFO + 1; + + private const STREAM_ENCRYPTED_PACKAGE = 'EncryptedPackage'; + + private const STORAGE_DATA_SPACES = "\x06DataSpaces"; + + private const STREAM_VERSION = 'Version'; + + private const STREAM_DATA_SPACE_MAP = 'DataSpaceMap'; + + private const STORAGE_DATA_SPACE_INFO = 'DataSpaceInfo'; + + private const STREAM_STRONG_ENCRYPTION_DATA_SPACE = 'StrongEncryptionDataSpace'; + + private const STORAGE_TRANSFORM_INFO = 'TransformInfo'; + + private const STORAGE_STRONG_ENCRYPTION_TRANSFORM = 'StrongEncryptionTransform'; + + private const STREAM_PRIMARY = "\x06Primary"; + + private const STREAM_ENCRYPTION_INFO = 'EncryptionInfo'; + + /** @var array */ + private const HASH_ALGORITHMS = [ + 'SHA1' => ['sha1', 20], + 'SHA256' => ['sha256', 32], + 'SHA384' => ['sha384', 48], + 'SHA512' => ['sha512', 64], + ]; + + /** + * @return array{keyDataSalt: string, passwordSalt: string, encryptedVerifier: string, encryptedVerifierHash: string, encryptedKey: string, encryptedHmacKey: string, encryptedHmacValue: string, spinCount: int, keyBits: int, hashAlgorithm: string, hashSize: int} + */ + public static function parse(string $encryptionInfo, int $maxSpinCount = self::MAX_SPIN_COUNT): array + { + if (substr($encryptionInfo, 0, 8) !== "\x04\x00\x04\x00\x40\x00\x00\x00") { + throw new Exception('Unsupported XLSX encryption profile.'); + } + + $xml = @simplexml_load_string(substr($encryptionInfo, 8)); + if (!$xml instanceof SimpleXMLElement) { + throw new Exception('Malformed XLSX encryption information.'); + } + $namespaces = $xml->getDocNamespaces(true) ?: []; + if ($xml->getName() !== 'encryption' || !in_array(self::ENCRYPTION_NAMESPACE, $namespaces, true) || !in_array(self::PASSWORD_NAMESPACE, $namespaces, true)) { + throw new Exception('Unsupported XLSX encryption profile.'); + } + $xml->registerXPathNamespace('e', self::ENCRYPTION_NAMESPACE); + $xml->registerXPathNamespace('p', self::PASSWORD_NAMESPACE); + $keyDataNodes = $xml->xpath('/e:encryption/e:keyData') ?: []; + $integrityNodes = $xml->xpath('/e:encryption/e:dataIntegrity') ?: []; + $keyEncryptorNodes = $xml->xpath('/e:encryption/e:keyEncryptors/e:keyEncryptor') ?: []; + $encryptedKeyNodes = $xml->xpath('/e:encryption/e:keyEncryptors/e:keyEncryptor/p:encryptedKey') ?: []; + $keyData = $keyDataNodes[0] ?? null; + $integrity = $integrityNodes[0] ?? null; + $keyEncryptor = $keyEncryptorNodes[0] ?? null; + $encryptedKey = $encryptedKeyNodes[0] ?? null; + if (!$keyData instanceof SimpleXMLElement || !$integrity instanceof SimpleXMLElement || !$keyEncryptor instanceof SimpleXMLElement || !$encryptedKey instanceof SimpleXMLElement || count($keyDataNodes) !== 1 || count($integrityNodes) !== 1 || count($keyEncryptorNodes) !== 1 || count($encryptedKeyNodes) !== 1) { + throw new Exception('Unsupported XLSX encryption profile.'); + } + $keyBits = self::decimalAttribute($keyData, 'keyBits'); + $hashAlgorithm = (string) $keyData['hashAlgorithm']; + $hashSize = self::decimalAttribute($keyData, 'hashSize'); + $spinCount = self::decimalAttribute($encryptedKey, 'spinCount'); + $keyDataSaltSize = self::decimalAttribute($keyData, 'saltSize'); + $keyDataBlockSize = self::decimalAttribute($keyData, 'blockSize'); + $encryptedKeySaltSize = self::decimalAttribute($encryptedKey, 'saltSize'); + $encryptedKeyBlockSize = self::decimalAttribute($encryptedKey, 'blockSize'); + $encryptedKeyBits = self::decimalAttribute($encryptedKey, 'keyBits'); + $encryptedKeyHashSize = self::decimalAttribute($encryptedKey, 'hashSize'); + if ( + (string) $keyData['cipherAlgorithm'] !== 'AES' || (string) $keyData['cipherChaining'] !== 'ChainingModeCBC' + || !self::isSupportedProfile($keyBits, $hashAlgorithm, $hashSize) || $keyDataSaltSize !== 16 || $keyDataBlockSize !== 16 + || (string) $encryptedKey['cipherAlgorithm'] !== 'AES' + || (string) $encryptedKey['cipherChaining'] !== 'ChainingModeCBC' + || (string) $encryptedKey['hashAlgorithm'] !== $hashAlgorithm || $encryptedKeySaltSize !== 16 || $encryptedKeyBlockSize !== 16 || $encryptedKeyBits !== $keyBits + || $encryptedKeyHashSize !== $hashSize || $spinCount > min($maxSpinCount, self::MAX_SPIN_COUNT) + || (string) $keyEncryptor['uri'] !== self::PASSWORD_KEY_ENCRYPTOR_URI + ) { + throw new Exception('Unsupported XLSX encryption profile.'); + } + + $result = [ + 'keyDataSalt' => self::decode($keyData['saltValue']), + 'passwordSalt' => self::decode($encryptedKey['saltValue']), + 'encryptedVerifier' => self::decode($encryptedKey['encryptedVerifierHashInput']), + 'encryptedVerifierHash' => self::decode($encryptedKey['encryptedVerifierHashValue']), + 'encryptedKey' => self::decode($encryptedKey['encryptedKeyValue']), + 'encryptedHmacKey' => self::decode($integrity['encryptedHmacKey']), + 'encryptedHmacValue' => self::decode($integrity['encryptedHmacValue']), + 'spinCount' => $spinCount, + 'keyBits' => $keyBits, + 'hashAlgorithm' => $hashAlgorithm, + 'hashSize' => $hashSize, + ]; + if ( + strlen($result['keyDataSalt']) !== 16 || strlen($result['passwordSalt']) !== 16 + || strlen($result['encryptedVerifier']) !== 16 || strlen($result['encryptedVerifierHash']) !== self::paddedLength($hashSize) + || strlen($result['encryptedKey']) !== self::paddedLength(intdiv($keyBits, 8)) || strlen($result['encryptedHmacKey']) !== self::paddedLength($hashSize) + || strlen($result['encryptedHmacValue']) !== self::paddedLength($hashSize) + ) { + throw new Exception('Malformed XLSX encryption information.'); + } + + return $result; + } + + /** @param array{keyDataSalt: string, passwordSalt: string, encryptedVerifier: string, encryptedVerifierHash: string, encryptedKey: string, encryptedHmacKey: string, encryptedHmacValue: string, spinCount: int, keyBits: int, hashAlgorithm: string, hashSize: int} $info */ + public static function decrypt(array $info, string $encryptedPackage, string $password): string + { + if ($password === '') { + throw new Exception('XLSX encryption password required.'); + } + if (strlen($encryptedPackage) < 8) { + throw new Exception('Malformed encrypted XLSX package.'); + } + $hash = self::passwordHash($password, $info['passwordSalt'], $info['spinCount'], $info['hashAlgorithm']); + $verifierKey = self::deriveKey($hash, self::BLOCK_KEY_VERIFIER, $info['hashAlgorithm'], $info['keyBits']); + $verifierHashKey = self::deriveKey($hash, self::BLOCK_KEY_VERIFIER_HASH, $info['hashAlgorithm'], $info['keyBits']); + $verifier = self::aesDecrypt($info['encryptedVerifier'], $verifierKey, $info['passwordSalt'], $info['keyBits']); + $expectedHash = self::aesDecrypt($info['encryptedVerifierHash'], $verifierHashKey, $info['passwordSalt'], $info['keyBits']); + if (!hash_equals(self::hash($info['hashAlgorithm'], $verifier), substr($expectedHash, 0, $info['hashSize']))) { + throw new Exception('XLSX encryption password is incorrect.'); + } + $secretKey = self::aesDecrypt($info['encryptedKey'], self::deriveKey($hash, self::BLOCK_KEY_ENCRYPTED_KEY, $info['hashAlgorithm'], $info['keyBits']), $info['passwordSalt'], $info['keyBits']); + $secretKey = substr($secretKey, 0, intdiv($info['keyBits'], 8)); + if (strlen($secretKey) !== intdiv($info['keyBits'], 8)) { + throw new Exception('Malformed XLSX encryption information.'); + } + self::verifyIntegrity($info, $secretKey, $encryptedPackage); + $size = self::unpackSize(substr($encryptedPackage, 0, 8)); + $offset = 8; + $plain = ''; + for ($block = 0; $size > 0; ++$block) { + $length = min(self::SEGMENT_SIZE, $size); + $cipherLength = (int) (ceil($length / self::BLOCK_SIZE) * self::BLOCK_SIZE); + $cipher = substr($encryptedPackage, $offset, $cipherLength); + if (strlen($cipher) !== $cipherLength) { + throw new Exception('Malformed encrypted XLSX package.'); + } + $iv = self::iv($info['keyDataSalt'], pack('V', $block), $info['hashAlgorithm']); + $plain .= substr(self::aesDecrypt($cipher, $secretKey, $iv, $info['keyBits']), 0, $length); + $offset += $cipherLength; + $size -= $length; + } + if ($offset !== strlen($encryptedPackage)) { + throw new Exception('Malformed encrypted XLSX package.'); + } + + return $plain; + } + + /** @param array{keyDataSalt: string, passwordSalt: string, encryptedVerifier: string, encryptedVerifierHash: string, encryptedKey: string, encryptedHmacKey: string, encryptedHmacValue: string, spinCount: int, keyBits: int, hashAlgorithm: string, hashSize: int} $info */ + public static function decryptFile(array $info, string $inputFilename, string $outputFilename, string $password): void + { + if ($password === '') { + throw new Exception('XLSX encryption password required.'); + } + $input = @fopen($inputFilename, 'rb'); + if ($input === false) { + throw new Exception('Could not open XLSX package for decryption.'); + } + + try { + $hash = self::passwordHash($password, $info['passwordSalt'], $info['spinCount'], $info['hashAlgorithm']); + $verifier = self::aesDecrypt($info['encryptedVerifier'], self::deriveKey($hash, self::BLOCK_KEY_VERIFIER, $info['hashAlgorithm'], $info['keyBits']), $info['passwordSalt'], $info['keyBits']); + $expected = self::aesDecrypt($info['encryptedVerifierHash'], self::deriveKey($hash, self::BLOCK_KEY_VERIFIER_HASH, $info['hashAlgorithm'], $info['keyBits']), $info['passwordSalt'], $info['keyBits']); + if (!hash_equals(self::hash($info['hashAlgorithm'], $verifier), substr($expected, 0, $info['hashSize']))) { + throw new Exception('XLSX encryption password is incorrect.'); + } + $secretKey = substr(self::aesDecrypt($info['encryptedKey'], self::deriveKey($hash, self::BLOCK_KEY_ENCRYPTED_KEY, $info['hashAlgorithm'], $info['keyBits']), $info['passwordSalt'], $info['keyBits']), 0, intdiv($info['keyBits'], 8)); + if (strlen($secretKey) !== intdiv($info['keyBits'], 8)) { + throw new Exception('Malformed XLSX encryption information.'); + } + self::verifyIntegrityFile($info, $secretKey, $input); + $output = @fopen($outputFilename, 'wb'); + if ($output === false) { + throw new Exception('Could not open XLSX package for decryption.'); + } + rewind($input); + + try { + $size = self::unpackSize(self::read($input, 8)); + for ($block = 0; $size > 0; ++$block) { + $length = min(self::SEGMENT_SIZE, $size); + $cipher = self::read($input, self::paddedLength($length)); + $iv = self::iv($info['keyDataSalt'], pack('V', $block), $info['hashAlgorithm']); + self::write($output, substr(self::aesDecrypt($cipher, $secretKey, $iv, $info['keyBits']), 0, $length)); + $size -= $length; + } + if (fread($input, 1) !== '') { + throw new Exception('Malformed encrypted XLSX package.'); + } + } finally { + fclose($output); + } + } finally { + fclose($input); + } + } + + /** + * Create the EncryptionInfo and EncryptedPackage streams for an Agile-encrypted XLSX. + * + * @return array{encryptionInfo: string, encryptedPackage: string} + */ + public static function encrypt(string $plainPackage, string $password, int $keyBits = 256, string $hashAlgorithm = 'SHA512', int $spinCount = 100000): array + { + if ($password === '') { + throw new Exception('XLSX encryption password required.'); + } + if (!self::isSupportedProfile($keyBits, $hashAlgorithm, self::HASH_ALGORITHMS[$hashAlgorithm][1] ?? 0) || $spinCount < 0 || $spinCount > self::MAX_SPIN_COUNT) { + throw new Exception('Unsupported XLSX encryption profile.'); + } + + $passwordSalt = random_bytes(self::BLOCK_SIZE); + $keyDataSalt = random_bytes(self::BLOCK_SIZE); + $hashSize = self::hashSize($hashAlgorithm); + $passwordHash = self::passwordHash($password, $passwordSalt, $spinCount, $hashAlgorithm); + $verifier = random_bytes(self::BLOCK_SIZE); + $secretKey = random_bytes(self::keyLength($keyBits)); + $encryptedVerifier = self::aesEncrypt($verifier, self::deriveKey($passwordHash, self::BLOCK_KEY_VERIFIER, $hashAlgorithm, $keyBits), $passwordSalt, $keyBits); + $encryptedVerifierHash = self::aesEncrypt(str_pad(self::hash($hashAlgorithm, $verifier), self::paddedLength($hashSize), "\x00"), self::deriveKey($passwordHash, self::BLOCK_KEY_VERIFIER_HASH, $hashAlgorithm, $keyBits), $passwordSalt, $keyBits); + $encryptedKey = self::aesEncrypt(str_pad($secretKey, self::paddedLength(strlen($secretKey)), "\x00"), self::deriveKey($passwordHash, self::BLOCK_KEY_ENCRYPTED_KEY, $hashAlgorithm, $keyBits), $passwordSalt, $keyBits); + + $encryptedPackage = self::packSize(strlen($plainPackage)); + for ($block = 0, $offset = 0; $offset < strlen($plainPackage); ++$block, $offset += self::SEGMENT_SIZE) { + $segment = substr($plainPackage, $offset, self::SEGMENT_SIZE); + $iv = self::iv($keyDataSalt, pack('V', $block), $hashAlgorithm); + $encryptedPackage .= self::aesEncrypt(str_pad($segment, self::paddedLength(strlen($segment)), "\x00"), $secretKey, $iv, $keyBits); + } + + $hmacKey = random_bytes(self::hashSize($hashAlgorithm)); + $hmacKeyIv = self::iv($keyDataSalt, self::BLOCK_KEY_HMAC_KEY, $hashAlgorithm); + $hmacValueIv = self::iv($keyDataSalt, self::BLOCK_KEY_HMAC_VALUE, $hashAlgorithm); + $encryptedHmacKey = self::aesEncrypt(str_pad($hmacKey, self::paddedLength($hashSize), "\x00"), $secretKey, $hmacKeyIv, $keyBits); + $encryptedHmacValue = self::aesEncrypt(str_pad(hash_hmac(self::HASH_ALGORITHMS[$hashAlgorithm][0], $encryptedPackage, $hmacKey, true), self::paddedLength($hashSize), "\x00"), $secretKey, $hmacValueIv, $keyBits); + + $encryptionInfo = "\x04\x00\x04\x00\x40\x00\x00\x00" . self::encryptionInfoXml( + $keyDataSalt, + $passwordSalt, + $encryptedVerifier, + $encryptedVerifierHash, + $encryptedKey, + $encryptedHmacKey, + $encryptedHmacValue, + $keyBits, + $hashAlgorithm, + $hashSize, + $spinCount + ); + + return ['encryptionInfo' => $encryptionInfo, 'encryptedPackage' => $encryptedPackage]; + } + + /** + * Encrypt a ZIP package without loading either package into memory. + * + * @return array{encryptionInfo: string, encryptedPackageFilename: string} + */ + public static function encryptFile(string $plainPackageFilename, string $password, int $keyBits = 256, string $hashAlgorithm = 'SHA512', int $spinCount = 100000): array + { + if ($password === '') { + throw new Exception('XLSX encryption password required.'); + } + if (!self::isSupportedProfile($keyBits, $hashAlgorithm, self::HASH_ALGORITHMS[$hashAlgorithm][1] ?? 0) || $spinCount < 0 || $spinCount > self::MAX_SPIN_COUNT) { + throw new Exception('Unsupported XLSX encryption profile.'); + } + $size = @filesize($plainPackageFilename); + if ($size === false) { + throw new Exception('Could not determine XLSX package size.'); + } + $input = fopen($plainPackageFilename, 'rb'); + if ($input === false) { + throw new Exception('Could not open XLSX package for encryption.'); + } + $encryptedPackageFilename = SharedFile::temporaryFilename(); + $output = fopen($encryptedPackageFilename, 'wb'); + if ($output === false) { + fclose($input); + @unlink($encryptedPackageFilename); + + throw new Exception('Could not create encrypted XLSX package.'); + } + + try { + $passwordSalt = random_bytes(self::BLOCK_SIZE); + $keyDataSalt = random_bytes(self::BLOCK_SIZE); + $hashSize = self::hashSize($hashAlgorithm); + $passwordHash = self::passwordHash($password, $passwordSalt, $spinCount, $hashAlgorithm); + $verifier = random_bytes(self::BLOCK_SIZE); + $secretKey = random_bytes(self::keyLength($keyBits)); + $encryptedVerifier = self::aesEncrypt($verifier, self::deriveKey($passwordHash, self::BLOCK_KEY_VERIFIER, $hashAlgorithm, $keyBits), $passwordSalt, $keyBits); + $encryptedVerifierHash = self::aesEncrypt(str_pad(self::hash($hashAlgorithm, $verifier), self::paddedLength($hashSize), "\x00"), self::deriveKey($passwordHash, self::BLOCK_KEY_VERIFIER_HASH, $hashAlgorithm, $keyBits), $passwordSalt, $keyBits); + $encryptedKey = self::aesEncrypt(str_pad($secretKey, self::paddedLength(strlen($secretKey)), "\x00"), self::deriveKey($passwordHash, self::BLOCK_KEY_ENCRYPTED_KEY, $hashAlgorithm, $keyBits), $passwordSalt, $keyBits); + $hmacKey = random_bytes(self::hashSize($hashAlgorithm)); + $hmac = hash_init(self::HASH_ALGORITHMS[$hashAlgorithm][0], HASH_HMAC, $hmacKey); + $header = self::packSize($size); + self::write($output, $header); + hash_update($hmac, $header); + $remaining = $size; + for ($block = 0; $remaining > 0; ++$block) { + $length = min(self::SEGMENT_SIZE, $remaining); + $segment = fread($input, $length); + if ($segment === false || strlen($segment) !== $length) { + throw new Exception('Could not read XLSX package for encryption.'); + } + $iv = self::iv($keyDataSalt, pack('V', $block), $hashAlgorithm); + $cipher = self::aesEncrypt(str_pad($segment, self::paddedLength(strlen($segment)), "\x00"), $secretKey, $iv, $keyBits); + self::write($output, $cipher); + hash_update($hmac, $cipher); + $remaining -= $length; + } + $extra = fread($input, 1); + if ($extra === false || $extra !== '') { + throw new Exception('XLSX package changed while being encrypted.'); + } + $hmacKeyIv = self::iv($keyDataSalt, self::BLOCK_KEY_HMAC_KEY, $hashAlgorithm); + $hmacValueIv = self::iv($keyDataSalt, self::BLOCK_KEY_HMAC_VALUE, $hashAlgorithm); + $encryptedHmacKey = self::aesEncrypt(str_pad($hmacKey, self::paddedLength($hashSize), "\x00"), $secretKey, $hmacKeyIv, $keyBits); + $encryptedHmacValue = self::aesEncrypt(str_pad(hash_final($hmac, true), self::paddedLength($hashSize), "\x00"), $secretKey, $hmacValueIv, $keyBits); + $encryptionInfo = "\x04\x00\x04\x00\x40\x00\x00\x00" . self::encryptionInfoXml($keyDataSalt, $passwordSalt, $encryptedVerifier, $encryptedVerifierHash, $encryptedKey, $encryptedHmacKey, $encryptedHmacValue, $keyBits, $hashAlgorithm, $hashSize, $spinCount); + } catch (Throwable $e) { + @unlink($encryptedPackageFilename); + + throw $e; + } finally { + fclose($input); + fclose($output); + } + + return ['encryptionInfo' => $encryptionInfo, 'encryptedPackageFilename' => $encryptedPackageFilename]; + } + + /** + * Write an Office encrypted package CFB container using a file-backed EncryptedPackage stream. + * + * @param resource $fileHandle + */ + public static function writeContainerFromFile($fileHandle, string $encryptionInfo, string $encryptedPackageFilename): void + { + $containerFilename = SharedFile::temporaryFilename(); + $container = fopen($containerFilename, 'w+b'); + if ($container === false) { + @unlink($containerFilename); + + throw new Exception('Could not create encrypted XLSX container.'); + } + + try { + self::writeEcma376Container($container, $encryptionInfo, $encryptedPackageFilename); + rewind($container); + while (!feof($container)) { + $data = fread($container, 8192); + if ($data === false) { + throw new Exception('Could not read encrypted XLSX container.'); + } + if ($data !== '' && fwrite($fileHandle, $data) !== strlen($data)) { + throw new Exception('Could not write encrypted XLSX container.'); + } + } + } finally { + fclose($container); + @unlink($containerFilename); + } + } + + /** + * Serialize the ECMA-376 encrypted-package CFB layout. The directory tree + * is prescribed by the Data Spaces structure; sector allocation is dynamic + * so normal workbook size is not artificially constrained. + * + * @param resource $fileHandle + */ + private static function writeEcma376Container($fileHandle, string $encryptionInfo, string $encryptedPackageFilename): void + { + $packageSize = filesize($encryptedPackageFilename); + if ($packageSize === false || $packageSize < self::CFB_MINI_STREAM_CUTOFF || $packageSize > 0xFFFFFFFF) { + throw new Exception('Malformed encrypted XLSX package.'); + } + $smallStreams = [ + self::DIRECTORY_VERSION => [self::STREAM_VERSION, self::dataSpacesVersion()], + self::DIRECTORY_DATA_SPACE_MAP => [self::STREAM_DATA_SPACE_MAP, self::dataSpaceMap()], + self::DIRECTORY_STRONG_ENCRYPTION_DATA_SPACE => [self::STREAM_STRONG_ENCRYPTION_DATA_SPACE, self::strongEncryptionDataSpace()], + self::DIRECTORY_PRIMARY => [self::STREAM_PRIMARY, self::primaryTransform()], + self::DIRECTORY_ENCRYPTION_INFO => [self::STREAM_ENCRYPTION_INFO, $encryptionInfo], + ]; + $miniStarts = array_fill_keys(array_keys($smallStreams), 0); + $miniFat = []; + $miniCount = 0; + foreach ($smallStreams as $id => [, $content]) { + if (strlen($content) >= self::CFB_MINI_STREAM_CUTOFF) { + throw new Exception('Malformed XLSX encryption information.'); + } + $count = (int) ceil(strlen($content) / self::CFB_MINI_SECTOR_SIZE); + $miniStarts[$id] = $miniCount; + for ($i = 0; $i < $count - 1; ++$i) { + $miniFat[$miniCount + $i] = $miniCount + $i + 1; + } + $miniFat[$miniCount + $count - 1] = 0xFFFFFFFE; + $miniCount += $count; + } + $miniFatSectors = (int) ceil($miniCount / self::CFB_FAT_ENTRIES_PER_SECTOR); + $miniFat = array_pad($miniFat, $miniFatSectors * self::CFB_FAT_ENTRIES_PER_SECTOR, 0xFFFFFFFF); + $miniDataSectors = (int) ceil($miniCount / self::CFB_MINI_SECTORS_PER_SECTOR); + $directorySectors = (int) ceil(self::CFB_DIRECTORY_ENTRY_COUNT / self::CFB_DIRECTORY_ENTRIES_PER_SECTOR); + $packageSectors = (int) ceil($packageSize / self::CFB_SECTOR_SIZE); + $contentSectors = $miniFatSectors + $directorySectors + $miniDataSectors + $packageSectors; + $fatSectors = 1; + $difatSectors = 0; + do { + $requiredFatSectors = (int) ceil(($contentSectors + $fatSectors + $difatSectors) / self::CFB_FAT_ENTRIES_PER_SECTOR); + $requiredDifatSectors = $requiredFatSectors <= self::CFB_DIFAT_ENTRIES_IN_HEADER ? 0 : (int) ceil(($requiredFatSectors - self::CFB_DIFAT_ENTRIES_IN_HEADER) / self::CFB_DIFAT_ENTRIES_PER_SECTOR); + $changed = $requiredFatSectors !== $fatSectors || $requiredDifatSectors !== $difatSectors; + $fatSectors = $requiredFatSectors; + $difatSectors = $requiredDifatSectors; + } while ($changed); + $miniFatSector = $fatSectors; + $directorySector = $miniFatSector + $miniFatSectors; + $miniDataSector = $directorySector + $directorySectors; + $packageSector = $miniDataSector + $miniDataSectors; + $difatSector = $packageSector + $packageSectors; + + self::write($fileHandle, self::cfbHeader($fatSectors, $directorySector, $miniFatSector, $miniFatSectors, $difatSector, $difatSectors)); + $fat = array_fill(0, $fatSectors * self::CFB_FAT_ENTRIES_PER_SECTOR, 0xFFFFFFFF); + for ($sector = 0; $sector < $fatSectors; ++$sector) { + $fat[$sector] = 0xFFFFFFFD; + } + self::chainFat($fat, $miniFatSector, $miniFatSectors); + self::chainFat($fat, $directorySector, $directorySectors); + self::chainFat($fat, $miniDataSector, $miniDataSectors); + self::chainFat($fat, $packageSector, $packageSectors); + for ($sector = 0; $sector < $difatSectors; ++$sector) { + $fat[$difatSector + $sector] = 0xFFFFFFFC; + } + self::write($fileHandle, self::packSectors($fat)); + self::write($fileHandle, self::packSectors($miniFat)); + + $entries = [ + // CFB sibling trees sort by name length, then case-folded UTF-16 code points. + self::directoryEntry('Root Entry', 5, 1, 0xFFFFFFFF, 0xFFFFFFFF, self::DIRECTORY_ENCRYPTION_INFO, $miniDataSector, $miniCount * self::CFB_MINI_SECTOR_SIZE), + self::directoryEntry(self::STREAM_ENCRYPTED_PACKAGE, 2, 0, 0xFFFFFFFF, 0xFFFFFFFF, 0xFFFFFFFF, $packageSector, $packageSize), + self::directoryEntry(self::STORAGE_DATA_SPACES, 1, 0, 0xFFFFFFFF, 0xFFFFFFFF, self::DIRECTORY_DATA_SPACE_MAP, 0, 0), + self::directoryEntry(self::STREAM_VERSION, 2, 0, 0xFFFFFFFF, 0xFFFFFFFF, 0xFFFFFFFF, $miniStarts[self::DIRECTORY_VERSION], strlen($smallStreams[self::DIRECTORY_VERSION][1])), + self::directoryEntry(self::STREAM_DATA_SPACE_MAP, 2, 1, self::DIRECTORY_VERSION, self::DIRECTORY_DATA_SPACE_INFO, 0xFFFFFFFF, $miniStarts[self::DIRECTORY_DATA_SPACE_MAP], strlen($smallStreams[self::DIRECTORY_DATA_SPACE_MAP][1])), + self::directoryEntry(self::STORAGE_DATA_SPACE_INFO, 1, 0, 0xFFFFFFFF, 0xFFFFFFFF, self::DIRECTORY_TRANSFORM_INFO, 0, 0), + self::directoryEntry(self::STREAM_STRONG_ENCRYPTION_DATA_SPACE, 2, 0, 0xFFFFFFFF, 0xFFFFFFFF, 0xFFFFFFFF, $miniStarts[self::DIRECTORY_STRONG_ENCRYPTION_DATA_SPACE], strlen($smallStreams[self::DIRECTORY_STRONG_ENCRYPTION_DATA_SPACE][1])), + self::directoryEntry(self::STORAGE_TRANSFORM_INFO, 1, 1, self::DIRECTORY_STRONG_ENCRYPTION_DATA_SPACE, 0xFFFFFFFF, self::DIRECTORY_STRONG_ENCRYPTION_TRANSFORM, 0, 0), + self::directoryEntry(self::STORAGE_STRONG_ENCRYPTION_TRANSFORM, 1, 1, 0xFFFFFFFF, 0xFFFFFFFF, self::DIRECTORY_PRIMARY, 0, 0), + self::directoryEntry(self::STREAM_PRIMARY, 2, 1, 0xFFFFFFFF, 0xFFFFFFFF, 0xFFFFFFFF, $miniStarts[self::DIRECTORY_PRIMARY], strlen($smallStreams[self::DIRECTORY_PRIMARY][1])), + self::directoryEntry(self::STREAM_ENCRYPTION_INFO, 2, 1, self::DIRECTORY_DATA_SPACES, self::DIRECTORY_ENCRYPTED_PACKAGE, 0xFFFFFFFF, $miniStarts[self::DIRECTORY_ENCRYPTION_INFO], strlen($smallStreams[self::DIRECTORY_ENCRYPTION_INFO][1])), + ]; + self::write($fileHandle, str_pad(implode('', $entries), $directorySectors * self::CFB_SECTOR_SIZE, "\x00")); + $miniData = str_repeat("\x00", $miniDataSectors * self::CFB_SECTOR_SIZE); + foreach ($smallStreams as $id => [, $content]) { + $miniData = substr_replace($miniData, $content, $miniStarts[$id] * self::CFB_MINI_SECTOR_SIZE, strlen($content)); + } + self::write($fileHandle, $miniData); + $package = fopen($encryptedPackageFilename, 'rb'); + if ($package === false) { + throw new Exception('Could not open encrypted XLSX package.'); + } + + try { + while (!feof($package)) { + $data = fread($package, 8192); + if ($data === false) { + throw new Exception('Could not read encrypted XLSX package.'); + } + if ($data !== '') { + self::write($fileHandle, $data); + } + } + } finally { + fclose($package); + } + $padding = $packageSectors * self::CFB_SECTOR_SIZE - $packageSize; + if ($padding > 0) { + self::write($fileHandle, str_repeat("\x00", $padding)); + } + for ($sector = 0; $sector < $difatSectors; ++$sector) { + $firstFatSector = self::CFB_DIFAT_ENTRIES_IN_HEADER + $sector * self::CFB_DIFAT_ENTRIES_PER_SECTOR; + $fatReferences = []; + for ($i = 0; $i < self::CFB_DIFAT_ENTRIES_PER_SECTOR; ++$i) { + $fatReferences[] = $firstFatSector + $i < $fatSectors ? $firstFatSector + $i : 0xFFFFFFFF; + } + $fatReferences[] = $sector + 1 < $difatSectors ? $difatSector + $sector + 1 : 0xFFFFFFFE; + self::write($fileHandle, self::packSectors($fatReferences)); + } + } + + /** @param int[] $fat */ + private static function chainFat(array &$fat, int $start, int $count): void + { + for ($i = 0; $i < $count - 1; ++$i) { + $fat[$start + $i] = $start + $i + 1; + } + $fat[$start + $count - 1] = 0xFFFFFFFE; + } + + /** @param int[] $sectors */ + private static function packSectors(array $sectors): string + { + return pack('V*', ...$sectors); + } + + private static function cfbHeader(int $fatSectors, int $directorySector, int $miniFatSector, int $miniFatSectors, int $difatSector, int $difatSectors): string + { + $headerDifat = []; + for ($sector = 0; $sector < self::CFB_DIFAT_ENTRIES_IN_HEADER; ++$sector) { + $headerDifat[] = $sector < $fatSectors ? $sector : 0xFFFFFFFF; + } + + return "\xD0\xCF\x11\xE0\xA1\xB1\x1A\xE1" . str_repeat("\x00", 16) + . pack('v8', 0x3E, 3, 0xFFFE, 9, 6, 0, 0, 0) + . pack('V8', 0, $fatSectors, $directorySector, 0, self::CFB_MINI_STREAM_CUTOFF, $miniFatSector, $miniFatSectors, $difatSectors === 0 ? 0xFFFFFFFE : $difatSector) + . pack('V', $difatSectors) . self::packSectors($headerDifat); + } + + private static function directoryEntry(string $name, int $type, int $color, int $left, int $right, int $child, int $start, int $size): string + { + $name = OLE::ascToUcs($name); + + return str_pad($name, 64, "\x00") . pack('vCCVVV', strlen($name) + 2, $type, $color, $left, $right, $child) + . str_repeat("\x00", 16) . pack('V', 0) . str_repeat("\x00", 16) + . pack('V2', $start, $size % 4294967296) . pack('V', intdiv($size, 4294967296)); + } + + private static function decode(mixed $value): string + { + if (!is_string($value) && !$value instanceof Stringable) { + throw new Exception('Malformed XLSX encryption information.'); + } + $result = base64_decode((string) $value, true); + if ($result === false) { + throw new Exception('Malformed XLSX encryption information.'); + } + + return $result; + } + + private static function decimalAttribute(SimpleXMLElement $element, string $name): int + { + $value = (string) $element[$name]; + $maximum = (string) PHP_INT_MAX; + if ($value === '' || !ctype_digit($value) || strlen($value) > strlen($maximum) || (strlen($value) === strlen($maximum) && $value > $maximum)) { + throw new Exception('Malformed XLSX encryption information.'); + } + + return (int) $value; + } + + private static function passwordHash(string $password, string $salt, int $spinCount, string $algorithm = 'SHA512'): string + { + $hash = self::hash($algorithm, $salt . mb_convert_encoding($password, 'UTF-16LE', 'UTF-8')); + for ($i = 0; $i < $spinCount; ++$i) { + $hash = self::hash($algorithm, pack('V', $i) . $hash); + } + + return $hash; + } + + private static function deriveKey(string $hash, string $blockKey, string $algorithm = 'SHA512', int $keyBits = 256): string + { + return substr(str_pad(self::hash($algorithm, $hash . $blockKey), intdiv($keyBits, 8), "\x36"), 0, intdiv($keyBits, 8)); + } + + private static function aesDecrypt(string $data, string $key, string $iv, int $keyBits = 256): string + { + self::assertOpenSslAvailable(); + $result = openssl_decrypt($data, 'aes-' . $keyBits . '-cbc', $key, OPENSSL_RAW_DATA | OPENSSL_ZERO_PADDING, $iv); + if ($result === false) { + throw new Exception('Malformed XLSX encrypted data.'); + } + + return $result; + } + + private static function aesEncrypt(string $data, string $key, string $iv, int $keyBits = 256): string + { + self::assertOpenSslAvailable(); + $result = openssl_encrypt($data, 'aes-' . $keyBits . '-cbc', $key, OPENSSL_RAW_DATA | OPENSSL_ZERO_PADDING, $iv); + if ($result === false) { + throw new Exception('Could not encrypt XLSX data.'); + } + + return $result; + } + + private static function isSupportedProfile(int $keyBits, string $hashAlgorithm, int $hashSize): bool + { + return in_array($keyBits, [128, 192, 256], true) + && isset(self::HASH_ALGORITHMS[$hashAlgorithm]) + && self::HASH_ALGORITHMS[$hashAlgorithm][1] === $hashSize; + } + + private static function hash(string $algorithm, string $data): string + { + return hash(self::HASH_ALGORITHMS[$algorithm][0], $data, true); + } + + /** @return positive-int */ + private static function hashSize(string $algorithm): int + { + return match ($algorithm) { + 'SHA1' => 20, + 'SHA256' => 32, + 'SHA384' => 48, + 'SHA512' => 64, + default => throw new Exception('Unsupported XLSX encryption profile.'), + }; + } + + /** @return positive-int */ + private static function keyLength(int $keyBits): int + { + return match ($keyBits) { + 128 => 16, + 192 => 24, + 256 => 32, + default => throw new Exception('Unsupported XLSX encryption profile.'), + }; + } + + private static function iv(string $salt, string $blockKey, string $algorithm): string + { + return substr(str_pad(self::hash($algorithm, $salt . $blockKey), self::BLOCK_SIZE, "\x36"), 0, self::BLOCK_SIZE); + } + + private static function paddedLength(int $length): int + { + return (int) (ceil($length / self::BLOCK_SIZE) * self::BLOCK_SIZE); + } + + private static function assertOpenSslAvailable(): void + { + if (!function_exists('openssl_encrypt') || !function_exists('openssl_decrypt')) { + throw new Exception('XLSX encryption requires the OpenSSL extension.'); + } + } + + private static function packSize(int $size): string + { + if ($size < 0) { + throw new Exception('XLSX package is too large to encrypt.'); + } + + return pack('V2', $size % 4294967296, intdiv($size, 4294967296)); + } + + private static function unpackSize(string $data): int + { + $unpackedSize = unpack('Vlow/Vhigh', $data); + if ($unpackedSize === false || !isset($unpackedSize['low'], $unpackedSize['high']) || !is_int($unpackedSize['low']) || !is_int($unpackedSize['high'])) { + throw new Exception('Malformed encrypted XLSX package.'); + } + + return self::sizeFromWords($unpackedSize['low'], $unpackedSize['high'], PHP_INT_SIZE, PHP_INT_MAX); + } + + private static function sizeFromWords(int $low, int $high, int $integerSize, int $integerMax): int + { + if ($integerSize < 8) { + if ($high !== 0 || $low > $integerMax) { + throw new Exception('Encrypted XLSX package is too large for this platform.'); + } + + return $low; + } + if ($high > 0x7FFFFFFF) { + throw new Exception('Encrypted XLSX package is too large for this platform.'); + } + + return $low + $high * 4294967296; + } + + /** @param resource $fileHandle */ + private static function write($fileHandle, string $data): void + { + if (fwrite($fileHandle, $data) !== strlen($data)) { + throw new Exception('Could not write encrypted XLSX package.'); + } + } + + /** @param resource $fileHandle */ + private static function read($fileHandle, int $length): string + { + if ($length < 1) { + throw new Exception('Malformed encrypted XLSX package.'); + } + $data = fread($fileHandle, $length); + if ($data === false || strlen($data) !== $length) { + throw new Exception('Malformed encrypted XLSX package.'); + } + + return $data; + } + + private static function encryptionInfoXml(string $keyDataSalt, string $passwordSalt, string $encryptedVerifier, string $encryptedVerifierHash, string $encryptedKey, string $encryptedHmacKey, string $encryptedHmacValue, int $keyBits = 256, string $hashAlgorithm = 'SHA512', int $hashSize = 64, int $spinCount = 100000): string + { + $base64 = static fn (string $value): string => base64_encode($value); + + return '' + . '' + . '' + . '' + . ''; + } + + private static function dataSpacesVersion(): string + { + // Fixed Version stream required by the ECMA-376 Data Spaces construct. + return hex2bin('3c0000004d006900630072006f0073006f00660074002e0043006f006e007400610069006e00650072002e004400610074006100530070006100630065007300010000000100000001000000') ?: throw new Exception('Could not generate XLSX encryption DataSpaces stream.'); + } + + private static function primaryTransform(): string + { + // Fixed Primary transform descriptor for Microsoft.Container.EncryptionTransform. + return hex2bin('58000000010000004c0000007b00460046003900410033004600300033002d0035003600450046002d0034003600310033002d0042004400440035002d003500410034003100430031004400300037003200340036007d004e0000004d006900630072006f0073006f00660074002e0043006f006e007400610069006e00650072002e0045006e006300720079007000740069006f006e005400720061006e00730066006f0072006d00000001000000010000000100000000000000000000000000000004000000') ?: throw new Exception('Could not generate XLSX encryption DataSpaces stream.'); + } + + private static function dataSpaceMap(): string + { + // Fixed map binding EncryptedPackage to StrongEncryptionDataSpace. + return hex2bin('08000000010000006800000001000000000000002000000045006e0063007200790070007400650064005000610063006b00610067006500320000005300740072006f006e00670045006e006300720079007000740069006f006e004400610074006100530070006100630065000000') ?: throw new Exception('Could not generate XLSX encryption DataSpaces stream.'); + } + + private static function strongEncryptionDataSpace(): string + { + // Fixed definition binding StrongEncryptionDataSpace to its transform. + return hex2bin('0800000001000000320000005300740072006f006e00670045006e006300720079007000740069006f006e005400720061006e00730066006f0072006d000000') ?: throw new Exception('Could not generate XLSX encryption DataSpaces stream.'); + } + + /** @param array{keyDataSalt: string, passwordSalt: string, encryptedVerifier: string, encryptedVerifierHash: string, encryptedKey: string, encryptedHmacKey: string, encryptedHmacValue: string, spinCount: int, keyBits: int, hashAlgorithm: string, hashSize: int} $info */ + private static function verifyIntegrity(array $info, string $secretKey, string $encryptedPackage): void + { + $hmacKeyIv = self::iv($info['keyDataSalt'], self::BLOCK_KEY_HMAC_KEY, $info['hashAlgorithm']); + $hmacValueIv = self::iv($info['keyDataSalt'], self::BLOCK_KEY_HMAC_VALUE, $info['hashAlgorithm']); + $hmacKey = substr(self::aesDecrypt($info['encryptedHmacKey'], $secretKey, $hmacKeyIv, $info['keyBits']), 0, $info['hashSize']); + $expected = self::aesDecrypt($info['encryptedHmacValue'], $secretKey, $hmacValueIv, $info['keyBits']); + if (!hash_equals(hash_hmac(self::HASH_ALGORITHMS[$info['hashAlgorithm']][0], $encryptedPackage, $hmacKey, true), substr($expected, 0, $info['hashSize']))) { + throw new Exception('Encrypted XLSX package integrity check failed.'); + } + } + + /** + * @param array{keyDataSalt: string, passwordSalt: string, encryptedVerifier: string, encryptedVerifierHash: string, encryptedKey: string, encryptedHmacKey: string, encryptedHmacValue: string, spinCount: int, keyBits: int, hashAlgorithm: string, hashSize: int} $info + * @param resource $input + */ + private static function verifyIntegrityFile(array $info, string $secretKey, $input): void + { + $hmacKeyIv = self::iv($info['keyDataSalt'], self::BLOCK_KEY_HMAC_KEY, $info['hashAlgorithm']); + $hmacValueIv = self::iv($info['keyDataSalt'], self::BLOCK_KEY_HMAC_VALUE, $info['hashAlgorithm']); + $hmacKey = substr(self::aesDecrypt($info['encryptedHmacKey'], $secretKey, $hmacKeyIv, $info['keyBits']), 0, $info['hashSize']); + $expected = self::aesDecrypt($info['encryptedHmacValue'], $secretKey, $hmacValueIv, $info['keyBits']); + $hmac = hash_init(self::HASH_ALGORITHMS[$info['hashAlgorithm']][0], HASH_HMAC, $hmacKey); + while (!feof($input)) { + $data = fread($input, 8192); + if ($data === false) { + throw new Exception('Could not read encrypted XLSX package.'); + } + if ($data !== '') { + hash_update($hmac, $data); + } + } + if (!hash_equals(hash_final($hmac, true), substr($expected, 0, $info['hashSize']))) { + throw new Exception('Encrypted XLSX package integrity check failed.'); + } + } +} diff --git a/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Spreadsheet.php b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Spreadsheet.php index 3fe6d044..d708f754 100644 --- a/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Spreadsheet.php +++ b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Spreadsheet.php @@ -528,7 +528,7 @@ public function getCalculationEngine(): Calculation */ public function getCalculationEngineOrNull(): ?Calculation { - if (!isset($this->calculationEngine)) { //* @phpstan-ignore-line + if (!isset($this->calculationEngine)) { //* @phpstan-ignore isset.initializedProperty (may be null at destruct time) return null; } @@ -1157,7 +1157,7 @@ public function getWorksheetIterator(): Iterator */ public function copy(): self { - return unserialize(serialize($this)); //* @phpstan-ignore-line + return unserialize(serialize($this)); //* @phpstan-ignore return.type (phpstan is wrong) } /** diff --git a/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Style/ConditionalFormatting/CellMatcher.php b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Style/ConditionalFormatting/CellMatcher.php index f0deb56e..669bf705 100644 --- a/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Style/ConditionalFormatting/CellMatcher.php +++ b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Style/ConditionalFormatting/CellMatcher.php @@ -244,7 +244,7 @@ protected function processRangeOperator(Conditional $conditional): bool (string) $this->wrapCellValue(), self::COMPARISON_RANGE_OPERATORS[$conditional->getOperatorType()] ), - ...$conditions //* @phpstan-ignore-line + ...$conditions //* @phpstan-ignore argument.type (I don't know what is needed) ); return $this->evaluateExpression($expression); diff --git a/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Style/ConditionalFormatting/Wizard/CellValue.php b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Style/ConditionalFormatting/Wizard/CellValue.php index 435e6a60..8f3d8845 100644 --- a/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Style/ConditionalFormatting/Wizard/CellValue.php +++ b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Style/ConditionalFormatting/Wizard/CellValue.php @@ -67,7 +67,7 @@ protected function operand(int $index, mixed $operand, string $operandValueType $operand = $this->validateOperand($operand, $operandValueType); } - $this->operand[$index] = $operand; //* @phpstan-ignore-line + $this->operand[$index] = $operand; //* @phpstan-ignore assign.propertyType (I don't know what is needed) $this->operandValueType[$index] = $operandValueType; } @@ -192,8 +192,7 @@ public static function compareKeys(): bool $retVal = true; $array = array_merge(array_keys(self::SINGLE_OPERATORS), array_keys(self::RANGE_OPERATORS)); foreach ($array as $value) { - // PhpStan is correct about next statement, but we want to test anyhow - $retVal = $retVal && in_array($value, self::MAGIC_OPERATIONS, true); // @phpstan-ignore-line + $retVal = $retVal && in_array($value, self::MAGIC_OPERATIONS, true); } return $retVal; diff --git a/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Style/ConditionalFormatting/Wizard/TextValue.php b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Style/ConditionalFormatting/Wizard/TextValue.php index 934a364a..c1657666 100644 --- a/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Style/ConditionalFormatting/Wizard/TextValue.php +++ b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Style/ConditionalFormatting/Wizard/TextValue.php @@ -169,8 +169,7 @@ public static function compareKeys(): bool $retVal = true; $array = array_keys(self::OPERATORS); foreach ($array as $value) { - // PhpStan is correct about next statement, but we want to test anyhow - $retVal = $retVal && in_array($value, self::MAGIC_OPERATIONS, true); // @phpstan-ignore-line + $retVal = $retVal && in_array($value, self::MAGIC_OPERATIONS, true); } return $retVal; diff --git a/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Style/NumberFormat/NumberFormatter.php b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Style/NumberFormat/NumberFormatter.php index f869d073..22b02b12 100644 --- a/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Style/NumberFormat/NumberFormatter.php +++ b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Style/NumberFormat/NumberFormatter.php @@ -55,10 +55,8 @@ private static function processComplexNumberFormatMask(mixed $number, string $ma $number = floor($numberFloat / $divisor); $mask = substr_replace($mask, $blockValue, $offset, $size); } - /** @var string $numberString */ - $numberString = $number; if ($number > 0) { - $mask = substr_replace($mask, $numberString, $offset, 0); + $mask = substr_replace($mask, "$number", $offset, 0); } $result = $mask; } @@ -170,7 +168,7 @@ private static function formatStraightNumericValue(mixed $value, string $format, } if (preg_match('/0([^\d\.]+)0/', $format) || substr_count($format, '.') > 1) { if ($valueFloat == floor($valueFloat) && substr_count($format, '.') === 1) { - $value *= 10 ** strlen(explode('.', $format)[1]); //* @phpstan-ignore-line + $value *= 10 ** strlen(explode('.', $format)[1]); //* @phpstan-ignore assignOp.invalid ($value may be mixed) } $result = self::complexNumberFormatMask($value, $format); diff --git a/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Style/Style.php b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Style/Style.php index 9956c358..9df62897 100644 --- a/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Style/Style.php +++ b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Style/Style.php @@ -201,6 +201,18 @@ public function applyFromArray(array $styleArray, bool $advancedBorders = true): { if ($this->isSupervisor) { $pRange = $this->getSelectedCells(); + if (str_contains($pRange, ',')) { + $ranges = explode(',', $pRange); + $sheet = $this->getActiveSheet(); + foreach ($ranges as $range) { + $sheet + ->setSelectedCells(trim($range)); + $this->applyFromArray($styleArray, $advancedBorders); + } + $sheet->setSelectedCells($pRange); + + return $this; + } // Uppercase coordinate and strip any Worksheet reference from the selected range $pRange = strtoupper($pRange); diff --git a/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Worksheet/AutoFilter.php b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Worksheet/AutoFilter.php index 04070e5d..ad733025 100644 --- a/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Worksheet/AutoFilter.php +++ b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Worksheet/AutoFilter.php @@ -2,6 +2,7 @@ namespace PhpOffice\PhpSpreadsheet\Worksheet; +use Composer\Pcre\Preg; use DateTime; use DateTimeZone; use PhpOffice\PhpSpreadsheet\Calculation\Calculation; @@ -146,7 +147,7 @@ public function setRangeToMaxRow(): self $this->evaluated = false; if ($this->workSheet !== null) { $thisrange = $this->range; - $range = (string) preg_replace('/\d+$/', (string) $this->workSheet->getHighestRow(), $thisrange); + $range = Preg::replace('/\d+$/', (string) $this->workSheet->getHighestRow(), $thisrange); if ($range !== $thisrange) { $this->setRange($range); } @@ -239,12 +240,10 @@ public function getColumnByOffset(int $columnOffset): AutoFilter\Column public function setColumn(AutoFilter\Column|string $columnObjectOrString): static { $this->evaluated = false; - if ((is_string($columnObjectOrString)) && (!empty($columnObjectOrString))) { + if (is_string($columnObjectOrString)) { $column = $columnObjectOrString; - } elseif ($columnObjectOrString instanceof AutoFilter\Column) { - $column = $columnObjectOrString->getColumnIndex(); } else { - throw new Exception('Column is not within the autofilter range.'); + $column = $columnObjectOrString->getColumnIndex(); } $this->testColumnInRange($column); @@ -434,32 +433,15 @@ protected static function filterTestInCustomDataSet(mixed $cellValue, array $rul }; } else { // String values are always tested for equality, factoring in for wildcards (hence a regexp test) - switch ($ruleOperator) { - case Rule::AUTOFILTER_COLUMN_RULE_EQUAL: - $retVal = (bool) preg_match('/^' . $ruleValue . '$/i', $cellValueString); - - break; - case Rule::AUTOFILTER_COLUMN_RULE_NOTEQUAL: - $retVal = !((bool) preg_match('/^' . $ruleValue . '$/i', $cellValueString)); - - break; - case Rule::AUTOFILTER_COLUMN_RULE_GREATERTHAN: - $retVal = strcasecmp($cellValueString, $ruleValue) > 0; - - break; - case Rule::AUTOFILTER_COLUMN_RULE_GREATERTHANOREQUAL: - $retVal = strcasecmp($cellValueString, $ruleValue) >= 0; - - break; - case Rule::AUTOFILTER_COLUMN_RULE_LESSTHAN: - $retVal = strcasecmp($cellValueString, $ruleValue) < 0; - - break; - case Rule::AUTOFILTER_COLUMN_RULE_LESSTHANOREQUAL: - $retVal = strcasecmp($cellValueString, $ruleValue) <= 0; - - break; - } + $retVal = match ($ruleOperator) { + Rule::AUTOFILTER_COLUMN_RULE_EQUAL => Preg::isMatch('/^' . $ruleValue . '$/i', $cellValueString), + Rule::AUTOFILTER_COLUMN_RULE_NOTEQUAL => !(Preg::isMatch('/^' . $ruleValue . '$/i', $cellValueString)), + Rule::AUTOFILTER_COLUMN_RULE_GREATERTHAN => strcasecmp($cellValueString, $ruleValue) > 0, + Rule::AUTOFILTER_COLUMN_RULE_GREATERTHANOREQUAL => strcasecmp($cellValueString, $ruleValue) >= 0, + Rule::AUTOFILTER_COLUMN_RULE_LESSTHAN => strcasecmp($cellValueString, $ruleValue) < 0, + // Rule::AUTOFILTER_COLUMN_RULE_LESSTHANOREQUAL + default => strcasecmp($cellValueString, $ruleValue) <= 0, + }; } // If there are multiple conditions, then we need to test both using the appropriate join operator switch ($join) { @@ -752,14 +734,11 @@ private static function dynamicYesterday(): array private function dynamicFilterDateRange(string $dynamicRuleType, AutoFilter\Column &$filterColumn): array { $ruleValues = []; - $callBack = [__CLASS__, self::DATE_FUNCTIONS[$dynamicRuleType]]; // What if not found? + $callBack = [__CLASS__, self::DATE_FUNCTIONS[$dynamicRuleType] ?? throw new Exception("invalid dynamic rule type $dynamicRuleType")]; // Calculate start/end dates for the required date range based on current date // Val is lowest permitted value. // Maxval is greater than highest permitted value - $val = $maxval = 0; - if (is_callable($callBack)) { //* @phpstan-ignore-line - [$val, $maxval] = $callBack(); - } + [$val, $maxval] = $callBack(); $val = Date::dateTimeToExcel($val); $maxval = Date::dateTimeToExcel($maxval); @@ -1087,26 +1066,16 @@ public function autoExtendRange(int $startRow, int $endRow): int */ public function __clone() { - $vars = get_object_vars($this); - foreach ($vars as $key => $value) { - if (is_object($value)) { - if ($key === 'workSheet') { - // Detach from worksheet - $this->{$key} = null; - } else { - $this->{$key} = clone $value; - } - } elseif ((is_array($value)) && ($key == 'columns')) { - // The columns array of \PhpOffice\PhpSpreadsheet\Worksheet\Worksheet\AutoFilter objects - $this->{$key} = []; - foreach ($value as $k => $v) { - $this->{$key}[$k] = clone $v; //* @phpstan-ignore-line - // attach the new cloned Column to this new cloned Autofilter object - $this->{$key}[$k]->setParent($this); //* @phpstan-ignore-line - } - } else { - $this->{$key} = $value; - } + // workSheet is only property which is an object + // detach from worksheet + $this->workSheet = null; + // columns is the only property which is an array + $columns = $this->columns; + $this->columns = []; + foreach ($columns as $k => $v) { + $this->columns[$k] = clone $v; + // attach the new cloned Column to this new cloned Autofilter object + $this->columns[$k]->setParent($this); } } diff --git a/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Worksheet/AutoFilter/Column/Rule.php b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Worksheet/AutoFilter/Column/Rule.php index fa9768d9..eac61641 100644 --- a/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Worksheet/AutoFilter/Column/Rule.php +++ b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Worksheet/AutoFilter/Column/Rule.php @@ -274,8 +274,7 @@ public function setValue($value): static throw new PhpSpreadsheetException('Invalid rule value for column AutoFilter Rule.'); } // Set the dateTime grouping that we've anticipated - // I have no idea what Phpstan is complaining about below - $this->setGrouping(self::DATE_TIME_GROUPS[$grouping]); // @phpstan-ignore-line + $this->setGrouping(self::DATE_TIME_GROUPS[$grouping]); // @phpstan-ignore offsetAccess.notFound (no idea what phpstan is complaining about) } $this->value = $value; diff --git a/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Worksheet/Drawing.php b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Worksheet/Drawing.php index 1c33389d..bfc38b8e 100644 --- a/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Worksheet/Drawing.php +++ b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Worksheet/Drawing.php @@ -139,6 +139,7 @@ public function setPath(string $path, bool $verifyFile = true, ?ZipArchive $zip if (str_starts_with($path, 'https:') || str_starts_with($path, 'http:')) { $ctxArray = [ 'http' => [ + 'follow_location' => 0, 'user_agent' => 'Mozilla/5.0 (Macintosh; Intel Mac OS X 10_15_7) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/131.0.0.0 Safari/537.36', 'header' => [ //'Connection: keep-alive', // unacceptable performance diff --git a/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Worksheet/PivotTable/PivotCacheDefinition.php b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Worksheet/PivotTable/PivotCacheDefinition.php new file mode 100644 index 00000000..6d79654a --- /dev/null +++ b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Worksheet/PivotTable/PivotCacheDefinition.php @@ -0,0 +1,160 @@ + element. + */ + private ?int $cacheId; + + /** + * Name of the worksheet the source data lives on (worksheet source only). + */ + private ?string $sourceWorksheet = null; + + /** + * Source data range on that worksheet, e.g. "A1:D50" (worksheet source only). + */ + private ?string $sourceRange = null; + + /** + * Names of the cache fields, in declaration order. The index into this + * array is the field index referenced by the pivot table. + * + * @var string[] + */ + private array $cacheFields = []; + + /** + * Distinct values ("shared items") per field name, used when generating a + * cache definition for a newly created pivot table. + * + * @var array + */ + private array $sharedItems = []; + + /** + * Grouping configuration per field name, when a field is grouped. + * + * @var array + */ + private array $fieldGroups = []; + + public function __construct(?int $cacheId = null) + { + $this->cacheId = $cacheId; + } + + public function getCacheId(): ?int + { + return $this->cacheId; + } + + public function setCacheId(?int $cacheId): self + { + $this->cacheId = $cacheId; + + return $this; + } + + public function getSourceWorksheet(): ?string + { + return $this->sourceWorksheet; + } + + public function setSourceWorksheet(?string $sourceWorksheet): self + { + $this->sourceWorksheet = $sourceWorksheet; + + return $this; + } + + public function getSourceRange(): ?string + { + return $this->sourceRange; + } + + public function setSourceRange(?string $sourceRange): self + { + $this->sourceRange = $sourceRange; + + return $this; + } + + /** + * @return string[] + */ + public function getCacheFields(): array + { + return $this->cacheFields; + } + + public function addCacheField(string $name): self + { + $this->cacheFields[] = $name; + + return $this; + } + + /** + * @param string[] $cacheFields + */ + public function setCacheFields(array $cacheFields): self + { + $this->cacheFields = array_values($cacheFields); + + return $this; + } + + /** + * Return the name of the cache field at the given zero-based index, or null. + */ + public function getCacheFieldName(int $index): ?string + { + return $this->cacheFields[$index] ?? null; + } + + /** + * Set the distinct values recorded for a field (used when generating a new + * cache definition). + * + * @param string[] $items + */ + public function setSharedItems(string $fieldName, array $items): self + { + $this->sharedItems[$fieldName] = array_values($items); + + return $this; + } + + /** + * @return string[] + */ + public function getSharedItems(string $fieldName): array + { + return $this->sharedItems[$fieldName] ?? []; + } + + public function setFieldGroup(string $fieldName, PivotFieldGroup $group): self + { + $this->fieldGroups[$fieldName] = $group; + + return $this; + } + + public function getFieldGroup(string $fieldName): ?PivotFieldGroup + { + return $this->fieldGroups[$fieldName] ?? null; + } +} diff --git a/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Worksheet/PivotTable/PivotField.php b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Worksheet/PivotTable/PivotField.php new file mode 100644 index 00000000..b6237d43 --- /dev/null +++ b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Worksheet/PivotTable/PivotField.php @@ -0,0 +1,140 @@ + section (a value field). + */ + private bool $dataField = false; + + /** + * Aggregation function for a data field (e.g. sum, count, average). + * Null when this is not a data field. + */ + private ?string $subtotal = null; + + /** + * Display caption for a data field (e.g. "Sum of Amount"). Null when this + * is not a data field. + */ + private ?string $dataFieldCaption = null; + + public function __construct(int $index, string $name = '') + { + $this->index = $index; + $this->name = $name; + } + + public function getIndex(): int + { + return $this->index; + } + + public function getName(): string + { + return $this->name; + } + + public function setName(string $name): self + { + $this->name = $name; + + return $this; + } + + public function getAxis(): string + { + return $this->axis; + } + + public function setAxis(string $axis): self + { + $this->axis = $axis; + + return $this; + } + + public function isDataField(): bool + { + return $this->dataField; + } + + public function setDataField(bool $dataField): self + { + $this->dataField = $dataField; + + return $this; + } + + public function getSubtotal(): ?string + { + return $this->subtotal; + } + + public function setSubtotal(?string $subtotal): self + { + $this->subtotal = $subtotal; + + return $this; + } + + public function getDataFieldCaption(): ?string + { + return $this->dataFieldCaption; + } + + public function setDataFieldCaption(?string $dataFieldCaption): self + { + $this->dataFieldCaption = $dataFieldCaption; + + return $this; + } +} diff --git a/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Worksheet/PivotTable/PivotFieldGroup.php b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Worksheet/PivotTable/PivotFieldGroup.php new file mode 100644 index 00000000..947fb3be --- /dev/null +++ b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Worksheet/PivotTable/PivotFieldGroup.php @@ -0,0 +1,136 @@ +type = $type; + } + + /** + * Create a numeric range grouping (buckets of $interval width). + */ + public static function numeric(float $interval, ?float $startNum = null, ?float $endNum = null): self + { + $group = new self(self::TYPE_NUMERIC); + $group->interval = $interval; + $group->startNum = $startNum; + $group->endNum = $endNum; + + return $group; + } + + /** + * Create a date grouping by one or more calendar units. + * + * @param string|string[] $groupBy one or more GROUP_BY_* constants + */ + public static function date(array|string $groupBy, ?string $startDate = null, ?string $endDate = null): self + { + $group = new self(self::TYPE_DATE); + $group->groupBy = is_array($groupBy) ? array_values($groupBy) : [$groupBy]; + $group->startDate = $startDate; + $group->endDate = $endDate; + + return $group; + } + + public function getType(): string + { + return $this->type; + } + + public function isNumeric(): bool + { + return $this->type === self::TYPE_NUMERIC; + } + + public function isDate(): bool + { + return $this->type === self::TYPE_DATE; + } + + public function getInterval(): float + { + return $this->interval; + } + + public function getStartNum(): ?float + { + return $this->startNum; + } + + public function getEndNum(): ?float + { + return $this->endNum; + } + + /** + * @return string[] + */ + public function getGroupBy(): array + { + return $this->groupBy; + } + + public function getStartDate(): ?string + { + return $this->startDate; + } + + public function getEndDate(): ?string + { + return $this->endDate; + } +} diff --git a/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Worksheet/PivotTable/PivotTable.php b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Worksheet/PivotTable/PivotTable.php new file mode 100644 index 00000000..0230144b --- /dev/null +++ b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Worksheet/PivotTable/PivotTable.php @@ -0,0 +1,207 @@ +name = $name; + } + + public function isGenerated(): bool + { + return $this->generated; + } + + public function setGenerated(bool $generated): self + { + $this->generated = $generated; + + return $this; + } + + /** + * Code to execute when this pivot table is unset(). + */ + public function __destruct() + { + $this->worksheet = null; + } + + public function getName(): string + { + return $this->name; + } + + public function setName(string $name): self + { + $this->name = $name; + + return $this; + } + + public function getWorksheet(): ?Worksheet + { + return $this->worksheet; + } + + public function setWorksheet(?Worksheet $worksheet): self + { + $this->worksheet = $worksheet; + + return $this; + } + + public function getLocation(): string + { + return $this->location; + } + + public function setLocation(string $location): self + { + $this->location = $location; + + return $this; + } + + public function getCacheDefinition(): ?PivotCacheDefinition + { + return $this->cacheDefinition; + } + + public function setCacheDefinition(?PivotCacheDefinition $cacheDefinition): self + { + $this->cacheDefinition = $cacheDefinition; + + return $this; + } + + /** + * @return PivotField[] + */ + public function getFields(): array + { + return $this->fields; + } + + public function addField(PivotField $field): self + { + $this->fields[] = $field; + + return $this; + } + + /** + * Return only the fields placed on the row axis, in order. + * + * @return PivotField[] + */ + public function getRowFields(): array + { + return $this->getFieldsOnAxis(PivotField::AXIS_ROW); + } + + /** + * Return only the fields placed on the column axis, in order. + * + * @return PivotField[] + */ + public function getColumnFields(): array + { + return $this->getFieldsOnAxis(PivotField::AXIS_COLUMN); + } + + /** + * Return only the fields placed on the page/filter axis, in order. + * + * @return PivotField[] + */ + public function getPageFields(): array + { + return $this->getFieldsOnAxis(PivotField::AXIS_PAGE); + } + + /** + * Return only the value/data fields, in order. + * + * @return PivotField[] + */ + public function getDataFields(): array + { + return array_values( + array_filter( + $this->fields, + static fn (PivotField $field): bool => $field->isDataField() + ) + ); + } + + /** + * @return PivotField[] + */ + private function getFieldsOnAxis(string $axis): array + { + return array_values( + array_filter( + $this->fields, + static fn (PivotField $field): bool => $field->getAxis() === $axis + ) + ); + } + + public function __toString(): string + { + return $this->name; + } +} diff --git a/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Worksheet/PivotTable/PivotTableBuilder.php b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Worksheet/PivotTable/PivotTableBuilder.php new file mode 100644 index 00000000..701badf6 --- /dev/null +++ b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Worksheet/PivotTable/PivotTableBuilder.php @@ -0,0 +1,280 @@ +addRowField('Region') + * ->addColumnField('Product') + * ->addDataField('Amount', PivotField::SUBTOTAL_SUM); + * $pivotTable = $builder->build($pivotSheet, 'A3'); + * ``` + */ +class PivotTableBuilder +{ + private Worksheet $sourceWorksheet; + + private string $sourceRange; + + /** + * Field names in source-column order, taken from the header row. + * + * @var string[] + */ + private array $fieldNames; + + /** + * Requested placements, keyed by field name. + * + * @var array + */ + private array $placements = []; + + /** + * Requested field groupings, keyed by field name. + * + * @var array + */ + private array $groups = []; + + /** + * @param string $sourceRange the source data range including the header row, e.g. "A1:C100" + */ + public function __construct(Worksheet $sourceWorksheet, string $sourceRange) + { + $this->sourceWorksheet = $sourceWorksheet; + $this->sourceRange = str_replace('$', '', $sourceRange); + $this->fieldNames = $this->readHeaderNames(); + } + + /** + * Place a field on the row axis. + */ + public function addRowField(string $fieldName): self + { + return $this->place($fieldName, PivotField::AXIS_ROW, null, null); + } + + /** + * Place a field on the column axis. + */ + public function addColumnField(string $fieldName): self + { + return $this->place($fieldName, PivotField::AXIS_COLUMN, null, null); + } + + /** + * Place a field on the page (report filter) axis. + */ + public function addPageField(string $fieldName): self + { + return $this->place($fieldName, PivotField::AXIS_PAGE, null, null); + } + + /** + * Group a numeric field into fixed-width buckets (e.g. 0-100, 100-200). + * + * @param float $interval bucket width + * @param ?float $startNum lower bound of the first bucket (auto when null) + * @param ?float $endNum upper bound of the last bucket (auto when null) + */ + public function groupFieldByNumericRange(string $fieldName, float $interval, ?float $startNum = null, ?float $endNum = null): self + { + $this->assertFieldExists($fieldName); + $this->groups[$fieldName] = PivotFieldGroup::numeric($interval, $startNum, $endNum); + + return $this; + } + + /** + * Group a date/time field by one or more calendar units. + * + * @param string|string[] $groupBy one or more PivotFieldGroup::GROUP_BY_* constants + * @param ?string $startDate ISO-8601 start (auto when null) + * @param ?string $endDate ISO-8601 end (auto when null) + */ + public function groupFieldByDate(string $fieldName, array|string $groupBy, ?string $startDate = null, ?string $endDate = null): self + { + $this->assertFieldExists($fieldName); + $this->groups[$fieldName] = PivotFieldGroup::date($groupBy, $startDate, $endDate); + + return $this; + } + + /** + * Add a value (data) field with the given aggregation function. + * + * @param string $subtotal one of the PivotField::SUBTOTAL_* constants + * @param ?string $caption optional display caption (defaults to e.g. "Sum of Amount") + */ + public function addDataField(string $fieldName, string $subtotal = PivotField::SUBTOTAL_SUM, ?string $caption = null): self + { + return $this->place($fieldName, PivotField::AXIS_VALUES, $subtotal, $caption); + } + + /** + * Build the PivotTable model and register it on the target worksheet. + * + * @param string $targetCell top-left cell of the pivot table, e.g. "A3" + */ + public function build(Worksheet $targetWorksheet, string $targetCell, string $name = 'PivotTable1'): PivotTable + { + $this->assertHasDataField(); + + $cacheDefinition = new PivotCacheDefinition(1); + $cacheDefinition->setSourceWorksheet($this->sourceWorksheet->getTitle()); + $cacheDefinition->setSourceRange($this->sourceRange); + $cacheDefinition->setCacheFields($this->fieldNames); + foreach ($this->fieldNames as $fieldName) { + $cacheDefinition->setSharedItems($fieldName, $this->distinctValues($fieldName)); + if (isset($this->groups[$fieldName])) { + $cacheDefinition->setFieldGroup($fieldName, $this->groups[$fieldName]); + } + } + + $pivotTable = new PivotTable($name); + $pivotTable->setGenerated(true); + $pivotTable->setCacheDefinition($cacheDefinition); + $pivotTable->setLocation($this->targetLocation($targetCell)); + + foreach ($this->fieldNames as $index => $fieldName) { + $field = new PivotField($index, $fieldName); + if (isset($this->placements[$fieldName])) { + $placement = $this->placements[$fieldName]; + if ($placement['axis'] === PivotField::AXIS_VALUES) { + $field->setDataField(true); + $field->setSubtotal($placement['subtotal']); + $field->setDataFieldCaption($placement['caption'] ?? $this->defaultCaption($placement['subtotal'], $fieldName)); + } else { + $field->setAxis($placement['axis']); + } + } + $pivotTable->addField($field); + } + + $targetWorksheet->addPivotTable($pivotTable); + + return $pivotTable; + } + + private function place(string $fieldName, string $axis, ?string $subtotal, ?string $caption): self + { + $this->assertFieldExists($fieldName); + $this->placements[$fieldName] = ['axis' => $axis, 'subtotal' => $subtotal, 'caption' => $caption]; + + return $this; + } + + private function assertFieldExists(string $fieldName): void + { + if (!in_array($fieldName, $this->fieldNames, true)) { + throw new PhpSpreadsheetException("Pivot source field '{$fieldName}' does not exist in range {$this->sourceRange}"); + } + } + + private function assertHasDataField(): void + { + foreach ($this->placements as $placement) { + if ($placement['axis'] === PivotField::AXIS_VALUES) { + return; + } + } + + throw new PhpSpreadsheetException('A pivot table requires at least one data (value) field'); + } + + /** + * @return string[] + */ + private function readHeaderNames(): array + { + [$start, $end] = Coordinate::rangeBoundaries($this->sourceRange); + $startColumn = (int) $start[0]; + $endColumn = (int) $end[0]; + $headerRow = (int) $start[1]; + $names = []; + for ($col = $startColumn; $col <= $endColumn; ++$col) { + $cell = Coordinate::stringFromColumnIndex($col) . $headerRow; + $names[] = $this->sourceWorksheet->getCell($cell)->getValueString(); + } + + return $names; + } + + /** + * Distinct string values in a field's data rows, in first-seen order. + * + * @return string[] + */ + private function distinctValues(string $fieldName): array + { + $fieldIndex = array_search($fieldName, $this->fieldNames, true); + $result = []; + if ($fieldIndex !== false) { + [$start, $end] = Coordinate::rangeBoundaries($this->sourceRange); + $column = Coordinate::stringFromColumnIndex((int) $start[0] + (int) $fieldIndex); + $firstDataRow = (int) $start[1] + 1; + $lastRow = (int) $end[1]; + + $values = []; + for ($row = $firstDataRow; $row <= $lastRow; ++$row) { + $value = $this->sourceWorksheet->getCell($column . $row)->getValueString(); + if ($value !== '') { + $values[$value] = true; + } + } + + /** @var string[] $result */ + $result = array_keys($values); + } + + return $result; + } + + /** + * Resolve the pivot table's rendered range. The exact extent is recomputed + * by the spreadsheet application on refresh; a single-cell ref is a valid + * starting point that Excel expands. + */ + private function targetLocation(string $targetCell): string + { + $targetCell = str_replace('$', '', $targetCell); + + return "$targetCell:$targetCell"; + } + + private function defaultCaption(?string $subtotal, string $fieldName): string + { + $labels = [ + PivotField::SUBTOTAL_SUM => 'Sum', + PivotField::SUBTOTAL_COUNT => 'Count', + PivotField::SUBTOTAL_AVERAGE => 'Average', + PivotField::SUBTOTAL_MAX => 'Max', + PivotField::SUBTOTAL_MIN => 'Min', + PivotField::SUBTOTAL_PRODUCT => 'Product', + PivotField::SUBTOTAL_COUNT_NUMS => 'Count', + PivotField::SUBTOTAL_STD_DEV => 'StdDev', + PivotField::SUBTOTAL_STD_DEV_P => 'StdDevp', + PivotField::SUBTOTAL_VAR => 'Var', + PivotField::SUBTOTAL_VAR_P => 'Varp', + ]; + $label = $labels[$subtotal] ?? 'Sum'; + + return "{$label} of {$fieldName}"; + } +} diff --git a/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Worksheet/RowCellIterator.php b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Worksheet/RowCellIterator.php index 4d4901c8..59de9fad 100644 --- a/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Worksheet/RowCellIterator.php +++ b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Worksheet/RowCellIterator.php @@ -142,7 +142,15 @@ public function next(): void { do { ++$this->currentColumnIndex; - } while (($this->onlyExistingCells) && (!$this->cellCollection->has(Coordinate::stringFromColumnIndex($this->currentColumnIndex) . $this->rowIndex)) && ($this->currentColumnIndex <= $this->endColumnIndex)); + } while ( + $this->onlyExistingCells + && $this->currentColumnIndex <= $this->endColumnIndex + && !$this->cellCollection->has( + Coordinate::stringFromColumnIndex( + $this->currentColumnIndex + ) . $this->rowIndex + ) + ); } /** @@ -152,7 +160,15 @@ public function prev(): void { do { --$this->currentColumnIndex; - } while (($this->onlyExistingCells) && (!$this->cellCollection->has(Coordinate::stringFromColumnIndex($this->currentColumnIndex) . $this->rowIndex)) && ($this->currentColumnIndex >= $this->startColumnIndex)); + } while ( + $this->onlyExistingCells + && $this->currentColumnIndex >= $this->startColumnIndex + && !$this->cellCollection->has( + Coordinate::stringFromColumnIndex( + $this->currentColumnIndex + ) . $this->rowIndex + ) + ); } /** @@ -177,10 +193,28 @@ public function getCurrentColumnIndex(): int protected function adjustForExistingOnlyRange(): void { if ($this->onlyExistingCells) { - while ((!$this->cellCollection->has(Coordinate::stringFromColumnIndex($this->startColumnIndex) . $this->rowIndex)) && ($this->startColumnIndex <= $this->endColumnIndex)) { + while ( + $this->startColumnIndex <= $this->endColumnIndex + && ( + !$this->cellCollection->has( + Coordinate::stringFromColumnIndex( + $this->startColumnIndex + ) . $this->rowIndex + ) + ) + ) { ++$this->startColumnIndex; } - while ((!$this->cellCollection->has(Coordinate::stringFromColumnIndex($this->endColumnIndex) . $this->rowIndex)) && ($this->endColumnIndex >= $this->startColumnIndex)) { + while ( + $this->endColumnIndex >= $this->startColumnIndex + && ( + !$this->cellCollection->has( + Coordinate::stringFromColumnIndex( + $this->endColumnIndex + ) . $this->rowIndex + ) + ) + ) { --$this->endColumnIndex; } } diff --git a/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Worksheet/Sparkline/Sparkline.php b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Worksheet/Sparkline/Sparkline.php new file mode 100644 index 00000000..a487db37 --- /dev/null +++ b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Worksheet/Sparkline/Sparkline.php @@ -0,0 +1,84 @@ +setLocation($location); + } + $this->setDataRange($dataRange); + } + + public function getLocation(): string + { + return $this->location; + } + + /** + * Set the cell the sparkline is drawn in. Must be a single cell, not a range. + */ + public function setLocation(CellAddress|string $location): self + { + $location = (string) $location; + if (str_contains($location, ':')) { + throw new PhpSpreadsheetException('Sparkline location must be a single cell, not a range'); + } + // Normalise: strip absolute markers and any sheet qualifier. + $location = str_replace('$', '', $location); + if (str_contains($location, '!')) { + $location = substr($location, strrpos($location, '!') + 1); + } + // Validate by attempting to resolve the coordinate. + Coordinate::indexesFromString($location); + $this->location = strtoupper($location); + + return $this; + } + + public function getDataRange(): string + { + return $this->dataRange; + } + + public function setDataRange(string $dataRange): self + { + $this->dataRange = $dataRange; + + return $this; + } + + public function __toString(): string + { + return $this->location; + } +} diff --git a/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Worksheet/Sparkline/SparklineGroup.php b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Worksheet/Sparkline/SparklineGroup.php new file mode 100644 index 00000000..51373f26 --- /dev/null +++ b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Worksheet/Sparkline/SparklineGroup.php @@ -0,0 +1,403 @@ +type; + } + + public function setType(SparklineType $type): self + { + $this->type = $type; + + return $this; + } + + /** + * @return Sparkline[] + */ + public function getSparklines(): array + { + return $this->sparklines; + } + + public function addSparkline(Sparkline $sparkline): self + { + $this->sparklines[] = $sparkline; + + return $this; + } + + /** + * Convenience helper: create and add a sparkline from a location cell and + * data range, returning this group for chaining. + */ + public function createSparkline(CellAddress|string $location, string $dataRange): self + { + return $this->addSparkline(new Sparkline($location, $dataRange)); + } + + /** + * @param Sparkline[] $sparklines + */ + public function setSparklines(array $sparklines): self + { + $this->sparklines = array_values($sparklines); + + return $this; + } + + public function getLineWeight(): float + { + return $this->lineWeight; + } + + public function setLineWeight(float $lineWeight): self + { + $this->lineWeight = $lineWeight; + + return $this; + } + + public function getDisplayMarkers(): bool + { + return $this->displayMarkers; + } + + public function setDisplayMarkers(bool $displayMarkers): self + { + $this->displayMarkers = $displayMarkers; + + return $this; + } + + public function getDisplayHigh(): bool + { + return $this->displayHigh; + } + + public function setDisplayHigh(bool $displayHigh): self + { + $this->displayHigh = $displayHigh; + + return $this; + } + + public function getDisplayLow(): bool + { + return $this->displayLow; + } + + public function setDisplayLow(bool $displayLow): self + { + $this->displayLow = $displayLow; + + return $this; + } + + public function getDisplayFirst(): bool + { + return $this->displayFirst; + } + + public function setDisplayFirst(bool $displayFirst): self + { + $this->displayFirst = $displayFirst; + + return $this; + } + + public function getDisplayLast(): bool + { + return $this->displayLast; + } + + public function setDisplayLast(bool $displayLast): self + { + $this->displayLast = $displayLast; + + return $this; + } + + public function getDisplayNegative(): bool + { + return $this->displayNegative; + } + + public function setDisplayNegative(bool $displayNegative): self + { + $this->displayNegative = $displayNegative; + + return $this; + } + + public function getDisplayXAxis(): bool + { + return $this->displayXAxis; + } + + public function setDisplayXAxis(bool $displayXAxis): self + { + $this->displayXAxis = $displayXAxis; + + return $this; + } + + public function getDisplayHidden(): bool + { + return $this->displayHidden; + } + + public function setDisplayHidden(bool $displayHidden): self + { + $this->displayHidden = $displayHidden; + + return $this; + } + + public function getRightToLeft(): bool + { + return $this->rightToLeft; + } + + public function setRightToLeft(bool $rightToLeft): self + { + $this->rightToLeft = $rightToLeft; + + return $this; + } + + public function getDisplayEmptyCellsAs(): string + { + return $this->displayEmptyCellsAs; + } + + public function setDisplayEmptyCellsAs(string $displayEmptyCellsAs): self + { + $this->displayEmptyCellsAs = $displayEmptyCellsAs; + + return $this; + } + + public function getMinAxisType(): string + { + return $this->minAxisType; + } + + public function setMinAxisType(string $minAxisType): self + { + $this->minAxisType = $minAxisType; + + return $this; + } + + public function getMaxAxisType(): string + { + return $this->maxAxisType; + } + + public function setMaxAxisType(string $maxAxisType): self + { + $this->maxAxisType = $maxAxisType; + + return $this; + } + + public function getManualMin(): ?float + { + return $this->manualMin; + } + + public function setManualMin(?float $manualMin): self + { + $this->manualMin = $manualMin; + + return $this; + } + + public function getManualMax(): ?float + { + return $this->manualMax; + } + + public function setManualMax(?float $manualMax): self + { + $this->manualMax = $manualMax; + + return $this; + } + + public function getColorSeries(): ?string + { + return $this->colorSeries; + } + + public function setColorSeries(?string $colorSeries): self + { + $this->colorSeries = $colorSeries; + + return $this; + } + + public function getColorNegative(): ?string + { + return $this->colorNegative; + } + + public function setColorNegative(?string $colorNegative): self + { + $this->colorNegative = $colorNegative; + + return $this; + } + + public function getColorAxis(): ?string + { + return $this->colorAxis; + } + + public function setColorAxis(?string $colorAxis): self + { + $this->colorAxis = $colorAxis; + + return $this; + } + + public function getColorMarkers(): ?string + { + return $this->colorMarkers; + } + + public function setColorMarkers(?string $colorMarkers): self + { + $this->colorMarkers = $colorMarkers; + + return $this; + } + + public function getColorFirst(): ?string + { + return $this->colorFirst; + } + + public function setColorFirst(?string $colorFirst): self + { + $this->colorFirst = $colorFirst; + + return $this; + } + + public function getColorLast(): ?string + { + return $this->colorLast; + } + + public function setColorLast(?string $colorLast): self + { + $this->colorLast = $colorLast; + + return $this; + } + + public function getColorHigh(): ?string + { + return $this->colorHigh; + } + + public function setColorHigh(?string $colorHigh): self + { + $this->colorHigh = $colorHigh; + + return $this; + } + + public function getColorLow(): ?string + { + return $this->colorLow; + } + + public function setColorLow(?string $colorLow): self + { + $this->colorLow = $colorLow; + + return $this; + } +} diff --git a/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Worksheet/Sparkline/SparklineType.php b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Worksheet/Sparkline/SparklineType.php new file mode 100644 index 00000000..a2d70dbc --- /dev/null +++ b/vendor/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Worksheet/Sparkline/SparklineType.php @@ -0,0 +1,22 @@ + + */ + private ArrayObject $sparklineGroupCollection; + + /** + * Collection of PivotTable objects. + * + * @var ArrayObject + */ + private ArrayObject $pivotTableCollection; + /** * Worksheet title. */ @@ -325,7 +343,9 @@ public function __construct(?Spreadsheet $parent = null, string $title = 'Worksh { // Set parent and title $this->parent = $parent; - $this->setTitle($title, false); + // Chart collection must be set before title + $this->chartCollection = new ArrayObject(); + $this->setTitle($title, false, changeChartSheetNames: false); // setTitle can change $pTitle $this->setCodeName($this->getTitle()); $this->setSheetState(self::SHEETSTATE_VISIBLE); @@ -343,8 +363,6 @@ public function __construct(?Spreadsheet $parent = null, string $title = 'Worksh $this->drawingCollection = new ArrayObject(); // In Cell Drawing collection $this->inCellDrawingCollection = new ArrayObject(); - // Chart collection - $this->chartCollection = new ArrayObject(); // Protection $this->protection = new Protection(); // Default row dimension @@ -355,15 +373,22 @@ public function __construct(?Spreadsheet $parent = null, string $title = 'Worksh $this->autoFilter = new AutoFilter('', $this); // Table collection $this->tableCollection = new ArrayObject(); + // Sparkline group collection + $this->sparklineGroupCollection = new ArrayObject(); + + // Pivot table collection + $this->pivotTableCollection = new ArrayObject(); } /** * Disconnect all cells from this Worksheet object, * typically so that the worksheet object can be unset. + * The worksheet will be in an unusable state after + * this method has completed. */ public function disconnectCells(): void { - if (isset($this->cellCollection)) { //* @phpstan-ignore-line + if (isset($this->cellCollection)) { //* @phpstan-ignore isset.initializedProperty (may be null at destruct time) $this->cellCollection->unsetWorksheetCells(); unset($this->cellCollection); } @@ -380,7 +405,7 @@ public function __destruct() ?->clearCalculationCacheForWorksheet($this->title); $this->disconnectCells(); - unset($this->rowDimensions, $this->columnDimensions, $this->tableCollection, $this->drawingCollection, $this->inCellDrawingCollection, $this->chartCollection, $this->autoFilter); + unset($this->rowDimensions, $this->columnDimensions, $this->tableCollection, $this->sparklineGroupCollection, $this->drawingCollection, $this->inCellDrawingCollection, $this->chartCollection, $this->autoFilter, $this->pivotTableCollection); } /** @@ -462,7 +487,7 @@ private static function checkSheetTitle(string $sheetTitle): string */ public function getCoordinates(bool $sorted = true): array { - if (!isset($this->cellCollection)) { //* @phpstan-ignore-line + if (!isset($this->cellCollection)) { //* @phpstan-ignore isset.initializedProperty (may be null at destruct time) return []; } @@ -796,8 +821,9 @@ public function calculateColumnWidths(): static $this->activePane = $holdActivePane; } if ($activeSheet !== null && $activeSheet >= 0) { - // Not sure what PhpStan doesn't like about next stmt - $this->getParent()?->setActiveSheetIndex($activeSheet); // @phpstan-ignore-line + // Okay, I get it now - if $activeSheet is not null, + // then $this->getParent() must also be non-null. + $this->getParent()->setActiveSheetIndex($activeSheet); } $this->setSelectedCells($selectedCells); @@ -875,7 +901,7 @@ public function getTitle(): string * * @return $this */ - public function setTitle(string $title, bool $updateFormulaCellReferences = true, bool $validate = true): static + public function setTitle(string $title, bool $updateFormulaCellReferences = true, bool $validate = true, bool $changeChartSheetNames = true): static { // Is this a 'rename' or not? if ($this->getTitle() == $title) { @@ -928,10 +954,61 @@ public function setTitle(string $title, bool $updateFormulaCellReferences = true ReferenceHelper::getInstance()->updateNamedFormulae($this->parent, $oldTitle, $newTitle); } } + if ($changeChartSheetNames) { + $this->changeChartSheetNames($oldTitle, $title); + } return $this; } + private function changeChartSheetNames(string $oldTitle, string $title): void + { + $worksheets = [$this]; + if ($this->parent !== null) { + $sheets = $this->parent->getAllSheets(); + if (in_array($this, $sheets, true)) { + $worksheets = $sheets; + } + } + $titleq = "'$title'!"; + $oldTitleq1 = preg_quote("'$oldTitle'!"); + $oldTitleq2 = preg_quote("$oldTitle!"); + $preg1 = "/$oldTitleq1|\\b$oldTitleq2/"; + foreach ($worksheets as $sheet) { + foreach ($sheet->getChartCollection() as $chart) { + foreach (($chart->getPlotArea()?->getPlotGroup() ?? []) as $plotGroup) { + foreach ($plotGroup->getPlotCategories() as $plotCategory) { + $dataSource = (string) $plotCategory->getDataSource(); + $dataSource2 = Preg::replace($preg1, $titleq, $dataSource); + if ($dataSource2 !== $dataSource) { + $plotCategory->setDataSource( + $dataSource2 + ); + } + } + foreach ($plotGroup->getPlotLabels() as $plotLabel) { + $dataSource = (string) $plotLabel->getDataSource(); + $dataSource2 = Preg::replace($preg1, $titleq, $dataSource); + if ($dataSource2 !== $dataSource) { + $plotLabel->setDataSource( + $dataSource2 + ); + } + } + foreach ($plotGroup->getPlotValues() as $plotValue) { + $dataSource = (string) $plotValue->getDataSource(); + $dataSource2 = Preg::replace($preg1, $titleq, $dataSource); + if ($dataSource2 !== $dataSource) { + $plotValue->setDataSource( + $dataSource2 + ); + } + } + } + } + } + } + /** * Get sheet state. * @@ -1234,8 +1311,7 @@ private function getWorksheetAndCoordinate(string $coordinate): array throw new Exception('Sheet not found for named range: ' . $namedRange->getName()); } - /** @phpstan-ignore-next-line */ - $cellCoordinate = ltrim(substr($namedRange->getValue(), strrpos($namedRange->getValue(), '!')), '!'); + $cellCoordinate = ltrim(substr($namedRange->getValue(), (int) strrpos($namedRange->getValue(), '!')), '!'); $finalCoordinate = str_replace('$', '', $cellCoordinate); } } @@ -1683,7 +1759,7 @@ public function duplicateStyle(Style $style, string $range): static public function duplicateConditionalStyle(array $styles, string $range = ''): static { foreach ($styles as $cellStyle) { - if (!($cellStyle instanceof Conditional)) { // @phpstan-ignore-line + if (!($cellStyle instanceof Conditional)) { throw new Exception('Style is not a conditional style'); } } @@ -2171,6 +2247,133 @@ public function removeTableCollection(): self return $this; } + /** + * Get collection of SparklineGroups. + * + * @return ArrayObject + */ + public function getSparklineGroupCollection(): ArrayObject + { + return $this->sparklineGroupCollection; + } + + /** + * Add a SparklineGroup. + * + * @return $this + */ + public function addSparklineGroup(SparklineGroup $sparklineGroup): self + { + $this->sparklineGroupCollection[] = $sparklineGroup; + + return $this; + } + + /** + * Add a single Sparkline, wrapping it in its own SparklineGroup. + * + * This is a convenience method for the common case of adding one sparkline + * with default formatting; the created group is returned so its formatting + * can be adjusted. + * + * @param SparklineType $type the type of sparkline (defaults to line) + */ + public function addSparkline(Sparkline $sparkline, SparklineType $type = SparklineType::Line): SparklineGroup + { + $group = new SparklineGroup(); + $group->setType($type); + $group->addSparkline($sparkline); + $this->addSparklineGroup($group); + + return $group; + } + + /** + * Remove all SparklineGroups. + * + * @return $this + */ + public function removeSparklineGroupCollection(): self + { + $this->sparklineGroupCollection = new ArrayObject(); + + return $this; + } + + /** + * Get collection of PivotTables. + * + * @return ArrayObject + */ + public function getPivotTableCollection(): ArrayObject + { + return $this->pivotTableCollection; + } + + /** + * Get collection of PivotTables (alias of getPivotTableCollection()). + * + * @return ArrayObject + */ + public function getPivotTables(): ArrayObject + { + return $this->pivotTableCollection; + } + + /** + * Add a PivotTable to this worksheet. + * + * @return $this + */ + public function addPivotTable(PivotTable $pivotTable): self + { + $pivotTable->setWorksheet($this); + $this->pivotTableCollection[] = $pivotTable; + + return $this; + } + + /** + * @return string[] array of PivotTable names + */ + public function getPivotTableNames(): array + { + $pivotTableNames = []; + + foreach ($this->pivotTableCollection as $pivotTable) { + $pivotTableNames[] = $pivotTable->getName(); + } + + return $pivotTableNames; + } + + /** + * @param string $name the pivot table name to search + * + * @return null|PivotTable The pivot table from the collection, or null if not found + */ + public function getPivotTableByName(string $name): ?PivotTable + { + $name = StringHelper::strToUpper($name); + foreach ($this->pivotTableCollection as $pivotTable) { + if (StringHelper::strToUpper($pivotTable->getName()) === $name) { + return $pivotTable; + } + } + + return null; + } + + /** + * Remove collection of PivotTables. + */ + public function removePivotTableCollection(): self + { + $this->pivotTableCollection = new ArrayObject(); + + return $this; + } + /** * Get Freeze Pane. */ @@ -2443,6 +2646,18 @@ public function removeRow(int $row, int $numberOfRows = 1): static if ($row < 1) { throw new Exception('Rows to be deleted should at least start from row 1.'); } + if ($numberOfRows === 0) { + return $this; + } + if ($numberOfRows < 0) { + $newRow = max(1, $row + $numberOfRows + 1); + $numberOfRows = $row - $newRow + 1; + $row = $newRow; + } + $newHighestRow = $this->cachedHighestRow; + if ($newHighestRow >= $row) { + $newHighestRow = max($row - 1, $this->cachedHighestRow - $numberOfRows); + } $startRow = $row; $endRow = $startRow + $numberOfRows - 1; $removeKeys = []; @@ -2499,6 +2714,7 @@ public function removeRow(int $row, int $numberOfRows = 1): static } $this->rowDimensions = $holdRowDimensions; + $this->cachedHighestRow = $newHighestRow; return $this; } @@ -2537,6 +2753,19 @@ public function removeColumn(string $column, int $numberOfColumns = 1): static throw new Exception('Column references should not be numeric.'); } $startColumnInt = Coordinate::columnIndexFromString($column); + if ($numberOfColumns === 0) { + return $this; + } + if ($numberOfColumns < 0) { + $newStartColumnInt = max(1, $startColumnInt + $numberOfColumns + 1); + $numberOfColumns = $startColumnInt - $newStartColumnInt + 1; + $startColumnInt = $newStartColumnInt; + $column = Coordinate::stringFromColumnIndex($startColumnInt); + } + $newHighestColumn = $this->cachedHighestColumn; + if ($newHighestColumn >= $startColumnInt) { + $newHighestColumn = max($startColumnInt - 1, $this->cachedHighestColumn - $numberOfColumns); + } $endColumnInt = $startColumnInt + $numberOfColumns - 1; $removeKeys = []; $addKeys = []; @@ -2587,6 +2816,8 @@ public function removeColumn(string $column, int $numberOfColumns = 1): static $this->columnDimensions = $holdColumnDimensions; if ($pColumnIndex > $highestColumnIndex) { + $this->cachedHighestColumn = $newHighestColumn; + return $this; } @@ -2596,6 +2827,7 @@ public function removeColumn(string $column, int $numberOfColumns = 1): static $this->cellCollection->removeColumn($highestColumn); $highestColumn = Coordinate::stringFromColumnIndex(Coordinate::columnIndexFromString($highestColumn) - 1); } + $this->cachedHighestColumn = $newHighestColumn; $this->garbageCollect();