From f416c6fb072d8f950d03bdf573e73c006c7cab34 Mon Sep 17 00:00:00 2001 From: rotimi Date: Tue, 7 May 2024 00:16:41 -0600 Subject: [PATCH] Psalm code tweaks --- src/FileIoUtils.php | 9 ++-- src/OrmClassesGenerator.php | 89 ++++++++++++++++++++++++++++++++++++- src/SchemaUtils.php | 32 ++++++++++--- 3 files changed, 121 insertions(+), 9 deletions(-) diff --git a/src/FileIoUtils.php b/src/FileIoUtils.php index 6ebd446..ea60b13 100644 --- a/src/FileIoUtils.php +++ b/src/FileIoUtils.php @@ -20,9 +20,12 @@ public static function get(string $file): string { $error = error_get_last(); - throw new \Exception($error['message']); + throw new \Exception(($error === null) ? "ERROR: Could not get the contents of the file `{$file}`" : $error['message']); } + /** + * @psalm-suppress PossiblyUnusedReturnValue + */ public static function put(string $file, string $data): int { $level = error_reporting(0); @@ -36,7 +39,7 @@ public static function put(string $file, string $data): int { $error = error_get_last(); - throw new \Exception($error['message']); + throw new \Exception(($error === null) ? "ERROR: Could not write data `{$data}` to the file `{$file}`" : $error['message']); } public static function isFile(string $file): bool { @@ -59,7 +62,7 @@ public static function mkdir(string $dir, int $mode = 0777, bool $deep = true): $error = error_get_last(); - throw new \Exception($error['message']); + throw new \Exception(($error === null) ? "ERROR: Could not create the directory / folder: `{$dir}`" : $error['message']); } public static function concatDirAndFileName(string $dir, string $file): string { diff --git a/src/OrmClassesGenerator.php b/src/OrmClassesGenerator.php index 5c01c64..fa13985 100644 --- a/src/OrmClassesGenerator.php +++ b/src/OrmClassesGenerator.php @@ -7,6 +7,7 @@ * OrmClassesGenerator is the main class that generates collection, model & record classes for any application using LeanOrm * * @author rotimi + * @psalm-suppress UnusedClass */ class OrmClassesGenerator { @@ -68,6 +69,10 @@ public function __construct(protected array $config) { $ds = DIRECTORY_SEPARATOR; $this->defaultTemplatesDirectory = realpath(__DIR__ . "{$ds}..{$ds}templates{$ds}"); + /** + * @psalm-suppress MixedAssignment + * @psalm-suppress UnresolvableInclude + */ $this->defaultConfig = require __DIR__ . "{$ds}..{$ds}sample-config.php"; if(!array_key_exists('pdo', $this->config)) { @@ -79,15 +84,28 @@ public function __construct(protected array $config) { throw new \Exception('`pdo` entry in config is not an array & is also not a PDO instance!'); } + /** + * @psalm-suppress MixedArgument + */ $this->pdo = ($this->config['pdo'] instanceof \PDO) ? $this->config['pdo'] : new \PDO(...$this->config['pdo']); - // fill config with defaults + /** + * Fill config with defaults + * + * @psalm-suppress MixedAssignment + */ foreach ($this->defaultConfig as $key=>$val) { + /** + * @psalm-suppress MixedArgument + */ if(!array_key_exists($key, $this->config)) { + /** + * @psalm-suppress MixedArrayOffset + */ $this->config[$key] = $val; } } @@ -116,11 +134,19 @@ public function __construct(protected array $config) { if( OtherUtils::isNonEmptyString($this->config['custom_templates_directory']) ) { + /** + * @psalm-suppress MixedArgument + * @psalm-suppress PossiblyInvalidCast + * @psalm-suppress PossiblyInvalidArgument + */ if(!FileIoUtils::isDir($this->config['custom_templates_directory'])) { throw new \Exception('`custom_templates_directory` entry in config is not a valid directory!'); } + /** + * @psalm-suppress MixedAssignment + */ $this->customTemplatesDirectory = $this->config['custom_templates_directory']; } elseif ( @@ -321,15 +347,35 @@ protected function generateClassFiles(string $tableOrViewName=''): ?int { echo "\tGenerating class files for table `{$tableName}` ....". PHP_EOL; + /** + * @psalm-suppress MixedAssignment + * @psalm-suppress MixedFunctionCall + */ $collectionOrModelNamePrefix = $this->config['table_name_to_collection_and_model_class_prefix_transformer']($tableName); + /** + * @psalm-suppress MixedAssignment + * @psalm-suppress MixedFunctionCall + */ $recordNamePrefix = $this->config['table_name_to_record_class_prefix_transformer']($tableName); + /** + * @psalm-suppress MixedOperand + */ $collectionClassName = $collectionOrModelNamePrefix. 'Collection.php'; + /** + * @psalm-suppress MixedOperand + */ $modelClassName = $collectionOrModelNamePrefix. 'Model.php'; + /** + * @psalm-suppress MixedOperand + */ $fieldsFileName = $collectionOrModelNamePrefix. 'FieldsMetadata.php'; + /** + * @psalm-suppress MixedOperand + */ $recordClassName = $recordNamePrefix. 'Record.php'; echo "\t\tCollection class file name: `{$collectionClassName}`". PHP_EOL; @@ -337,6 +383,9 @@ protected function generateClassFiles(string $tableOrViewName=''): ?int { echo "\t\tFields Metadata file name: `{$fieldsFileName}`". PHP_EOL; echo "\t\tRecord class file name: `{$recordClassName}`". PHP_EOL; + /** + * @psalm-suppress MixedArgument + */ $destinationDirectory = FileIoUtils::concatDirAndFileName($this->destinationDirectory, $collectionOrModelNamePrefix); @@ -344,6 +393,9 @@ protected function generateClassFiles(string $tableOrViewName=''): ?int { $this->filesToWrite[$destinationDirectory] = []; + /** + * @psalm-suppress MixedArgument + */ $this->filesToWrite[$destinationDirectory][$collectionClassName] = $this->generateCollectionClassFile($tableName, $collectionOrModelNamePrefix, $recordNamePrefix); @@ -381,6 +433,9 @@ protected function generateCollectionClassFile(string $tableName, string $collec return strtr($this->loadedCollectionTemplateFile, $translations); } + /** + * @psalm-suppress PossiblyUnusedParam + */ protected function generateFieldsMetadataFile(string $tableName, string $collectionOrModelNamePrefix, string $recordNamePrefix): string { $colDefs = SchemaUtils::fetchTableColsFromDB($tableName, $this->pdo); @@ -406,6 +461,9 @@ protected function generateFieldsMetadataFile(string $tableName, string $collect return strtr($this->loadedFieldsMetadataTemplateFile, $translations); } + /** + * @psalm-suppress MixedArgument + */ protected function generateModelClassFile(string $tableName, string $collectionOrModelNamePrefix, string $recordNamePrefix): string { $colDefs = SchemaUtils::fetchTableColsFromDB($tableName, $this->pdo); @@ -466,6 +524,9 @@ protected function generateRecordClassFile(string $tableName, string $collection return strtr($this->loadedRecordTemplateFile, $translations); } + /** + * @psalm-suppress RedundantCastGivenDocblockType + */ protected function generateColNamesAsPhpDocClassProperties(string $tableName): string { $colDefs = SchemaUtils::fetchTableColsFromDB($tableName, $this->pdo); @@ -483,6 +544,7 @@ protected function generateColNamesAsPhpDocClassProperties(string $tableName): s } $props .= " * @property mixed \${$col->name} {$coltype}"; + if ($col->size !== null) { $props .= "({$col->size}"; @@ -512,12 +574,25 @@ protected function writeGeneratedClassFilesToDestinationDirectory(): ?int { echo "Creating generated collection, model & record class files ....". PHP_EOL; + /** + * @psalm-suppress MixedAssignment + */ foreach ($this->filesToWrite as $modelDirectory => $modelFilesInfo) { + /** + * @psalm-suppress MixedArgumentTypeCoercion + */ $this->mkdir($modelDirectory); + /** + * @psalm-suppress MixedAssignment + */ foreach ($modelFilesInfo as $fileName => $fileContents) { + /** + * @psalm-suppress MixedArgument + * @psalm-suppress MixedArgumentTypeCoercion + */ $destinationFile = FileIoUtils::concatDirAndFileName($modelDirectory, $fileName); if(FileIoUtils::isFile($destinationFile) && !str_contains($destinationFile, 'FieldsMetadata')) { @@ -529,6 +604,9 @@ protected function writeGeneratedClassFilesToDestinationDirectory(): ?int { echo ((FileIoUtils::isFile($destinationFile))? "Updating " : "Creating " ) . "`{$destinationFile}`!" . PHP_EOL; + /** + * @psalm-suppress MixedArgument + */ FileIoUtils::put($destinationFile, $fileContents); } @@ -582,8 +660,14 @@ protected function loadTableAndViewNames(): ?int { sort($tableNames); + /** + * @psalm-suppress MixedAssignment + */ foreach($tableNames as $tableName) { + /** + * @psalm-suppress MixedArgument + */ if( ( strtolower(SchemaUtils::getPdoDriverName($this->pdo)) === 'sqlite' @@ -600,6 +684,9 @@ protected function loadTableAndViewNames(): ?int { } echo "Adding table `{$tableName}`" . PHP_EOL; + /** + * @psalm-suppress MixedPropertyTypeCoercion + */ $this->tableAndViewNames[] = $tableName; } // foreach($tableNames as $tableName) diff --git a/src/SchemaUtils.php b/src/SchemaUtils.php index 543cfaa..105ab57 100644 --- a/src/SchemaUtils.php +++ b/src/SchemaUtils.php @@ -39,8 +39,14 @@ public static function fetchTableListFromDB(\PDO $pdo): array { if(strtolower(static::getPdoDriverName($pdo)) === 'pgsql') { // Calculate schema name for postgresql + /** + * @psalm-suppress MixedAssignment + */ $schemaName = static::dbFetchValue($pdo, 'SELECT CURRENT_SCHEMA'); + /** + * @psalm-suppress MixedArgument + */ return $schema->fetchTableList($schemaName); } @@ -48,7 +54,7 @@ public static function fetchTableListFromDB(\PDO $pdo): array { } /** - * @return mixed[]|\Rotexsoft\SqlSchema\Column[] + * @return \Rotexsoft\SqlSchema\Column[] */ public static function fetchTableColsFromDB(string $table_name, \PDO $pdo): array { @@ -64,8 +70,13 @@ public static function columnExistsInDbTable(string $table_name, string $column_ return array_key_exists($column_name, $schema_definitions); } + /** + * @psalm-suppress MixedInferredReturnType + */ public static function getPdoDriverName(\PDO $pdo): string { - + /** + * @psalm-suppress MixedReturnStatement + */ return $pdo->getAttribute(\PDO::ATTR_DRIVER_NAME); } @@ -88,7 +99,10 @@ public static function getCurrentConnectionInfo(\PDO $pdo): string { try { if( $value !== 'PERSISTENT' ) { - + /** + * @psalm-suppress MixedArgument + * @psalm-suppress MixedOperand + */ $result .= "`{$key}`: " . @$pdo->getAttribute(constant(\PDO::class .'::ATTR_' . $value)); } @@ -99,7 +113,9 @@ public static function getCurrentConnectionInfo(\PDO $pdo): string { } if( $value === 'PERSISTENT' ) { - + /** + * @psalm-suppress MixedArgument + */ $result .= "`{$key}`: " . var_export(@$pdo->getAttribute(constant(\PDO::class .'::ATTR_' . $value)), true); } @@ -109,7 +125,10 @@ public static function getCurrentConnectionInfo(\PDO $pdo): string { return $result; } - + + /** + * @psalm-suppress MoreSpecificReturnType + */ protected static function getSchemaQueryingObject(\PDO $pdo): \Rotexsoft\SqlSchema\AbstractSchema { // a column definition factory @@ -119,6 +138,9 @@ protected static function getSchemaQueryingObject(\PDO $pdo): \Rotexsoft\SqlSche $schemaClassName = '\\Rotexsoft\\SqlSchema\\' . ucfirst($pdoDriverName) . 'Schema'; // the schema discovery object + /** + * @psalm-suppress LessSpecificReturnStatement + */ return new $schemaClassName($pdo, $columnFactory); }