Skip to content

Commit

Permalink
Merge pull request #6 from creative-commoners/pulls/1.1/branch-on-push
Browse files Browse the repository at this point in the history
FIX Update getInstallerVersion
  • Loading branch information
GuySartorelli authored Jun 30, 2022
2 parents 9e32eac + 9ce493f commit 8081a29
Show file tree
Hide file tree
Showing 7 changed files with 234 additions and 22 deletions.
27 changes: 27 additions & 0 deletions .github/workflows/ci.yml
Original file line number Diff line number Diff line change
@@ -0,0 +1,27 @@
name: CI

on:
push:
pull_request:
workflow_dispatch:

jobs:
ci:
name: CI
runs-on: ubuntu-latest
steps:

- name: Checkout code
uses: actions/checkout@7884fcad6b5d53d10323aee724dc68d8b9096a2e # v2.4.2

- name: Install PHP
uses: shivammathur/setup-php@3eda58347216592f618bb1dff277810b6698e4ca # v2.19.1
with:
php-version: 8.1
extensions: yaml

- name: Install PHPUnit
run: wget https://phar.phpunit.de/phpunit-9.5.phar

- name: PHPUnit
run: php phpunit-9.5.phar --verbose --colors=always
1 change: 1 addition & 0 deletions .gitignore
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
.phpunit.result.cache
8 changes: 2 additions & 6 deletions action.php
Original file line number Diff line number Diff line change
Expand Up @@ -4,10 +4,6 @@
include 'job_creator.php';

// Reads inputs.yml and creates a new json matrix
$inputs = yaml_parse(file_get_contents('__inputs.yml'));
if ($inputs === false) {
echo 'Unable to parse __inputs.yml';
exit(1);
}
$yml = file_get_contents('__inputs.yml');
$jobCreator = new JobCreator();
echo $jobCreator->createJson($inputs);
echo $jobCreator->createJson($yml);
59 changes: 43 additions & 16 deletions job_creator.php
Original file line number Diff line number Diff line change
Expand Up @@ -13,23 +13,30 @@ public function getInstallerVersion(string $githubRepository, string $branch): s
if (in_array($repo, NO_INSTALLER_REPOS)) {
return '';
}
// e.g. ['4', '11']
$portions = explode('.', $branch);
if (count($portions) == 1) {
return '4.x-dev';
// e.g. pulls/4.10/some-bugfix or pulls/4/some-feature
// for push events to the creative-commoners account
if (preg_match('#^pulls/([0-9\.]+)/#', $branch, $matches)) {
$branch = $matches[1];
}
if (in_array($repo, LOCKSTEPED_REPOS)) {
return '4.' . $portions[1] . '.x-dev';
} else {
// use the latest minor version of installer
$installerVersions = array_keys(INSTALLER_TO_PHP_VERSIONS);
// remove '4' version
$installerVersions = array_diff($installerVersions, ['4']);
// get the minor portions of the verisons e.g. [9, 10, 11]
$minorPortions = array_map(fn($portions) => (int) explode('.', $portions)[1], $installerVersions);
sort($minorPortions);
return '4.' . $minorPortions[count($minorPortions) - 1] . '.x-dev';
// e.g. 4.10-release
$branch = preg_replace('#^([0-9\.]+)-release$#', '$1', $branch);
if (in_array($repo, LOCKSTEPED_REPOS) && is_numeric($branch)) {
// e.g. ['4', '11']
$portions = explode('.', $branch);
if (count($portions) == 1) {
return '4.x-dev';
} else {
return '4.' . $portions[1] . '.x-dev';
}
}
// use the latest minor version of installer
$installerVersions = array_keys(INSTALLER_TO_PHP_VERSIONS);
// remove '4' version
$installerVersions = array_diff($installerVersions, ['4']);
// get the minor portions of the verisons e.g. [9, 10, 11]
$minorPortions = array_map(fn($portions) => (int) explode('.', $portions)[1], $installerVersions);
sort($minorPortions);
return '4.' . $minorPortions[count($minorPortions) - 1] . '.x-dev';
}

public function createJob(int $phpIndex, array $opts): array
Expand Down Expand Up @@ -180,8 +187,28 @@ private function buildDynamicMatrix(
return $matrix;
}

public function createJson(array $inputs): string
public function getInputs(string $yml): array
{
$message = 'Failed to parse yml';
try {
$inputs = yaml_parse($yml);
} catch (Exception $e) {
throw new Exception($message);
}
if (!$inputs) {
throw new Exception($message);
}
if (array_key_exists('github_my_ref', $inputs)) {
if (!preg_match("#github_my_ref: *'#", $yml)) {
throw new Exception('github_my_ref needs to be surrounded by single-quotes');
}
}
return $inputs;
}

public function createJson(string $yml): string
{
$inputs = $this->getInputs($yml);
// $myRef will either be a branch for push (i.e cron) and pull-request (target branch), or a semver tag
$myRef = $inputs['github_my_ref'];
$isTag = preg_match('#^[0-9]+\.[0-9]+\.[0-9]+$#', $myRef, $m);
Expand Down
8 changes: 8 additions & 0 deletions phpunit.xml
Original file line number Diff line number Diff line change
@@ -0,0 +1,8 @@
<?xml version="1.0" encoding="UTF-8"?>
<phpunit bootstrap="tests/bootstrap.php" colors="true">
<testsuites>
<testsuite name="Default">
<directory>tests</directory>
</testsuite>
</testsuites>
</phpunit>
149 changes: 149 additions & 0 deletions tests/JobCreatorTest.php
Original file line number Diff line number Diff line change
@@ -0,0 +1,149 @@
<?php

use PHPUnit\Framework\TestCase;

class JobCreatorTest extends TestCase
{
/**
* @dataProvider provideGetInstallerVersion
*/
public function testGetInstallerVersion(
string $githubRepository,
string $branch,
string $expected
): void {
$creator = new JobCreator();
$actual = $creator->getInstallerVersion($githubRepository, $branch);
$this->assertSame($expected, $actual);
}

private function getLatestInstallerVersion(): string
{
$versions = array_keys(INSTALLER_TO_PHP_VERSIONS);
natsort($versions);
$versions = array_reverse($versions);
return $versions[0];
}

public function provideGetInstallerVersion(): array
{
$latest = $this->getLatestInstallerVersion() . '.x-dev';
return [
// no-installer repo
['myaccount/recipe-cms', '4', ''],
['myaccount/recipe-cms', '4.10', ''],
['myaccount/recipe-cms', 'burger', ''],
['myaccount/recipe-cms', 'pulls/4/myfeature', ''],
['myaccount/recipe-cms', 'pulls/4.10/myfeature', ''],
['myaccount/recipe-cms', 'pulls/burger/myfeature', ''],
['myaccount/recipe-cms', '4-release', ''],
['myaccount/recipe-cms', '4.10-release', ''],
// lockstepped repo with 4.* naming
['myaccount/silverstripe-framework', '4', '4.x-dev'],
['myaccount/silverstripe-framework', '4.10', '4.10.x-dev'],
['myaccount/silverstripe-framework', 'burger', $latest],
['myaccount/silverstripe-framework', 'pulls/4/mybugfix', '4.x-dev'],
['myaccount/silverstripe-framework', 'pulls/4.10/mybugfix', '4.10.x-dev'],
['myaccount/silverstripe-framework', 'pulls/burger/myfeature', $latest],
['myaccount/silverstripe-framework', '4-release', '4.x-dev'],
['myaccount/silverstripe-framework', '4.10-release', '4.10.x-dev'],
// lockstepped repo with 1.* naming
['myaccount/silverstripe-admin', '1', '4.x-dev'],
['myaccount/silverstripe-admin', '1.10', '4.10.x-dev'],
['myaccount/silverstripe-admin', 'burger', $latest],
['myaccount/silverstripe-admin', 'pulls/1/mybugfix', '4.x-dev'],
['myaccount/silverstripe-admin', 'pulls/1.10/mybugfix', '4.10.x-dev'],
['myaccount/silverstripe-admin', 'pulls/burger/myfeature', $latest],
['myaccount/silverstripe-admin', '1-release', '4.x-dev'],
['myaccount/silverstripe-admin', '1.10-release', '4.10.x-dev'],
// non-lockedstepped repo
['myaccount/silverstripe-tagfield', '2', $latest],
['myaccount/silverstripe-tagfield', '2.9', $latest],
['myaccount/silverstripe-tagfield', 'burger', $latest],
['myaccount/silverstripe-tagfield', 'pulls/2/mybugfix', $latest],
['myaccount/silverstripe-tagfield', 'pulls/2.9/mybugfix', $latest],
['myaccount/silverstripe-tagfield', 'pulls/burger/myfeature', $latest],
['myaccount/silverstripe-tagfield', '2-release', $latest],
['myaccount/silverstripe-tagfield', '2.9-release', $latest],
];
}

/**
* @dataProvider provideGetInputsValid
*/
public function testGetInputsValid(string $yml, array $expected)
{
if (!function_exists('yaml_parse')) {
$this->markTestSkipped('yaml extension is not installed');
}
$creator = new JobCreator();
$actual = $creator->getInputs($yml);
$this->assertSame($expected, $actual);
}

public function provideGetInputsValid(): array
{
return [
[
<<<EOT
endtoend: true
js: true
phpcoverage: false
phpcoverage_force_off: false
phplinting: true
phpunit: true
simple_matrix: false
github_repository: 'myaccount/silverstripe-versioned'
github_my_ref: 'pulls/1.10/module-standards'
EOT,
[
'endtoend' => true,
'js' => true,
'phpcoverage' => false,
'phpcoverage_force_off' => false,
'phplinting' => true,
'phpunit' => true,
'simple_matrix' => false,
'github_repository' => 'myaccount/silverstripe-versioned',
'github_my_ref'=> 'pulls/1.10/module-standards'
]
],
];
}

/**
* @dataProvider provideGetInputsInvalid
*/
public function testGetInputsInvalid(string $yml, string $expectedMessage)
{
if (!function_exists('yaml_parse')) {
$this->markTestSkipped('yaml extension is not installed');
}
$this->expectException(Exception::class);
$this->expectExceptionMessage($expectedMessage);
$creator = new JobCreator();
$creator->getInputs($yml);
}

public function provideGetInputsInvalid(): array
{
return [
// missing quotes around github_my_ref (would turn into an int, so 1.10 becomes 1.1)
[
<<<EOT
github_my_ref: 1.10
EOT,
'github_my_ref needs to be surrounded by single-quotes'
],
// invalid yml
[
<<<EOT
this: --
is: - total: ' nonsense
"
EOT,
'Failed to parse yml'
],
];
}
}
4 changes: 4 additions & 0 deletions tests/bootstrap.php
Original file line number Diff line number Diff line change
@@ -0,0 +1,4 @@
<?php
// working directory will be root
include 'consts.php';
include 'job_creator.php';

0 comments on commit 8081a29

Please sign in to comment.