这个库提供了一种在 Swift 上以类似 Retrofit 的方式定义 API 契约的方法。
它提供了以这种方式定义 API 的可能性
final class SchedulesApi: ApiDomain {
@Get("/api/v1/schedule")
var getSchedules: (GetSchedulesRequest) async throws -> GetSchedulesResponse
@Put("/api/v1/schedule")
var createSchedule: (CreateScheduleRequest) async throws -> Empty
@Post("/api/v1/schedule/{schedule_id}")
var updateSchedule: (UpdateScheduleRequest) async throws -> UpdateScheduleResponse
@Delete("/api/v1/schedule/{schedule_id}")
var deleteSchedule: (DeleteScheduleRequest) async throws -> Either<DeleteScheduleResponse, DeleteScheduleErrorResponse>
}
*Request
类型提供了关于端点契约的更多细节,即定义参数及其到 HTTP 参数的映射 - Query
、Header
、Path
、JsonBody
struct GetSchedulesRequest {
@Query var page: Int
@Query("limit") var schedulesPerPage: Int = 0
@Header("X-Account-Id") var accountId: String = ""
}
struct CreateScheduleRequest {
@Header("X-Account-Id") var accountId: String = ""
@JsonBody var scheduleBody: Schedule
}
struct DeleteScheduleRequest {
@Path("schedule_id") var ScheduleId: String = ""
@Header("X-Account-Id") var accountId: String = ""
}
用法非常简单
let transport: HttpTransport = ....
let api = SchedulesApi(transport: transport)
let request = GetSchedulesRequest(page: 1, schedulesPerPage: 30, accountId: "acc_id")
let response = try await api.getSchedules(request)
此外,响应可以以直接且自描述的方式进行模拟
api.getSchedules = { _ in
GetSchedulesResponse(....)
}
api.deleteSchedule = { _ in
throw URLError(.userAuthenticationRequired)
}
api.deleteSchedule = { _ in
.errorResponse(DeleteScheduleErrorResponse(errorMessage: "Schedule not found"))
}
在最简单的情况下,ApiDomain
可以实现如下
class ApiDomain: Domain {
override init(transport: HttpTransport) {
super.init(transport: transport)
transport.setConfiguration(scheme: "https", host: "rest.bandsintown.com", sharedHeaders: nil)
}
}
更复杂的解决方案可以包括,例如,会话令牌管理。
HttpTransport
是描述 HTTP 网络通信层的协议。
public protocol HttpTransport {
func setConfiguration(scheme: String, host: String, sharedHeaders: [String: String]?)
func sendRequest(with params: HttpRequestParams) async throws -> HttpOperationResult
}
DemoProject
包含基于 UrlSession 的简单实现,但您可以根据您的需求提供您自己的实现。
支持的 HTTP 方法
@Delete
@Get
@Head
@Patch
@Post
@Put
支持的参数类型
@Header
@Path
@Query
@JsonBody
默认情况下,参数名称取自变量名,但可以自定义
@Header("X-Account-Id") var accountId: String = ""
支持的响应类型
Decodable
的类型Either<Response: Decodable, ErrorResponse: Decodable>
Empty
Either
类型允许获取成功或错误响应。
响应模拟。您可以通过直接赋值给 API 的端点定义来轻松模拟响应
api.deleteSchedule = { _ in
.errorResponse(DeleteScheduleErrorResponse(errorMessage: "Schedule not found"))
}
如果您正在 Xcode 中处理项目,RetroSwift 可以轻松集成
File > Add Packages...
Package Dependencies
并单击 +
按钮https://github.com/level-two/RetroSwift
General
选项卡上找到 Frameworks, Libraries and Embedded content
部分,单击“+”并将 RetroSwift 库添加为依赖项要在 SwiftPM 项目中使用此库,请将以下行添加到您的 Package.swift
文件中的 dependencies
.package(url: "https://github.com/level-two/RetroSwift", from: "0.0.1"),
并将其作为您目标的依赖项包含在内
.target(
...
dependencies: [
"RetroSwift",
],
...
),
最后,将 import RetroSwift
添加到您的源代码中。