mcp-swagger-server/docs/swagger2openapi-integration...

405 lines
13 KiB
Markdown
Raw Blame History

This file contains ambiguous Unicode characters

This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

# Swagger2OpenAPI 集成实现方案
## 1. swagger2openapi 包介绍
### 1.1 包的作用
`swagger2openapi` 是一个专门用于将 Swagger 2.0 (OpenAPI 2.0) 规范转换为 OpenAPI 3.0.x 规范的 Node.js 包。它具有以下主要功能:
- **自动转换**:将 Swagger 2.0 规范自动转换为 OpenAPI 3.0.x 格式
- **引用保护**:默认保留几乎所有的 `$ref` JSON 引用,不会解引用所有项目
- **模式转换**:自动"修复"不兼容的 Swagger 2.0 模式问题
- **验证功能**:内置 OpenAPI 3.0.x 验证功能
- **多种输入源**支持从文件、URL、字符串等多种方式加载规范
- **规范扩展**:支持有限的现实世界规范扩展
### 1.2 核心特性
- **引用保护**:保持 `$ref` 引用而不是完全解引用
- **错误修复**自动修复小错误patch 模式)
- **灵活配置**:丰富的配置选项
- **多格式支持**:支持 JSON 和 YAML 格式
- **高性能**:经过 74,426 个真实世界 Swagger 2.0 定义的测试
## 2. 在 mcp-swagger-parser 中的应用场景
### 2.1 当前痛点
- 许多传统 API 仍然使用 Swagger 2.0 格式
- 现有的 `@apidevtools/swagger-parser` 主要针对 OpenAPI 3.0+
- 需要手动处理 Swagger 2.0 到 OpenAPI 3.0 的转换
### 2.2 集成收益
- **自动兼容**:无缝支持 Swagger 2.0 规范
- **透明转换**:用户无需关心底层版本转换
- **减少错误**:自动修复常见的 Swagger 2.0 问题
- **提升体验**:统一的 API 接口处理两种格式
## 3. 技术实现方案
### 3.1 架构设计
```
┌─────────────────────────────────────────────────────────────┐
│ OpenAPIParser │
├─────────────────────────────────────────────────────────────┤
│ ┌─────────────────┐ ┌─────────────────┐ ┌─────────────────┐ │
│ │ URL Parser │ │ File Parser │ │ Text Parser │ │
│ └─────────────────┘ └─────────────────┘ └─────────────────┘ │
├─────────────────────────────────────────────────────────────┤
│ ┌─────────────────────────────────────────────────────────┐ │
│ │ Version Detection & Conversion │ │
│ │ ┌─────────────────┐ ┌─────────────────────────────┐ │ │
│ │ │ Swagger 2.0 │ │ OpenAPI 3.0+ │ │ │
│ │ │ Detection │ │ Direct Parse │ │ │
│ │ └─────────────────┘ └─────────────────────────────┘ │ │
│ │ │ │ │ │
│ │ ▼ │ │ │
│ │ ┌─────────────────┐ │ │ │
│ │ │ swagger2openapi │ │ │ │
│ │ │ Conversion │ │ │ │
│ │ └─────────────────┘ │ │ │
│ │ │ │ │ │
│ │ └──────────────────────────┘ │ │
│ └─────────────────────────────────────────────────────────┘ │
├─────────────────────────────────────────────────────────────┤
│ ┌─────────────────┐ ┌─────────────────┐ ┌─────────────────┐ │
│ │ Validator │ │ Normalizer │ │ Transformer │ │
│ └─────────────────┘ └─────────────────┘ └─────────────────┘ │
└─────────────────────────────────────────────────────────────┘
```
### 3.2 核心组件实现
#### 3.2.1 版本检测器 (VersionDetector)
```typescript
export class VersionDetector {
static detect(spec: any): 'swagger2' | 'openapi3' | 'unknown' {
if (spec.swagger && spec.swagger.startsWith('2.')) {
return 'swagger2';
}
if (spec.openapi && spec.openapi.startsWith('3.')) {
return 'openapi3';
}
return 'unknown';
}
}
```
#### 3.2.2 Swagger2OpenAPI 转换器 (Swagger2OpenAPIConverter)
```typescript
import * as swagger2openapi from 'swagger2openapi';
export class Swagger2OpenAPIConverter {
private options: swagger2openapi.Options;
constructor(options: ConversionOptions = {}) {
this.options = {
patch: true, // 修复小错误
warnOnly: false, // 遇到错误时抛出异常
resolveInternal: false, // 不解析内部引用
...options
};
}
async convert(swagger2Spec: any): Promise<OpenAPISpec> {
try {
const result = await swagger2openapi.convertObj(swagger2Spec, this.options);
return result.openapi;
} catch (error) {
throw new Swagger2OpenAPIConversionError(
`Failed to convert Swagger 2.0 to OpenAPI 3.0: ${error.message}`,
error
);
}
}
}
```
#### 3.2.3 增强的解析器 (EnhancedParser)
```typescript
export class EnhancedParser extends OpenAPIParser {
private converter: Swagger2OpenAPIConverter;
constructor(config: ParserConfig = {}) {
super(config);
this.converter = new Swagger2OpenAPIConverter({
patch: config.autoFix !== false,
warnOnly: !config.strictMode
});
}
protected async processSpec(
spec: any,
metadata: Partial<ParseResult['metadata']>
): Promise<ParseResult> {
// 检测版本
const version = VersionDetector.detect(spec);
// 如果是 Swagger 2.0,先转换为 OpenAPI 3.0
if (version === 'swagger2') {
console.log('检测到 Swagger 2.0 规范,正在转换为 OpenAPI 3.0...');
spec = await this.converter.convert(spec);
// 更新元数据
metadata.conversionPerformed = true;
metadata.originalVersion = 'swagger2';
metadata.targetVersion = 'openapi3';
}
// 调用父类处理逻辑
return super.processSpec(spec, metadata);
}
}
```
### 3.3 配置选项扩展
#### 3.3.1 新增配置接口
```typescript
export interface EnhancedParserConfig extends ParserConfig {
// Swagger 2.0 转换选项
swagger2Options?: {
patch?: boolean; // 是否修复小错误
warnOnly?: boolean; // 是否仅警告而不抛出异常
resolveInternal?: boolean; // 是否解析内部引用
targetVersion?: string; // 目标 OpenAPI 版本
preserveRefs?: boolean; // 是否保留引用
};
// 自动检测和转换
autoConvert?: boolean; // 是否自动转换 Swagger 2.0
autoFix?: boolean; // 是否自动修复错误
}
```
#### 3.3.2 默认配置
```typescript
export const ENHANCED_DEFAULT_CONFIG: Required<EnhancedParserConfig> = {
...DEFAULT_PARSER_CONFIG,
swagger2Options: {
patch: true,
warnOnly: false,
resolveInternal: false,
targetVersion: '3.0.0',
preserveRefs: true
},
autoConvert: true,
autoFix: true
};
```
### 3.4 错误处理增强
#### 3.4.1 新增错误类型
```typescript
export class Swagger2OpenAPIConversionError extends OpenAPIParseError {
constructor(
message: string,
public originalError?: Error,
public conversionOptions?: any
) {
super(message, ERROR_CODES.CONVERSION_ERROR);
this.name = 'Swagger2OpenAPIConversionError';
}
}
export class UnsupportedVersionError extends OpenAPIParseError {
constructor(version: string) {
super(
`Unsupported API specification version: ${version}`,
ERROR_CODES.UNSUPPORTED_VERSION
);
this.name = 'UnsupportedVersionError';
}
}
```
#### 3.4.2 错误码扩展
```typescript
export const ERROR_CODES = {
...existingErrorCodes,
CONVERSION_ERROR: 'CONVERSION_ERROR',
UNSUPPORTED_VERSION: 'UNSUPPORTED_VERSION',
VERSION_DETECTION_FAILED: 'VERSION_DETECTION_FAILED'
};
```
### 3.5 类型定义增强
#### 3.5.1 元数据扩展
```typescript
export interface EnhancedParseMetadata extends ParseMetadata {
conversionPerformed?: boolean;
originalVersion?: 'swagger2' | 'openapi3';
targetVersion?: string;
conversionDuration?: number;
patchesApplied?: number;
}
```
#### 3.5.2 解析结果扩展
```typescript
export interface EnhancedParseResult extends ParseResult {
metadata: EnhancedParseMetadata;
conversionWarnings?: string[];
}
```
## 4. 实现步骤
### 4.1 Phase 1: 基础集成 (Week 1)
1. **安装依赖**
```bash
npm install swagger2openapi @types/swagger2openapi
```
2. **创建版本检测器**
- 实现 `VersionDetector`
- 添加版本检测逻辑
- 编写单元测试
3. **创建转换器**
- 实现 `Swagger2OpenAPIConverter`
- 配置转换选项
- 处理转换错误
### 4.2 Phase 2: 解析器增强 (Week 2)
1. **增强主解析器**
- 修改 `OpenAPIParser`
- 集成版本检测和转换逻辑
- 更新配置接口
2. **错误处理完善**
- 添加新的错误类型
- 完善错误消息和堆栈跟踪
- 添加错误恢复机制
### 4.3 Phase 3: 功能完善 (Week 3)
1. **配置选项扩展**
- 扩展配置接口
- 实现配置验证
- 添加配置文档
2. **元数据和日志增强**
- 扩展元数据信息
- 添加转换过程日志
- 实现性能监控
### 4.4 Phase 4: 测试和优化 (Week 4)
1. **全面测试**
- 单元测试覆盖
- 集成测试
- 性能测试
2. **文档和示例**
- 更新 API 文档
- 添加使用示例
- 编写迁移指南
## 5. 使用示例
### 5.1 基本使用
```typescript
import { parseAndTransform } from 'mcp-swagger-parser';
// 自动检测和转换 Swagger 2.0
const tools = await parseAndTransform('swagger2-api.json', {
parserConfig: {
autoConvert: true,
swagger2Options: {
patch: true,
warnOnly: false
}
}
});
```
### 5.2 高级配置
```typescript
const parser = new OpenAPIParser({
autoConvert: true,
swagger2Options: {
patch: true,
resolveInternal: false,
targetVersion: '3.0.3'
}
});
const result = await parser.parseFromUrl('https://api.example.com/swagger.json');
if (result.metadata.conversionPerformed) {
console.log(`转换完成: ${result.metadata.originalVersion} -> ${result.metadata.targetVersion}`);
console.log(`转换耗时: ${result.metadata.conversionDuration}ms`);
}
```
### 5.3 错误处理
```typescript
try {
const result = await parseFromFile('swagger2.yaml');
} catch (error) {
if (error instanceof Swagger2OpenAPIConversionError) {
console.error('Swagger 2.0 转换失败:', error.message);
console.error('原始错误:', error.originalError);
} else if (error instanceof UnsupportedVersionError) {
console.error('不支持的版本:', error.message);
}
}
```
## 6. 兼容性考虑
### 6.1 向后兼容
- 现有 API 保持不变
- 新功能通过配置选项启用
- 默认行为保持一致
### 6.2 性能影响
- 转换操作仅在检测到 Swagger 2.0 时执行
- 内存使用增加约 10-20%
- 解析时间增加约 5-15%
### 6.3 依赖管理
- `swagger2openapi` 作为直接依赖
- 版本锁定确保稳定性
- 定期更新和安全扫描
## 7. 测试策略
### 7.1 测试覆盖
- 单元测试:> 90%
- 集成测试:主要使用场景
- 性能测试:基准测试和回归测试
### 7.2 测试数据
- 真实世界的 Swagger 2.0 规范
- 边缘情况和错误情况
- 大型复杂规范的性能测试
### 7.3 持续集成
- 自动化测试流水线
- 多 Node.js 版本测试
- 依赖安全扫描
## 8. 风险评估
### 8.1 技术风险
- **依赖风险**swagger2openapi 包维护状态
- **转换风险**:复杂规范的转换准确性
- **性能风险**:大型规范的处理性能
### 8.2 缓解策略
- 版本锁定和定期评估
- 全面的测试覆盖
- 性能监控和优化
## 9. 总结
通过集成 `swagger2openapi``mcp-swagger-parser` 将能够:
1. **无缝支持** Swagger 2.0 和 OpenAPI 3.0+ 规范
2. **自动转换** 旧版规范到新版格式
3. **提升用户体验** 通过统一的 API 接口
4. **增强错误处理** 和调试能力
5. **保持向后兼容** 现有功能
这个集成方案既能满足现有用户需求,又能扩展对传统 API 的支持,是一个平衡的技术决策。