diff --git a/.github/workflows/ci.yml b/.github/workflows/ci.yml index e4046c760..6ad41d067 100644 --- a/.github/workflows/ci.yml +++ b/.github/workflows/ci.yml @@ -43,6 +43,41 @@ jobs: - name: Run build run: npm run build + phpstan: + name: PHPStan + runs-on: ubuntu-latest + steps: + - name: Checkout repository + uses: actions/checkout@v4 + + - name: Setup PHP + uses: shivammathur/setup-php@v2 + with: + php-version: '8.3' + + - name: Cache Composer + uses: actions/cache@v4 + with: + path: ~/.composer/cache + key: ${{ runner.os }}-composer-phpstan-${{ hashFiles('**/composer.lock') }} + restore-keys: | + ${{ runner.os }}-composer-phpstan- + + - name: Install Composer dependencies + run: composer install --no-interaction --no-progress + + - name: Cache PHPStan result cache + uses: actions/cache@v4 + with: + path: .phpstan-cache + key: ${{ runner.os }}-phpstan-${{ hashFiles('**/composer.lock', 'phpstan.neon.dist') }}-${{ github.sha }} + restore-keys: | + ${{ runner.os }}-phpstan-${{ hashFiles('**/composer.lock', 'phpstan.neon.dist') }}- + ${{ runner.os }}-phpstan- + + - name: Run PHPStan + run: composer phpstan + e2e: name: E2E (Playwright) runs-on: ubuntu-latest diff --git a/.gitignore b/.gitignore index 0a408a57f..219524cb7 100644 --- a/.gitignore +++ b/.gitignore @@ -58,3 +58,6 @@ package/dist # AI generated files .claude/ + +# PHPStan result cache +/.phpstan-cache/ diff --git a/composer.json b/composer.json index bf0f95ba6..e7531d730 100644 --- a/composer.json +++ b/composer.json @@ -11,7 +11,11 @@ "phpcompatibility/phpcompatibility-wp": "dev-master", "phpcompatibility/php-compatibility": "dev-develop as 9.99.99", "automattic/vipwpcs": "^3.0", - "wp-coding-standards/wpcs": "^3.0" + "wp-coding-standards/wpcs": "^3.0", + "phpstan/phpstan": "^2.0", + "szepeviktor/phpstan-wordpress": "^2.0", + "php-stubs/wp-cli-stubs": "^2.10", + "php-stubs/woocommerce-stubs": "^9.0" }, "config": { "platform": { @@ -27,6 +31,9 @@ ], "fix": [ "phpcbf" + ], + "phpstan": [ + "phpstan analyse --memory-limit=-1" ] }, "minimum-stability": "dev" diff --git a/composer.lock b/composer.lock index ba8e58578..3803b2de2 100644 --- a/composer.lock +++ b/composer.lock @@ -4,7 +4,7 @@ "Read more about it at https://getcomposer.org/doc/01-basic-usage.md#installing-dependencies", "This file is @generated automatically" ], - "content-hash": "7dec3f7732c4f100acf0b8d51d11218b", + "content-hash": "b8cd5a14604ce418e38204b454e4447a", "packages": [], "packages-dev": [ { @@ -136,6 +136,146 @@ }, "time": "2022-02-04T12:51:07+00:00" }, + { + "name": "php-stubs/woocommerce-stubs", + "version": "v9.9.5", + "source": { + "type": "git", + "url": "https://github.com/php-stubs/woocommerce-stubs.git", + "reference": "3f4d4e14afe6150569bd96cf14e8a17a84812447" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/php-stubs/woocommerce-stubs/zipball/3f4d4e14afe6150569bd96cf14e8a17a84812447", + "reference": "3f4d4e14afe6150569bd96cf14e8a17a84812447", + "shasum": "" + }, + "require": { + "php-stubs/wordpress-stubs": "^5.3 || ^6.0" + }, + "require-dev": { + "php": "~7.1 || ~8.0", + "php-stubs/generator": "^0.8.0" + }, + "suggest": { + "symfony/polyfill-php73": "Symfony polyfill backporting some PHP 7.3+ features to lower PHP versions", + "szepeviktor/phpstan-wordpress": "WordPress extensions for PHPStan" + }, + "type": "library", + "notification-url": "https://packagist.org/downloads/", + "license": [ + "MIT" + ], + "description": "WooCommerce function and class declaration stubs for static analysis.", + "homepage": "https://github.com/php-stubs/woocommerce-stubs", + "keywords": [ + "PHPStan", + "static analysis", + "woocommerce", + "wordpress" + ], + "support": { + "issues": "https://github.com/php-stubs/woocommerce-stubs/issues", + "source": "https://github.com/php-stubs/woocommerce-stubs/tree/v9.9.5" + }, + "time": "2025-07-14T17:12:48+00:00" + }, + { + "name": "php-stubs/wordpress-stubs", + "version": "v6.9.4", + "source": { + "type": "git", + "url": "https://github.com/php-stubs/wordpress-stubs.git", + "reference": "90a9412826b9944f93b10bf41d795b5fe68abcd5" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/php-stubs/wordpress-stubs/zipball/90a9412826b9944f93b10bf41d795b5fe68abcd5", + "reference": "90a9412826b9944f93b10bf41d795b5fe68abcd5", + "shasum": "" + }, + "conflict": { + "phpdocumentor/reflection-docblock": "5.6.1" + }, + "require-dev": { + "dealerdirect/phpcodesniffer-composer-installer": "^1.0", + "nikic/php-parser": "^5.5", + "php": "^7.4 || ^8.0", + "php-stubs/generator": "^0.8.6", + "phpdocumentor/reflection-docblock": "^6.0", + "phpstan/phpstan": "^2.1", + "phpunit/phpunit": "^9.5", + "symfony/polyfill-php80": "*", + "szepeviktor/phpcs-psr-12-neutron-hybrid-ruleset": "^1.1.1", + "wp-coding-standards/wpcs": "3.1.0 as 2.3.0" + }, + "suggest": { + "paragonie/sodium_compat": "Pure PHP implementation of libsodium", + "symfony/polyfill-php80": "Symfony polyfill backporting some PHP 8.0+ features to lower PHP versions", + "szepeviktor/phpstan-wordpress": "WordPress extensions for PHPStan" + }, + "type": "library", + "notification-url": "https://packagist.org/downloads/", + "license": [ + "MIT" + ], + "description": "WordPress function and class declaration stubs for static analysis.", + "homepage": "https://github.com/php-stubs/wordpress-stubs", + "keywords": [ + "PHPStan", + "static analysis", + "wordpress" + ], + "support": { + "issues": "https://github.com/php-stubs/wordpress-stubs/issues", + "source": "https://github.com/php-stubs/wordpress-stubs/tree/v6.9.4" + }, + "time": "2026-05-01T20:36:01+00:00" + }, + { + "name": "php-stubs/wp-cli-stubs", + "version": "v2.12.0", + "source": { + "type": "git", + "url": "https://github.com/php-stubs/wp-cli-stubs.git", + "reference": "af16401e299a3fd2229bd0fa9a037638a4174a9d" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/php-stubs/wp-cli-stubs/zipball/af16401e299a3fd2229bd0fa9a037638a4174a9d", + "reference": "af16401e299a3fd2229bd0fa9a037638a4174a9d", + "shasum": "" + }, + "require": { + "php-stubs/wordpress-stubs": "^4.7 || ^5.0 || ^6.0" + }, + "require-dev": { + "php": "~7.3 || ~8.0", + "php-stubs/generator": "^0.8.0" + }, + "suggest": { + "symfony/polyfill-php73": "Symfony polyfill backporting some PHP 7.3+ features to lower PHP versions", + "szepeviktor/phpstan-wordpress": "WordPress extensions for PHPStan" + }, + "type": "library", + "notification-url": "https://packagist.org/downloads/", + "license": [ + "MIT" + ], + "description": "WP-CLI function and class declaration stubs for static analysis.", + "homepage": "https://github.com/php-stubs/wp-cli-stubs", + "keywords": [ + "PHPStan", + "static analysis", + "wordpress", + "wp-cli" + ], + "support": { + "issues": "https://github.com/php-stubs/wp-cli-stubs/issues", + "source": "https://github.com/php-stubs/wp-cli-stubs/tree/v2.12.0" + }, + "time": "2025-06-10T09:58:05+00:00" + }, { "name": "phpcompatibility/php-compatibility", "version": "dev-develop", @@ -477,6 +617,71 @@ }, "time": "2023-06-26T10:35:06+00:00" }, + { + "name": "phpstan/phpstan", + "version": "2.2.x-dev", + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/phpstan/phpstan/zipball/c4cda3fb3d5fe1615d1b53edee13525600e39868", + "reference": "c4cda3fb3d5fe1615d1b53edee13525600e39868", + "shasum": "" + }, + "require": { + "php": "^7.4|^8.0" + }, + "conflict": { + "phpstan/phpstan-shim": "*" + }, + "default-branch": true, + "bin": [ + "phpstan", + "phpstan.phar" + ], + "type": "library", + "autoload": { + "files": [ + "bootstrap.php" + ] + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "MIT" + ], + "authors": [ + { + "name": "Ondřej Mirtes" + }, + { + "name": "Markus Staab" + }, + { + "name": "Vincent Langlet" + } + ], + "description": "PHPStan - PHP Static Analysis Tool", + "keywords": [ + "dev", + "static analysis" + ], + "support": { + "docs": "https://phpstan.org/user-guide/getting-started", + "forum": "https://github.com/phpstan/phpstan/discussions", + "issues": "https://github.com/phpstan/phpstan/issues", + "security": "https://github.com/phpstan/phpstan/security/policy", + "source": "https://github.com/phpstan/phpstan-src" + }, + "funding": [ + { + "url": "https://github.com/ondrejmirtes", + "type": "github" + }, + { + "url": "https://github.com/phpstan", + "type": "github" + } + ], + "time": "2026-06-17T15:28:08+00:00" + }, { "name": "sirbrillig/phpcs-variable-analysis", "version": "2.x-dev", @@ -617,6 +822,70 @@ ], "time": "2024-01-24T01:41:07+00:00" }, + { + "name": "szepeviktor/phpstan-wordpress", + "version": "2.x-dev", + "source": { + "type": "git", + "url": "https://github.com/szepeviktor/phpstan-wordpress.git", + "reference": "84577e2ea1e4c2a95537fe5ea2ac8e18f4ceab1a" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/szepeviktor/phpstan-wordpress/zipball/84577e2ea1e4c2a95537fe5ea2ac8e18f4ceab1a", + "reference": "84577e2ea1e4c2a95537fe5ea2ac8e18f4ceab1a", + "shasum": "" + }, + "require": { + "php": "^7.4 || ^8.0", + "php-stubs/wordpress-stubs": ">=6.6.2", + "phpstan/phpstan": "^2.0" + }, + "require-dev": { + "composer/composer": "^2.1.14", + "composer/semver": "^3.4", + "dealerdirect/phpcodesniffer-composer-installer": "^1.0", + "php-parallel-lint/php-parallel-lint": "^1.1", + "phpstan/phpstan-strict-rules": "^2.0", + "phpunit/phpunit": "^9.0", + "szepeviktor/phpcs-psr-12-neutron-hybrid-ruleset": "^1.0", + "wp-coding-standards/wpcs": "3.1.0 as 2.3.0" + }, + "suggest": { + "swissspidy/phpstan-no-private": "Detect usage of internal core functions, classes and methods" + }, + "default-branch": true, + "type": "phpstan-extension", + "extra": { + "phpstan": { + "includes": [ + "extension.neon" + ] + } + }, + "autoload": { + "psr-4": { + "SzepeViktor\\PHPStan\\WordPress\\": "src/" + } + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "MIT" + ], + "description": "WordPress extensions for PHPStan", + "keywords": [ + "PHPStan", + "code analyse", + "code analysis", + "static analysis", + "wordpress" + ], + "support": { + "issues": "https://github.com/szepeviktor/phpstan-wordpress/issues", + "source": "https://github.com/szepeviktor/phpstan-wordpress/tree/2.x" + }, + "time": "2026-05-22T16:22:09+00:00" + }, { "name": "wp-coding-standards/wpcs", "version": "3.0.1", @@ -694,17 +963,17 @@ ], "minimum-stability": "dev", "stability-flags": { - "phpcompatibility/phpcompatibility-wp": 20, - "phpcompatibility/php-compatibility": 20 + "phpcompatibility/php-compatibility": 20, + "phpcompatibility/phpcompatibility-wp": 20 }, "prefer-stable": false, "prefer-lowest": false, "platform": { "ext-json": "*" }, - "platform-dev": [], + "platform-dev": {}, "platform-overrides": { - "php": "5.6.20" + "php": "7.4" }, - "plugin-api-version": "2.6.0" + "plugin-api-version": "2.9.0" } diff --git a/php/cache/class-cache-point.php b/php/cache/class-cache-point.php index dcdd85907..91abc3777 100644 --- a/php/cache/class-cache-point.php +++ b/php/cache/class-cache-point.php @@ -107,9 +107,9 @@ public function __construct( Cache $cache ) { * @hook cloudinary_on_demand_sync_limit * @default 100 * - * @param $value {int} The default number of static assets. + * @param int $value The default number of static assets. * - * @return {int} + * @return int */ $this->sync_limit = apply_filters( 'cloudinary_on_demand_sync_limit', 100 ); $this->register_post_type(); @@ -118,7 +118,7 @@ public function __construct( Cache $cache ) { add_filter( 'get_post_metadata', array( $this, 'get_meta' ), 10, 3 ); add_filter( 'delete_post_metadata', array( $this, 'delete_meta' ), 10, 4 ); add_action( 'shutdown', array( $this, 'meta_updates' ) ); - add_action( 'wp_resource_hints', array( $this, 'dns_prefetch' ), 10, 2 ); + add_filter( 'wp_resource_hints', array( $this, 'dns_prefetch' ), 10, 2 ); } /** diff --git a/php/cache/class-file-system.php b/php/cache/class-file-system.php index 0baaf610a..44e06d17b 100644 --- a/php/cache/class-file-system.php +++ b/php/cache/class-file-system.php @@ -172,6 +172,8 @@ public function get_file_src_root( $file_url ) { ); } } + + return array(); } /** diff --git a/php/class-assets.php b/php/class-assets.php index ce4e1beea..afdd8e79f 100644 --- a/php/class-assets.php +++ b/php/class-assets.php @@ -158,8 +158,8 @@ protected function register_hooks() { add_filter( 'cloudinary_set_usable_asset', array( $this, 'check_usable_asset' ) ); // Actions. add_action( 'cloudinary_ready', array( $this, 'setup' ) ); - add_action( 'cloudinary_thread_queue_details_query', array( $this, 'connect_post_type' ) ); - add_action( 'cloudinary_build_queue_query', array( $this, 'connect_post_type' ) ); + add_filter( 'cloudinary_thread_queue_details_query', array( $this, 'connect_post_type' ) ); + add_filter( 'cloudinary_build_queue_query', array( $this, 'connect_post_type' ) ); add_action( 'cloudinary_string_replace', array( $this, 'add_url_replacements' ), 20 ); add_action( 'shutdown', array( $this, 'meta_updates' ) ); add_action( 'admin_bar_menu', array( $this, 'admin_bar_cache' ), 100 ); diff --git a/php/class-cache.php b/php/class-cache.php index 52d4d8c1d..bb89c51e1 100644 --- a/php/class-cache.php +++ b/php/class-cache.php @@ -227,7 +227,7 @@ protected function register_hooks() { add_action( 'admin_init', array( $this, 'admin_rewrite' ), 0 ); } add_filter( 'cloudinary_api_rest_endpoints', array( $this, 'rest_endpoints' ) ); - add_action( 'http_request_args', array( $this, 'prevent_caching_internal_requests' ), 10, 5 ); // phpcs:ignore WordPressVIPMinimum.Hooks.RestrictedHooks.http_request_args + add_filter( 'http_request_args', array( $this, 'prevent_caching_internal_requests' ), 10, 2 ); // phpcs:ignore WordPressVIPMinimum.Hooks.RestrictedHooks.http_request_args } /** @@ -261,9 +261,9 @@ public function bypass_cache() { * @hook cloudinary_bypass_cache * @default false * - * @param $bypass {bool} True to bypass, false to not. + * @param bool $bypass True to bypass, false to not. * - * @return {bool} + * @return bool */ return apply_filters( 'cloudinary_bypass_cache', ! is_null( $bypass ) ); } @@ -486,9 +486,9 @@ protected function get_inline_types() { * @hook cloudinary_plugin_asset_cache_inline_types * @default array() * - * @param $inline_types {array} The types of files to be encoded inline. + * @param array $inline_types The types of files to be encoded inline. * - * @return {array} + * @return array */ return apply_filters( 'cloudinary_plugin_asset_cache_inline_types', $inline_types ); } @@ -577,9 +577,9 @@ protected function get_filetype_filters() { * @hook cloudinary_plugin_asset_cache_filters * @default array() * - * @param $default_filters {array} The types of files to be filtered. + * @param array $default_filters The types of files to be filtered. * - * @return {array} + * @return array */ return apply_filters( 'cloudinary_plugin_asset_cache_filters', $default_filters ); } diff --git a/php/class-delivery-feature.php b/php/class-delivery-feature.php index 3f2b8468d..3af79ff73 100644 --- a/php/class-delivery-feature.php +++ b/php/class-delivery-feature.php @@ -203,7 +203,7 @@ public function filter_is_active() { * @hook cloudinary_is_{$class_name}_active * @since 3.0.4 * - * @param $is_active {bool} Flag if active. + * @param bool $is_active Flag if active. */ return apply_filters( "cloudinary_is_{$class_name}_active", $is_active ); } diff --git a/php/class-delivery.php b/php/class-delivery.php index ec0c577d6..9d01c0e6b 100644 --- a/php/class-delivery.php +++ b/php/class-delivery.php @@ -411,10 +411,10 @@ public function is_deliverable( $attachment_id ) { * * @hook cloudinary_is_deliverable * - * @param $is {bool} The default value. - * @param $attachment_id {int} The attachment ID. + * @param bool $is The default value. + * @param int $attachment_id The attachment ID. * - * @return {bool} + * @return bool */ return apply_filters( 'cloudinary_is_deliverable', $is, $attachment_id ); } @@ -706,7 +706,7 @@ protected function setup_hooks() { add_filter( 'cloudinary_current_post_id', array( $this, 'get_current_post_id' ) ); add_filter( 'the_content', array( $this, 'add_post_id' ) ); - add_action( 'wp_resource_hints', array( $this, 'dns_prefetch' ), 10, 2 ); + add_filter( 'wp_resource_hints', array( $this, 'dns_prefetch' ), 10, 2 ); $metadata = Utils::METADATA; @@ -741,9 +741,9 @@ public function dns_prefetch( $urls, $relation_type ) { * @since 3.2.12 * @default array ( 'dns-prefetch', 'preconnect' ) * - * @param $types {array} The types of resource hints to use. + * @param array $types The types of resource hints to use. * - * @return {array} The modified resource hints to use. + * @return array The modified resource hints to use. */ $resource_hints = apply_filters( 'cloudinary_dns_prefetch_types', array( 'dns-prefetch', 'preconnect' ) ); @@ -845,7 +845,7 @@ protected function init_delivery() { * @hook cloudinary_init_delivery * @since 2.7.5 * - * @param $delivery {Delivery} The delivery object. + * @param Delivery $delivery The delivery object. */ do_action( 'cloudinary_init_delivery', $this ); } @@ -936,9 +936,9 @@ public function find_attachment_size_urls() { * @hook cloudinary_contextualized_post_id * @since 3.2.0 * - * @param $post_id {int} The post ID. + * @param int $post_id The post ID. * - * @return {int} + * @return int */ $post_id = apply_filters( 'cloudinary_contextualized_post_id', $result->post_id ); @@ -1079,10 +1079,10 @@ function ( $tag ) use ( $content ) { * @hook cloudinary_delivery_get_id * @since 2.7.6 * - * @param $attachment_id {int} The attachment ID. - * @param $tag_element {array} The tag element. + * @param int $attachment_id The attachment ID. + * @param array $tag_element The tag element. * - * @return {int|false} + * @return int|false */ $set['id'] = apply_filters( 'cloudinary_delivery_get_id', $set['id'], $set ); if ( empty( $set['id'] ) ) { @@ -1218,8 +1218,8 @@ protected function standardize_tag( $tag_element ) { * @since 3.2.4 * @default {false} * - * @param $skip {bool} True to unset attributes. - * @param $tag_element {array} The tag element. + * @param bool $skip True to unset attributes. + * @param array $tag_element The tag element. * * @retun {bool} */ @@ -1316,8 +1316,8 @@ protected function standardize_tag( $tag_element ) { * @since 3.2.4 * @default {false} * - * @param $unset {bool} True to unset attributes. - * @param $tag_element {array} The tag element. + * @param bool $unset True to unset attributes. + * @param array $tag_element The tag element. * * @retun {bool} */ @@ -1328,7 +1328,6 @@ protected function standardize_tag( $tag_element ) { $tag_element['atts']['width'], $tag_element['atts']['height'], $tag_element['atts']['data-crop'], - $tag_element['atts']['srcset'], $tag_element['atts']['data-responsive'] ); @@ -1366,9 +1365,9 @@ protected function standardize_tag( $tag_element ) { * @hook cloudinary_edit_asset_permalink * @since 3.2.0 * - * @param $permalink {string} The permalink. + * @param string $permalink The permalink. * - * @return {string} + * @return string */ $permalink = apply_filters( 'cloudinary_edit_asset_permalink', add_query_arg( 'asset', $tag_element['id'], $base_url ) ); @@ -1383,9 +1382,9 @@ protected function standardize_tag( $tag_element ) { * @hook cloudinary_bypass_seo_url * @since 3.1.5 * - * @param $bypass_seo_url {bool} Whether to bypass SEO URLs. + * @param bool $bypass_seo_url Whether to bypass SEO URLs. * - * @return {bool} + * @return bool */ $bypass_seo_url = apply_filters( 'cloudinary_bypass_seo_url', false ); @@ -1421,9 +1420,9 @@ public function rebuild_tag( $tag_element ) { * @since 3.0.0 * @default {true} * - * @param $apply {bool} True to apply, false to skip. + * @param bool $apply True to apply, false to skip. * - * @return {bool} + * @return bool */ if ( apply_filters( 'cloudinary_apply_breakpoints', true ) ) { $meta = wp_get_attachment_metadata( $tag_element['id'] ); @@ -1452,9 +1451,9 @@ public function rebuild_tag( $tag_element ) { * @hook cloudinary_pre_image_tag | cloudinary_pre_video_tag * @since 2.7.5 * - * @param $tag_element {array} The tag_element (tag + attributes array). + * @param array $tag_element The tag_element (tag + attributes array). * - * @return {array} + * @return array */ $tag_element = apply_filters( "cloudinary_pre_{$tag_element['type']}_tag", $tag_element ); @@ -1473,10 +1472,10 @@ public function rebuild_tag( $tag_element ) { * @hook cloudinary_image_tag | cloudinary_video_tag * @since 3.0.0 * - * @param $replace {string} The new HTML tag. - * @param $tag_element {array} The tag_element (tag + attributes array). + * @param string $replace The new HTML tag. + * @param array $tag_element The tag_element (tag + attributes array). * - * @return {array} + * @return array */ return apply_filters( "cloudinary_{$tag_element['type']}_tag", $replace, $tag_element ); } @@ -1497,10 +1496,10 @@ public function parse_element( $element, $content = '' ) { * @since 3.2.6 * @default {false} * - * @param $skip {bool} True to skip parsing. - * @param $element {string} The element to parse. + * @param bool $skip True to skip parsing. + * @param string $element The element to parse. * - * @return {bool} + * @return bool */ if ( apply_filters( 'cloudinary_skip_parse_element', false, $element ) ) { return null; @@ -1517,7 +1516,7 @@ public function parse_element( $element, $content = '' ) { * @since 3.1.3 * @default {false} * - * @param $enabeld {bool} Is the Crop and Gravity control enabled? + * @param bool $enabeld Is the Crop and Gravity control enabled? * * @retrun {bool} */ @@ -1693,9 +1692,9 @@ public function parse_element( $element, $content = '' ) { * @hook cloudinary_parse_element * @since 3.0.9 * - * @param $tag_element {array} The tag element. + * @param array $tag_element The tag element. * - * @return {array} The tag element. + * @return array The tag element. */ $tag_element = apply_filters( 'cloudinary_parse_element', $tag_element ); @@ -1756,10 +1755,10 @@ protected function is_content_dir( $url ) { * @hook cloudinary_is_content_dir * @since 2.7.6 * - * @param $is_local {bool} If the url is a local asset. - * @param $url {string} The url. + * @param bool $is_local If the url is a local asset. + * @param string $url The url. * - * @return {bool} + * @return bool */ return apply_filters( 'cloudinary_is_content_dir', $is_local, $url ); } @@ -1788,9 +1787,9 @@ protected function is_allowed_type( $ext ) { * @hook cloudinary_allowed_extensions * @since 3.0.0 * - * @param $allowed_types {array} Array of allowed file extensions. + * @param array $allowed_types Array of allowed file extensions. * - * @return {array} + * @return array */ $allowed_types = apply_filters( 'cloudinary_allowed_extensions', $allowed_types ); } @@ -1839,9 +1838,9 @@ protected function set_usability( $item, $auto_sync = null ) { * @hook cloudinary_set_usable_asset * @since 3.0.2 * - * @param $item {array} The found asset array. + * @param object $item The found asset object. * - * @return {array} + * @return object */ $item = apply_filters( 'cloudinary_set_usable_asset', $item ); @@ -1851,9 +1850,9 @@ protected function set_usability( $item, $auto_sync = null ) { * @hook cloudinary_content_url * @since 3.1.6 * - * @param $url {string} The default content_url. + * @param string $url The default content_url. * - * @return {string} + * @return string */ $content_url = apply_filters( 'cloudinary_content_url', content_url() ); @@ -1870,11 +1869,11 @@ protected function set_usability( $item, $auto_sync = null ) { * @hook cloudinary_delivery_searchable_url * @since 3.1.6 * - * @param $url {string} The URL to be searched for and prepared to be delivered by Cloudinary. - * @param $item {array} The found asset array. - * @param $content_url {string} The content URL. + * @param string $url The URL to be searched for and prepared to be delivered by Cloudinary. + * @param object $item The found asset object. + * @param string $content_url The content URL. * - * @return {string} + * @return string */ $url = apply_filters( 'cloudinary_delivery_searchable_url', $url, $item, $content_url ); diff --git a/php/class-extensions.php b/php/class-extensions.php index 488f27ccc..ed5a9c2c6 100644 --- a/php/class-extensions.php +++ b/php/class-extensions.php @@ -174,8 +174,8 @@ public function register_extensions() { * @hook cloudinary_register_extensions * @since 3.0.0 * - * @param $extensions {array) The list of extensions to register. - * @param $plugin {Plugin} The core plugin object. + * @param array $extensions The list of extensions to register. + * @param Plugin $plugin The core plugin object. */ $extensions = apply_filters( 'cloudinary_register_extensions', $extensions, $this->plugin ); foreach ( $extensions as $slug => $extension ) { diff --git a/php/class-media.php b/php/class-media.php index 2bd521279..e9eb695bd 100644 --- a/php/class-media.php +++ b/php/class-media.php @@ -177,13 +177,13 @@ public function init_hook() { * @hook cloudinary_media_filters * @since 3.0.0 * - * @param $filters {array} The default filters. + * @param array $filters The default filters. */ $this->cloudinary_filters = apply_filters( 'cloudinary_media_filters', array( - SYNC::META_KEYS['sync_error'] => __( 'Error', 'cloudinary' ), - SYNC::META_KEYS['unsynced'] => __( 'Unsynced', 'cloudinary' ), + Sync::META_KEYS['sync_error'] => __( 'Error', 'cloudinary' ), + Sync::META_KEYS['unsynced'] => __( 'Unsynced', 'cloudinary' ), ) ); } @@ -323,10 +323,10 @@ public function is_media( $attachment_id ) { * @since 2.7.6 * @default false * - * @param $is_media {bool} Flag if is media. - * @param $attachment_id {int} The attachment ID. + * @param bool $is_media Flag if is media. + * @param int $attachment_id The attachment ID. * - * @return {bool} + * @return bool */ return apply_filters( 'cloudinary_is_media', $is_media, $attachment_id ); } @@ -423,10 +423,10 @@ public function is_uploadable_media( $attachment_id ) { * @hook cloudinary_is_uploadable_media * @since 2.7.7 * - * @param $is_local {bool} The attachment ID. - * @param $media_host {string} The html tag. + * @param bool $is_local The attachment ID. + * @param string $media_host The html tag. * - * @return {bool} + * @return bool */ return apply_filters( 'cloudinary_is_uploadable_media', $is_uploadable, $media_host ); } @@ -1018,7 +1018,7 @@ public function get_crop_transformations( $attachment_id, $size ) { * @since 3.1.3 * @default {false} * - * @param $enabeld {bool} Is the Crop and Gravity control enabled? + * @param bool $enabeld Is the Crop and Gravity control enabled? * * @retrun {bool} */ @@ -1436,7 +1436,7 @@ public function cloudinary_url( $attachment_id, $size = array(), $transformation // Early bail for admin AJAX requests. - if ( defined( 'DOING_AJAX' ) && DOING_AJAX && is_admin() ) { + if ( wp_doing_ajax() && is_admin() ) { $cache[ $key ] = $url; return $cache[ $key ]; @@ -1475,10 +1475,10 @@ public function local_url( $attachment_id ) { * @hook cloudinary_local_url * @since 3.0.0 * - * @param $url {string|false} The local URL - * @param $attachment_id {int} The attachment ID. + * @param string|false $url The local URL + * @param int $attachment_id The attachment ID. * - * @return {string|false} + * @return string|false */ return apply_filters( 'cloudinary_local_url', $urls[ $attachment_id ], $attachment_id ); } @@ -1530,10 +1530,10 @@ public function raw_cloudinary_url( $attachment_id ) { * @hook cloudinary_raw_url * @since 3.0.0 * - * @param $url {string|false} The local URL - * @param $attachment_id {int} The attachment ID. + * @param string|false $url The local URL + * @param int $attachment_id The attachment ID. * - * @return {string|false} + * @return string|false */ return apply_filters( 'cloudinary_raw_url', $url, $attachment_id ); } @@ -2036,11 +2036,11 @@ public function editor_assets() { * @hook cloudinary_max_files_import * @since 3.1.3 * - * @param $max_files {int} The maximum number of files that can be imported from Cloudinary. + * @param int $max_files The maximum number of files that can be imported from Cloudinary. * * @default 20 * - * @return {int} + * @return int * * @example * is_main_query() ) { $request = Utils::get_sanitized_text( 'cloudinary-filter' ); - if ( SYNC::META_KEYS['sync_error'] === $request ) { + if ( Sync::META_KEYS['sync_error'] === $request ) { $meta_query = $query->get( 'meta_query' ); if ( ! is_array( $meta_query ) ) { $meta_query = array(); @@ -3082,7 +3082,7 @@ public function apply_media_library_filters( $query ) { $query->set( 'meta_query', $meta_query ); } - if ( SYNC::META_KEYS['unsynced'] === $request ) { + if ( Sync::META_KEYS['unsynced'] === $request ) { global $wpdb; $wpdb->cld_table = Utils::get_relationship_table(); $result = $wpdb->get_col( "SELECT post_id FROM $wpdb->cld_table WHERE public_id IS NULL" ); // phpcs:ignore WordPress.DB.DirectDatabaseQuery.DirectQuery,WordPress.DB.DirectDatabaseQuery.NoCaching diff --git a/php/class-plugin.php b/php/class-plugin.php index 8fc848758..d734e1251 100644 --- a/php/class-plugin.php +++ b/php/class-plugin.php @@ -212,7 +212,7 @@ public function setup_settings() { * @hook cloudinary_connected * @since 3.0.0 * - * @param $plugin {Plugin} The core plugin object. + * @param Plugin $plugin The core plugin object. */ do_action( 'cloudinary_connected', $this ); } @@ -222,7 +222,7 @@ public function setup_settings() { * @hook cloudinary_init_settings * @since 2.7.5 * - * @param $plugin {Plugin} The core plugin object. + * @param Plugin $plugin The core plugin object. */ do_action( 'cloudinary_init_settings', $this ); @@ -464,7 +464,7 @@ public function setup() { * @hook cloudinary_ready * @since 3.0.0 * - * @param $plugin {Plugin} The core plugin object. + * @param Plugin $plugin The core plugin object. */ do_action( 'cloudinary_ready', $this ); } diff --git a/php/class-settings.php b/php/class-settings.php index 9948400a1..eee38f218 100644 --- a/php/class-settings.php +++ b/php/class-settings.php @@ -366,8 +366,8 @@ public function get_value( ...$slugs ) { * * @hook cloudinary_setting_get_value * - * @param $value {mixed} The setting value. - * @param $slug {string} The setting slug. + * @param mixed $value The setting value. + * @param string $slug The setting slug. */ $return[ $slug ] = apply_filters( 'cloudinary_setting_get_value', $value, $slug ); } @@ -530,11 +530,11 @@ public function set_pending( $slug, $new_value, $current_value = null ) { * @hook cloudinary_settings_save_setting * @since 2.7.6 * - * @param $new_value {int} The new setting value. - * @param $current_value {string} The setting current value. - * @param $setting {Setting} The setting object. + * @param int $new_value The new setting value. + * @param string $current_value The setting current value. + * @param Setting $setting The setting object. * - * @return {mixed} + * @return mixed */ $new_value = apply_filters( "cloudinary_settings_save_setting_{$slug}", $new_value, $current_value, $setting ); $new_value = apply_filters( 'cloudinary_settings_save_setting', $new_value, $current_value, $setting ); diff --git a/php/class-string-replace.php b/php/class-string-replace.php index 5b099d628..0e8667dfe 100644 --- a/php/class-string-replace.php +++ b/php/class-string-replace.php @@ -81,7 +81,7 @@ protected function admin_filters() { * Add Public Filters. */ protected function public_filters() { - add_action( 'template_include', array( $this, 'init_debug' ), PHP_INT_MAX ); + add_filter( 'template_include', array( $this, 'init_debug' ), PHP_INT_MAX ); if ( ! defined( 'REST_REQUEST' ) || ! REST_REQUEST ) { // Not needed on REST API. add_action( 'parse_request', array( $this, 'init' ), - 1000 ); // Not crazy low, but low enough to catch most cases, but not too low that it may break AMP. } @@ -275,8 +275,8 @@ protected function prime_replacements( $content, $context = 'view' ) { * @hook cloudinary_string_replace * @since 3.0.3 Added the `$context` argument. * - * @param $content {string} The html of the page. - * @param $context {string} The render context. + * @param string $content The html of the page. + * @param string $context The render context. */ do_action( 'cloudinary_string_replace', $content, $context ); } diff --git a/php/class-svg.php b/php/class-svg.php index acb912ade..415f382a4 100644 --- a/php/class-svg.php +++ b/php/class-svg.php @@ -245,7 +245,7 @@ public function setup_hooks() { // Add filters. add_filter( 'upload_mimes', array( $this, 'add_svg_mime' ) ); // phpcs:ignore WordPressVIPMinimum.Hooks.RestrictedHooks.upload_mimes add_filter( 'ext2type', array( $this, 'add_svg_ext_type' ) ); - add_filter( 'wp_check_filetype_and_ext', array( $this, 'check_svg_type' ), 10, 4 ); + add_filter( 'wp_check_filetype_and_ext', array( $this, 'check_svg_type' ), 10, 3 ); add_filter( 'cloudinary_allowed_extensions', array( $this, 'allow_svg_for_cloudinary' ) ); add_filter( 'cloudinary_upload_options', array( $this, 'remove_svg_eagers' ), 10, 2 ); add_filter( 'cloudinary_upload_args', array( $this, 'upload_args' ), 10, 2 ); diff --git a/php/class-sync.php b/php/class-sync.php index b5e3522fd..fbf39a698 100644 --- a/php/class-sync.php +++ b/php/class-sync.php @@ -332,7 +332,9 @@ public function can_sync( $attachment_id, $type = 'file' ) { * Filter to allow changing if an asset is allowed to be synced. * Return a WP Error with reason why it can't be synced. * - * @param int $attachment_id The attachment post ID. + * @param bool|\WP_Error $can Whether the asset can be synced. + * @param int $attachment_id The attachment post ID. + * @param string $type The sync type. * * @return bool|\WP_Error */ @@ -386,10 +388,10 @@ public function get_signature( $attachment_id, $cached = true ) { * * @hook cloudinary_get_signature * - * @param $return {array} The attachment signature. - * @param $attachment_id {int} The attachment ID. + * @param array $return The attachment signature. + * @param int $attachment_id The attachment ID. * - * @return {array} + * @return array */ $return = apply_filters( 'cloudinary_get_signature', $return, $attachment_id ); @@ -674,7 +676,7 @@ public function setup_sync_base_struct() { /** * Do action for setting up sync types. * - * @param \Cloudinary\Sync $this The sync object. + * @param \Cloudinary\Sync $sync The sync object. */ do_action( 'cloudinary_register_sync_types', $this ); } @@ -772,10 +774,10 @@ public function get_asset_state( $attachment_id ) { * * @hook cloudinary_asset_state * - * @param $state {int} The attachment state. - * @param $attachment_id {int} The attachment ID. + * @param int $state The attachment state. + * @param int $attachment_id The attachment ID. * - * @return {array} + * @return array */ return apply_filters( 'cloudinary_asset_state', $state, $attachment_id ); } @@ -806,11 +808,11 @@ public function sync_base( $attachment_id ) { * * @hook cloudinary_sync_base * - * @param $signatures {array} The attachments required signatures. - * @param $post {WP_Post} The attachment post. - * @param $sync {Sync} The sync object instance. + * @param array $signatures The attachments required signatures. + * @param WP_Post $post The attachment post. + * @param Sync $sync The sync object instance. * - * @return {array} + * @return array */ $return = apply_filters( 'cloudinary_sync_base', $return, get_post( $attachment_id ), $this ); @@ -1220,7 +1222,7 @@ public function setup() { add_filter( 'cloudinary_setting_get_value', array( $this, 'filter_get_cloudinary_folder' ), 10, 2 ); add_filter( 'cloudinary_get_signature', array( $this, 'get_signature_syncable_type' ), 10, 2 ); - add_action( 'admin_init', array( $this, 'maybe_cleanup_errored' ), 10, 2 ); + add_action( 'admin_init', array( $this, 'maybe_cleanup_errored' ) ); add_action( 'rest_api_init', array( $this, 'rest_api_is_synced_field' ) ); } diff --git a/php/class-utils.php b/php/class-utils.php index d733479a8..293552f61 100644 --- a/php/class-utils.php +++ b/php/class-utils.php @@ -217,12 +217,12 @@ public static function user_can( $task, $capability = 'manage_options', $context * 2 * ); * - * @param $capability {string} The capability. - * @param $context {string} The context for the task. - * @param $args {mixed} The optional arguments. + * @param string $capability The capability. + * @param string $context The context for the task. + * @param mixed $args The optional arguments. * * @default 'manage_options' - * @return {string} + * @return string */ $capability = apply_filters( "cloudinary_task_capability_{$task}", $capability, $context, ...$args ); @@ -248,12 +248,12 @@ public static function user_can( $task, $capability = 'manage_options', $context * 3 * ); * - * @param $capability {string} The current capability for the task. - * @param $task {string} The task. - * @param $context {string} The context for the task. - * @param $args {mixed} The optional arguments. + * @param string $capability The current capability for the task. + * @param string $task The task. + * @param string $context The context for the task. + * @param mixed $args The optional arguments. * - * @return {string} + * @return string */ $capability = apply_filters( 'cloudinary_task_capability', $capability, $task, $context, ...$args ); // phpcs:enable WordPress.WhiteSpace.DisallowInlineTabs.NonIndentTabsUsed @@ -400,9 +400,9 @@ protected static function get_upgrade_sequence() { * @hook cloudinary_upgrade_sequence * @since 3.0.1 * - * @param $upgrade_sequence {array} The default sequence. + * @param array $upgrade_sequence The default sequence. * - * @return {array} + * @return array */ return apply_filters( 'cloudinary_upgrade_sequence', $upgrade_sequence ); } @@ -634,7 +634,7 @@ public static function is_frontend_ajax() { $admin_base = admin_url(); $is_admin = $referer ? 0 === strpos( $referer, $admin_base ) : false; // Check if this is a frontend ajax request. - $is_frontend_ajax = ! $is_admin && defined( 'DOING_AJAX' ) && DOING_AJAX; + $is_frontend_ajax = ! $is_admin && wp_doing_ajax(); // If it's not an obvious WP ajax request, check if it's a custom frontend ajax request. if ( ! $is_frontend_ajax && ! $is_admin ) { // Catch the content type of the $_SERVER['CONTENT_TYPE'] variable. @@ -883,9 +883,9 @@ public static function maybe_get_third_party_changes( $attributes, $tag ) { * @hook cloudinary_ignored_data_keywords * @since 3.0.8 * - * @param $lazy_keys {array} The built-in ignore data-* keywords. + * @param array $lazy_keys The built-in ignore data-* keywords. * - * @return {array} + * @return array */ $filtered_keys = apply_filters( 'cloudinary_ignored_data_keywords', $lazy_keys ); @@ -895,9 +895,9 @@ public static function maybe_get_third_party_changes( $attributes, $tag ) { * @hook cloudinary_ignored_class_keywords * @since 3.0.8 * - * @param $lazy_classes {array} The built-in ignore class keywords. + * @param array $lazy_classes The built-in ignore class keywords. * - * @return {array} + * @return array */ $filtered_classes = apply_filters( 'cloudinary_ignored_class_keywords', $lazy_classes ); } @@ -1083,8 +1083,8 @@ public static function query_relations( $public_ids, $urls = array() ) { * * @hook cloudinary_media_context_query * @since 3.2.0 - * @param $media_context_query {string} The default media context query. - * @return {string} + * @param string $media_context_query The default media context query. + * @return string */ $media_context_query = apply_filters( 'cloudinary_media_context_query', 'media_context = %s' ); @@ -1243,10 +1243,10 @@ public static function get_media_context( $attachment_id = null ) { * @since 3.1.9 * @default {'default'} * - * @param $media_context {string} The media context. - * @param $attachment_id {int|null} The attachment ID. + * @param string $media_context The media context. + * @param int|null $attachment_id The attachment ID. * - * @return {string} + * @return string */ $context = apply_filters( 'cloudinary_media_context', 'default', $attachment_id ); @@ -1267,8 +1267,8 @@ public static function get_media_context_things( $media_context_things = array( * * @hook cloudinary_media_context_things * @since 3.2.0 - * @param $media_context_things {array} The default media context things. - * @return {array} + * @param array $media_context_things The default media context things. + * @return array */ $media_context_things = apply_filters( 'cloudinary_media_context_things', $media_context_things ); @@ -1296,11 +1296,11 @@ public static function home_url( $path = '', $scheme = null ) { * @hook cloudinary_home_url * @since 3.2.0 * - * @param $home_url {string} The home url. - * @param $path {string} The path to be appended to the home URL. - * @param $scheme {string} The scheme to give the home URL context. Accepts 'http', 'https', or 'relative'. + * @param string $home_url The home url. + * @param string $path The path to be appended to the home URL. + * @param string $scheme The scheme to give the home URL context. Accepts 'http', 'https', or 'relative'. * - * @return {string} + * @return string */ return apply_filters( 'cloudinary_home_url', $home_url, $path, $scheme ); } @@ -1326,11 +1326,11 @@ public static function site_url( $path = '', $scheme = null ) { * @hook cloudinary_site_url * @since 3.2.2 * - * @param $site_url {string} The site URL. - * @param $path {string} The path to be appended to the site URL. - * @param $scheme {string} The scheme to give the site URL context. Accepts 'http', 'https', or 'relative'. + * @param string $site_url The site URL. + * @param string $path The path to be appended to the site URL. + * @param string $scheme The scheme to give the site URL context. Accepts 'http', 'https', or 'relative'. * - * @return {string} + * @return string */ return apply_filters( 'cloudinary_site_url', $site_url, $path, $scheme ); } @@ -1352,11 +1352,11 @@ public static function rest_url( $path = '', $scheme = null ) { * @hook cloudinary_rest_url * @since 3.2.2 * - * @param $rest_url {string} The rest url. - * @param $path {string} The path to be appended to the rest URL. - * @param $scheme {string} The scheme to give the rest URL context. Accepts 'http', 'https', or 'relative'. + * @param string $rest_url The rest url. + * @param string $path The path to be appended to the rest URL. + * @param string $scheme The scheme to give the rest URL context. Accepts 'http', 'https', or 'relative'. * - * @return {string} + * @return string */ return apply_filters( 'cloudinary_rest_url', $rest_url, $path, $scheme ); } @@ -1593,9 +1593,9 @@ public static function sanitize_svg( $svg_content ) { * @hook cloudinary_allowed_svg_tags * @since 3.2.15 * - * @param $allowed_tags {array} The allowed SVG tags and their attributes. + * @param array $allowed_tags The allowed SVG tags and their attributes. * - * @return {array} + * @return array */ $allowed_tags = apply_filters( 'cloudinary_allowed_svg_tags', $allowed_tags ); diff --git a/php/connect/class-api.php b/php/connect/class-api.php index f50701b99..dc5939270 100644 --- a/php/connect/class-api.php +++ b/php/connect/class-api.php @@ -209,9 +209,9 @@ public function url( $resource, $function = null, $endpoint = false ) { // phpcs * @hook cloudinary_bypass_seo_url * @since 3.1.5 * - * @param $bypass_seo_url {bool} Whether to bypass SEO URLs. + * @param bool $bypass_seo_url Whether to bypass SEO URLs. * - * @return {bool} + * @return bool */ $bypass_seo_url = apply_filters( 'cloudinary_bypass_seo_url', false ); @@ -294,10 +294,10 @@ function ( $item ) use ( $transformation_index ) { * @hook cloudinary_upload_eager_formats * @since 3.1.6 * - * @param $formats {array} The default formats. - * @param $type {string} The asset type. + * @param array $formats The default formats. + * @param string $type The asset type. * - * @return {array} + * @return array */ $formats = apply_filters( 'cloudinary_upload_eager_formats', $formats, $type ); @@ -517,10 +517,10 @@ public function upload( $attachment_id, $args, $headers = array(), $try_remote = * @since 3.1.8 * @default true * - * @param $use_original {bool} The default value. - * @param $attachment_id {int} The attachment ID. + * @param bool $use_original The default value. + * @param int $attachment_id The attachment ID. * - * @return {bool} + * @return bool */ $use_original = apply_filters( 'cloudinary_use_original_image', true, $attachment_id ); if ( $use_original && function_exists( 'wp_get_original_image_url' ) && wp_attachment_is_image( $attachment_id ) ) { @@ -598,8 +598,8 @@ public function upload( $attachment_id, $args, $headers = array(), $try_remote = * @hook cloudinary_upload_args * @since 3.0.1 * - * @param $call_args {array} The default args. - * @param $attachment_id {int} The attachment ID. + * @param array $call_args The default args. + * @param int $attachment_id The attachment ID. */ $call_args = apply_filters( 'cloudinary_upload_args', $call_args, $attachment_id ); @@ -632,8 +632,8 @@ public function upload( $attachment_id, $args, $headers = array(), $try_remote = * @hook cloudinary_uploaded_asset * @since 3.0.1 * - * @param $attachment_id {int} The attachment ID. - * @param $result {array|WP_Error} The upload result. + * @param int $attachment_id The attachment ID. + * @param array|WP_Error $result The upload result. */ do_action( 'cloudinary_uploaded_asset', $attachment_id, $result ); @@ -897,9 +897,9 @@ public function get_public_id( $attachment_id, $args = array(), $original_public * @hook cloudinary_bypass_seo_url * @since 3.1.5 * - * @param $bypass_seo_url {bool} Whether to bypass SEO URLs. + * @param bool $bypass_seo_url Whether to bypass SEO URLs. * - * @return {bool} + * @return bool */ $bypass_seo_url = apply_filters( 'cloudinary_bypass_seo_url', false ); @@ -929,11 +929,11 @@ public function get_public_id( $attachment_id, $args = array(), $original_public * @hook cloudinary_seo_public_id * @since 3.1.5 * - * @param $sufix {string} The public_id suffix. - * @param $relationship {Relationship} The relationship. - * @param $attachment_id {int} The attachment ID. + * @param string $sufix The public_id suffix. + * @param Relationship $relationship The relationship. + * @param int $attachment_id The attachment ID. * - * @return {string} + * @return string */ $suffix = apply_filters( 'cloudinary_seo_public_id', "{$filename}.{$relationship->format}", $relationship, $attachment_id ); diff --git a/php/delivery/class-lazy-load.php b/php/delivery/class-lazy-load.php index e50225ce3..ed52219e4 100644 --- a/php/delivery/class-lazy-load.php +++ b/php/delivery/class-lazy-load.php @@ -94,9 +94,9 @@ public function bypass_lazy_load( $bypass, $tag_element ) { * @hook cloudinary_lazy_load_bypass_classes * @since 3.0.9 * - * @param $classes {array} Classes that bypass the Lazy Load. + * @param array $classes Classes that bypass the Lazy Load. * - * @return {bool} + * @return bool * * @example * is_enabled() || Utils::is_amp() || apply_filters( 'cloudinary_lazy_load_bypass', false, $tag_element ) ) { $tag_element = $this->apply_breakpoints( $tag_element ); diff --git a/php/media/class-global-transformations.php b/php/media/class-global-transformations.php index aaaf64158..75f93534c 100644 --- a/php/media/class-global-transformations.php +++ b/php/media/class-global-transformations.php @@ -596,7 +596,7 @@ public function get_current_post() { * @hook cloudinary_current_post_id * @default null * - * @return {WP_Post|null} + * @return WP_Post|null */ $post_id = apply_filters( 'cloudinary_current_post_id', null ); @@ -717,7 +717,7 @@ function ( $taxonomy ) use ( $global ) { // Add ordering metaboxes and featured overwrite. add_action( 'add_meta_boxes', array( $this, 'taxonomy_ordering' ), 10, 2 ); add_action( 'save_post', array( $this, 'save_taxonomy_ordering' ), 10, 1 ); - add_action( 'save_post', array( $this, 'save_overwrite_transformations_featured_image' ), 10, 3 ); + add_action( 'save_post', array( $this, 'save_overwrite_transformations_featured_image' ), 10, 1 ); add_filter( 'admin_post_thumbnail_html', array( $this, 'classic_overwrite_transformations_featured_image' ), 10, 3 ); // Filter and action the custom column. diff --git a/php/media/class-upgrade.php b/php/media/class-upgrade.php index 6b2a86479..2db0b1015 100644 --- a/php/media/class-upgrade.php +++ b/php/media/class-upgrade.php @@ -64,8 +64,8 @@ public function convert_cloudinary_version( $attachment_id ) { * @hook cloudinary_upgrade_asset * @since 3.0.5 * - * @param $attachment_id {int} The attachment ID. - * @param $version {string} The current plugin version. + * @param int $attachment_id The attachment ID. + * @param string $version The current plugin version. */ do_action( 'cloudinary_upgrade_asset', $attachment_id, $this->media->plugin->version ); @@ -201,9 +201,18 @@ public function get_fetch_public_id( $path, $attachment_id ) { */ public function migrate_legacy_meta( $attachment_id ) { + /** + * The raw attachment metadata, which may contain plugin-specific keys + * beyond WordPress core's documented shape. + * + * @var array $old_meta + */ $old_meta = wp_get_attachment_metadata( $attachment_id, true ); - $v2_meta = get_post_meta( $attachment_id, Sync::META_KEYS['cloudinary_legacy'], true ); - $v3_meta = array(); + if ( ! is_array( $old_meta ) ) { + $old_meta = array(); + } + $v2_meta = get_post_meta( $attachment_id, Sync::META_KEYS['cloudinary_legacy'], true ); + $v3_meta = array(); // Direct from old meta to v3, create v2 to chain the upgrade path. if ( isset( $old_meta[ Sync::META_KEYS['cloudinary_legacy'] ] ) && empty( $v2_meta ) ) { diff --git a/php/media/class-video.php b/php/media/class-video.php index 01b01cb16..57ab0c2ef 100644 --- a/php/media/class-video.php +++ b/php/media/class-video.php @@ -694,7 +694,7 @@ static function ( $return, $tag, $attr, $m ) { // phpcs:ignore Universal.NamingC return $return; }, 10, - 5 + 4 ); } diff --git a/php/sync/class-sync-queue.php b/php/sync/class-sync-queue.php index 220b9b7c5..1725171a6 100644 --- a/php/sync/class-sync-queue.php +++ b/php/sync/class-sync-queue.php @@ -109,9 +109,9 @@ public function setup( $sync ) { * * @hook cloudinary_queue_threads * - * @param $count {int} The number of manual sync threads to use. + * @param int $count The number of manual sync threads to use. * - * @return {int} + * @return int */ $queue_threads_count = apply_filters( 'cloudinary_queue_threads', 2 ); for ( $i = 0; $i < $queue_threads_count; ++$i ) { @@ -123,9 +123,9 @@ public function setup( $sync ) { * * @hook cloudinary_autosync_threads * - * @param $count {int} The number of autosync threads to use. + * @param int $count The number of autosync threads to use. * - * @return {int} + * @return int */ $autosync_thread_count = apply_filters( 'cloudinary_autosync_threads', 2 ); for ( $i = 0; $i < $autosync_thread_count; ++$i ) { @@ -474,9 +474,9 @@ public function build_queue() { * @hook cloudinary_build_queue_query * @since 2.7.6 * - * @param $args {array} The arguments for the query. + * @param array $args The arguments for the query. * - * @return {array} + * @return array */ $args = apply_filters( 'cloudinary_build_queue_query', $args ); @@ -740,10 +740,10 @@ protected function get_thread_queue_details( $thread ) { * @hook cloudinary_thread_queue_details_query * @since 2.7.6 * - * @param $args {array} The arguments for the query. - * @param $thread {string} The thread name. + * @param array $args The arguments for the query. + * @param string $thread The thread name. * - * @return {array} + * @return array */ $args = apply_filters( 'cloudinary_thread_queue_details_query', $args, $thread ); diff --git a/php/sync/class-unsync.php b/php/sync/class-unsync.php index 3150b6c55..c903ae307 100644 --- a/php/sync/class-unsync.php +++ b/php/sync/class-unsync.php @@ -254,7 +254,7 @@ public function unsync_attachment( $attachment_id ) { * @hook cloudinary_unsync_asset * @since 3.0.0 * - * @param $attachment_id {int} The attachment ID. + * @param int $attachment_id The attachment ID. */ do_action( 'cloudinary_unsync_asset', $attachment_id ); } diff --git a/php/ui/class-component.php b/php/ui/class-component.php index fe8918db6..28514b39c 100644 --- a/php/ui/class-component.php +++ b/php/ui/class-component.php @@ -15,6 +15,10 @@ * Abstract Component. * * @package Cloudinary\UI + * + * @method array wrap( array $struct ) Filter the wrap part structure. + * @method array header( array $struct ) Filter the header part structure. + * @method array hr( array $struct ) Filter the hr part structure. */ abstract class Component { @@ -325,7 +329,7 @@ protected function is_enabled() { * * @param bool $echo Flag to echo output or return it. * - * @return string + * @return string|null */ public function render( $echo = false ) { // phpcs:ignore Universal.NamingConventions.NoReservedKeywordParameterNames.echoFound // Setup the component. @@ -353,6 +357,8 @@ public function render( $echo = false ) { // phpcs:ignore Universal.NamingConven return $return; } echo $return; // phpcs:ignore WordPress.Security.EscapeOutput + + return null; } /** diff --git a/php/ui/component/class-cache-status.php b/php/ui/component/class-cache-status.php index ba449b2da..317a0f6ff 100644 --- a/php/ui/component/class-cache-status.php +++ b/php/ui/component/class-cache-status.php @@ -16,7 +16,7 @@ * * @package Cloudinary\UI */ -class Cache_Status extends media_status { +class Cache_Status extends Media_Status { /** Holds the cache point instance. * diff --git a/php/ui/component/class-crops.php b/php/ui/component/class-crops.php index d3f2e2c41..80878a2c4 100644 --- a/php/ui/component/class-crops.php +++ b/php/ui/component/class-crops.php @@ -19,9 +19,9 @@ class Crops extends Select { /** - * Holds the demo file name. + * Holds the demo file names. * - * @var string + * @var array */ protected $demo_files = array( 'docs/addons/objectdetection/dirt-road-1851258_1280.jpg', @@ -124,9 +124,9 @@ protected function input( $struct ) { * @hook cloudinary_registered_sizes * @since 3.1.3 * - * @param $demo_files {array} array of demo files. + * @param array $demo_files array of demo files. * - * @return {array} + * @return array */ $examples = apply_filters( 'cloudinary_demo_crop_files', $this->demo_files ); diff --git a/phpcs.xml.dist b/phpcs.xml.dist index eb91779b3..21063c4c4 100644 --- a/phpcs.xml.dist +++ b/phpcs.xml.dist @@ -58,5 +58,7 @@ /js/ /node_modules/ /vendor/ + + /tests/phpstan/stubs/ *.js diff --git a/phpstan.neon.dist b/phpstan.neon.dist new file mode 100644 index 000000000..c4bf7ab4e --- /dev/null +++ b/phpstan.neon.dist @@ -0,0 +1,33 @@ +includes: + - vendor/szepeviktor/phpstan-wordpress/extension.neon + +parameters: + # Persist the result cache in a known project-relative path so CI can cache + # it between runs for faster analysis. + tmpDir: .phpstan-cache + # The HookCallbackRule "action callback should not return anything" check is + # too strict for dual-purpose methods that are both called directly (return + # value used) and registered on a real action (return value harmlessly + # discarded). Genuine filter-vs-action bugs are caught during review. The + # rule's argument-count checks (arguments.count) remain active. + ignoreErrors: + - + identifier: return.void + message: '#^Action callback returns .+ but should not return anything\.$#' + level: 0 + paths: + - php + - cloudinary.php + scanFiles: + - instance.php + - vendor/php-stubs/wp-cli-stubs/wp-cli-stubs.php + - vendor/php-stubs/wp-cli-stubs/wp-cli-commands-stubs.php + - vendor/php-stubs/woocommerce-stubs/woocommerce-stubs.php + - tests/phpstan/stubs/wpml.php + - tests/phpstan/stubs/wpcom-vip.php + excludePaths: + - build/* + - node_modules/* + - vendor/* + # Extends WPCOM_VIP_CLI_Command, only available on the WordPress VIP platform. + - php/class-cli-vip.php diff --git a/tests/phpstan/stubs/wpcom-vip.php b/tests/phpstan/stubs/wpcom-vip.php new file mode 100644 index 000000000..8e48f1962 --- /dev/null +++ b/tests/phpstan/stubs/wpcom-vip.php @@ -0,0 +1,17 @@ +