diff --git a/.github/workflows/main.yml b/.github/workflows/main.yml index 82dc364d0..cf6e82687 100644 --- a/.github/workflows/main.yml +++ b/.github/workflows/main.yml @@ -87,7 +87,7 @@ jobs: # This is non-ideal because it only checks for the last commit of the PR, not all of them, but better than nothing - name: Check PHPDoc types - run: ./bin/check-phpdoc-types + run: ./bin/check-phpdoc-types.php php-cs-fixer: runs-on: ubuntu-latest diff --git a/.php-cs-fixer.dist.php b/.php-cs-fixer.dist.php index d4acca504..9be2934cd 100644 --- a/.php-cs-fixer.dist.php +++ b/.php-cs-fixer.dist.php @@ -1,9 +1,8 @@ exclude('vendor') + ->exclude('vendor', 'docs', '.git', '.github') ->notPath('src/PhpSpreadsheet/Writer/ZipStream3.php') - ->name('/(\.php|^generate-document|^generate-locales|^check-phpdoc-types)$/') ->in(__DIR__); $config = new PhpCsFixer\Config(); diff --git a/.phpcs.xml.dist b/.phpcs.xml.dist index ccaa25f0a..69f2bc6f4 100644 --- a/.phpcs.xml.dist +++ b/.phpcs.xml.dist @@ -6,12 +6,7 @@ src tests infra - bin/generate-document - bin/generate-locales - bin/check-phpdoc-types - - samples/Header.php - */tests/Core/*/*Test\.(inc|css|js)$ + bin diff --git a/bin/check-phpdoc-types b/bin/check-phpdoc-types.php old mode 100755 new mode 100644 similarity index 100% rename from bin/check-phpdoc-types rename to bin/check-phpdoc-types.php diff --git a/bin/generate-document b/bin/generate-document.php old mode 100755 new mode 100644 similarity index 90% rename from bin/generate-document rename to bin/generate-document.php index ec8be555a..6f1e93547 --- a/bin/generate-document +++ b/bin/generate-document.php @@ -4,7 +4,7 @@ use PhpOffice\PhpSpreadsheet\Calculation\Calculation; use PhpOffice\PhpSpreadsheetInfra\DocumentGenerator; -require_once 'vendor/autoload.php'; +require_once __DIR__ . '/..' . '/vendor/autoload.php'; $phpSpreadsheetFunctions = Calculation::getFunctions(); ksort($phpSpreadsheetFunctions); diff --git a/bin/generate-locales b/bin/generate-locales.php similarity index 87% rename from bin/generate-locales rename to bin/generate-locales.php index 724a0cabf..6504a1c57 100644 --- a/bin/generate-locales +++ b/bin/generate-locales.php @@ -4,7 +4,7 @@ use PhpOffice\PhpSpreadsheet\Calculation\Calculation; use PhpOffice\PhpSpreadsheetInfra\LocaleGenerator; -require_once 'vendor/autoload.php'; +require_once __DIR__ . '/..' . '/vendor/autoload.php'; $phpSpreadsheetFunctions = Calculation::getFunctions(); diff --git a/bin/pre-commit b/bin/pre-commit index 87a2cb4b9..348bb7174 100755 --- a/bin/pre-commit +++ b/bin/pre-commit @@ -24,7 +24,7 @@ if [ "$files" != "" ]; then fi # Check PHPDoc types -./bin/check-phpdoc-types +./bin/check-phpdoc-types.php if [ $? -ne 0 ]; then pass=false fi diff --git a/infra/DocumentGenerator.php b/infra/DocumentGenerator.php index f31d64892..52e6005dd 100644 --- a/infra/DocumentGenerator.php +++ b/infra/DocumentGenerator.php @@ -33,11 +33,19 @@ class DocumentGenerator return $result; } + /** @return array */ private static function getCategories(): array { - return (new ReflectionClass(Category::class))->getConstants(); + /** @var array */ + $x = (new ReflectionClass(Category::class))->getConstants(); + + return $x; } + /** + * @param int[] $lengths + * @param null|array $values + */ private static function tableRow(array $lengths, ?array $values = null): string { $result = ''; @@ -46,7 +54,7 @@ class DocumentGenerator if ($i > 0) { $result .= '|' . $pad; } - $result .= str_pad($value ?? '', $length, $pad); + $result .= str_pad("$value", $length ?? 0, $pad); } return rtrim($result, ' '); @@ -71,7 +79,7 @@ class DocumentGenerator } /** - * @param array[] $phpSpreadsheetFunctions + * @param array> $phpSpreadsheetFunctions */ public static function generateFunctionListByName(array $phpSpreadsheetFunctions): string { diff --git a/infra/LocaleGenerator.php b/infra/LocaleGenerator.php index 66e0fa0b0..91b595b41 100644 --- a/infra/LocaleGenerator.php +++ b/infra/LocaleGenerator.php @@ -30,6 +30,7 @@ class LocaleGenerator protected string $translationBaseFolder; + /** @var string[] */ protected array $phpSpreadsheetFunctions; protected Spreadsheet $translationSpreadsheet; @@ -38,16 +39,23 @@ class LocaleGenerator protected Worksheet $localeTranslations; + /** @var string[] */ protected array $localeLanguageMap = []; + /** @var array */ protected array $errorCodeMap = []; private Worksheet $functionNameTranslations; + /** @var string[] */ protected array $functionNameLanguageMap = []; + /** @var array */ protected array $functionNameMap = []; + /** + * @param string[] $phpSpreadsheetFunctions + */ public function __construct( string $translationBaseFolder, string $translationSpreadsheetName, @@ -268,6 +276,7 @@ class LocaleGenerator return $worksheet; } + /** @return string[] */ protected function mapLanguageColumns(Worksheet $translationWorksheet): array { $sheetName = $translationWorksheet->getTitle(); @@ -282,7 +291,7 @@ class LocaleGenerator $cells->setIterateOnlyExistingCells(true); foreach ($cells as $cell) { if ($this->localeCanBeSupported($translationWorksheet, $cell)) { - $languageNameMap[$cell->getColumn()] = $cell->getValue(); + $languageNameMap[$cell->getColumn()] = $cell->getValueString(); $this->log($cell->getColumn() . ' -> ' . $cell->getValueString()); } } diff --git a/phpstan.neon.dist b/phpstan.neon.dist index aa465103d..2aa78a2ef 100644 --- a/phpstan.neon.dist +++ b/phpstan.neon.dist @@ -13,9 +13,7 @@ parameters: - src/ - tests/ - infra/ - - bin/generate-document - - bin/generate-locales - - bin/check-phpdoc-types + - bin/ excludePaths: - src/PhpSpreadsheet/Chart/Renderer/JpGraph.php - src/PhpSpreadsheet/Chart/Renderer/JpGraphRendererBase.php diff --git a/samples/Basic3/39_Dropdown.php b/samples/Basic3/39_Dropdown.php index 3fdaa5554..398d7e362 100644 --- a/samples/Basic3/39_Dropdown.php +++ b/samples/Basic3/39_Dropdown.php @@ -22,6 +22,7 @@ $spreadsheet->getProperties() ->setKeywords('Office PhpSpreadsheet php') ->setCategory('Test result file'); +/** @return array */ function transpose(string $value): array { return [$value]; diff --git a/samples/Chart33a/33_Chart_create_line_dateaxis.php b/samples/Chart33a/33_Chart_create_line_dateaxis.php index 77da32601..d928a2c67 100644 --- a/samples/Chart33a/33_Chart_create_line_dateaxis.php +++ b/samples/Chart33a/33_Chart_create_line_dateaxis.php @@ -338,6 +338,7 @@ $spreadsheet->setActiveSheetIndex(1); $helper->write($spreadsheet, __FILE__, ['Xlsx'], true, resetActiveSheet: false); $spreadsheet->disconnectWorksheets(); +/** return array{'min': float|int, 'max': float|int} */ function dateRange(int $nrows, Spreadsheet $wrkbk): array { $dataSheet = $wrkbk->getSheetByNameOrThrow('Data'); diff --git a/samples/DefinedNames/CrossWorksheetNamedFormula.php b/samples/DefinedNames/CrossWorksheetNamedFormula.php index af7210de1..5c6b20259 100644 --- a/samples/DefinedNames/CrossWorksheetNamedFormula.php +++ b/samples/DefinedNames/CrossWorksheetNamedFormula.php @@ -40,6 +40,7 @@ setYearlyData($worksheet, '2020', $data2020); $worksheet = $spreadsheet->addSheet(new Worksheet($spreadsheet)); setYearlyData($worksheet, '2020', [], 'GROWTH'); +/** @param array> $yearlyData */ function setYearlyData(Worksheet $worksheet, string $year, array $yearlyData, ?string $title = null): void { // Set up some basic data diff --git a/samples/Pdf/Mpdf2.php b/samples/Pdf/Mpdf2.php index ca0ed2e83..60d76d2f2 100644 --- a/samples/Pdf/Mpdf2.php +++ b/samples/Pdf/Mpdf2.php @@ -16,7 +16,7 @@ class Mpdf2 extends Mpdf * be used by Mpdf (which would instead use a default substitution). * Other configuration options may be specified here. * - * @param array $config Configuration array + * @param array $config Configuration array */ protected function createExternalWriterInstance($config): \Mpdf\Mpdf { diff --git a/samples/Reader/10_Simple_file_reader_using_a_configurable_read_filter.php b/samples/Reader/10_Simple_file_reader_using_a_configurable_read_filter.php index 49c076861..bc63b68c9 100644 --- a/samples/Reader/10_Simple_file_reader_using_a_configurable_read_filter.php +++ b/samples/Reader/10_Simple_file_reader_using_a_configurable_read_filter.php @@ -13,6 +13,7 @@ $sheetname = 'Data Sheet #3'; class MyReadFilter implements IReadFilter { + /** @param array $columns */ public function __construct( private int $startRow, private int $endRow, diff --git a/src/PhpSpreadsheet/Cell/AdvancedValueBinder.php b/src/PhpSpreadsheet/Cell/AdvancedValueBinder.php index ffdf160d8..7c2f989b8 100644 --- a/src/PhpSpreadsheet/Cell/AdvancedValueBinder.php +++ b/src/PhpSpreadsheet/Cell/AdvancedValueBinder.php @@ -110,6 +110,7 @@ class AdvancedValueBinder extends DefaultValueBinder implements IValueBinder return parent::bindValue($cell, $value); } + /** @param array{0: non-falsy-string, 1: ?string, 2: numeric-string, 3: numeric-string, 4: numeric-string} $matches */ protected function setImproperFraction(array $matches, Cell $cell): bool { // Convert value to number @@ -130,6 +131,7 @@ class AdvancedValueBinder extends DefaultValueBinder implements IValueBinder return true; } + /** @param array{0: non-falsy-string, 1: ?string, 2: numeric-string, 3: numeric-string} $matches */ protected function setProperFraction(array $matches, Cell $cell): bool { // Convert value to number diff --git a/src/PhpSpreadsheet/Theme.php b/src/PhpSpreadsheet/Theme.php index adeef80b3..2366fd672 100644 --- a/src/PhpSpreadsheet/Theme.php +++ b/src/PhpSpreadsheet/Theme.php @@ -135,6 +135,7 @@ class Theme 'Geor' => 'Sylfaen', ]; + /** @return string[] */ public function getThemeColors(): array { return $this->themeColors; @@ -152,6 +153,7 @@ class Theme return $this->themeColorName; } + /** @param null|string[] $themeColors */ public function setThemeColorName(string $name, ?array $themeColors = null): self { $this->themeColorName = $name; @@ -182,11 +184,13 @@ class Theme return $this->majorFontComplexScript; } + /** @return string[] */ public function getMajorFontSubstitutions(): array { return $this->majorFontSubstitutions; } + /** @param null|string[] $substitutions */ public function setMajorFontValues(?string $latin, ?string $eastAsian, ?string $complexScript, ?array $substitutions): self { if (!empty($latin)) { @@ -220,11 +224,13 @@ class Theme return $this->minorFontComplexScript; } + /** @return string[] */ public function getMinorFontSubstitutions(): array { return $this->minorFontSubstitutions; } + /** @param null|string[] $substitutions */ public function setMinorFontValues(?string $latin, ?string $eastAsian, ?string $complexScript, ?array $substitutions): self { if (!empty($latin)) { diff --git a/src/PhpSpreadsheet/Worksheet/Worksheet.php b/src/PhpSpreadsheet/Worksheet/Worksheet.php index 60bf3b12a..9863f7223 100644 --- a/src/PhpSpreadsheet/Worksheet/Worksheet.php +++ b/src/PhpSpreadsheet/Worksheet/Worksheet.php @@ -158,6 +158,8 @@ class Worksheet /** * Conditional styles. Indexed by cell coordinate, e.g. 'A1'. + * + * @var Conditional[][] */ private array $conditionalStylesCollection = []; @@ -1558,6 +1560,8 @@ class Worksheet /** * Get collection of conditional styles. + * + * @return Conditional[][] */ public function getConditionalStylesCollection(): array { diff --git a/src/PhpSpreadsheet/Writer/Html.php b/src/PhpSpreadsheet/Writer/Html.php index 4d7bfcafb..c72f55124 100644 --- a/src/PhpSpreadsheet/Writer/Html.php +++ b/src/PhpSpreadsheet/Writer/Html.php @@ -488,7 +488,7 @@ class Html extends BaseWriter foreach ($condStylesCollection as $condStyles) { foreach ($condStyles as $key => $cs) { if ($cs->getConditionType() === Conditional::CONDITION_COLORSCALE) { - $cs->getColorScale()->setScaleArray(); + $cs->getColorScale()?->setScaleArray(); } } } diff --git a/tests/PhpSpreadsheetTests/Reader/Xlsx/Issue4049Test.php b/tests/PhpSpreadsheetTests/Reader/Xlsx/Issue4049Test.php index d1d6cde38..a73d0fee1 100644 --- a/tests/PhpSpreadsheetTests/Reader/Xlsx/Issue4049Test.php +++ b/tests/PhpSpreadsheetTests/Reader/Xlsx/Issue4049Test.php @@ -26,12 +26,14 @@ class Issue4049Test extends AbstractFunctional $colorScale = $cond1[0]->getColorScale(); self::assertNotNull($colorScale); $min = $colorScale->getMinimumConditionalFormatValueObject(); + self::assertNotNull($min); self::assertSame('formula', $min->getType()); self::assertSame('25', $min->getCellFormula()); self::assertNull($colorScale->getMidpointConditionalFormatValueObject()); $max = $colorScale->getMaximumConditionalFormatValueObject(); + self::assertNotNull($max); self::assertSame('max', $max->getType()); self::assertNull($max->getValue());