Skip to content

Commit

Permalink
Add packages/stub-generator (#36652)
Browse files Browse the repository at this point in the history
This is a tool for extracting specific stubs from a large codebase.
We'll use this to generate wpcom stubs for Phan.
  • Loading branch information
anomiex authored Apr 9, 2024
1 parent e6e928a commit 75e6e35
Show file tree
Hide file tree
Showing 50 changed files with 4,892 additions and 0 deletions.
17 changes: 17 additions & 0 deletions projects/packages/stub-generator/.gitattributes
Original file line number Diff line number Diff line change
@@ -0,0 +1,17 @@
# Files not needed to be distributed in the package.
.gitattributes export-ignore
.github/ export-ignore

# Files to include in the mirror repo, but excluded via gitignore
# Remember to end all directories with `/**` to properly tag every file.
# /src/js/example.min.js production-include

# Files to exclude from the mirror repo, but included in the monorepo.
# Remember to end all directories with `/**` to properly tag every file.
.gitignore production-exclude
changelog/** production-exclude
phpunit.xml.dist production-exclude
.phpcs.dir.xml production-exclude
.phpcs.dir.phpcompatibility.xml production-exclude
tests/** production-exclude
.phpcsignore production-exclude
2 changes: 2 additions & 0 deletions projects/packages/stub-generator/.gitignore
Original file line number Diff line number Diff line change
@@ -0,0 +1,2 @@
vendor/
node_modules/
17 changes: 17 additions & 0 deletions projects/packages/stub-generator/.phan/baseline.php
Original file line number Diff line number Diff line change
@@ -0,0 +1,17 @@
<?php
/**
* This is an automatically generated baseline for Phan issues.
* When Phan is invoked with --load-baseline=path/to/baseline.php,
* The pre-existing issues listed in this file won't be emitted.
*
* This file can be updated by invoking Phan with --save-baseline=path/to/baseline.php
* (can be combined with --load-baseline)
*/
return [
// This baseline has no suppressions
// Currently, file_suppressions and directory_suppressions are the only supported suppressions
'file_suppressions' => [
],
// 'directory_suppressions' => ['src/directory_name' => ['PhanIssueName1', 'PhanIssueName2']] can be manually added if needed.
// (directory_suppressions will currently be ignored by subsequent calls to --save-baseline, but may be preserved in future Phan releases)
];
19 changes: 19 additions & 0 deletions projects/packages/stub-generator/.phan/config.php
Original file line number Diff line number Diff line change
@@ -0,0 +1,19 @@
<?php
/**
* This configuration will be read and overlaid on top of the
* default configuration. Command-line arguments will be applied
* after this file is read.
*
* @package automattic/jetpack-stub-generator
*/

// Require base config.
require __DIR__ . '/../../../../.phan/config.base.php';

return make_phan_config(
dirname( __DIR__ ),
array(
'is_wordpress' => false,
'exclude_file_regex' => array( 'tests/php/fixtures/' ),
)
);
Original file line number Diff line number Diff line change
@@ -0,0 +1,5 @@
<?xml version="1.0"?>
<ruleset>
<rule ref="Jetpack-Compat-NoWP" />
<rule ref="Jetpack-Compat-74" />
</ruleset>
8 changes: 8 additions & 0 deletions projects/packages/stub-generator/.phpcs.dir.xml
Original file line number Diff line number Diff line change
@@ -0,0 +1,8 @@
<?xml version="1.0"?>
<ruleset>
<rule ref="Jetpack-NoWP" />

<!-- Ideally we'd just configure PHPCompatibility with the right PHP version, but it uses <config> rather than <properties>. Sigh. -->
<!-- So instead we have to manually disable certain sniffs. -->
<rule ref="./.phpcs.dir.phpcompatibility.xml" />
</ruleset>
1 change: 1 addition & 0 deletions projects/packages/stub-generator/.phpcsignore
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
tests/php/fixtures/
10 changes: 10 additions & 0 deletions projects/packages/stub-generator/CHANGELOG.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,10 @@
# Changelog

All notable changes to this project will be documented in this file.

The format is based on [Keep a Changelog](https://keepachangelog.com/en/1.0.0/)
and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0.html).

## 1.0.0 - 2024-03-28
### Added
- Initial version.
102 changes: 102 additions & 0 deletions projects/packages/stub-generator/README.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,102 @@
# stub-generator

Extract stubs for specific functions/classes/etc from a codebase.

This is intended for situations where you want stubs for specific parts of a large code base.
If you want to extract stubs for everything, something like [php-stubs/generator](https://packagist.org/packages/php-stubs/generator) might work better for you.

## Usage

This is a fairly simple command-line application:

```
vendor/bin/jetpack-stub-generator definition-file.php
```

### Options

--json
: Definition file is JSON rather than PHP.

--output _&lt;file&gt;_
: Write the stubs to the specified file, rather than to standard output.

### Definition file

The definition file specifies which stubs are extracted from which files, and some other configuration.

The annotated example here is in PHP format. Equivalent JSON structure may be used with the `--json` flag.

```php

<?php

return [
// Text to put at the top of the output, after the opening `<?php`. Default empty.
'header' => '',

// Text to put at the end of the output. Default empty.
'footer' => '',

// Set true to strip descriptions and unrecognized tags from the phpdoc.
'strip-docs' => false,

// Path which `files` are relative to. Defaults to the directory containing the definition file,
// and if it's relative it's relative to that.
'basedir' => '.',

// Files to process, and what to extract from them.
'files' => [
'path/to/file.php' => [
// Constants to extract, by name.
'constant' => [ 'CONSTANT_ONE', 'CONSTANT_TWO' ],

// Functions to extract, by name.
'function' => [ 'functionOne', 'functionTwo' ],

// Classes to extract,
'class' => [
'ClassName' => [
'constant' => [ 'CLASS_CONSTANT' ],
'property' => [ 'propertyName' ],
'method' => [ 'methodName', 'staticOrDynamicNoDifference' ],
],
],
'interface' => [ /* constants, properties, and methods, just like classes */ ],
'trait' => [ /* constants, properties, and methods, just like classes */ ],
],

// A `'*'` can be used to avoid having to list everything, if you want everything in a file.
'path/to/file2.php' => [
// If you want to extract everything in a category from the file, you can do it like this.
'function' => '*',

'class' => [
// It also works for extracting parts of classes, interfaces, and traits.
'ClassName' => [
'property' => '*',
'method' => '*',
],

// And for whole classes, interfaces, and traits for that matter.
'ClassName2' => '*',
],
],

// This works too.
'path/to/file3.php' => '*',

// OTOH, there's no globbing or "entire directory" functionality for filenames.
// Since this is a PHP file, you can easily do that yourself.
],
];
```

## Security

Need to report a security vulnerability? Go to [https://automattic.com/security/](https://automattic.com/security/) or directly to our security bug bounty site [https://hackerone.com/automattic](https://hackerone.com/automattic).

## License

stub-generator is licensed under [GNU General Public License v2 (or later)](./LICENSE.txt)

55 changes: 55 additions & 0 deletions projects/packages/stub-generator/bin/jetpack-stub-generator
Original file line number Diff line number Diff line change
@@ -0,0 +1,55 @@
#!/usr/bin/env php
<?php
/**
* A tool for generating stubs.
*
* @package automattic/jetpack-stub-generator
*/

use Composer\XdebugHandler\XdebugHandler;

// Make sure this script is being run over the PHP CLI.
if ( 'cli' !== php_sapi_name() ) {
return;
}

$files = array(
// Pulled in via Composer?
__DIR__ . '/../../../autoload.php',
// Local repo?
__DIR__ . '/../vendor/autoload.php',
// Pulled in via Composer, but not symlinked from vendor/bin/?
__DIR__ . '/../autoload.php',
);
// Also check relative to the executed path if "vendor" is part of it,
// in case composer symlinked it somewhere.
if ( ! empty( $argv[0] ) ) {
$pos = strrpos( $argv[0], DIRECTORY_SEPARATOR . 'vendor' . DIRECTORY_SEPARATOR );
if ( false !== $pos ) {
$files[] = substr( $argv[0], 0, $pos ) . '/vendor/autoload.php';
} elseif ( substr( $argv[0], 0, 7 ) === 'vendor' . DIRECTORY_SEPARATOR ) {
$files[] = './vendor/autoload.php';
}
}
foreach ( $files as $file ) {
if ( file_exists( $file ) ) {
require $file;

$xdebug = new XdebugHandler( 'JETPACK_STUB_GENERATOR' );
$xdebug->check();
unset( $xdebug );

$app = new Automattic\Jetpack\StubGenerator\Application();
exit( $app->run() );
}
}

$err = <<<EOF
You need to set up the project dependencies using Composer:
composer install
You can learn all about Composer on https://getcomposer.org/.
EOF;
fprintf( STDERR, "%s\n", $err );
exit( 1 );
Empty file.
5 changes: 5 additions & 0 deletions projects/packages/stub-generator/changelog/fake-change-file
Original file line number Diff line number Diff line change
@@ -0,0 +1,5 @@
Significance: patch
Type: added
Comment: Tooling requires some file (other than .gitkeep) be touched. 🤷


63 changes: 63 additions & 0 deletions projects/packages/stub-generator/composer.json
Original file line number Diff line number Diff line change
@@ -0,0 +1,63 @@
{
"name": "automattic/jetpack-stub-generator",
"description": "Extract stubs for specific functions/classes/etc from a codebase.",
"type": "project",
"license": "GPL-2.0-or-later",
"keywords": [
"stub",
"generator",
"cli",
"dev"
],
"require": {
"php": ">=7.4",
"composer/xdebug-handler": "^3.0.4",
"nikic/php-parser": "^5.0.2",
"phpstan/phpdoc-parser": "^1.28.0",
"symfony/console": "^5.3 || ^6.0 || ^7.0"
},
"require-dev": {
"yoast/phpunit-polyfills": "1.1.0",
"automattic/jetpack-changelogger": "@dev"
},
"autoload": {
"psr-4": {
"Automattic\\Jetpack\\StubGenerator\\": "src/"
}
},
"scripts": {
"phpunit": [
"./vendor/phpunit/phpunit/phpunit --colors=always"
],
"test-php": [
"@composer phpunit"
]
},
"bin": [
"bin/jetpack-stub-generator"
],
"repositories": [
{
"type": "path",
"url": "../../packages/*",
"options": {
"monorepo": true
}
}
],
"minimum-stability": "dev",
"prefer-stable": true,
"extra": {
"autotagger": true,
"branch-alias": {
"dev-trunk": "1.0.x-dev"
},
"changelogger": {
"link-template": "https://github.com/Automattic/jetpack-stub-generator/compare/v${old}...v${new}"
},
"mirror-repo": "Automattic/jetpack-stub-generator",
"version-constants": {
"::VERSION": "src/Application.php"
}
}
}
12 changes: 12 additions & 0 deletions projects/packages/stub-generator/phpunit.xml.dist
Original file line number Diff line number Diff line change
@@ -0,0 +1,12 @@
<phpunit bootstrap="tests/php/bootstrap.php" backupGlobals="false" colors="true" convertDeprecationsToExceptions="true">
<testsuites>
<testsuite name="main">
<directory suffix="Test.php">tests/php</directory>
</testsuite>
</testsuites>
<filter>
<whitelist processUncoveredFilesFromWhitelist="false">
<directory suffix=".php">src</directory>
</whitelist>
</filter>
</phpunit>
Loading

0 comments on commit 75e6e35

Please sign in to comment.