open-code-modeling/json-schema-to-php-ast

提供从JSON模式创建PhpParser节点访问器的工厂,例如值对象

0.5.4 2021-07-27 14:32 UTC

README

通过PHP AST将JSON模式编译为PHP类/值对象。

安装

$ composer require open-code-modeling/json-schema-to-php-ast --dev

使用

请参阅“tests”文件夹中的单元测试以获取全面示例。

您可以使用每个值对象工厂将PHP AST节点访问器或高级构建器API与您的值对象组合。使用此库的最简单方法是使用ValueObjectFactory

假设您有以下JSON模式

{
    "$schema": "https://json-schema.fullstack.org.cn/draft-07/schema#",
    "definitions": {
        "address": {
            "type": "object",
            "properties": {
                "street_address": {
                    "type": "string"
                },
                "city": {
                    "type": ["string", "null"]
                },
                "federal_state": {
                    "$ref": "#/definitions/state"
                }
            },
            "required": [
                "street_address",
                "city",
                "federal_state"
            ]
        },
        "state": {
            "type": "string",
            "enum": ["NY", "DC"]
        }
    },
    "type": "object",
    "properties": {
        "billing_address": {
            "$ref": "#/definitions/address"
        },
        "shipping_addresses": {
            "type": "array",
            "items": {
                "$ref": "#/definitions/address"
            }
        }
    },
    "required": [
        "billing_address"
    ]
}

然后您可以使用ValueObjectFactory生成以下类的PHP代码

  • 订单
  • 配送地址
  • 地址
  • 街道地址
  • 城市
<?php

use OpenCodeModeling\CodeAst\Builder\FileCollection;
use OpenCodeModeling\CodeAst\Package\ClassInfoList;
use OpenCodeModeling\CodeAst\Package\Psr4Info;
use OpenCodeModeling\Filter\FilterFactory;
use OpenCodeModeling\JsonSchemaToPhp\Type\Type;
use OpenCodeModeling\JsonSchemaToPhpAst\ValueObjectFactory;

$parser = (new PhpParser\ParserFactory())->create(PhpParser\ParserFactory::ONLY_PHP7);
$printer = new PhpParser\PrettyPrinter\Standard(['shortArraySyntax' => true]);

// configure your Composer info
// FilterFactory of library open-code-modeling/php-filter is used for sake of brevity
$classInfoList = new ClassInfoList(
    ...Psr4Info::fromComposer(
        'src/',
        file_get_contents('composer.json'),
        FilterFactory::directoryToNamespaceFilter(),
        FilterFactory::namespaceToDirectoryFilter(),
    )
);

$valueObjectFactory = new ValueObjectFactory(
    $classInfoList,
    $parser,
    $printer,
    true,
    FilterFactory::classNameFilter(),
    FilterFactory::propertyNameFilter(),
    FilterFactory::methodNameFilter(),
    FilterFactory::constantNameFilter(),
    FilterFactory::constantValueFilter()
);

// $json contains the json string from above
$decodedJson = \json_decode($json, true, 512, \JSON_BIGINT_AS_STRING | \JSON_THROW_ON_ERROR);

$typeSet = Type::fromDefinition($decodedJson);
$srcFolder = 'tmp/';

$fileCollection = FileCollection::emptyList();
$classBuilder = ClassBuilder::fromScratch('Order', 'YourNamespaceFromComposer')->setFinal(true);

$valueObjectFactory->generateClasses($classBuilder, $fileCollection, $typeSet, $srcFolder);

// $fileCollection contains 6 classes

// now let's add constants and getter methods of properties for non value objects
$valueObjectFactory->addGetterMethodsForProperties($fileCollection, true);
$valueObjectFactory->addClassConstantsForProperties($fileCollection);

// generate PHP code
$files = $valueObjectFactory->generateFiles($fileCollection);

foreach ($files as $filename => $code) {
    // store PHP code to filesystem
}