Skip to content

Commit

Permalink
backend
Browse files Browse the repository at this point in the history
  • Loading branch information
mtvbrianking committed Jan 30, 2021
1 parent 4359d71 commit 87155b1
Show file tree
Hide file tree
Showing 7 changed files with 457 additions and 61 deletions.
6 changes: 4 additions & 2 deletions composer.json
Original file line number Diff line number Diff line change
Expand Up @@ -19,12 +19,14 @@
],
"require": {
"php": "^7.2.5|^8.0",
"illuminate/support": "^6.0|^7.0|^8.0"
"illuminate/contracts": "^6.0|^7.0|^8.0",
"illuminate/http": "^6.0|^7.0|^8.0",
"illuminate/support": "^6.0|^7.0|^8.0",
"symfony/console": "^4.3.4|^5.0"
},
"require-dev": {
"code-lts/doctum": "^5.3",
"friendsofphp/php-cs-fixer": "^2.18",
"illuminate/container": "^6.0|^7.0|^8.0",
"orchestra/testbench": "^4.0|^5.0|^6.0",
"phpunit/phpunit": "^8.0|^9.0"
},
Expand Down
42 changes: 41 additions & 1 deletion config/artisan-gui.php
Original file line number Diff line number Diff line change
@@ -1,5 +1,45 @@
<?php

return [
// ...
/*
|--------------------------------------------------------------------------
| Environment to run
|--------------------------------------------------------------------------
*/
'env' => 'local',

/*
|--------------------------------------------------------------------------
| Run only in debug mode
|--------------------------------------------------------------------------
*/
'debug' => true,

/*
|--------------------------------------------------------------------------
| Exclude hidden commands
|--------------------------------------------------------------------------
*/
'hide' => true,

/*
|--------------------------------------------------------------------------
| Commands to exclude from GUI
|--------------------------------------------------------------------------
*/
'exclude' => [
'inspire',
'serve',
'tinker',
'test',
],

/*
|--------------------------------------------------------------------------
| Default options
|--------------------------------------------------------------------------
*/
'options' => [
'--no-interaction' => true,
],
];
58 changes: 0 additions & 58 deletions readme.md
Original file line number Diff line number Diff line change
Expand Up @@ -13,61 +13,3 @@ Install via composer package manager:
```bash
composer require bmatovu/laravel-artisan-gui
```

Alternatively, generate a Github repository using the `Use this template` call to action button or the link below...

> https://github.com/mtvbrianking/laravel-artisan-gui/generate
### Own the package

Update the `composer.json` file to match your credentials.

Change the namespaces to match those you're using in `src`.

Change the type from `project` to `library`

```bash
composer dump-autoload
```

## Testing

We've defaulted to [Orchestra's testbench](https://github.com/orchestral/testbench)

```bash
composer test
```

### Code Style & Quality

We've added [StyleCI](https://styleci.io) configurations with the Laravel present to get you started.

Also added [ScrutinizerCI](https://scrutinizer-ci.com) configurations for code quality, test coverage inspection.

Locally, you can restort to [PHP-CS-Fixer](https://github.com/FriendsOfPHP/PHP-CS-Fixer).

```bash
composer cs-fix
```

### Source code documentation

You need to download [Doctum](https://github.com/code-lts/doctum) for source code documentation.

```bash
composer doc
```

To auto deploy documentation; be sure to add a [`Github token`](https://github.com/settings/tokens) for authorization.

### Sharing the package

You may share your package via [Packagist](packagist.org)

## Useful resources

- [Laravel Package Development - Blog](https://laravelpackage.com)

- [Laravel Package Development - Documentation](https://laravel.com/docs/master/packages)

- [Travis CI + GitHub Pages - Automated deployment](https://www.youtube.com/watch?v=BFpSD2eoXUk)
9 changes: 9 additions & 0 deletions routes/web.php
Original file line number Diff line number Diff line change
@@ -0,0 +1,9 @@
<?php

use Bmatovu\AristanGui\Http\CommandController;
use Illuminate\Support\Facades\Route;

Route::pattern('command', '^[a-z0-9\-\:]*$');

Route::get('/commands', [CommandController::class, '__invoke'])->name('commands');
Route::post('/commands/{command}', [CommandController::class, 'execute'])->name('commands.execute');
2 changes: 2 additions & 0 deletions src/ArtisanGuiServiceProvider.php
Original file line number Diff line number Diff line change
Expand Up @@ -18,6 +18,8 @@ public function boot()
__DIR__.'/../config/artisan-gui.php' => base_path('config/artisan-gui.php'),
], 'config');
}

$this->loadRoutesFrom(__DIR__.'/../routes/web.php');
}

/**
Expand Down
173 changes: 173 additions & 0 deletions src/Http/CommandController.php
Original file line number Diff line number Diff line change
@@ -0,0 +1,173 @@
<?php

namespace Bmatovu\AristanGui\Http;

use Bmatovu\AristanGui\Support\Commander;
use Illuminate\Contracts\Console\Kernel;
use Illuminate\Foundation\Validation\ValidatesRequests;
use Illuminate\Http\Request;
use Symfony\Component\Console\Command\Command;
use Symfony\Component\Console\Output\BufferedOutput;
use Symfony\Component\HttpKernel\Exception\NotFoundHttpException;

class CommandController
{
use ValidatesRequests;

/**
* Create a new controller instance.
*
* @param Kernel $kernel
*
* @return void
*/
public function __construct(Kernel $kernel)
{
$this->kernel = $kernel;
}

/**
* Get artisan commands.
*
* @return \Illuminate\Http\Response
*/
public function __invoke()
{
$commander = new Commander($this->kernel);

return response([
'namespaces' => $commander->getNamespaces(),
'definition' => $commander->getDefinition(),
'commands' => $commander->getCommands(),
]);
}

/**
* Execute artisan command.
*
* @param \Illuminate\Http\Request $request
*
* @throws \Symfony\Component\HttpKernel\Exception\NotFoundHttpException
*
* @return \Illuminate\Http\Response
*/
public function execute(Request $request)
{
$command = $this->resolve($request->command);

$validated = $this->validate($request, $this->rules($command));

$parameters = array_merge($validated, config('artisan.options'));

$outputBuffer = new BufferedOutput();

try {
$exitCode = $this->kernel->call($command->getName(), $parameters, $outputBuffer);
// $output = $this->kernel->output();
$output = $outputBuffer->fetch();
} catch (\Exception $exception) {
$exitCode = $exception->getCode() ?? 500;
$output = $exception->getMessage();
}

return response([
'command' => $command->getName(),
'parameters' => $this->flatten($parameters),
'exit-code' => $exitCode,
'output' => $output,
]);
}

/**
* Flatten command parameters.
*
* @param array $parameters
*
* @return string
*/
protected function flatten(array $parameters)
{
$cli_params = '';

foreach ($parameters as $name => $value) {
if (empty($value)) {
continue;
}

if (strpos($name, '--') === 0) {
if (is_bool($value)) {
$cli_params .= " {$name}";

continue;
}
}

if (is_array($value)) {
// foreach ($value as $item) {
// $cli_params .= " {$name}=\"{$item}\"";
// }

$items = implode(',', $value);
$cli_params .= " {$name}=\"{$items}\"";

continue;
}

$cli_params .= " {$name}=\"{$value}\"";
}

return $cli_params;
}

/**
* Resolve command from kernel.
*
* @param string $name Command name
*
* @throws \Symfony\Component\HttpKernel\Exception\NotFoundHttpException
*
* @return \Symfony\Component\Console\Command\Command
*/
protected function resolve($name): Command
{
$commands = $this->kernel->all();

$command = $commands[$name] ?? null;

if (! $command) {
throw new NotFoundHttpException('Unknown command.');
}

return $command;
}

/**
* Build command validation rules.
*
* @param \Symfony\Component\Console\Command\Command $command
*
* @return array
*/
protected function rules(Command $command): array
{
$rules = [];

foreach ($command->getDefinition()->getArguments() as $argument) {
$rules[$argument->getName()] = array_filter([
$argument->isRequired() ? 'required' : 'nullable',
$argument->isArray() ? 'array': '',
]);
}

foreach ($command->getDefinition()->getOptions() as $option) {
$name = $option->getName();

$rules["--{$name}"] = array_filter([
$option->isValueRequired() ? 'required' : 'nullable',
$option->isArray() ? 'array': ($option->acceptValue() ? 'string' : 'bool'),
]);
}

return $rules;
}
}
Loading

0 comments on commit 87155b1

Please sign in to comment.