WIP
This commit is contained in:
1
.gitignore
vendored
1
.gitignore
vendored
@@ -2,6 +2,7 @@
|
||||
/.vscode
|
||||
/vendor
|
||||
/nbproject
|
||||
/tmp
|
||||
|
||||
.phpunit.result.cache
|
||||
.phpunit.cache
|
||||
|
||||
@@ -12,7 +12,7 @@
|
||||
],
|
||||
"keywords": ["postman", "collection", "converter", "http", "wget", "curl", "api", "convert"],
|
||||
"require": {
|
||||
"php": "^8.2",
|
||||
"php": "^8.4",
|
||||
"ext-json": "*",
|
||||
"ext-mbstring": "*",
|
||||
"ext-readline": "*"
|
||||
@@ -32,6 +32,6 @@
|
||||
"sort-packages": true
|
||||
},
|
||||
"require-dev": {
|
||||
"phpunit/phpunit": "^10.3"
|
||||
"phpunit/phpunit": "^12.5"
|
||||
}
|
||||
}
|
||||
|
||||
734
composer.lock
generated
734
composer.lock
generated
File diff suppressed because it is too large
Load Diff
@@ -7,7 +7,7 @@ use PmConverter\Handler;
|
||||
const EOL = PHP_EOL;
|
||||
const DS = DIRECTORY_SEPARATOR;
|
||||
|
||||
const PM_VERSION = '1.7';
|
||||
const PM_VERSION = '1.8';
|
||||
|
||||
$paths = [
|
||||
__DIR__ . '/../../autoload.php',
|
||||
|
||||
10
pm-convert-settings.json
Normal file
10
pm-convert-settings.json
Normal file
@@ -0,0 +1,10 @@
|
||||
{
|
||||
"directories": [
|
||||
"tmp"
|
||||
],
|
||||
"output": "tmp/output",
|
||||
"preserveOutput": false,
|
||||
"formats": [
|
||||
"opencollection"
|
||||
]
|
||||
}
|
||||
@@ -18,7 +18,7 @@ class ArgumentParser
|
||||
/**
|
||||
* @var array Parsed and ready to use
|
||||
*/
|
||||
protected array $parsed = [];
|
||||
protected ?array $parsed = null;
|
||||
|
||||
/**
|
||||
* Constructor
|
||||
@@ -103,6 +103,11 @@ class ArgumentParser
|
||||
$this->parsed[AN::Formats][] = ConvertFormat::Wget;
|
||||
break;
|
||||
|
||||
case '--openc':
|
||||
case '--opencollection':
|
||||
$this->parsed[AN::Formats][] = ConvertFormat::OpenCollection;
|
||||
break;
|
||||
|
||||
case '--v2.0':
|
||||
$this->parsed[AN::Formats][] = ConvertFormat::Postman20;
|
||||
break;
|
||||
@@ -163,7 +168,7 @@ class ArgumentParser
|
||||
}
|
||||
}
|
||||
|
||||
return $this->parsed;
|
||||
return $this->parsed ?? [];
|
||||
}
|
||||
|
||||
/**
|
||||
|
||||
@@ -118,7 +118,7 @@ class Collection implements Stringable
|
||||
throw new Exception("cannot read file: $filepath");
|
||||
}
|
||||
|
||||
$json = json_decode($content, true);
|
||||
$json = json_decode($content, true, flags: JSON_THROW_ON_ERROR);
|
||||
$schema = $json['info']['schema'] ?? '';
|
||||
|
||||
if (str_ends_with($schema, 'v2.0.0/collection.json')) {
|
||||
|
||||
@@ -7,6 +7,7 @@ namespace PmConverter\Converters;
|
||||
|
||||
use PmConverter\Converters\Curl\CurlConverter;
|
||||
use PmConverter\Converters\Http\HttpConverter;
|
||||
use PmConverter\Converters\OpenCollection\OpenCollectionConverter;
|
||||
use PmConverter\Converters\Postman20\Postman20Converter;
|
||||
use PmConverter\Converters\Postman21\Postman21Converter;
|
||||
use PmConverter\Converters\Wget\WgetConverter;
|
||||
@@ -16,6 +17,7 @@ enum ConvertFormat: string
|
||||
case Http = HttpConverter::class;
|
||||
case Curl = CurlConverter::class;
|
||||
case Wget = WgetConverter::class;
|
||||
case OpenCollection = OpenCollectionConverter::class;
|
||||
case Postman20 = Postman20Converter::class;
|
||||
case Postman21 = Postman21Converter::class;
|
||||
|
||||
@@ -25,6 +27,7 @@ enum ConvertFormat: string
|
||||
'http' => ConvertFormat::Http,
|
||||
'curl' => ConvertFormat::Curl,
|
||||
'wget' => ConvertFormat::Wget,
|
||||
'opencollection' => ConvertFormat::OpenCollection,
|
||||
'v2.0' => ConvertFormat::Postman20,
|
||||
'v2.1' => ConvertFormat::Postman21,
|
||||
};
|
||||
@@ -36,6 +39,7 @@ enum ConvertFormat: string
|
||||
ConvertFormat::Http => 'http',
|
||||
ConvertFormat::Curl => 'curl',
|
||||
ConvertFormat::Wget => 'wget',
|
||||
ConvertFormat::OpenCollection => 'opencollection',
|
||||
ConvertFormat::Postman20 => 'v2.0',
|
||||
ConvertFormat::Postman21 => 'v2.1',
|
||||
};
|
||||
|
||||
86
src/Converters/OpenCollection/OpenCollectionConverter.php
Normal file
86
src/Converters/OpenCollection/OpenCollectionConverter.php
Normal file
@@ -0,0 +1,86 @@
|
||||
<?php
|
||||
|
||||
declare(strict_types=1);
|
||||
|
||||
namespace PmConverter\Converters\OpenCollection;
|
||||
|
||||
use PmConverter\Collection;
|
||||
use PmConverter\Converters\Abstract\AbstractConverter;
|
||||
use PmConverter\FileSystem;
|
||||
|
||||
class OpenCollectionConverter extends AbstractConverter
|
||||
{
|
||||
protected const FILE_EXT = 'yml';
|
||||
|
||||
protected const OUTPUT_DIR = 'opencollection';
|
||||
|
||||
protected const REQUEST_CLASS = OpenCollectionRequest::class;
|
||||
|
||||
/**
|
||||
* @inheritDoc
|
||||
*/
|
||||
public function convert(Collection $collection): static
|
||||
{
|
||||
$this->collection = $collection;
|
||||
$this->outputPath = FileSystem::makeDir($this->outputPath);
|
||||
$this->setCollectionVars();
|
||||
|
||||
// Write main collection file
|
||||
$this->writeCollectionFile($collection);
|
||||
|
||||
foreach ($collection->iterate() as $path => $item) {
|
||||
$request = $this->makeRequest($item);
|
||||
$this->writeRequest($request, $path);
|
||||
}
|
||||
return $this;
|
||||
}
|
||||
|
||||
/**
|
||||
* Writes main OpenCollection collection file
|
||||
*
|
||||
* @param Collection $collection
|
||||
* @return void
|
||||
*/
|
||||
protected function writeCollectionFile(Collection $collection): void
|
||||
{
|
||||
$filepath = sprintf('%s%scollection.%s', $this->outputPath, DS, static::FILE_EXT);
|
||||
$content = $this->generateCollectionContent($collection);
|
||||
file_put_contents($filepath, $content);
|
||||
}
|
||||
|
||||
/**
|
||||
* Generates collection YAML content
|
||||
*
|
||||
* @param Collection $collection
|
||||
* @return string
|
||||
*/
|
||||
protected function generateCollectionContent(Collection $collection): string
|
||||
{
|
||||
$output = [
|
||||
'name: ' . ($collection->name ?? 'Untitled Collection'),
|
||||
'type: collection',
|
||||
'',
|
||||
];
|
||||
|
||||
if (!empty($collection->info?->description)) {
|
||||
$output[] = 'description: |';
|
||||
$output[] = ' ' . str_replace("\n", "\n ", $collection->info->description);
|
||||
$output[] = '';
|
||||
}
|
||||
|
||||
$output[] = 'version: 1';
|
||||
$output[] = '';
|
||||
$output[] = 'baseVars: []';
|
||||
$output[] = '';
|
||||
$output[] = 'environments: []';
|
||||
$output[] = '';
|
||||
$output[] = 'requests:';
|
||||
|
||||
foreach ($collection->iterate() as $path => $item) {
|
||||
$requestRef = str_replace(DS, '/', $path . '/' . $item->name);
|
||||
$output[] = ' - $ref: ./' . $requestRef . '.yml';
|
||||
}
|
||||
|
||||
return implode("\n", $output);
|
||||
}
|
||||
}
|
||||
112
src/Converters/OpenCollection/OpenCollectionRequest.php
Normal file
112
src/Converters/OpenCollection/OpenCollectionRequest.php
Normal file
@@ -0,0 +1,112 @@
|
||||
<?php
|
||||
|
||||
declare(strict_types=1);
|
||||
|
||||
namespace PmConverter\Converters\OpenCollection;
|
||||
|
||||
use PmConverter\Converters\Abstract\AbstractRequest;
|
||||
use PmConverter\Exceptions\EmptyHttpVerbException;
|
||||
|
||||
/**
|
||||
* Class to determine file content with OpenCollection format
|
||||
*/
|
||||
class OpenCollectionRequest extends AbstractRequest
|
||||
{
|
||||
/**
|
||||
* @inheritDoc
|
||||
*/
|
||||
protected function prepareDescription(): array
|
||||
{
|
||||
return empty($this->description)
|
||||
? []
|
||||
: ['description: |', ' ' . str_replace("\n", "\n ", $this->description), ''];
|
||||
}
|
||||
|
||||
/**
|
||||
* @inheritDoc
|
||||
* @throws EmptyHttpVerbException
|
||||
*/
|
||||
protected function prepareHeaders(): array
|
||||
{
|
||||
$output = ['headers:'];
|
||||
foreach ($this->headers as $name => $data) {
|
||||
$prefix = $data['disabled'] ? '# ' : '';
|
||||
$output[] = sprintf('%s %s: %s', $prefix, $name, $data['value']);
|
||||
}
|
||||
return $output;
|
||||
}
|
||||
|
||||
/**
|
||||
* @inheritDoc
|
||||
*/
|
||||
protected function prepareBody(): array
|
||||
{
|
||||
$output = ['body:'];
|
||||
|
||||
switch ($this->getBodymode()) {
|
||||
case 'formdata':
|
||||
$output[] = ' type: formdata';
|
||||
$output[] = ' files:';
|
||||
foreach ($this->body as $key => $data) {
|
||||
$disabled = $data['disabled'] ?? false;
|
||||
$prefix = $disabled ? '# ' : ' ';
|
||||
if ($data['type'] === 'file') {
|
||||
$output[] = sprintf('%s- name: %s', $prefix, $key);
|
||||
$output[] = sprintf('%s type: file', $prefix);
|
||||
$output[] = sprintf('%s value: %s', $prefix, $data['value']);
|
||||
} else {
|
||||
$output[] = sprintf('%s- name: %s', $prefix, $key);
|
||||
$output[] = sprintf('%s type: text', $prefix);
|
||||
$output[] = sprintf('%s value: %s', $prefix, $data['value']);
|
||||
}
|
||||
}
|
||||
break;
|
||||
default:
|
||||
$output[] = ' type: raw';
|
||||
if (!empty($this->body)) {
|
||||
$output[] = ' content: |';
|
||||
$bodyContent = is_string($this->body) ? $this->body : json_encode($this->body, JSON_PRETTY_PRINT);
|
||||
foreach (explode("\n", $bodyContent) as $line) {
|
||||
$output[] = ' ' . $line;
|
||||
}
|
||||
}
|
||||
break;
|
||||
}
|
||||
|
||||
return $output;
|
||||
}
|
||||
|
||||
/**
|
||||
* @inheritDoc
|
||||
* @throws EmptyHttpVerbException
|
||||
*/
|
||||
public function __toString(): string
|
||||
{
|
||||
$output = [
|
||||
'name: ' . $this->getName(),
|
||||
'type: request',
|
||||
'',
|
||||
];
|
||||
|
||||
$output[] = 'method: ' . strtolower($this->getVerb());
|
||||
$output[] = '';
|
||||
|
||||
$url = $this->getRawUrl();
|
||||
$output[] = 'url: ' . $url;
|
||||
$output[] = '';
|
||||
|
||||
$output = array_merge($output, $this->prepareDescription());
|
||||
|
||||
if (!empty($this->headers)) {
|
||||
$output = array_merge($output, $this->prepareHeaders());
|
||||
$output[] = '';
|
||||
}
|
||||
|
||||
if ($this->verb !== 'GET' && !empty($this->body)) {
|
||||
$output = array_merge($output, $this->prepareBody());
|
||||
$output[] = '';
|
||||
}
|
||||
|
||||
return implode("\n", $output);
|
||||
}
|
||||
}
|
||||
@@ -150,6 +150,7 @@ class Handler
|
||||
"\t--http - generate raw *.http files (default)",
|
||||
"\t--curl - generate shell scripts with curl command",
|
||||
"\t--wget - generate shell scripts with wget command",
|
||||
"\t--opencollection - generate OpenCollection YAML files",
|
||||
"\t--v2.0 - convert from Postman Collection Schema v2.1 into v2.0",
|
||||
"\t--v2.1 - convert from Postman Collection Schema v2.0 into v2.1",
|
||||
"\t-a, --all - convert to all of formats listed above",
|
||||
|
||||
@@ -82,18 +82,9 @@ class Settings
|
||||
}
|
||||
|
||||
$filePath = trim($filePath);
|
||||
|
||||
if (!file_exists($filePath)) {
|
||||
throw new Exception("file does not exist: $filePath");
|
||||
}
|
||||
|
||||
if (!is_file($filePath)) {
|
||||
throw new Exception("not a file: $filePath");
|
||||
}
|
||||
|
||||
if (!is_readable($filePath)) {
|
||||
throw new Exception("file is not readable: $filePath");
|
||||
}
|
||||
file_exists($filePath) || throw new Exception("file does not exist: $filePath");
|
||||
is_file($filePath) || throw new Exception("not a file: $filePath");
|
||||
is_readable($filePath) || throw new Exception("file is not readable: $filePath");
|
||||
|
||||
$content = file_get_contents($filePath);
|
||||
$settings = json_decode($content ?: '{}', true, JSON_THROW_ON_ERROR);
|
||||
|
||||
Reference in New Issue
Block a user