J. King
2 years ago
commit
393a435f7b
12 changed files with 391 additions and 0 deletions
@ -0,0 +1,7 @@ |
|||||
|
* text=auto encoding=utf-8 |
||||
|
|
||||
|
*.html diff=html |
||||
|
*.php diff=php |
||||
|
*.bat eol=crlf |
||||
|
*.cmd eol=crlf |
||||
|
.gitignore -eol |
@ -0,0 +1,27 @@ |
|||||
|
# Temporary files |
||||
|
|
||||
|
/tests/coverage/ |
||||
|
/.php_cs.cache |
||||
|
/tests/.phpunit.result.cache |
||||
|
|
||||
|
# Dependencies |
||||
|
|
||||
|
/vendor/ |
||||
|
/vendor-bin/*/vendor |
||||
|
|
||||
|
# Windows files |
||||
|
|
||||
|
Thumbs.db |
||||
|
ehthumbs.db |
||||
|
Desktop.ini |
||||
|
$RECYCLE.BIN/ |
||||
|
|
||||
|
|
||||
|
# macOS files |
||||
|
|
||||
|
.DS_Store |
||||
|
.AppleDouble |
||||
|
.LSOverride |
||||
|
._* |
||||
|
.Spotlight-V100 |
||||
|
.Trashes |
@ -0,0 +1,80 @@ |
|||||
|
<?php |
||||
|
declare(strict_types=1); |
||||
|
namespace MensBeam\Docopt; |
||||
|
|
||||
|
const BASE = __DIR__.DIRECTORY_SEPARATOR; |
||||
|
|
||||
|
$paths = [ |
||||
|
__FILE__, |
||||
|
BASE."RoboFile.php", |
||||
|
BASE."lib", |
||||
|
BASE."tests", |
||||
|
]; |
||||
|
$rules = [ |
||||
|
// house rules where PSR series is silent |
||||
|
'align_multiline_comment' => ['comment_type' => "phpdocs_only"], |
||||
|
'array_syntax' => ['syntax' => "short"], |
||||
|
'binary_operator_spaces' => [ |
||||
|
'default' => "single_space", |
||||
|
'operators' => ['=>' => "align_single_space"], |
||||
|
], |
||||
|
'cast_spaces' => ['space' => "single"], |
||||
|
'concat_space' => ['spacing' => "none"], |
||||
|
'list_syntax' => ['syntax' => "short"], |
||||
|
'magic_constant_casing' => true, |
||||
|
'magic_method_casing' => true, |
||||
|
'modernize_types_casting' => true, |
||||
|
'native_function_casing' => true, |
||||
|
'native_function_type_declaration_casing' => true, |
||||
|
'no_binary_string' => true, |
||||
|
'no_blank_lines_after_phpdoc' => true, |
||||
|
'no_empty_comment' => true, |
||||
|
'no_empty_phpdoc' => true, |
||||
|
'no_extra_blank_lines' => true, // this could probably use more configuration |
||||
|
'no_mixed_echo_print' => ['use' => "echo"], |
||||
|
'no_short_bool_cast' => true, |
||||
|
'no_trailing_comma_in_singleline_array' => true, |
||||
|
'no_unneeded_control_parentheses' => true, |
||||
|
'no_unneeded_curly_braces' => true, |
||||
|
'no_unused_imports' => true, |
||||
|
'no_whitespace_before_comma_in_array' => true, |
||||
|
'normalize_index_brace' => true, |
||||
|
'object_operator_without_whitespace' => true, |
||||
|
'pow_to_exponentiation' => true, |
||||
|
'set_type_to_cast' => true, |
||||
|
'standardize_not_equals' => true, |
||||
|
'trailing_comma_in_multiline_array' => true, |
||||
|
'unary_operator_spaces' => true, |
||||
|
'yoda_style' => false, |
||||
|
// PSR standard to apply |
||||
|
'@PSR2' => true, |
||||
|
// PSR-12 rules; php-cs-fixer does not yet support PSR-12 natively |
||||
|
'compact_nullable_typehint' => true, |
||||
|
'declare_equal_normalize' => ['space' => "none"], |
||||
|
'function_typehint_space' => true, |
||||
|
'lowercase_cast' => true, |
||||
|
'lowercase_static_reference' => true, |
||||
|
'no_alternative_syntax' => true, |
||||
|
'no_empty_statement' => true, |
||||
|
'no_leading_import_slash' => true, |
||||
|
'no_leading_namespace_whitespace' => true, |
||||
|
'no_whitespace_in_blank_line' => true, |
||||
|
'return_type_declaration' => ['space_before' => "none"], |
||||
|
'single_trait_insert_per_statement' => true, |
||||
|
'short_scalar_cast' => true, |
||||
|
'visibility_required' => ['elements' => ["const", "property", "method"]], |
||||
|
// house exceptions to PSR rules |
||||
|
'braces' => ['position_after_functions_and_oop_constructs' => "same"], |
||||
|
'function_declaration' => ['closure_function_spacing' => "none"], |
||||
|
'new_with_braces' => false, // no option to specify absence of braces |
||||
|
]; |
||||
|
|
||||
|
$finder = \PhpCsFixer\Finder::create(); |
||||
|
foreach ($paths as $path) { |
||||
|
if (is_file($path)) { |
||||
|
$finder = $finder->append([$path]); |
||||
|
} else { |
||||
|
$finder = $finder->in($path); |
||||
|
} |
||||
|
} |
||||
|
return \PhpCsFixer\Config::create()->setRiskyAllowed(true)->setRules($rules)->setFinder($finder); |
@ -0,0 +1,147 @@ |
|||||
|
<?php |
||||
|
|
||||
|
use Robo\Result; |
||||
|
|
||||
|
const BASE = __DIR__.\DIRECTORY_SEPARATOR; |
||||
|
const BASE_TEST = BASE."tests".\DIRECTORY_SEPARATOR; |
||||
|
define("IS_WIN", defined("PHP_WINDOWS_VERSION_MAJOR")); |
||||
|
define("IS_MAC", php_uname("s") === "Darwin"); |
||||
|
define("IS_LINUX", !IS_WIN && !IS_MAC); |
||||
|
error_reporting(0); |
||||
|
|
||||
|
function norm(string $path): string { |
||||
|
$out = realpath($path); |
||||
|
if (!$out) { |
||||
|
$out = str_replace(["/", "\\"], \DIRECTORY_SEPARATOR, $path); |
||||
|
} |
||||
|
return $out; |
||||
|
} |
||||
|
|
||||
|
class RoboFile extends \Robo\Tasks { |
||||
|
/** Runs the typical test suite |
||||
|
* |
||||
|
* Arguments passed to the task are passed on to PHPUnit. Thus one may, for |
||||
|
* example, run the following command and get the expected results: |
||||
|
* |
||||
|
* ./robo test --testsuite TTRSS --exclude-group slow --testdox |
||||
|
* |
||||
|
* Please see the PHPUnit documentation for available options. |
||||
|
*/ |
||||
|
public function test(array $args): Result { |
||||
|
return $this->runTests(escapeshellarg(\PHP_BINARY), "typical", $args); |
||||
|
} |
||||
|
|
||||
|
/** Runs the full test suite |
||||
|
* |
||||
|
* This includes pedantic tests which may help to identify problems. |
||||
|
* See help for the "test" task for more details. |
||||
|
*/ |
||||
|
public function testFull(array $args): Result { |
||||
|
return $this->runTests(escapeshellarg(\PHP_BINARY), "full", $args); |
||||
|
} |
||||
|
|
||||
|
/** |
||||
|
* Runs a quick subset of the test suite |
||||
|
* |
||||
|
* See help for the "test" task for more details. |
||||
|
*/ |
||||
|
public function testQuick(array $args): Result { |
||||
|
return $this->runTests(escapeshellarg(\PHP_BINARY), "quick", $args); |
||||
|
} |
||||
|
|
||||
|
/** Produces a code coverage report |
||||
|
* |
||||
|
* By default this task produces an HTML-format coverage report in |
||||
|
* tests/coverage/. Additional reports may be produced by passing |
||||
|
* arguments to this task as one would to PHPUnit. |
||||
|
* |
||||
|
* Robo first tries to use pcov and will fall back first to xdebug then |
||||
|
* phpdbg. Neither pcov nor xdebug need to be enabled to be used; they |
||||
|
* only need to be present in the extension load path to be used. |
||||
|
*/ |
||||
|
public function coverage(array $args): Result { |
||||
|
// run tests with code coverage reporting enabled |
||||
|
$exec = $this->findCoverageEngine(); |
||||
|
return $this->runTests($exec, "coverage", array_merge(["--coverage-html", BASE_TEST."coverage"], $args)); |
||||
|
} |
||||
|
|
||||
|
/** Produces a code coverage report, with redundant tests |
||||
|
* |
||||
|
* Depending on the environment, some tests that normally provide |
||||
|
* coverage may be skipped, while working alternatives are normally |
||||
|
* suppressed for reasons of time. This coverage report will try to |
||||
|
* run all tests which may cover code. |
||||
|
* |
||||
|
* See also help for the "coverage" task for more details. |
||||
|
*/ |
||||
|
public function coverageFull(array $args): Result { |
||||
|
// run tests with code coverage reporting enabled |
||||
|
$exec = $this->findCoverageEngine(); |
||||
|
return $this->runTests($exec, "typical", array_merge(["--coverage-html", BASE_TEST."coverage"], $args)); |
||||
|
} |
||||
|
|
||||
|
/** Runs the coding standards fixer */ |
||||
|
public function clean($opts = ['demo|d' => false]): Result { |
||||
|
$t = $this->taskExec(norm(BASE."vendor/bin/php-cs-fixer")); |
||||
|
$t->arg("fix"); |
||||
|
if ($opts['demo']) { |
||||
|
$t->args("--dry-run", "--diff")->option("--diff-format", "udiff"); |
||||
|
} |
||||
|
return $t->run(); |
||||
|
} |
||||
|
|
||||
|
protected function findCoverageEngine(): string { |
||||
|
$dir = rtrim(ini_get("extension_dir"), "/").\DIRECTORY_SEPARATOR; |
||||
|
$ext = IS_WIN ? "dll" : "so"; |
||||
|
$php = escapeshellarg(\PHP_BINARY); |
||||
|
$code = escapeshellarg(BASE."lib"); |
||||
|
if (extension_loaded("pcov")) { |
||||
|
return "$php -d pcov.enabled=1 -d pcov.directory=$code"; |
||||
|
} elseif (extension_loaded("xdebug")) { |
||||
|
return "$php -d xdebug.mode=coverage"; |
||||
|
} elseif (file_exists($dir."pcov.$ext")) { |
||||
|
return "$php -d extension=pcov.$ext -d pcov.enabled=1 -d pcov.directory=$code"; |
||||
|
} elseif (file_exists($dir."xdebug.$ext")) { |
||||
|
return "$php -d zend_extension=xdebug.$ext -d xdebug.mode=coverage"; |
||||
|
} else { |
||||
|
if (IS_WIN) { |
||||
|
$dbg = dirname(\PHP_BINARY)."\\phpdbg.exe"; |
||||
|
$dbg = file_exists($dbg) ? $dbg : ""; |
||||
|
} else { |
||||
|
$dbg = trim(`which phpdbg 2>/dev/null`); |
||||
|
} |
||||
|
if ($dbg) { |
||||
|
return escapeshellarg($dbg)." -qrr"; |
||||
|
} else { |
||||
|
return $php; |
||||
|
} |
||||
|
} |
||||
|
} |
||||
|
|
||||
|
protected function blackhole(bool $all = false): string { |
||||
|
$hole = IS_WIN ? "nul" : "/dev/null"; |
||||
|
return $all ? ">$hole 2>&1" : "2>$hole"; |
||||
|
} |
||||
|
|
||||
|
protected function runTests(string $executor, string $set, array $args): Result { |
||||
|
switch ($set) { |
||||
|
case "typical": |
||||
|
$set = ["--exclude-group", "optional"]; |
||||
|
break; |
||||
|
case "quick": |
||||
|
$set = ["--exclude-group", "optional,slow"]; |
||||
|
break; |
||||
|
case "coverage": |
||||
|
$set = ["--exclude-group", "optional,coverageOptional"]; |
||||
|
break; |
||||
|
case "full": |
||||
|
$set = []; |
||||
|
break; |
||||
|
default: |
||||
|
throw new \Exception; |
||||
|
} |
||||
|
$execpath = norm(BASE."vendor-bin/phpunit/vendor/phpunit/phpunit/phpunit"); |
||||
|
$confpath = realpath(BASE_TEST."phpunit.dist.xml") ?: norm(BASE_TEST."phpunit.xml"); |
||||
|
return $this->taskExec($executor)->option("-d", "zend.assertions=1")->arg($execpath)->option("-c", $confpath)->args(array_merge($set, $args))->run(); |
||||
|
} |
||||
|
} |
@ -0,0 +1,38 @@ |
|||||
|
{ |
||||
|
"name": "mensbeam/docopt-ng", |
||||
|
"type": "library", |
||||
|
"description": "A PHP port of Docopt-ng", |
||||
|
"license": "MIT", |
||||
|
"authors": [ |
||||
|
{ |
||||
|
"name": "J. King", |
||||
|
"email": "jking@jkingweb.ca", |
||||
|
"homepage": "https://jkingweb.ca/" |
||||
|
} |
||||
|
|
||||
|
], |
||||
|
"require": { |
||||
|
"php": ">=7.1" |
||||
|
}, |
||||
|
"require-dev": { |
||||
|
"bamarni/composer-bin-plugin": "*" |
||||
|
}, |
||||
|
"config": { |
||||
|
"allow-plugins": { |
||||
|
"bamarni/composer-bin-plugin": true |
||||
|
} |
||||
|
}, |
||||
|
"scripts": { |
||||
|
"post-install-cmd": ["@composer bin all install"], |
||||
|
"post-update-cmd": ["@composer bin all update"] |
||||
|
}, |
||||
|
"autoload": { |
||||
|
"classmap": ["lib/Docopt.php"] |
||||
|
}, |
||||
|
"autoload-dev": { |
||||
|
"psr-4": { |
||||
|
"MensBeam\\Docopt\\Test\\": "tests/lib/", |
||||
|
"MensBeam\\Docopt\\TestCase\\": "tests/cases/" |
||||
|
} |
||||
|
} |
||||
|
} |
@ -0,0 +1,14 @@ |
|||||
|
#! /bin/sh |
||||
|
base=`dirname "$0"` |
||||
|
roboCommand="$1" |
||||
|
if [ $# -eq 0 ]; then |
||||
|
"$base/vendor/bin/robo" |
||||
|
else |
||||
|
shift |
||||
|
ulimit -n 2048 |
||||
|
if [ "$1" = "clean" ]; then |
||||
|
"$base/vendor/bin/robo" "$roboCommand" "$@" |
||||
|
else |
||||
|
"$base/vendor/bin/robo" "$roboCommand" -- "$@" |
||||
|
fi |
||||
|
fi |
@ -0,0 +1,21 @@ |
|||||
|
@echo off |
||||
|
setlocal |
||||
|
set base=%~dp0 |
||||
|
set roboCommand=%1 |
||||
|
|
||||
|
rem get all arguments except the first |
||||
|
shift |
||||
|
set "args=" |
||||
|
:parse |
||||
|
if "%~1" neq "" ( |
||||
|
set args=%args% %1 |
||||
|
shift |
||||
|
goto :parse |
||||
|
) |
||||
|
if defined args set args=%args:~1% |
||||
|
|
||||
|
if "%1"=="clean" ( |
||||
|
call "%base%vendor\bin\robo" "%roboCommand%" %args% |
||||
|
) else ( |
||||
|
call "%base%vendor\bin\robo" "%roboCommand%" -- %args% |
||||
|
) |
@ -0,0 +1,18 @@ |
|||||
|
<?php |
||||
|
declare(strict_types=1); |
||||
|
namespace MensBeam\Docopt; |
||||
|
|
||||
|
const NS_BASE = __NAMESPACE__."\\"; |
||||
|
define(NS_BASE."BASE", dirname(__DIR__).DIRECTORY_SEPARATOR); |
||||
|
ini_set("memory_limit", "-1"); |
||||
|
ini_set("zend.assertions", "1"); |
||||
|
ini_set("assert.exception", "true"); |
||||
|
require_once BASE."vendor".DIRECTORY_SEPARATOR."autoload.php"; |
||||
|
|
||||
|
if (function_exists("xdebug_set_filter")) { |
||||
|
if (defined("XDEBUG_PATH_INCLUDE")) { |
||||
|
xdebug_set_filter(\XDEBUG_FILTER_CODE_COVERAGE, XDEBUG_PATH_INCLUDE, [BASE."lib/"]); |
||||
|
} else { |
||||
|
xdebug_set_filter(\XDEBUG_FILTER_CODE_COVERAGE, XDEBUG_PATH_WHITELIST, [BASE."lib/"]); |
||||
|
} |
||||
|
} |
@ -0,0 +1,23 @@ |
|||||
|
<?xml version="1.0"?> |
||||
|
<phpunit |
||||
|
colors="true" |
||||
|
bootstrap="bootstrap.php" |
||||
|
cacheTokens="true" |
||||
|
convertErrorsToExceptions="false" |
||||
|
convertNoticesToExceptions="false" |
||||
|
convertWarningsToExceptions="false" |
||||
|
beStrictAboutTestsThatDoNotTestAnything="true" |
||||
|
beStrictAboutOutputDuringTests="true" |
||||
|
forceCoversAnnotation="true" |
||||
|
executionOrder="defects" |
||||
|
> |
||||
|
|
||||
|
<filter> |
||||
|
<whitelist processUncoveredFilesFromWhitelist="true"> |
||||
|
<directory suffix=".php">../lib</directory> |
||||
|
</whitelist> |
||||
|
</filter> |
||||
|
|
||||
|
<testsuites> |
||||
|
</testsuites> |
||||
|
</phpunit> |
@ -0,0 +1,5 @@ |
|||||
|
{ |
||||
|
"require-dev": { |
||||
|
"friendsofphp/php-cs-fixer": "^2.8" |
||||
|
} |
||||
|
} |
@ -0,0 +1,6 @@ |
|||||
|
{ |
||||
|
"require-dev": { |
||||
|
"phpunit/phpunit": "^9.0", |
||||
|
"clue/arguments": "^2.0" |
||||
|
} |
||||
|
} |
@ -0,0 +1,5 @@ |
|||||
|
{ |
||||
|
"require-dev": { |
||||
|
"consolidation/robo": "^3.0" |
||||
|
} |
||||
|
} |
Loading…
Reference in new issue