Options provides a features to Enum and OptionSet types such as:
Providing additional value types besides the RawType rawValue
Being able to interchange between Enum and OptionSet types
Using an additional value type for a CodableOptionSet
Example
Let’s say you have Enum type:
enum ContinuousIntegrationSystem {
case github
case travisci
case circleci
case bitrise
}
We want two things:
Use it as an OptionSet so we can store multiple CI sytems
Store and parse it via a String
If OptionSet requires an IntRawType, how can we parse and store as String?
With Options we can enable ContinuousIntegrationSystem to do both:
enum ContinuousIntegrationSystem: Int, MappedValueCollectionRepresented {
case github
case travisci
case circleci
case bitrise
typealias MappedType = String
static let mappedValues = [
"github",
"travisci",
"circleci",
"bitrise"
]
}
typealias ContinuousIntegrationSystemSet = EnumSet<ContinuousIntegrationSystem>
let systems = ContinuousIntegrationSystemSet([.travisci, .github])
Installation
Swift Package Manager is Apple’s decentralized dependency manager to integrate libraries to your Swift projects. It is now fully integrated with Xcode 11.
To integrate Options into your project using SPM, specify it in your Package.swift file:
enum ContinuousIntegrationSystem: Int {
case github
case travisci
case circleci
case bitrise
}
We want to be able to make it available as an OptionSet so it needs an RawType of Int.
However we want to decode and encode it via Codable as a String.
Options has a protocol MappedValueRepresentable which allows to do that by implementing it.
enum ContinuousIntegrationSystem: Int, MappedValueRepresentable {
case github
case travisci
case circleci
case bitrise
static func rawValue(basedOn string: String) throws -> Int {
if (string == "github") {
return 0
} else {
...
} else {
throw ...
}
}
static func mappedValue(basedOn rawValue: Int) throws -> String {
if (rawValue == 0) {
return "github"
} else {
...
} else {
throw ...
}
}
}
By using MappedValueCollectionRepresented, you can simplify implementing MappedValueRepresentable:
enum ContinuousIntegrationSystem: Int, MappedValueCollectionRepresented {
case github
case travisci
case circleci
case bitrise
static let mappedValues = [
"github",
"travisci",
"circleci",
"bitrise"
]
}
Now we we’ve made it simplifies implementing MappedValueRepresentable so let’s look how to use it with Codable.
EnumSet allows you to interchangeably use Enum with an OptionSet. EnumSet is a Generic struct while takes any Enum type with a RawType. So we can create an OptionSet instance which uses out ContinuousIntegrationSystem:
let systems = EnumSet<ContinuousIntegrationSystem>([.travisci, .github])
Converting EnumSet to Enum Array
If your Enum implements CaseIterable, then you can extract the individual ContinuousIntegrationSystem enum values with .array():
enum ContinuousIntegrationSystem: Int, CaseIterable {
case github
case travisci
case circleci
case bitrise
}
let systems = EnumSet<ContinuousIntegrationSystem>([.travisci, .github])
print(systems.array())
Lastly, let’s put all this together.
Codable EnumSet using a MappedValueRepresentable Enum
If your enum implements MappedValueRepresentable and you use it in an EnumSet, then you can allow for your OptionSet to be Codable as an Array of values rather than the cumulative rawValue:
enum ContinuousIntegrationSystem: Int, MappedValueCollectionRepresented, CaseIterable {
case github
case travisci
case circleci
case bitrise
static let mappedValues = [
"github",
"travisci",
"circleci",
"bitrise"
]
}
struct BuildSetup : Codable {
let systems: EnumSet<ContinuousIntegrationSystem>
}
let systems = BuildSetup(systems: EnumSet<ContinuousIntegrationSystem>(values: [.travisci, .github]))
For our systems variable, our Codable data would be:
{
"systems" : ["travisci", "github"]
}
This will make it easier for making our data human-readable instead of using the rawValue of 3.
Options
Swift Package for more powerful
Enumtypes.Table of Contents
MappedValueRepresentableEnumMappedValueCollectionRepresentedMappedEnumTypeEnumSetEnumSetto Enum ArrayEnumSetusing aMappedValueRepresentableEnumIntroduction
Options provides a features to
EnumandOptionSettypes such as:RawType rawValueEnumandOptionSettypesCodableOptionSetExample
Let’s say you have
Enumtype:We want two things:
OptionSetso we can store multiple CI sytemsStringIf
OptionSetrequires anIntRawType, how can we parse and store asString?With Options we can enable
ContinuousIntegrationSystemto do both:Installation
Swift Package Manager is Apple’s decentralized dependency manager to integrate libraries to your Swift projects. It is now fully integrated with Xcode 11.
To integrate Options into your project using SPM, specify it in your Package.swift file:
Usage
Setting up a MappedValueRepresentable Enum
So let’s say we our
enum:We want to be able to make it available as an
OptionSetso it needs anRawTypeofInt. However we want to decode and encode it viaCodableas aString.Options has a protocol
MappedValueRepresentablewhich allows to do that by implementing it.This can be simplified further by using
MappedValueCollectionRepresented.Using MappedValueCollectionRepresented
By using
MappedValueCollectionRepresented, you can simplify implementingMappedValueRepresentable:Now we we’ve made it simplifies implementing
MappedValueRepresentableso let’s look how to use it withCodable.Codable Enums using a MappedEnum Type
So you’ve setup a
MappedValueRepresentableenum, the next part is having theMappedTypewhich in this case isStringthe part that’s used inCodable.This is where
MappedEnumis used:Now if the
Stringcan be used in encoding and decoding the value rather than theRawTypeInt:Next, let’s take a look how we could use
ContinuousIntegrationSystemin anOptionSet.Using Enums in OptionSets with EnumSet
EnumSetallows you to interchangeably useEnumwith anOptionSet.EnumSetis a Genericstructwhile takes anyEnumtype with aRawType. So we can create anOptionSetinstance which uses outContinuousIntegrationSystem:Converting EnumSet to Enum Array
If your
EnumimplementsCaseIterable, then you can extract the individualContinuousIntegrationSystemenum values with.array():Lastly, let’s put all this together.
Codable EnumSet using a MappedValueRepresentable Enum
If your
enumimplementsMappedValueRepresentableand you use it in anEnumSet, then you can allow for yourOptionSetto beCodableas anArrayof values rather than the cumulativerawValue:For our
systemsvariable, ourCodabledata would be:This will make it easier for making our data human-readable instead of using the
rawValueof3.Further Code Documentation
Documentation Here
License
This code is distributed under the MIT license. See the LICENSE file for more info.