Skip to content

Commit

Permalink
improve custom commands
Browse files Browse the repository at this point in the history
  • Loading branch information
boxblinkracer committed Dec 19, 2024
1 parent cd9ed63 commit da53fa9
Show file tree
Hide file tree
Showing 7 changed files with 183 additions and 35 deletions.
6 changes: 6 additions & 0 deletions CHANGELOG.md
Original file line number Diff line number Diff line change
Expand Up @@ -3,6 +3,12 @@
All notable changes of releases are documented in this file
using the [Keep a CHANGELOG](https://keepachangelog.com/) principles.

## [unreleased]

### Added

- Add new feature to **register custom commands** if you write extensions for PHPUnuhi (thx @flkasper)

## [1.23.0]

### Added
Expand Down
33 changes: 24 additions & 9 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -109,7 +109,9 @@ Now that you know this, let's get started!
* [8.15 Spell Checkers](#815-spell-checkers)
* [8.15.1 Aspell](#8151-aspell)
* [8.15.2 OpenAI](#8152-openai)
* [9. Suggest](#9-suggest)
* [9. Custom Commands](#9-custom-commands)
* [10. Suggest](#10-suggest)

<!-- TOC -->


Expand Down Expand Up @@ -1361,11 +1363,11 @@ translation keys and their values.

```json
{
"id": "group--state_machine_018f6237aded716a9d5d74d49254115d.name",
"group": "state_machine_018f6237aded716a9d5d74d49254115d",
"key": "name",
"en-GB": "Refund state",
"de-DE": "Erstattungsstatus"
"id": "group--state_machine_018f6237aded716a9d5d74d49254115d.name",
"group": "state_machine_018f6237aded716a9d5d74d49254115d",
"key": "name",
"en-GB": "Refund state",
"de-DE": "Erstattungsstatus"
}
```

Expand Down Expand Up @@ -1649,8 +1651,21 @@ Please make sure to install it properly on your system before using it.

With the OpenAI service you do even get improvements for gramma and not just spelling.

## 9. Suggest
## 9. Custom Commands

You can even create extension with custom commands.
In that case, all you need to do, is to create a configuration XML that has a bootstrap file.

In that bootstrap file, just load your classes and register your Symfony commands.

```php
include_once __DIR__ . '/src/CustomCommand.php';

\PHPUnuhi\AppManager::registerExtensionCommand(new CustomCommand());
```

## 10. Suggest

* This extension, [phpunuhi-export-excel](https://github.com/TumTum/phpunuhi-export-excel), _is optional_ and enables
the export of translations into a spreadsheet file. With this functionality, all translation data can be conveniently
* This extension, [phpunuhi-export-excel](https://github.com/TumTum/phpunuhi-export-excel), _is optional_ and enables
the export of translations into a spreadsheet file. With this functionality, all translation data can be conveniently
stored and managed in a spreadsheet format. It is ideal for exporting and importing translations.
112 changes: 86 additions & 26 deletions src/AppManager.php
Original file line number Diff line number Diff line change
Expand Up @@ -24,58 +24,118 @@
use PHPUnuhi\Commands\ValidateSimilarityCommand;
use PHPUnuhi\Commands\ValidateSpellingCommand;
use PHPUnuhi\Commands\ValidateStructureCommand;
use PHPUnuhi\Exceptions\ConfigurationException;
use Symfony\Component\Console\Application;
use Symfony\Component\Console\Command\Command;

class AppManager
{
/** @var array<Command> $extensionCommands */
/**
* @var array<Command> $extensionCommands
*/
private static array $extensionCommands = [];


/**
* @throws Exception
*/
public static function run(): void
{
$application = new Application('PHPUnuhi', PHPUnuhi::getVersion());

$application->add(new AvailableServicesCommand());
$application->add(new StatusCommand());
$application->add(new ListTranslationKeysCommand());
$application->add(new ListTranslationsCommand());
// Check if configuration argument is provided
global $argv;
$configPath = self::getConfigurationPath($argv);

$application->add(new ValidateCommand());
$application->add(new ValidateAllCommand());
$application->add(new ValidateMessCommand());
$application->add(new ValidateCoverageCommand());
$application->add(new ValidateStructureCommand());
$application->add(new ValidateSpellingCommand());
$application->add(new ValidateSimilarityCommand());

$application->add(new ImportCommand());
$application->add(new ExportCommand());

$application->add(new TranslateCommand());

$application->add(new MigrateCommand());
$application->add(new FixStructureCommand());
$application->add(new FixMessCommand());
// Load bootstrap if specified in the configuration
if ($configPath !== null) {
self::loadBootstrap($configPath);
}

$application->add(new ScanUsageCommand());
$application = new Application('PHPUnuhi', PHPUnuhi::getVersion());

$application->add(new FixSpellingCommand());
// Register commands
$application->addCommands(self::getDefaultCommands());

foreach (self::$extensionCommands as $command) {
$application->add($command);
}

$application->setDefaultCommand('list');

$application->run();
}

/**
* @return Command[]
*/
private static function getDefaultCommands(): array
{
return [
new AvailableServicesCommand(),
new StatusCommand(),
new ListTranslationKeysCommand(),
new ListTranslationsCommand(),
new ValidateCommand(),
new ValidateAllCommand(),
new ValidateMessCommand(),
new ValidateCoverageCommand(),
new ValidateStructureCommand(),
new ValidateSpellingCommand(),
new ValidateSimilarityCommand(),
new ImportCommand(),
new ExportCommand(),
new TranslateCommand(),
new MigrateCommand(),
new FixStructureCommand(),
new FixMessCommand(),
new ScanUsageCommand(),
new FixSpellingCommand(),
];
}


public static function registerExtensionCommand(Command $command): void
{
self::$extensionCommands[$command->getName()] = $command;
}


/**
* @param array<mixed> $args
*/
private static function getConfigurationPath(array $args): ?string
{
foreach ($args as $arg) {
if (str_starts_with($arg, '--configuration=')) {
return str_replace('--configuration=', '', $arg);
}
}
return null;
}

/**
* Loads the bootstrap file if specified in the configuration XML.
*
* @throws Exception
*/
private static function loadBootstrap(string $configPath): void
{
if (!file_exists($configPath)) {
throw new Exception("Configuration file not found: $configPath");
}

$xml = simplexml_load_string((string)file_get_contents($configPath));
if (!$xml) {
throw new Exception("Invalid XML in configuration file: $configPath");
}

$rootConfigDir = dirname($configPath) . '/';

$bootstrap = (string)($xml->attributes()->bootstrap ?? '');
$bootstrap = (string)realpath($rootConfigDir . '/' . $bootstrap);

if (file_exists($bootstrap)) {
require_once $bootstrap;
} elseif (!file_exists($bootstrap)) {
throw new ConfigurationException('Bootstrap file not found: ' . $bootstrap);
}
}
}
5 changes: 5 additions & 0 deletions tests/svrunit/fixtures/custom-command/autoload.php
Original file line number Diff line number Diff line change
@@ -0,0 +1,5 @@
<?php

include_once __DIR__ . '/src/CustomCommand.php';

\PHPUnuhi\AppManager::registerExtensionCommand(new CustomCommand());
23 changes: 23 additions & 0 deletions tests/svrunit/fixtures/custom-command/phpunuhi.xml
Original file line number Diff line number Diff line change
@@ -0,0 +1,23 @@
<phpunuhi
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:noNamespaceSchemaLocation="../../../../schema/dev-main.xsd"
bootstrap="autoload.php"
>

<translations>

<set name="json">
<format>
<json indent="2" sort="true"/>
</format>
<locales>
<locale name="de">./de.json</locale>
<locale name="en" base="true">./en.json</locale>
<locale name="nl">./nl.json</locale>
</locales>

</set>

</translations>

</phpunuhi>
34 changes: 34 additions & 0 deletions tests/svrunit/fixtures/custom-command/src/CustomCommand.php
Original file line number Diff line number Diff line change
@@ -0,0 +1,34 @@
<?php

use PHPUnuhi\Traits\CommandTrait;
use Symfony\Component\Console\Command\Command;
use Symfony\Component\Console\Input\InputInterface;
use Symfony\Component\Console\Input\InputOption;
use Symfony\Component\Console\Output\OutputInterface;
use Symfony\Component\Console\Style\SymfonyStyle;

class CustomCommand extends Command
{
use CommandTrait;

/**
* @return void
*/
protected function configure(): void
{
$this
->setName('custom:command-xy')
->setDescription('Custom Command')
->addOption('configuration', null, InputOption::VALUE_REQUIRED, '', '');

parent::configure();
}

public function execute(InputInterface $input, OutputInterface $output): int
{
$io = new SymfonyStyle($input, $output);
$io->title('PHPUnuhi Custom Command XY');

return 0;
}
}
5 changes: 5 additions & 0 deletions tests/svrunit/tests/extensions.yml
Original file line number Diff line number Diff line change
@@ -0,0 +1,5 @@
commands:

- name: "custom:command-xy from extension is working"
command: "(($EXEC)) custom:command-xy --configuration=./tests/svrunit/fixtures/custom-command/phpunuhi.xml"
expected: "PHPUnuhi Custom Command XY"

0 comments on commit da53fa9

Please sign in to comment.