This article has been archived, as it was published several years ago, so some of its information might now be outdated. For more recent articles, please visit the main article feed.
Result’s convenience APIs
Basics article available: The Result TypeThe Swift standard library’s Result
type might just be a simple enum with cases for modeling an operation’s success
or failure
, but it also comes with several really useful convenience APIs built-in.
For example, it has a closure-based initializer, which we can use to easily convert any expression that throws
into a Result
value:
let data: Data = ...
let decoder = JSONDecoder()
// This will create a Result<Model, Error> instance, which will contain
// 'success' if its expression succeeded, and 'failure' if it ended
// up throwing an error:
let result = Result {
try decoder.decode(Model.self, from: data)
}
// The above API is really useful when we want to return a Result
// value from an asynchronous operation, for example by calling
// a completion handler:
completionHandler(result)
Above we’re converting a raw Data
value into a decoded Result
, but we can also do the opposite — and extract a Data
value from a Result
instance, which we’ll then decode:
func decode(_ result: Result<Data, Error>) throws -> Model {
// Using Result's 'get' method, we can either extract its
// underlying value, or throw any error that it contains:
let data = try result.get()
let decoder = JSONDecoder()
return try decoder.decode(Model.self, from: data)
}
Finally, Result
also ships with a series of really useful mapping functions, for example map
— which enables us to convert any result’s value into a new type, without having to do any error handling as part of such an operation:
let dataResult: Result<Data, Error> = ...
let stringResult = dataResult.map {
String(decoding: $0, as: UTF8.self)
}

Swift by Sundell is brought to you by the Genius Scan SDK — Add a powerful document scanner to any mobile app, and turn scans into high-quality PDFs with one line of code. Try it today.