sudiptochoudhury / php-api-client-forge
在PHP中创建RESTful API客户端
Requires
- php: >=7.0.0
- ext-json: *
- doctrine/inflector: ^1.3|^2.0
- guzzlehttp/guzzle-services: ^1.1
- monolog/monolog: ^1.12|^2.3.5|^3.5.0
Requires (Dev)
- mockery/mockery: ^1.1.0
- phpunit/phpunit: ^7.2.0
This package is auto-updated.
Last update: 2024-09-11 09:22:50 UTC
README
使用最少的代码从Postman集合数据(或其他来源)在PHP中创建RESTful API客户端
php-api-client-forge
- 从Postman集合数据(或其他来源)创建RESTful API客户端类
- 自动生成class
@method
文档用于phpDoc - 自动生成Markdown API文档
从Postman导出的JSON导入API定义到与Guzzle\Description格式兼容的JSON或传递一个GuzzleHttp\Command\Guzzle\Description
对象,您的API类即可使用。
作为奖励,您还将获得一个自动生成的Markdown格式的API文档。此外,您将获得一个包含
@method
声明的PHP文件,用于phpDoc类文档。
此软件包需要作为父软件包使用。通过扩展Client
类来创建您自己的API类。
此软件包专门设计用于导入以JSON格式导出的Postman集合(集合v2.1 - Schema)。
基础知识
<?php namespace My\Namespace\ApiProvider; use SudiptoChoudhury\Support\Forge\Api\Client as ApiForge; class Api extends ApiForge { protected $DEFAULT_API_JSON_PATH = './config/GuzzleDescription.json'; protected $DEFAULTS = [ 'AuthToken' => 'xxxxxxxxxxxxxxxxxxxxxxxxxx', 'ClientID' => 'xxxxxxxxxxxxxxx', 'client' => [ 'base_uri' => 'https://api.provider.com/api/v1/', 'verify' => false, 'headers' => [ 'Authorization' => 'authtoken {{AuthToken}}', 'X-clientID' => "{{ClientID}}", ], ], ]; }
应该就是这样。没有其他需要。所有API端点都将智能转换为该类的函数。例如,如果您有一个端点[GET]/products
,您将获得一个getProducts
函数。这里有一些更多示例
尽可能使单复数一致。
可能会出现这种情况,即API端点结构相同,但传递给它的数据决定了完全不同的操作。理想情况下,这种情况不应发生,但并非所有API端点都是理想创建的。因此,像
[get]/products?filter_by=active
这样的端点以及另一个端点[get]/products
将具有相同的名称。为了保留两个端点,默认行为是在重复名称前添加一个_
。但是,您可以添加过滤器或钩子,将重复的名称完全更改为其他名称。
安装
要求
- PHP 7.0+的任何版本都可以
使用Composer安装
您可以通过将以下行添加到composer.json文件中的require
块(将dev-master替换为最新稳定版本)来通过Composer安装库:
"sudiptochoudhury/php-api-client-forge": "dev-master"
或运行以下命令
composer require sudiptochoudhury/php-api-client-forge
导入Postman JSON
使用COllecton v2.1格式导出您的Postman集合。它将以JSON格式导出。为文件命名,例如postman.json
,并将其保存在项目的文件夹中。
接下来,扩展Import
类(推荐)或直接使用。
通过扩展Import
类
<?php namespace My\Namespace\ApiProvider; use SudiptoChoudhury\Support\Forge\Api\Import as ParentImport; /** * Class Import * * @package Pour\Package\Name */ class Import extends ParentImport { protected $DEFAULT_API_JSON_PATH = './config/GuzzleDescription.json'; protected $DEFAULT_SOURCE_JSON_PATH = './config/postman.json'; }
您已经准备好导入。就是这样(尽管有许多可配置选项和钩子……我们很快就会谈到这些)。
现在,让我们将导入到代码库的另一个部分。
<?php use My\Namespace\ApiProvider\Import; ... new (Import())->writeDefinition(); ...
完成!
直接使用父类
这甚至更简单(尽管如此)
<?php use SudiptoChoudhury\Support\Forge\Api\Import; ... new (Import([ './config/postman.json' ]))->writeDefinition( './config/GuzzleDescription.json'); ...
更简单,对吧!
您将找到一个新的.json
文件、一个新的.md
文件和一个新的.php
文件,这些文件将有助于您在API项目中取得成功。
.json
文件显然基于创建GuzzleHttp\Command\Guzzle\Description
对象所需的数据结构。
.php
文件包含phpDoc @method
定义,可能看起来像这样
<?php /** * @method array getHostedpage(array $parameters) Getting the details of a particular hosted page * @method array getHostedpages() Listing all the hostedpages
您可以将方法定义部分复制到从Client
类扩展的API类中。
.md
文件是一个包含API函数详细信息、等效端点、参数、参数的默认值(如果有定义)和描述的Markdown文件——所有这些都是从Postman JSON文件中派生出来的。
然而,我建议您使用扩展选项,因为您将获得大量选项来在将Postman数据转换为Guzzle Description的过程中挂钩到父代码的各个部分。您可能想要添加默认值或更改名称、更改描述或跳过一些项目。所有这些都可以通过覆盖Import父类的函数和定义自定义过滤器函数来完成。
什么是自定义过滤器函数?!!!
好的,让我们举一个例子。假设您看到您想要更改[get]/products
的重复函数名称,正如我在上一节中提到的示例。默认情况下,重复名称将被设置为_getProducts
(还记得吗?默认情况下,在名称前添加一个_
)。
现在,在您的扩展Import
类中,只需定义此内容
<?php /** This is a filter * @param $apiFunctionName * @param array $helperData * @return string */ public function filterFinalName($apiFunctionName, $helperData = []) { if ($apiFunctionName === '_getProducts') { $apiFunctionName = 'getActiveProducts'; } return $apiFunctionName; }
这是一个过滤器函数。名称必须以filter
开头,然后是过滤器名称,然后可以可选地添加一个_
和任何您想要的后续内容,以防您想为同一过滤器定义多个函数(如filterFinalName_xxx
或filterFinalName_001
)。
每个过滤器函数都将接收要修改的第一个参数的值。可选的第二个参数将是一个辅助数据项的关联数组,这些数据项可能有助于确定如何应用过滤器的逻辑。有时它也可能是构建文档布局的数据源。例如,Markdown API表是通过默认过滤器生成的。您可以覆盖它以以自己的方式生成API表。也许您不喜欢表格结构,您可以设计自己的结构。天高任鸟飞。此外,还有很多过滤器专门用于创建完整的Markdown文档,包括标题、菜单、描述、表格、页眉、页脚、安装、甚至捐赠和联系方式。只需点击所需的布局过滤器,并填写您自己的内容。
下表提供了所有过滤器的详细信息。
但在那之前,您也可以通过完全覆盖父类的方法来实现类似的功能。例如,可以通过覆盖
readApiName
方法来扩展或替换现有的逻辑,以检测函数名,并使用您自己的逻辑。然而,过滤器可以帮助您以更细粒度的方式更改事物。您可以为单个要覆盖的函数应用多达10个过滤器,您可能只需要使用其中一个过滤器,而不是编写一大堆覆盖代码。当然,选择权在您手中。