-
Notifications
You must be signed in to change notification settings - Fork 0
Feature/http api new approach #348
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
base: main
Are you sure you want to change the base?
Changes from 7 commits
001cf17
92778e1
8131fca
f02e3f2
a1b8b2b
481f9df
fc77a2c
a7eb80b
df74d4e
c219ea7
07d3919
2b7ee4c
710cf89
5891dac
c772342
544c673
b846798
5664f94
5bf799c
cdfdfb3
bcb5e57
cf63e87
dff73f0
caa5ffd
40333b6
c97f42d
0e5c409
eb198e2
ca67141
a67cd65
ad08004
c89da33
c466160
f8ebcde
b2d7c7a
03453a4
86f71d7
1095d7c
14f9eed
bde3390
c67c059
f9a03c3
1d019f5
2881291
b358f90
e051fef
f632d1e
0a8c530
e3f631b
23d4d7d
5cb4fc1
e97d98d
4dc3803
97423fb
f3e550a
49efec2
3009ae1
c2b7fda
32a87ee
9d24f14
4018274
9b7a3c9
ad2861d
0d3bcc1
ecf502a
b91a66f
584ac80
2525735
aa43277
c8191d0
d515000
22c102e
6a5b374
96e1ad5
b9c5747
ab22f12
5393d81
1b10084
8d4c69e
1d71c5c
c1d2197
b22fbe8
3d9aa4f
a9cf9ba
e05c915
82a28be
d75633e
25909c2
d8af316
154fe88
8813ec1
fba9c10
53784c3
4e94dee
e965792
fcd79f2
5959e1f
7bba0f1
048e39b
32b78fe
7cdbe98
8850461
c864495
9e5bd80
481cb98
4a9f31e
40cc67a
a751d49
bb966be
8beb160
5494522
697c98c
70d73eb
6289d7e
ff4188f
c0fe743
e06838d
26307e8
3526533
c774c90
00d3880
06a2750
1b8fe70
f051084
f60325e
9fdaafd
2a1c897
9236559
78b9ec6
579e306
6989c24
121835e
c89072c
4d49399
001d2d8
7f05397
ebdd397
aeb8568
File filter
Filter by extension
Conversations
Jump to
Diff view
Diff view
There are no files selected for viewing
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,154 @@ | ||
| <?php | ||
|
|
||
| namespace Icinga\Module\Notifications\Clicommands; | ||
|
|
||
| use FilesystemIterator; | ||
| use Icinga\Application\Icinga; | ||
| use Icinga\Cli\Command; | ||
| use Icinga\Module\Notifications\Api\OpenApiPreprocessor\AddGlobal401Response; | ||
| use Icinga\Module\Notifications\Common\PsrLogger; | ||
| use OpenApi\Generator; | ||
| use RecursiveDirectoryIterator; | ||
| use RecursiveIteratorIterator; | ||
| use RuntimeException; | ||
| use SplFileInfo; | ||
| use Throwable; | ||
|
|
||
| class OpenapiCommand extends Command | ||
| { | ||
| public function runAction(): void | ||
| { | ||
| echo "\n\n\ntest\n\n\n"; | ||
| } | ||
|
|
||
| public function generateAction(): void | ||
| { | ||
|
|
||
| /** | ||
| * CLI tool to generate an OpenAPI JSON file from PHP attributes using swagger-php. | ||
| * | ||
| * Usage: | ||
| * icingacli openapi generate \ | ||
| * --dir ./src \ | ||
| * --exclude vendor,tests \ | ||
| * --include ApiController.php,UserController.php \ | ||
| * --output ./docs/openapi.json \ | ||
| * --api-version v1 | ||
| * --oad-version 3.1.0 | ||
| */ | ||
|
|
||
| $directoryInNotifications = $this->params->get('dir', '/library/Notifications/Api/'); | ||
| $exclude = $this->params->get('exclude'); | ||
| $include = $this->params->get('include'); | ||
| $outputPath = $this->params->get('output'); | ||
| $apiVersion = $this->params->get('api-version', 'v1'); | ||
| $oadVersion = $this->params->get('oad-version', '3.1.0'); | ||
|
|
||
| $notificationsPath = Icinga::app()->getModuleManager()->getModule('notifications')->getBaseDir(); | ||
| $directory = $notificationsPath . $directoryInNotifications; | ||
|
Check failure on line 48 in application/clicommands/OpenapiCommand.php
|
||
|
|
||
| $baseDirectory = realpath($directory); | ||
| if ($baseDirectory === false || !is_dir($baseDirectory)) { | ||
| throw new RuntimeException("Invalid directory: {$directory}"); | ||
| } | ||
|
|
||
| $exclude = isset($exclude) ? array_map('trim', explode(',', $exclude)) : []; | ||
|
Check failure on line 55 in application/clicommands/OpenapiCommand.php
|
||
| $include = isset($include) ? array_map('trim', explode(',', $include)) : []; | ||
|
Check failure on line 56 in application/clicommands/OpenapiCommand.php
|
||
| $outputPath = $notificationsPath . ($outputPath ?? '/doc/api/api-' . $apiVersion . '-public.json'); | ||
|
Check failure on line 57 in application/clicommands/OpenapiCommand.php
|
||
|
|
||
| $files = $this->collectPhpFiles($baseDirectory, $exclude, $include); | ||
|
|
||
| echo "→ Scanning directory: $baseDirectory\n"; | ||
| echo "→ Found " . count($files) . " PHP files\n"; | ||
| // die; | ||
|
|
||
| $generator = new Generator(new PsrLogger()); | ||
| $generator->setVersion($oadVersion); | ||
|
Check failure on line 66 in application/clicommands/OpenapiCommand.php
|
||
| $generator->getProcessorPipeline()->add(new AddGlobal401Response()); | ||
|
|
||
| try { | ||
| $openapi = $generator->generate($files); | ||
|
|
||
| $json = $openapi->toJson( | ||
|
Check failure on line 72 in application/clicommands/OpenapiCommand.php
|
||
| JSON_UNESCAPED_SLASHES | JSON_UNESCAPED_UNICODE | JSON_INVALID_UTF8_IGNORE | JSON_PRETTY_PRINT | ||
| ); | ||
|
|
||
| $dir = dirname($outputPath); | ||
| if (!is_dir($dir)) { | ||
| mkdir($dir, 0755, true); | ||
| } | ||
|
|
||
| file_put_contents($outputPath, $json); | ||
|
|
||
| echo "✅ OpenAPI documentation written to: $outputPath\n"; | ||
| } catch (Throwable $e) { | ||
| fwrite(STDERR, "❌ Error generating OpenAPI: " . $e->getMessage() . "\n"); | ||
| exit(1); | ||
| } | ||
| } | ||
|
|
||
| /** | ||
| * Recursively scan a directory for PHP files. | ||
| */ | ||
| function collectPhpFiles(string $baseDirectory, array $exclude, array $include): array | ||
|
Check failure on line 93 in application/clicommands/OpenapiCommand.php
|
||
| { | ||
| $baseDirectory = rtrim($baseDirectory, '/') . '/'; | ||
| if (! is_dir($baseDirectory)) { | ||
| throw new RuntimeException("Directory $baseDirectory does not exist"); | ||
| } | ||
| if (! is_readable($baseDirectory)) { | ||
| throw new RuntimeException("Directory $baseDirectory is not readable"); | ||
| } | ||
|
|
||
| $files = []; | ||
| $iterator = new RecursiveIteratorIterator( | ||
| new RecursiveDirectoryIterator($baseDirectory, FilesystemIterator::SKIP_DOTS) | ||
| ); | ||
|
|
||
| // echo PHP_EOL; | ||
| // var_dump($iterator); | ||
| // echo PHP_EOL . PHP_EOL; | ||
| // die(); | ||
|
|
||
| /** @var SplFileInfo $file */ | ||
| foreach ($iterator as $file) { | ||
| if (! $file->isFile() || $file->getExtension() !== 'php') { | ||
| continue; | ||
| } | ||
|
|
||
| $path = $file->getPathname(); | ||
|
|
||
| // Exclude | ||
| if ($exclude !== [] && $this->matchesAnyPattern($path, $exclude)) { | ||
| continue; | ||
| } | ||
|
|
||
| // Include filter (if defined) | ||
| if ($include !== [] && ! $this->matchesAnyPattern($path, $include)) { | ||
| continue; | ||
| } | ||
|
|
||
| $files[] = $path; | ||
| } | ||
|
|
||
| if (empty($files)) { | ||
| throw new RuntimeException("No PHP files found in $baseDirectory"); | ||
| } | ||
|
|
||
| return $files; | ||
| } | ||
| // | ||
| function matchesAnyPattern(string $string, array $patterns): bool | ||
| { | ||
| foreach ($patterns as $pattern) { | ||
| // Escape regex special chars except for '*' | ||
| $regex = '/^' . str_replace('\*', '.*', preg_quote($pattern, '/')) . '$/'; | ||
| // echo PHP_EOL . $regex . PHP_EOL; die; | ||
| if (preg_match($regex, $string)) { | ||
| return true; | ||
| } | ||
| } | ||
|
|
||
| return false; | ||
| } | ||
| } | ||
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,31 @@ | ||
| # REST API | ||
|
|
||
| The Icinga Notifications module provides a REST API that allows you to manage notification-related resources programmatically. | ||
|
|
||
| With this API, you can: | ||
| - Manage **contacts** and **contact groups** | ||
| - Read available **notification channels** | ||
|
|
||
| This API enables easy integration with external tools, automation workflows, and configuration management systems. | ||
|
|
||
| --- | ||
|
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. |
||
|
|
||
| ## API Versioning | ||
|
|
||
| The Notifications API follows a **versioned** structure to ensure backward compatibility and predictable upgrades. | ||
|
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Before
And now
Later
Please stick to a single version, so remove Notifications here. |
||
|
|
||
| The current and first stable version is: /icingaweb2/notifications/api/v1 | ||
|
|
||
| Future versions will be accessible under corresponding paths (for example, `/api/v2`), allowing you to migrate at your own pace. | ||
|
|
||
| --- | ||
|
|
||
| ## API Description | ||
|
|
||
| The complete API reference for version `v1` is available in [`api/v1.md`](api/v1.md). | ||
|
|
||
| It contains an OpenAPI v3.1 description with detailed information about all endpoints, including: | ||
| - Request and response schemas | ||
| - Example payloads | ||
| - Authentication requirements | ||
| - Error handling | ||

There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
The Icinga Notifications moduleIcinga Notifications Web