From 4582f808f05205e7a32ecd6ae42dee00295872f1 Mon Sep 17 00:00:00 2001 From: Igor Scheller Date: Sun, 21 Jul 2019 02:34:52 +0200 Subject: [PATCH] Added version to credits and metrics page --- .gitlab-ci.yml | 4 +- config/app.php | 1 + contrib/Dockerfile | 3 ++ resources/views/pages/credits.twig | 1 + src/Application.php | 1 + src/Controllers/CreditsController.php | 13 +++++- src/Controllers/Metrics/Controller.php | 21 +++++++++- src/Helpers/Version.php | 42 +++++++++++++++++++ src/Helpers/VersionServiceProvider.php | 15 +++++++ storage/app/.gitignore | 2 + .../Controllers/CreditsControllerTest.php | 16 ++++--- .../Controllers/Metrics/ControllerTest.php | 22 ++++++---- tests/Unit/Helpers/Stub/files/VERSION | 1 + .../Helpers/VersionServiceProviderTest.php | 25 +++++++++++ tests/Unit/Helpers/VersionTest.php | 28 +++++++++++++ 15 files changed, 179 insertions(+), 16 deletions(-) create mode 100644 src/Helpers/Version.php create mode 100644 src/Helpers/VersionServiceProvider.php create mode 100644 storage/app/.gitignore create mode 100644 tests/Unit/Helpers/Stub/files/VERSION create mode 100644 tests/Unit/Helpers/VersionServiceProviderTest.php create mode 100644 tests/Unit/Helpers/VersionTest.php diff --git a/.gitlab-ci.yml b/.gitlab-ci.yml index db26ce4c..b9bb8654 100644 --- a/.gitlab-ci.yml +++ b/.gitlab-ci.yml @@ -38,7 +38,9 @@ build-image: <<: *docker_definition stage: build script: - - docker build --pull --build-arg NGINX_IMAGE="${TEST_IMAGE}-nginx" -t "${TEST_IMAGE}" -f contrib/Dockerfile . + - apk -q add git + - VERSION="$(git describe --abbrev=0 --tags)-${CI_COMMIT_REF_NAME}+${CI_PIPELINE_ID}.${CI_COMMIT_SHORT_SHA}" + - docker build --pull --build-arg NGINX_IMAGE="${TEST_IMAGE}-nginx" --build-arg VERSION="${VERSION}" -t "${TEST_IMAGE}" -f contrib/Dockerfile . - docker push "${TEST_IMAGE}" test: diff --git a/config/app.php b/config/app.php index 17fdee11..8850f74e 100644 --- a/config/app.php +++ b/config/app.php @@ -27,6 +27,7 @@ return [ \Engelsystem\Middleware\SessionHandlerServiceProvider::class, // Additional services + \Engelsystem\Helpers\VersionServiceProvider::class, \Engelsystem\Mail\MailerServiceProvider::class, ], diff --git a/contrib/Dockerfile b/contrib/Dockerfile index dd3bd308..f04fff11 100644 --- a/contrib/Dockerfile +++ b/contrib/Dockerfile @@ -32,6 +32,9 @@ COPY --from=composer /app/composer.lock /app/ RUN find /app/storage/ -type f -not -name .gitignore -exec rm {} \; RUN rm -f /app/import/* /app/config/config.php +ARG VERSION +RUN if [[ ! -f /app/storage/app/VERSION ]] && [[ ! -z "${VERSION}" ]]; then echo -n "${VERSION}" > /app/storage/app/VERSION; fi + # Build the PHP container FROM php:7-fpm-alpine WORKDIR /var/www diff --git a/resources/views/pages/credits.twig b/resources/views/pages/credits.twig index eb98c7e7..3bb04895 100644 --- a/resources/views/pages/credits.twig +++ b/resources/views/pages/credits.twig @@ -15,6 +15,7 @@

Source code

+

Version: {{ version }}

The original engelsystem was written by cookie. diff --git a/src/Application.php b/src/Application.php index ac69c20a..99c68231 100644 --- a/src/Application.php +++ b/src/Application.php @@ -111,6 +111,7 @@ class Application extends Container $this->instance('path.lang', $this->get('path.resources') . DIRECTORY_SEPARATOR . 'lang'); $this->instance('path.views', $this->get('path.resources') . DIRECTORY_SEPARATOR . 'views'); $this->instance('path.storage', $appPath . DIRECTORY_SEPARATOR . 'storage'); + $this->instance('path.storage.app', $this->get('path.storage') . DIRECTORY_SEPARATOR . 'app'); $this->instance('path.cache', $this->get('path.storage') . DIRECTORY_SEPARATOR . 'cache'); $this->instance('path.cache.routes', $this->get('path.cache') . DIRECTORY_SEPARATOR . 'routes.cache.php'); $this->instance('path.cache.views', $this->get('path.cache') . DIRECTORY_SEPARATOR . 'views'); diff --git a/src/Controllers/CreditsController.php b/src/Controllers/CreditsController.php index b2805b84..ade97649 100644 --- a/src/Controllers/CreditsController.php +++ b/src/Controllers/CreditsController.php @@ -3,6 +3,7 @@ namespace Engelsystem\Controllers; use Engelsystem\Config\Config; +use Engelsystem\Helpers\Version; use Engelsystem\Http\Response; class CreditsController extends BaseController @@ -13,14 +14,19 @@ class CreditsController extends BaseController /** @var Response */ protected $response; + /** @var Version */ + protected $version; + /** * @param Response $response * @param Config $config + * @param Version $version */ - public function __construct(Response $response, Config $config) + public function __construct(Response $response, Config $config, Version $version) { $this->config = $config; $this->response = $response; + $this->version = $version; } /** @@ -30,7 +36,10 @@ class CreditsController extends BaseController { return $this->response->withView( 'pages/credits.twig', - ['credits' => $this->config->get('credits')] + [ + 'credits' => $this->config->get('credits'), + 'version' => $this->version->getVersion(), + ] ); } } diff --git a/src/Controllers/Metrics/Controller.php b/src/Controllers/Metrics/Controller.php index f6ea3967..ffb2a41b 100644 --- a/src/Controllers/Metrics/Controller.php +++ b/src/Controllers/Metrics/Controller.php @@ -4,6 +4,7 @@ namespace Engelsystem\Controllers\Metrics; use Engelsystem\Config\Config; use Engelsystem\Controllers\BaseController; +use Engelsystem\Helpers\Version; use Engelsystem\Http\Exceptions\HttpForbidden; use Engelsystem\Http\Request; use Engelsystem\Http\Response; @@ -26,25 +27,31 @@ class Controller extends BaseController /** @var Stats */ protected $stats; + /** @var Version */ + protected $version; + /** * @param Response $response * @param MetricsEngine $engine * @param Config $config * @param Request $request * @param Stats $stats + * @param Version $version */ public function __construct( Response $response, MetricsEngine $engine, Config $config, Request $request, - Stats $stats + Stats $stats, + Version $version ) { $this->config = $config; $this->engine = $engine; $this->request = $request; $this->response = $response; $this->stats = $stats; + $this->version = $version; } /** @@ -68,6 +75,18 @@ class Controller extends BaseController $data = [ $this->config->get('app_name') . ' stats', + 'info' => [ + 'type' => 'gauge', + 'help' => 'About the environment', + [ + 'labels' => [ + 'os' => PHP_OS_FAMILY, + 'php' => implode('.', [PHP_MAJOR_VERSION, PHP_MINOR_VERSION]), + 'version' => $this->version->getVersion(), + ], + 'value' => 1, + ], + ], 'users' => [ 'type' => 'gauge', ['labels' => ['state' => 'incoming'], 'value' => $this->stats->newUsers()], diff --git a/src/Helpers/Version.php b/src/Helpers/Version.php new file mode 100644 index 00000000..97fe6ef3 --- /dev/null +++ b/src/Helpers/Version.php @@ -0,0 +1,42 @@ +storage = $storage; + $this->config = $config; + } + + /** + * @return string + */ + public function getVersion() + { + $file = $this->storage . DIRECTORY_SEPARATOR . $this->versionFile; + + $version = 'n/a'; + if (file_exists($file)) { + $version = trim(file_get_contents($file)); + } + + return $this->config->get('version', $version); + } +} diff --git a/src/Helpers/VersionServiceProvider.php b/src/Helpers/VersionServiceProvider.php new file mode 100644 index 00000000..41e10158 --- /dev/null +++ b/src/Helpers/VersionServiceProvider.php @@ -0,0 +1,15 @@ +app->when(Version::class) + ->needs('$storage') + ->give($this->app->get('path.storage.app')); + } +} diff --git a/storage/app/.gitignore b/storage/app/.gitignore new file mode 100644 index 00000000..78d91016 --- /dev/null +++ b/storage/app/.gitignore @@ -0,0 +1,2 @@ +/* +!.gitignore diff --git a/tests/Unit/Controllers/CreditsControllerTest.php b/tests/Unit/Controllers/CreditsControllerTest.php index 42ea4ea1..303bf60e 100644 --- a/tests/Unit/Controllers/CreditsControllerTest.php +++ b/tests/Unit/Controllers/CreditsControllerTest.php @@ -4,9 +4,10 @@ namespace Engelsystem\Test\Unit\Controllers; use Engelsystem\Config\Config; use Engelsystem\Controllers\CreditsController; +use Engelsystem\Helpers\Version; use Engelsystem\Http\Response; +use Engelsystem\Test\Unit\TestCase; use PHPUnit\Framework\MockObject\MockObject; -use PHPUnit\Framework\TestCase; class CreditsControllerTest extends TestCase { @@ -19,12 +20,17 @@ class CreditsControllerTest extends TestCase /** @var Response|MockObject $response */ $response = $this->createMock(Response::class); $config = new Config(['foo' => 'bar', 'credits' => ['lor' => 'em']]); + /** @var Version|MockObject $version */ + $version = $this->createMock(Version::class); - $response->expects($this->once()) - ->method('withView') - ->with('pages/credits.twig', ['credits' => ['lor' => 'em']]); + $this->setExpects( + $response, + 'withView', + ['pages/credits.twig', ['credits' => ['lor' => 'em'], 'version' => '42.1.0-test']] + ); + $this->setExpects($version, 'getVersion', [], '42.1.0-test'); - $controller = new CreditsController($response, $config); + $controller = new CreditsController($response, $config, $version); $controller->index(); } } diff --git a/tests/Unit/Controllers/Metrics/ControllerTest.php b/tests/Unit/Controllers/Metrics/ControllerTest.php index 18daa96a..f203200c 100644 --- a/tests/Unit/Controllers/Metrics/ControllerTest.php +++ b/tests/Unit/Controllers/Metrics/ControllerTest.php @@ -6,6 +6,7 @@ use Engelsystem\Config\Config; use Engelsystem\Controllers\Metrics\Controller; use Engelsystem\Controllers\Metrics\MetricsEngine; use Engelsystem\Controllers\Metrics\Stats; +use Engelsystem\Helpers\Version; use Engelsystem\Http\Exceptions\HttpForbidden; use Engelsystem\Http\Request; use Engelsystem\Http\Response; @@ -28,7 +29,8 @@ class ControllerTest extends TestCase /** @var MetricsEngine|MockObject $engine */ /** @var Stats|MockObject $stats */ /** @var Config $config */ - list($response, $request, $engine, $stats, $config) = $this->getMocks(); + /** @var Version|MockObject $version */ + list($response, $request, $engine, $stats, $config, $version) = $this->getMocks(); $request->server = new ServerBag(); $request->server->set('REQUEST_TIME_FLOAT', 0.0123456789); @@ -37,6 +39,7 @@ class ControllerTest extends TestCase ->method('get') ->willReturnCallback(function ($path, $data) use ($response) { $this->assertEquals('/metrics', $path); + $this->assertArrayHasKey('info', $data); $this->assertArrayHasKey('users', $data); $this->assertArrayHasKey('licenses', $data); $this->assertArrayHasKey('users_working', $data); @@ -122,7 +125,9 @@ class ControllerTest extends TestCase 'XL' => 'X Large', ]); - $controller = new Controller($response, $engine, $config, $request, $stats); + $this->setExpects($version, 'getVersion', [], '0.42.42'); + + $controller = new Controller($response, $engine, $config, $request, $stats, $version); $controller->metrics(); } @@ -137,7 +142,8 @@ class ControllerTest extends TestCase /** @var MetricsEngine|MockObject $engine */ /** @var Stats|MockObject $stats */ /** @var Config $config */ - list($response, $request, $engine, $stats, $config) = $this->getMocks(); + /** @var Version|MockObject $version */ + list($response, $request, $engine, $stats, $config, $version) = $this->getMocks(); $response->expects($this->once()) ->method('withHeader') @@ -168,7 +174,7 @@ class ControllerTest extends TestCase $this->setExpects($stats, 'arrivedUsers', null, 10, $this->exactly(2)); $this->setExpects($stats, 'currentlyWorkingUsers', null, 5); - $controller = new Controller($response, $engine, $config, $request, $stats); + $controller = new Controller($response, $engine, $config, $request, $stats, $version); $controller->stats(); } @@ -182,7 +188,8 @@ class ControllerTest extends TestCase /** @var MetricsEngine|MockObject $engine */ /** @var Stats|MockObject $stats */ /** @var Config $config */ - list($response, $request, $engine, $stats, $config) = $this->getMocks(); + /** @var Version|MockObject $version */ + list($response, $request, $engine, $stats, $config, $version) = $this->getMocks(); $request->expects($this->once()) ->method('get') @@ -191,7 +198,7 @@ class ControllerTest extends TestCase $config->set('api_key', 'fooBar!'); - $controller = new Controller($response, $engine, $config, $request, $stats); + $controller = new Controller($response, $engine, $config, $request, $stats, $version); $this->expectException(HttpForbidden::class); $this->expectExceptionMessage(json_encode(['error' => 'The api_key is invalid'])); @@ -212,7 +219,8 @@ class ControllerTest extends TestCase /** @var Stats|MockObject $stats */ $stats = $this->createMock(Stats::class); $config = new Config(); + $version = $this->createMock(Version::class); - return [$response, $request, $engine, $stats, $config]; + return [$response, $request, $engine, $stats, $config, $version]; } } diff --git a/tests/Unit/Helpers/Stub/files/VERSION b/tests/Unit/Helpers/Stub/files/VERSION new file mode 100644 index 00000000..749a96f3 --- /dev/null +++ b/tests/Unit/Helpers/Stub/files/VERSION @@ -0,0 +1 @@ +0.42.0-testing diff --git a/tests/Unit/Helpers/VersionServiceProviderTest.php b/tests/Unit/Helpers/VersionServiceProviderTest.php new file mode 100644 index 00000000..609c649d --- /dev/null +++ b/tests/Unit/Helpers/VersionServiceProviderTest.php @@ -0,0 +1,25 @@ +instance('path.storage.app', '/tmp'); + + $serviceProvider = new VersionServiceProvider($app); + $serviceProvider->register(); + + $this->assertArrayHasKey(Version::class, $app->contextual); + } +} diff --git a/tests/Unit/Helpers/VersionTest.php b/tests/Unit/Helpers/VersionTest.php new file mode 100644 index 00000000..40569abb --- /dev/null +++ b/tests/Unit/Helpers/VersionTest.php @@ -0,0 +1,28 @@ +assertEquals('n/a', $version->getVersion()); + + $version = new Version(__DIR__ . '/Stub/files', $config); + $this->assertEquals('0.42.0-testing', $version->getVersion()); + + $config->set('version', '1.2.3-dev'); + $this->assertEquals('1.2.3-dev', $version->getVersion()); + } +}