Skip to content

Instantly share code, notes, and snippets.

View onmyway133's full-sized avatar
๐Ÿ˜‡
What you don't know is what you haven't learned

Khoa onmyway133

๐Ÿ˜‡
What you don't know is what you haven't learned
View GitHub Profile
public class Transformer<T> {
let toData: (T) throws -> Data
let fromData: (Data) throws -> T
public init(toData: @escaping (T) throws -> Data, fromData: @escaping (Data) throws -> T) {
self.toData = toData
self.fromData = fromData
}
}
/// A protocol used for saving and loading from storage
public protocol StorageAware {
associatedtype T
...
}
let storage: Storage<User> = ...
storage.setObject(superman, forKey: "user")
let imageStorage = storage.transformImage() // Storage<UIImage>
imageStorage.setObject(image, forKey: "image")
let stringStorage = storage.transformCodable(ofType: String.self) // Storage<String>
stringStorage.setObject("hello world", forKey: "string")
class DataProducer<T: Codable> {
let object: T?
let image: Image?
init(object: T) {
self.object = object
self.image = nil
}
init(image: Image) {
protocol DataConvertible {
func toData() -> Data
static func fromData() -> Self
}
// WARNING: Does not compile
extension Codable: DataConvertible { // Non-nominal type 'Codable' (aka 'Decodable & Encodable') cannot be extended
}
// WARNING: Does not compile
extension Storage {
func save(object: Any, forKey: String) {
switch object {
case let image as Image:
let data = UIImagePNGRepresentation(image)
case let object as Codable:
let encoder = JSONEncoder()
try? encoder.encode(object) // Cannot invoke 'encode' with an argument list of type '(Codable)'
default:
extension TypeWrapperStorage: StorageAware {
public func entry<T: Codable>(forKey key: String) throws -> Entry<T> {
let wrapperEntry = try internalStorage.entry(forKey: key) as Entry<TypeWrapper<T>>
return Entry(object: wrapperEntry.object.object, expiry: wrapperEntry.expiry)
}
public func setObject<T: Codable>(_ object: T, forKey key: String,
expiry: Expiry? = nil) throws {
let wrapper = TypeWrapper<T>(object: object)
try internalStorage.setObject(wrapper, forKey: key, expiry: expiry)
struct PrimitiveWrapper<T: Codable>: Codable {
let value: T
init(value: T) {
self.value = value
}
}
extension PrimitiveStorage: StorageAware {
public func entry<T: Codable>(forKey key: String) throws -> Entry<T> {
do {
return try internalStorage.entry(forKey: key) as Entry<T>
} catch let error as Swift.DecodingError {
// Expected to decode T but found a dictionary instead.
switch error {
case .typeMismatch(_, let context) where context.codingPath.isEmpty:
let wrapperEntry = try internalStorage.entry(forKey: key) as Entry<PrimitiveWrapper<T>>
let primitiveEntry = Entry(object: wrapperEntry.object.value,
let wrapper = ImageWrapper(image: starIconImage)
try? storage.setObject(wrapper, forKey: "star")
let icon = try? storage.object(ofType: ImageWrapper.self, forKey: "star").image