|
40 | 40 | * | wp-cli/server-command | Daniel Bachhuber | dev-main | available | 2.x-dev | |
41 | 41 | * +-----------------------+------------------+----------+-----------+----------------+ |
42 | 42 | * |
43 | | - * # Install the latest development version of the package. |
| 43 | + * # Install the latest stable version of the package. |
44 | 44 | * $ wp package install wp-cli/server-command |
45 | | - * Installing package wp-cli/server-command (dev-main) |
| 45 | + * Installing package wp-cli/server-command (^2.0) |
46 | 46 | * Updating /home/person/.wp-cli/packages/composer.json to require the package... |
47 | 47 | * Using Composer to install the package... |
48 | 48 | * --- |
@@ -204,10 +204,10 @@ public function browse( $_, $assoc_args ) { |
204 | 204 | * |
205 | 205 | * ## EXAMPLES |
206 | 206 | * |
207 | | - * # Install a package hosted at a git URL. |
| 207 | + * # Install the latest stable version of a package. |
208 | 208 | * $ wp package install runcommand/hook |
209 | 209 | * |
210 | | - * # Install the latest stable version. |
| 210 | + * # Install the latest stable version (explicitly specified). |
211 | 211 | * $ wp package install wp-cli/server-command:@stable |
212 | 212 | * |
213 | 213 | * # Install a package hosted at a GitLab.com URL. |
@@ -239,16 +239,21 @@ public function install( $args, $assoc_args ) { |
239 | 239 | } |
240 | 240 | if ( $this->is_git_repository( $package_name ) ) { |
241 | 241 | if ( '' === $version ) { |
| 242 | + $version = '@stable'; |
242 | 243 | if ( preg_match( '#^(?:https?://github\.com/|git@github\.com:)#i', $package_name ) ) { |
243 | 244 | $version = "dev-{$this->get_github_default_branch( $package_name, $insecure )}"; |
244 | 245 | } else { |
245 | | - $version = 'dev-master'; |
| 246 | + $version = '@stable'; |
246 | 247 | } |
247 | 248 | } |
248 | 249 | $git_package = $package_name; |
249 | 250 | $matches = []; |
250 | 251 | if ( preg_match( '#([^:\/]+\/[^\/]+)\.git#', $package_name, $matches ) ) { |
251 | | - $package_name = $this->check_git_package_name( $matches[1], $package_name, $version, $insecure ); |
| 252 | + $extracted_package_name = $matches[1]; |
| 253 | + if ( '@stable' === $version ) { |
| 254 | + $version = $this->resolve_stable_version( $extracted_package_name, $insecure ); |
| 255 | + } |
| 256 | + $package_name = $this->check_git_package_name( $extracted_package_name, $package_name, $version, $insecure ); |
252 | 257 | } else { |
253 | 258 | WP_CLI::error( "Couldn't parse package name from expected path '<name>/<package>'." ); |
254 | 259 | } |
@@ -320,12 +325,11 @@ public function install( $args, $assoc_args ) { |
320 | 325 | $git_package = $package; |
321 | 326 |
|
322 | 327 | if ( '' === $version ) { |
323 | | - $version = "dev-{$this->get_github_default_branch( $package_name, $insecure )}"; |
| 328 | + $version = '@stable'; |
324 | 329 | } |
325 | 330 |
|
326 | 331 | if ( '@stable' === $version ) { |
327 | | - $tag = $this->get_github_latest_release_tag( $package_name, $insecure ); |
328 | | - $version = $this->guess_version_constraint_from_tag( $tag ); |
| 332 | + $version = $this->resolve_stable_version( $package_name, $insecure ); |
329 | 333 | } |
330 | 334 | $package_name = $this->check_github_package_name( $package_name, $version, $insecure ); |
331 | 335 | } |
@@ -1502,26 +1506,45 @@ private function get_raw_git_version( $version ) { |
1502 | 1506 | return str_replace( [ '^', '~' ], '', $version ); |
1503 | 1507 | } |
1504 | 1508 |
|
| 1509 | + /** |
| 1510 | + * Resolves '@stable' version to an actual version constraint. |
| 1511 | + * |
| 1512 | + * @param string $package_name Name of the repository. |
| 1513 | + * @param bool $insecure Whether to retry downloads without certificate validation if TLS handshake fails. |
| 1514 | + * |
| 1515 | + * @return string Version constraint. |
| 1516 | + */ |
| 1517 | + private function resolve_stable_version( $package_name, $insecure ) { |
| 1518 | + $tag = $this->get_github_latest_release_tag( $package_name, $insecure ); |
| 1519 | + return $this->guess_version_constraint_from_tag( $tag ); |
| 1520 | + } |
| 1521 | + |
1505 | 1522 | /** |
1506 | 1523 | * Gets the release tag for the latest stable release of a GitHub repository. |
1507 | 1524 | * |
| 1525 | + * If there is no release, falls back to the default branch prefixed with 'dev-'. |
| 1526 | + * |
1508 | 1527 | * @param string $package_name Name of the repository. |
| 1528 | + * @param bool $insecure Whether to retry downloads without certificate validation if TLS handshake fails. |
1509 | 1529 | * |
1510 | | - * @return string Release tag. |
| 1530 | + * @return string Release tag or 'dev-{default_branch}' if no release exists. |
1511 | 1531 | */ |
1512 | 1532 | private function get_github_latest_release_tag( $package_name, $insecure ) { |
1513 | 1533 | $url = "https://api.github.com/repos/{$package_name}/releases/latest"; |
1514 | 1534 | $options = [ 'insecure' => $insecure ]; |
1515 | 1535 | $response = Utils\http_request( 'GET', $url, null, [], $options ); |
1516 | | - if ( 20 !== (int) substr( (string) $response->status_code, 0, 2 ) ) { |
1517 | | - WP_CLI::warning( 'Could not guess stable version from GitHub repository, falling back to master branch' ); |
1518 | | - return 'master'; |
1519 | | - } |
1520 | 1536 |
|
| 1537 | + // Check for successful response and valid JSON |
1521 | 1538 | $package_data = json_decode( $response->body ); |
1522 | | - if ( JSON_ERROR_NONE !== json_last_error() ) { |
1523 | | - WP_CLI::warning( 'Could not guess stable version from GitHub repository, falling back to master branch' ); |
1524 | | - return 'master'; |
| 1539 | + |
| 1540 | + if ( 20 !== (int) substr( (string) $response->status_code, 0, 2 ) |
| 1541 | + || JSON_ERROR_NONE !== json_last_error() |
| 1542 | + || null === $package_data |
| 1543 | + || ! isset( $package_data->tag_name ) ) { |
| 1544 | + |
| 1545 | + $default_branch = $this->get_github_default_branch( $package_name, $insecure ); |
| 1546 | + WP_CLI::warning( "Could not guess stable version from GitHub repository, falling back to {$default_branch} branch" ); |
| 1547 | + return "dev-{$default_branch}"; |
1525 | 1548 | } |
1526 | 1549 |
|
1527 | 1550 | $tag = $package_data->tag_name; |
|
0 commit comments