Fixed the code duplication from supporting different Swift versions in the AmiiboLiveClient client in the library target.

This commit is contained in:
2025-10-02 02:38:47 +02:00
parent 463d15975c
commit 8d0f00ec36
2 changed files with 106 additions and 232 deletions
@@ -51,44 +51,7 @@ extension AmiiboLiveClient: AmiiboClient {
public func getAmiibos( public func getAmiibos(
by filter: AmiiboFilter by filter: AmiiboFilter
) async throws(AmiiboServiceError) -> [Amiibo] { ) async throws(AmiiboServiceError) -> [Amiibo] {
let response: Operations.getAmiibos.Output try await fetchAmiibos(filter)
do {
response = try await client.getAmiibos(
.init(query: .init(
amiiboSeries: filter.series,
character: filter.gameCharacter,
gameseries: filter.gameSeries,
id: filter.identifier,
name: filter.name,
showgames: filter.showGames,
showusage: filter.showUsage,
_type: filter.type
))
)
} catch let error as ClientError {
if error.underlyingError is DecodingError {
throw AmiiboServiceError.decoding
} else {
throw AmiiboServiceError.unknown
}
} catch {
throw AmiiboServiceError.unknown
}
switch response {
case let .ok(ok):
switch ok.body {
case let .json(output):
return map(output)
}
case .badRequest:
throw AmiiboServiceError.badRequest
case let .undocumented(statusCode, _):
throw AmiiboServiceError.undocumented(statusCode)
}
} }
/// Gets a list of amiibo series based on a given filter. /// Gets a list of amiibo series based on a given filter.
@@ -98,38 +61,7 @@ extension AmiiboLiveClient: AmiiboClient {
public func getAmiiboSeries( public func getAmiiboSeries(
by filter: AmiiboSeriesFilter by filter: AmiiboSeriesFilter
) async throws(AmiiboServiceError) -> [AmiiboSeries] { ) async throws(AmiiboServiceError) -> [AmiiboSeries] {
let response: Operations.getAmiiboSeries.Output try await fetchAmiiboSeries(filter)
do {
response = try await client.getAmiiboSeries(
.init(query: .init(
key: filter.key,
name: filter.name
))
)
} catch {
throw AmiiboServiceError.unknown
}
switch response {
case let .ok(ok):
switch ok.body {
case let .json(output):
return map(output, as: AmiiboSeries.self)
}
case .badRequest:
throw AmiiboServiceError.badRequest
case .internalServerError:
throw AmiiboServiceError.notAvailable
case .notFound:
throw AmiiboServiceError.notFound
case let .undocumented(statusCode, _):
throw AmiiboServiceError.undocumented(statusCode)
}
} }
/// Gets a list of amiibo types based on a given filter. /// Gets a list of amiibo types based on a given filter.
@@ -139,38 +71,7 @@ extension AmiiboLiveClient: AmiiboClient {
public func getAmiiboTypes( public func getAmiiboTypes(
by filter: AmiiboTypeFilter by filter: AmiiboTypeFilter
) async throws(AmiiboServiceError) -> [AmiiboType] { ) async throws(AmiiboServiceError) -> [AmiiboType] {
let response: Operations.getAmiiboTypes.Output try await fetchAmiiboTypes(filter)
do {
response = try await client.getAmiiboTypes(
.init(query: .init(
key: filter.key,
name: filter.name
))
)
} catch {
throw AmiiboServiceError.unknown
}
switch response {
case let .ok(ok):
switch ok.body {
case let .json(output):
return map(output, as: AmiiboType.self)
}
case .badRequest:
throw AmiiboServiceError.badRequest
case .internalServerError:
throw AmiiboServiceError.notAvailable
case .notFound:
throw AmiiboServiceError.notFound
case let .undocumented(statusCode, _):
throw AmiiboServiceError.undocumented(statusCode)
}
} }
/// Gets a list of game characters based on a given filter. /// Gets a list of game characters based on a given filter.
@@ -180,38 +81,7 @@ extension AmiiboLiveClient: AmiiboClient {
public func getGameCharacters( public func getGameCharacters(
by filter: GameCharacterFilter by filter: GameCharacterFilter
) async throws(AmiiboServiceError) -> [GameCharacter] { ) async throws(AmiiboServiceError) -> [GameCharacter] {
let response: Operations.getGameCharacters.Output try await fetchGameCharacters(filter)
do {
response = try await client.getGameCharacters(
.init(query: .init(
key: filter.key,
name: filter.name
))
)
} catch {
throw AmiiboServiceError.unknown
}
switch response {
case let .ok(ok):
switch ok.body {
case let .json(output):
return map(output, as: GameCharacter.self)
}
case .badRequest:
throw AmiiboServiceError.badRequest
case .internalServerError:
throw AmiiboServiceError.notAvailable
case .notFound:
throw AmiiboServiceError.notFound
case let .undocumented(statusCode, _):
throw AmiiboServiceError.undocumented(statusCode)
}
} }
/// Gets a list of game series based on a given filter. /// Gets a list of game series based on a given filter.
@@ -221,62 +91,14 @@ extension AmiiboLiveClient: AmiiboClient {
public func getGameSeries( public func getGameSeries(
by filter: GameSeriesFilter by filter: GameSeriesFilter
) async throws(AmiiboServiceError) -> [GameSeries] { ) async throws(AmiiboServiceError) -> [GameSeries] {
let response: Operations.getGameSeries.Output try await fetchGameSeries(filter)
do {
response = try await client.getGameSeries(
.init(query: .init(
key: filter.key,
name: filter.name
))
)
} catch {
throw AmiiboServiceError.unknown
}
switch response {
case let .ok(ok):
switch ok.body {
case let .json(output):
return map(output, as: GameSeries.self)
}
case .badRequest:
throw AmiiboServiceError.badRequest
case .internalServerError:
throw AmiiboServiceError.notAvailable
case .notFound:
throw AmiiboServiceError.notFound
case let .undocumented(statusCode, _):
throw AmiiboServiceError.undocumented(statusCode)
}
} }
/// Gets the date when the data was last updated. /// Gets the date when the data was last updated.
/// - Returns: A last updated date. /// - Returns: A last updated date.
/// - Throws: An ``AmiiboServiceError`` error in case some issue is encountered while generating the result. /// - Throws: An ``AmiiboServiceError`` error in case some issue is encountered while generating the result.
public func getLastUpdated() async throws(AmiiboServiceError) -> Date { public func getLastUpdated() async throws(AmiiboServiceError) -> Date {
let response: Operations.getLastUpdated.Output try await fetchLastUpdated()
do {
response = try await client.getLastUpdated()
} catch {
throw AmiiboServiceError.unknown
}
switch response {
case let .ok(ok):
switch ok.body {
case let .json(output):
return output.lastUpdated
}
case let .undocumented(statusCode, _):
throw AmiiboServiceError.undocumented(statusCode)
}
} }
#else #else
/// Gets a list of amiibo items based on a given filter. /// Gets a list of amiibo items based on a given filter.
@@ -285,6 +107,72 @@ extension AmiiboLiveClient: AmiiboClient {
/// - Throws: An ``AmiiboServiceError`` error in case some issue is encountered while generating the result. /// - Throws: An ``AmiiboServiceError`` error in case some issue is encountered while generating the result.
public func getAmiibos( public func getAmiibos(
by filter: AmiiboFilter by filter: AmiiboFilter
) async throws -> [Amiibo] {
try await fetchAmiibos(filter)
}
/// Gets a list of amiibo series based on a given filter.
/// - Parameter filter: A filter to remove unwanted items from the result.
/// - Returns: A list of filtered amiibo series.
/// - Throws: An ``AmiiboServiceError`` error in case some issue is encountered while generating the result.
public func getAmiiboSeries(
by filter: AmiiboSeriesFilter
) async throws -> [AmiiboSeries] {
try await fetchAmiiboSeries(filter)
}
/// Gets a list of amiibo types based on a given filter.
/// - Parameter filter: A filter to remove unwanted items from the result.
/// - Returns: A list of filtered amiibo types.
/// - Throws: An ``AmiiboServiceError`` error in case some issue is encountered while generating the result.
public func getAmiiboTypes(
by filter: AmiiboTypeFilter
) async throws -> [AmiiboType] {
try await fetchAmiiboTypes(filter)
}
/// Gets a list of game characters based on a given filter.
/// - Parameter filter: A filter to remove unwanted items from the result.
/// - Returns: A list of filtered game characters.
/// - Throws: An ``AmiiboServiceError`` error in case some issue is encountered while generating the result.
public func getGameCharacters(
by filter: GameCharacterFilter
) async throws -> [GameCharacter] {
try await fetchGameCharacters(filter)
}
/// Gets a list of game series based on a given filter.
/// - Parameter filter: A filter to remove unwanted items from the result.
/// - Returns: A list of filtered game series.
/// - Throws: An ``AmiiboServiceError`` error in case some issue is encountered while generating the result.
public func getGameSeries(
by filter: GameSeriesFilter
) async throws -> [GameSeries] {
try await fetchGameSeries(filter)
}
/// Gets the date when the data was last updated.
/// - Returns: A last updated date.
/// - Throws: An ``AmiiboServiceError`` error in case some issue is encountered while generating the result.
public func getLastUpdated() async throws -> Date {
try await fetchLastUpdated()
}
#endif
}
// MARK: - Helpers
private extension AmiiboLiveClient {
// MARK: Functions
/// Fetches a list of amiibo items based on a given filter.
/// - Parameter filter: A filter to remove unwanted items from the result.
/// - Returns: A list of fetched amiibo items filtered, if requested.
/// - Throws: An ``AmiiboServiceError`` error in case some issue is encountered while generating the result.
func fetchAmiibos(
_ filter: AmiiboFilter
) async throws -> [Amiibo] { ) async throws -> [Amiibo] {
let response: Operations.getAmiibos.Output let response: Operations.getAmiibos.Output
@@ -301,6 +189,8 @@ extension AmiiboLiveClient: AmiiboClient {
_type: filter.type _type: filter.type
)) ))
) )
} catch is CancellationError {
throw AmiiboServiceError.cancelled
} catch let error as ClientError { } catch let error as ClientError {
if error.underlyingError is DecodingError { if error.underlyingError is DecodingError {
throw AmiiboServiceError.decoding throw AmiiboServiceError.decoding
@@ -317,21 +207,19 @@ extension AmiiboLiveClient: AmiiboClient {
case let .json(output): case let .json(output):
return map(output) return map(output)
} }
case .badRequest: case .badRequest:
throw AmiiboServiceError.badRequest throw AmiiboServiceError.badRequest
case let .undocumented(statusCode, _): case let .undocumented(statusCode, _):
throw AmiiboServiceError.undocumented(statusCode) throw AmiiboServiceError.undocumented(statusCode)
} }
} }
/// Gets a list of amiibo series based on a given filter. /// Fetches a list of amiibo series based on a given filter.
/// - Parameter filter: A filter to remove unwanted items from the result. /// - Parameter filter: A filter to remove unwanted items from the result.
/// - Returns: A list of filtered amiibo series. /// - Returns: A list of fetched amiibo series filtered, if requested.
/// - Throws: An ``AmiiboServiceError`` error in case some issue is encountered while generating the result. /// - Throws: An ``AmiiboServiceError`` error in case some issue is encountered while generating the result.
public func getAmiiboSeries( func fetchAmiiboSeries(
by filter: AmiiboSeriesFilter _ filter: AmiiboSeriesFilter
) async throws -> [AmiiboSeries] { ) async throws -> [AmiiboSeries] {
let response: Operations.getAmiiboSeries.Output let response: Operations.getAmiiboSeries.Output
@@ -342,6 +230,8 @@ extension AmiiboLiveClient: AmiiboClient {
name: filter.name name: filter.name
)) ))
) )
} catch is CancellationError {
throw AmiiboServiceError.cancelled
} catch { } catch {
throw AmiiboServiceError.unknown throw AmiiboServiceError.unknown
} }
@@ -352,27 +242,23 @@ extension AmiiboLiveClient: AmiiboClient {
case let .json(output): case let .json(output):
return map(output, as: AmiiboSeries.self) return map(output, as: AmiiboSeries.self)
} }
case .badRequest: case .badRequest:
throw AmiiboServiceError.badRequest throw AmiiboServiceError.badRequest
case .internalServerError: case .internalServerError:
throw AmiiboServiceError.notAvailable throw AmiiboServiceError.notAvailable
case .notFound: case .notFound:
throw AmiiboServiceError.notFound throw AmiiboServiceError.notFound
case let .undocumented(statusCode, _): case let .undocumented(statusCode, _):
throw AmiiboServiceError.undocumented(statusCode) throw AmiiboServiceError.undocumented(statusCode)
} }
} }
/// Gets a list of amiibo types based on a given filter. /// Fetches a list of amiibo types based on a given filter.
/// - Parameter filter: A filter to remove unwanted items from the result. /// - Parameter filter: A filter to remove unwanted items from the result.
/// - Returns: A list of filtered amiibo types. /// - Returns: A list of fetched amiibo types filtered, if requested.
/// - Throws: An ``AmiiboServiceError`` error in case some issue is encountered while generating the result. /// - Throws: An ``AmiiboServiceError`` error in case some issue is encountered while generating the result.
public func getAmiiboTypes( func fetchAmiiboTypes(
by filter: AmiiboTypeFilter _ filter: AmiiboTypeFilter
) async throws -> [AmiiboType] { ) async throws -> [AmiiboType] {
let response: Operations.getAmiiboTypes.Output let response: Operations.getAmiiboTypes.Output
@@ -383,6 +269,8 @@ extension AmiiboLiveClient: AmiiboClient {
name: filter.name name: filter.name
)) ))
) )
} catch is CancellationError {
throw AmiiboServiceError.cancelled
} catch { } catch {
throw AmiiboServiceError.unknown throw AmiiboServiceError.unknown
} }
@@ -393,27 +281,23 @@ extension AmiiboLiveClient: AmiiboClient {
case let .json(output): case let .json(output):
return map(output, as: AmiiboType.self) return map(output, as: AmiiboType.self)
} }
case .badRequest: case .badRequest:
throw AmiiboServiceError.badRequest throw AmiiboServiceError.badRequest
case .internalServerError: case .internalServerError:
throw AmiiboServiceError.notAvailable throw AmiiboServiceError.notAvailable
case .notFound: case .notFound:
throw AmiiboServiceError.notFound throw AmiiboServiceError.notFound
case let .undocumented(statusCode, _): case let .undocumented(statusCode, _):
throw AmiiboServiceError.undocumented(statusCode) throw AmiiboServiceError.undocumented(statusCode)
} }
} }
/// Gets a list of game characters based on a given filter. /// Fetches a list of game characters based on a given filter.
/// - Parameter filter: A filter to remove unwanted items from the result. /// - Parameter filter: A filter to remove unwanted items from the result.
/// - Returns: A list of filtered game characters. /// - Returns: A list of fetched game characters filtered, if requested.
/// - Throws: An ``AmiiboServiceError`` error in case some issue is encountered while generating the result. /// - Throws: An ``AmiiboServiceError`` error in case some issue is encountered while generating the result.
public func getGameCharacters( func fetchGameCharacters(
by filter: GameCharacterFilter _ filter: GameCharacterFilter
) async throws -> [GameCharacter] { ) async throws -> [GameCharacter] {
let response: Operations.getGameCharacters.Output let response: Operations.getGameCharacters.Output
@@ -424,6 +308,8 @@ extension AmiiboLiveClient: AmiiboClient {
name: filter.name name: filter.name
)) ))
) )
} catch is CancellationError {
throw AmiiboServiceError.cancelled
} catch { } catch {
throw AmiiboServiceError.unknown throw AmiiboServiceError.unknown
} }
@@ -434,27 +320,23 @@ extension AmiiboLiveClient: AmiiboClient {
case let .json(output): case let .json(output):
return map(output, as: GameCharacter.self) return map(output, as: GameCharacter.self)
} }
case .badRequest: case .badRequest:
throw AmiiboServiceError.badRequest throw AmiiboServiceError.badRequest
case .internalServerError: case .internalServerError:
throw AmiiboServiceError.notAvailable throw AmiiboServiceError.notAvailable
case .notFound: case .notFound:
throw AmiiboServiceError.notFound throw AmiiboServiceError.notFound
case let .undocumented(statusCode, _): case let .undocumented(statusCode, _):
throw AmiiboServiceError.undocumented(statusCode) throw AmiiboServiceError.undocumented(statusCode)
} }
} }
/// Gets a list of game series based on a given filter. /// Fetches a list of game series based on a given filter.
/// - Parameter filter: A filter to remove unwanted items from the result. /// - Parameter filter: A filter to remove unwanted items from the result.
/// - Returns: A list of filtered game series. /// - Returns: A list of fetched game series filtered, if requested.
/// - Throws: An ``AmiiboServiceError`` error in case some issue is encountered while generating the result. /// - Throws: An ``AmiiboServiceError`` error in case some issue is encountered while generating the result.
public func getGameSeries( func fetchGameSeries(
by filter: GameSeriesFilter _ filter: GameSeriesFilter
) async throws -> [GameSeries] { ) async throws -> [GameSeries] {
let response: Operations.getGameSeries.Output let response: Operations.getGameSeries.Output
@@ -465,6 +347,8 @@ extension AmiiboLiveClient: AmiiboClient {
name: filter.name name: filter.name
)) ))
) )
} catch is CancellationError {
throw AmiiboServiceError.cancelled
} catch { } catch {
throw AmiiboServiceError.unknown throw AmiiboServiceError.unknown
} }
@@ -475,29 +359,27 @@ extension AmiiboLiveClient: AmiiboClient {
case let .json(output): case let .json(output):
return map(output, as: GameSeries.self) return map(output, as: GameSeries.self)
} }
case .badRequest: case .badRequest:
throw AmiiboServiceError.badRequest throw AmiiboServiceError.badRequest
case .internalServerError: case .internalServerError:
throw AmiiboServiceError.notAvailable throw AmiiboServiceError.notAvailable
case .notFound: case .notFound:
throw AmiiboServiceError.notFound throw AmiiboServiceError.notFound
case let .undocumented(statusCode, _): case let .undocumented(statusCode, _):
throw AmiiboServiceError.undocumented(statusCode) throw AmiiboServiceError.undocumented(statusCode)
} }
} }
/// Gets the date when the data was last updated. /// Fetches the date when the data was last updated.
/// - Returns: A last updated date. /// - Returns: A fetched last updated date.
/// - Throws: An ``AmiiboServiceError`` error in case some issue is encountered while generating the result. /// - Throws: An ``AmiiboServiceError`` error in case some issue is encountered while generating the result.
public func getLastUpdated() async throws -> Date { func fetchLastUpdated() async throws -> Date {
let response: Operations.getLastUpdated.Output let response: Operations.getLastUpdated.Output
do { do {
response = try await client.getLastUpdated() response = try await client.getLastUpdated()
} catch is CancellationError {
throw AmiiboServiceError.cancelled
} catch { } catch {
throw AmiiboServiceError.unknown throw AmiiboServiceError.unknown
} }
@@ -508,20 +390,10 @@ extension AmiiboLiveClient: AmiiboClient {
case let .json(output): case let .json(output):
return output.lastUpdated return output.lastUpdated
} }
case let .undocumented(statusCode, _): case let .undocumented(statusCode, _):
throw AmiiboServiceError.undocumented(statusCode) throw AmiiboServiceError.undocumented(statusCode)
} }
} }
#endif
}
// MARK: - Helpers
private extension AmiiboLiveClient {
// MARK: Functions
/// Retrieves a list of amiibo items from a wrapper container. /// Retrieves a list of amiibo items from a wrapper container.
/// - Parameter wrapper: A wrapper container that either has an object or a list of items. /// - Parameter wrapper: A wrapper container that either has an object or a list of items.
@@ -14,6 +14,8 @@
public enum AmiiboServiceError: Error { public enum AmiiboServiceError: Error {
/// A bad request has been given to the client. /// A bad request has been given to the client.
case badRequest case badRequest
/// A call to an endpoint has been cancelled by the user.
case cancelled
/// A response cannot be decoded. /// A response cannot be decoded.
case decoding case decoding
/// An online service is not currently available. /// An online service is not currently available.