PHP code example of madong / swagger

1. Go to this page and download the library: Download madong/swagger library. Choose the download type require.

2. Extract the ZIP file and open the index.php.

3. Add this code to the index.php.
    
        
<?php
require_once('vendor/autoload.php');

/* Start to develop here. Best regards https://php-download.com/ */

    

madong / swagger example snippets


use Webman\Route;
use WebmanTech\Swagger\Swagger;
use OpenApi\Annotations as OA;

Route::group('/adminapi', function () {
    // Swagger 文档路由配置
    Swagger::create()->registerRoute([
        'route_prefix'   => '/openapi',
        'register_route' => true,
        'openapi_doc'    => [
            'scan_path' => [
                base_path('app/adminapi'),
                base_path('app/schema'),  // Schema 目录
            ],
            'exclude'   => [
                // 排除不需要扫描的文件
            ],
            'modify'    => function (OA\OpenApi $openapi) {
                $openapi->info->title   = config('app.name') . ' API';
                $openapi->info->version = '1.0.0';
                $openapi->servers       = [
                    new OA\Server([
                        'url'         => '/adminapi',
                        'description' => request()->host(),
                    ]),
                ];
                
                // 配置安全认证
                if (!$openapi->components instanceof OA\Components) {
                    $openapi->components = new OA\Components([]);
                }
                $openapi->components->securitySchemes = [
                    new OA\SecurityScheme([
                        'securityScheme' => 'api_key',
                        'type'           => 'apiKey',
                        'name'           => config('madong.jwt.app.token_name', 'Authorization'),
                        'in'             => 'header',
                    ]),
                ];
            },
        ],
    ]);
});



namespace app\schema;

use madong\swagger\annotation\schema\ApiProperty;

/**
 * 用户 Schema
 */
class UserSchema
{
    #[ApiProperty(property: 'id', type: 'integer', description: '用户ID')]
    public int $id;

    #[ApiProperty(property: 'username', type: 'string', description: '用户名')]
    public string $username;

    #[ApiProperty(property: 'email', type: 'string', description: '邮箱')]
    public string $email;

    #[ApiProperty(property: 'created_at', type: 'string', format: 'date-time', description: '创建时间')]
    public string $created_at;
}



namespace app\adminapi\controller;

use madong\swagger\annotation\response\DataResponse;
use madong\swagger\attribute\AllowAnonymous;
use OpenApi\Attributes as OA;
use support\Request;

class UserController
{
    #[OA\Get(
        path: '/user/{id}',
        summary: '获取用户信息',
        tags: ['用户管理']
    )]
    #[DataResponse(
        response: 200,
        schema: UserSchema::class,
        description: '成功获取用户信息'
    )]
    #[DataResponse(
        response: 404,
        example: ['error' => '用户不存在'],
        description: '用户未找到'
    )]
    #[AllowAnonymous]
    public function getUser(Request $request, int $id)
    {
        // ...
    }
}

use madong\swagger\attribute\AllowAnonymous;

class UserController
{
    // 跳过所有认证
    #[AllowAnonymous([AllowAnonymous(   #[AllowAnonymous(ublic function register()
    {
        // ...
    }

    #[AllowAnonymous::token('仅跳过 Token 验证')]
    public function checkPermission()
    {
        // ...
    }

    #[AllowAnonymous::permission('仅跳过权限验证')]
    public function getUserInfo()
    {
        // ...
    }
}

use madong\swagger\attribute\Permission;

class UserController
{
    // 单个权限
    #[Permission('user:list')]
    public function getUserList()
    {
        // ...
    }

    // 多个权限(AND 关系,需全部满足)
    #[Permission(['user:view', 'user:detail'])]
    public function getUserDetail()
    {
        // ...
    }

    // 多个权限(OR 关系,任一满足即可)
    #[Permission(['user:admin', 'user:super'], operation: 'or')]
    public function deleteUser()
    {
        // ...
    }

    // 使用便捷静态方法
    #[Permission::create('user:create')]
    public function createUser()
    {
        // ...
    }

    #[Permission::all(['user:view', 'user:export'])]
    public function exportUsers()
    {
        // ...
    }

    #[Permission::any(['user:admin', 'user:manager', 'user:super'])]
    public function manageUser()
    {
        // ...
    }
}

namespace app\request;

use madong\swagger\attribute\ValidationRule;

class UserRequest
{
    #[ValidationRule(
        rules: '

    #[ValidationRule(
        rules: ['=> '密码确认'],
        description: '密码'
    )]
    public string $password;

    #[ValidationRule(
        rules: 'nullable|integer|min:0|max:120',
        example: 25,
        description: '年龄'
    )]
    public ?int $age;
}

use madong\swagger\annotation\response\DataResponse;
use app\schema\UserSchema;

class UserController
{
    #[DataResponse(
        response: 200,
        schema: UserSchema::class,
        description: '成功获取用户信息'
    )]
    #[DataResponse(
        response: 404,
        example: ['error' => '用户不存在'],
        description: '用户未找到'
    )]
    public function getUser(int $id)
    {
        // ...
    }
}

use madong\swagger\annotation\response\PageResponse;
use app\schema\UserListSchema;

class UserController
{
    #[PageResponse(
        response: 200,
        schema: UserListSchema::class,
        description: '成功获取用户列表'
    )]
    public function getUserList()
    {
        // ...
    }
}

use madong\swagger\annotation\response\ListResponse;

class UserController
{
    #[ListResponse(
        response: 200,
        schema: UserListSchema::class,
        description: '成功获取用户列表'
    )]
    public function getAllUsers()
    {
        // ...
    }
}

use madong\swagger\annotation\response\TreeResponse;
use app\schema\MenuSchema;

class MenuController
{
    #[TreeResponse(
        response: 200,
        schema: MenuSchema::class,
        description: '成功获取菜单树'
    )]
    public function getMenuTree()
    {
        // ...
    }
}

use madong\swagger\annotation\response\ResultResponse;

class AuthController
{
    #[ResultResponse(
        response: 200,
        jsonExample: '{"code": 0, "message": "操作成功"}',
        description: '操作成功'
    )]
    #[ResultResponse(
        response: 401,
        jsonExample: '{"code": 401, "message": "未授权"}',
        description: '认证失败'
    )]
    public function login()
    {
        // ...
    }
}

use madong\swagger\annotation\response\SimpleResponse;

class UserController
{
    #[SimpleResponse(
        response: 200,
        example: ['flag' => true],
        description: '操作成功'
    )]
    #[SimpleResponse(
        response: 422,
        example: ['error' => '验证失败'],
        description: '验证错误'
    )]
    public function updateStatus()
    {
        // ...
    }
}

use madong\swagger\annotation\operation\ApiOperation;

#[ApiOperation(
    summary: '创建用户',
    description: '创建一个新的用户账号,需要管理员权限',
    tags: ['用户管理']
)]
public function createUser()
{
    // ...
}

use madong\swagger\annotation\operation\ApiParameter;

#[ApiParameter(
    name: 'id',
    in: 'path',
    description: '用户ID',
    

use madong\swagger\annotation\operation\ApiRequestBody;
use app\request\UserRequest;

#[ApiRequestBody(
    description: '用户信息',
    

use madong\swagger\helper\AnnotationHelper;
use madong\swagger\attribute\AllowAnonymous;
use madong\swagger\attribute\Permission;

// 获取方法上的 AllowAnonymous 注解
$AllowAnonymous = AnnotationHelper::getMethodAnnotation(
    'app\adminapi\controller\UserController',
    'login',
    AllowAnonymous::class
);

if ($AllowAnonymous && $AllowAnonymous->should

// 获取方法上的指定注解实例
AnnotationHelper::getMethodAnnotation(
    string $controllerClass,  // 控制器完整类名
    string $methodName,        // 方法名
    string $annotationClass    // 注解类名
): ?object

// 获取类上的指定注解实例
AnnotationHelper::getClassAnnotation(
    string $controllerClass,
    string $annotationClass
): ?object

// 获取方法上的所有 OA 注解实例
AnnotationHelper::getMethodOaAnnotations(
    string $controllerClass,
    string $methodName
): array

// 获取类上的所有 OA 注解实例
AnnotationHelper::getClassOaAnnotations(
    string $controllerClass
): array

// 获取方法上的所有注解实例
AnnotationHelper::getAllMethodAnnotations(
    string $controllerClass,
    string $methodName
): array

// 获取类上的所有注解实例
AnnotationHelper::getAllClassAnnotations(
    string $controllerClass
): array

// 检查方法是否存在指定注解
AnnotationHelper::hasMethodAnnotation(
    string $controllerClass,
    string $methodName,
    string $annotationClass
): bool

// 检查类是否存在指定注解
AnnotationHelper::hasClassAnnotation(
    string $controllerClass,
    string $annotationClass
): bool

namespace app\adminapi\middleware;

use madong\swagger\helper\AnnotationHelper;
use madong\swagger\attribute\AllowAnonymous;
use madong\swagger\attribute\Permission;
use Webman\Http\Request;
use Webman\Http\Response;
use Webman\MiddlewareInterface;

class PermissionMiddleware implements MiddlewareInterface
{
    public function process(Request $request, callable $handler): Response
    {
        $controllerClass = $request->controller;
        $action = $request->action;

        // 检查是否跳过认证
        $AllowAnonymous = AnnotationHelper::getMethodAnnotation(
            $controllerClass,
            $action,
            AllowAnonymous::class
        );

        if ($AllowAnonymous && $AllowAnonymous->should

use madong\swagger\helper\AnnotationHelper;
use OpenApi\Attributes as OA;

class DocGenerator
{
    public function generatePath(string $controllerClass, string $methodName): array
    {
        $paths = [];

        // 获取所有 OA 注解
        $oaAnnotations = AnnotationHelper::getMethodOaAnnotations(
            $controllerClass,
            $methodName
        );

        foreach ($oaAnnotations as $annotation) {
            if ($annotation instanceof OA\Get) {
                $paths['get'] = $this->generateGetDoc($annotation);
            } elseif ($annotation instanceof OA\Post) {
                $paths['post'] = $this->generatePostDoc($annotation);
            }
            // ... 其他 HTTP 方法
        }

        return $paths;
    }
}

use madong\swagger\helper\AnnotationHelper;
use madong\swagger\attribute\Permission;
use madong\swagger\annotation\operation\ApiOperation;

class ApiMetadataCollector
{
    public function collect(string $controllerClass, string $methodName): array
    {
        $metadata = [];

        // 获取 API 操作信息
        $apiOperation = AnnotationHelper::getMethodAnnotation(
            $controllerClass,
            $methodName,
            ApiOperation::class
        );

        if ($apiOperation) {
            $metadata['summary'] = $apiOperation->summary;
            $metadata['description'] = $apiOperation->description;
        }

        // 获取认证信息
        $AllowAnonymous = AnnotationHelper::getMethodAnnotation(
            $controllerClass,
            $methodName,
            AllowAnonymous::class
        );

        $metadata['

use madong\swagger\annotation\response\DataResponse;
use app\schema\UserSchema;

#[DataResponse(
    response: 200,
    schema: UserSchema::class,
    description: '成功获取用户信息'
)]
#[DataResponse(
    response: 404,
    example: ['error' => '用户不存在'],
    description: '用户未找到'
)]
#[DataResponse(
    response: 403,
    example: ['error' => '无权访问该用户'],
    description: '权限不足'
)]
public function getUser(int $id): Response
{
    // ...
}

use madong\swagger\annotation\response\DataResponse;
use madong\swagger\attribute\AllowAnonymous;
use madong\swagger\attribute\Permission;

// 避免混用
use madong\swagger\attribute\DataResponse;  // 错误:attribute 中没有 DataResponse
use madong\swagger\annotation\auth\AllowAnonymous;  // 可用但不推荐

#[DataResponse(response: 200, schema: UserSchema::class)]
#[DataResponse(response: 404, example: ['error' => '用户不存在'])]
#[DataResponse(response: 403, example: ['error' => '无权访问'])]

// 避免定义过多不常用的响应
#[DataResponse(response: 200, schema: UserSchema::class)]
#[DataResponse(response: 400, example: ['error' => 'Bad Request'])]
#[DataResponse(response: 401, example: ['error' => 'Unauthorized'])]
#[DataResponse(response: 403, example: ['error' => 'Forbidden'])]
#[DataResponse(response: 404, example: ['error' => 'Not Found'])]
#[DataResponse(response: 500, example: ['error' => 'Server Error'])]

use madong\swagger\helper\ResponseHelper;

// 推荐:使用 ResponseHelper
#[ResponseHelper::data(UserSchema::class, [
    'description' => '成功',
    'response' => 200
])]

// 不推荐:直接实例化
#[new DataResponse(
    schema: UserSchema::class,
    description: '成功',
    response: 200
)]

use madong\swagger\attribute\Permission;

#[Permission('user:manage')]
class UserController
{
    // 所有方法都需要 user:manage 权限
}

class UserController
{
    #[Permission('user:view')]
    public function getUser()
    {
        // 只需要 user:view 权限
    }

    #[Permission('user:delete')]
    public function deleteUser()
    {
        // 需要 user:delete 权限
    }
}

use madong\swagger\helper\ExampleHelper;

// 分页示例
#[PageResponse(
    response: 200,
    schema: UserSchema::class,
    listExample: ExampleHelper::page([
        ['id' => 1, 'name' => 'admin'],
        ['id' => 2, 'name' => 'user']
    ], 100, 1, 10)
)]

// 树形示例
#[TreeResponse(
    response: 200,
    schema: MenuSchema::class,
    dataExample: ExampleHelper::tree([
        ['id' => 1, 'name' => '系统', 'parent_id' => 0],
        ['id' => 2, 'name' => '用户', 'parent_id' => 1]
    ])
)]

use core\attribute\AllowAnonymous;
use core\attribute\Permission;

class UserController
{
    #[AllowAnonymous]
    public function login()
    {
        // ...
    }

    #[Permission('user:list')]
    public function getUserList()
    {
        // ...
    }
}

use madong\swagger\attribute\AllowAnonymous;
use madong\swagger\attribute\Permission;

class UserController
{
    #[AllowAnonymous]
    public function login()
    {
        // ...
    }

    #[Permission('user:list')]
    public function getUserList()
    {
        // ...
    }
}

// 推荐
AnnotationHelper::getMethodAnnotation($class, $method, AllowAnonymous::class);

// 等价(但不推荐混用)
AnnotationHelper::getMethodAnnotation($class, $method, \madong\...\auth\AllowAnonymous::class);

   // 正确
   use madong\swagger\annotation\response\DataResponse;
   
   // 错误(不存在)
   use madong\swagger\attribute\DataResponse;
   

use madong\swagger\helper\AnnotationHelper;
use madong\swagger\attribute\AllowAnonymous;

class PermissionMiddleware
{
    public function process(Request $request, callable $handler): Response
    {
        $controller = $request->controller;
        $action = $request->action;

        $AllowAnonymous = AnnotationHelper::getMethodAnnotation(
            $controller,
            $action,
            AllowAnonymous::class
        );

        if ($AllowAnonymous && $AllowAnonymous->should

Swagger::create()->registerRoute([
    'openapi_doc' => [
        'scan_path' => [
            base_path('app/adminapi'),
        ],
        'exclude' => [
            base_path('app/adminapi/controller/test'),  // 排除测试目录
        ],
    ],
]);
bash
   composer dump-autoload