Skip to content

Repository files navigation

RetroSwift

This library provides the approach to API contract definition in the Retrofit-like fashion on Swift.

It gives possibility to define API in this way:

finalclassSchedulesApi:ApiDomain{@Get("/api/v1/schedule")vargetSchedules:(GetSchedulesRequest)asyncthrows->GetSchedulesResponse@Put("/api/v1/schedule")varcreateSchedule:(CreateScheduleRequest)asyncthrows->Empty@Post("/api/v1/schedule/{schedule_id}")varupdateSchedule:(UpdateScheduleRequest)asyncthrows->UpdateScheduleResponse@Delete("/api/v1/schedule/{schedule_id}")vardeleteSchedule:(DeleteScheduleRequest)asyncthrows->Either<DeleteScheduleResponse,DeleteScheduleErrorResponse>}

*Request types provide more details on endpoints contracts, namely define parameters and their mapping to the HTTP params - Query, Header, Path, JsonBody, FormParam, FormFile:

structGetSchedulesRequest{@Queryvarpage:Int@Query("limit")varschedulesPerPage:Int=0@Header("X-Account-Id")varaccountId:String=""}structCreateScheduleRequest{@Header("X-Account-Id")varaccountId:String=""@JsonBodyvarscheduleBody:Schedule}structDeleteScheduleRequest{@Path("schedule_id")varScheduleId:String=""@Header("X-Account-Id")varaccountId:String=""}structSpeechToTextApiRequest{@FormParam("model_id")varmodelId=""@FormParam("language_code")varlanguageCode=""@FormParam("tag_audio_events")vartagAudioEvents=false@FormParam("num_speakers")varnumSpeakers=1@FormFile("file")varrecording=.empty
}

Usage is quite simple:

lettransport:HttpTransport=....letapi=SchedulesApi(transport: transport)letrequest=GetSchedulesRequest(page:1, schedulesPerPage:30, accountId:"acc_id")letresponse=tryawait api.getSchedules(request)

Sending multipart form:

letrequest=ElevenLabsApi.SpeechToTextApiRequest(
modelId:"scribe_v1",
languageCode: languageCode,
tagAudioEvents:false,
numSpeakers:1,
recording:.init(fileName:"recording.caf", mimeType:"audio/x-caf", content: recording))lettranscribedText=tryawait api.speechToText(request).text

Additionally responses can be mocked in a straightforward and self-describing way:

api.getSchedules ={ _ inGetSchedulesResponse(....)}
api.deleteSchedule ={ _ inthrowURLError(.userAuthenticationRequired)}
api.deleteSchedule ={ _ in.errorResponse(DeleteScheduleErrorResponse(errorMessage:"Schedule not found"))}

ApiDomain in the simplest case can be implemented as follow:

classApiDomain:Domain{overrideinit(transport:HttpTransport){
super.init(transport: transport)
transport.setConfiguration(scheme:"https", host:"rest.bandsintown.com", sharedHeaders:nil)}}

More complex solutions can include, for example, session token management.

HttpTransport is the protocol describing HTTP network communication layer.

publicprotocolHttpTransport{func setConfiguration(scheme:String, host:String, sharedHeaders:[String:String]?)func sendRequest(with params:HttpRequestParams)asyncthrows->HttpOperationResult}

DemoProject contains simple implementation based on the UrlSession, but you can provide yours depending on your needs.

Features

Supported HTTP methods:

  • @Delete
  • @Get
  • @Head
  • @Patch
  • @Post
  • @Put

Supported parameter types:

  • @Header
  • @Path
  • @Query
  • @JsonBody
  • @FormParam
  • @FormFile

By default parameter name is derived from the variable name, but it can be customized:

@Header("X-Account-Id")varaccountId:String=""

Supported response types:

  • any type conforming to Decodable
  • Either<Response: Decodable, ErrorResponse: Decodable>
  • Empty

Either type allows to get either success or error response.

Response mocking. You can easily mock response by assigning directly to the api's endpoint definition:

api.deleteSchedule ={ _ in.errorResponse(DeleteScheduleErrorResponse(errorMessage:"Schedule not found"))}

Adding RetroSwift as a Dependency

Xcode

If you're working with a project in Xcode RetroSwift can be easily integrated:

  1. In Xcode, select File > Add Packages...
  2. Or go to the project's settings, select your project from the list, go to the Package Dependencies and click + button
  3. Specify the Repository: https://github.com/level-two/RetroSwift
  4. Go to the Target, on General tab find Frameworks, Libraries and Embedded content section, click '+' and add RetroSwift library as a dependency

Swift Package Manager

To use this library in a SwiftPM project, add the following line to the dependencies in your Package.swift file:

.package(url:"https://github.com/level-two/RetroSwift", from:"0.0.1"),

and include it as a dependency for your target:

.target(...
dependencies:["RetroSwift",],...),

Finally, add import RetroSwift to your source code.

About

Retrofit-like API contract definition in Swift.

Topics

Resources

Stars

7 stars

Watchers

2 watching

Forks

Releases

Packages

Used by

Contributors

Languages