mirror of
https://github.com/caoer/CodableFirebase.git
synced 2026-04-20 07:05:29 +08:00
Add Firebase encoder
This commit is contained in:
@@ -15,6 +15,7 @@
|
||||
CEFDBF821FF3B35B00745EBE /* Encoder.swift in Sources */ = {isa = PBXBuildFile; fileRef = CEFDBF811FF3B35B00745EBE /* Encoder.swift */; };
|
||||
CEFDBF861FF3B56200745EBE /* Decoder.swift in Sources */ = {isa = PBXBuildFile; fileRef = CEFDBF851FF3B56200745EBE /* Decoder.swift */; };
|
||||
CEFDBF8A1FF3E24200745EBE /* FirebaseDecoder.swift in Sources */ = {isa = PBXBuildFile; fileRef = CEFDBF891FF3E24200745EBE /* FirebaseDecoder.swift */; };
|
||||
CEFDBF8C1FF3E3CB00745EBE /* FirebaseEncoder.swift in Sources */ = {isa = PBXBuildFile; fileRef = CEFDBF8B1FF3E3CB00745EBE /* FirebaseEncoder.swift */; };
|
||||
/* End PBXBuildFile section */
|
||||
|
||||
/* Begin PBXContainerItemProxy section */
|
||||
@@ -39,6 +40,7 @@
|
||||
CEFDBF811FF3B35B00745EBE /* Encoder.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = Encoder.swift; sourceTree = "<group>"; };
|
||||
CEFDBF851FF3B56200745EBE /* Decoder.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = Decoder.swift; sourceTree = "<group>"; };
|
||||
CEFDBF891FF3E24200745EBE /* FirebaseDecoder.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = FirebaseDecoder.swift; sourceTree = "<group>"; };
|
||||
CEFDBF8B1FF3E3CB00745EBE /* FirebaseEncoder.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = FirebaseEncoder.swift; sourceTree = "<group>"; };
|
||||
/* End PBXFileReference section */
|
||||
|
||||
/* Begin PBXFrameworksBuildPhase section */
|
||||
@@ -85,6 +87,7 @@
|
||||
CE7DD3821F9D04AE000225C5 /* FirestoreDecoder.swift */,
|
||||
CE7DD3811F9D04AE000225C5 /* FirestoreEncoder.swift */,
|
||||
CEFDBF891FF3E24200745EBE /* FirebaseDecoder.swift */,
|
||||
CEFDBF8B1FF3E3CB00745EBE /* FirebaseEncoder.swift */,
|
||||
CEFDBF851FF3B56200745EBE /* Decoder.swift */,
|
||||
CEFDBF811FF3B35B00745EBE /* Encoder.swift */,
|
||||
CE7DD36B1F9CFA81000225C5 /* Info.plist */,
|
||||
@@ -213,6 +216,7 @@
|
||||
buildActionMask = 2147483647;
|
||||
files = (
|
||||
CE7DD3831F9D04AE000225C5 /* FirestoreEncoder.swift in Sources */,
|
||||
CEFDBF8C1FF3E3CB00745EBE /* FirebaseEncoder.swift in Sources */,
|
||||
CEFDBF821FF3B35B00745EBE /* Encoder.swift in Sources */,
|
||||
CEFDBF861FF3B56200745EBE /* Decoder.swift in Sources */,
|
||||
CE7DD3841F9D04AE000225C5 /* FirestoreDecoder.swift in Sources */,
|
||||
|
||||
@@ -9,49 +9,10 @@
|
||||
import Foundation
|
||||
|
||||
class _FirebaseEncoder : Encoder {
|
||||
|
||||
/// The strategy to use for encoding `Date` values.
|
||||
public enum DateEncodingStrategy {
|
||||
/// Defer to `Date` for choosing an encoding. This is the default strategy.
|
||||
case deferredToDate
|
||||
|
||||
/// Encode the `Date` as a UNIX timestamp (as a JSON number).
|
||||
case secondsSince1970
|
||||
|
||||
/// Encode the `Date` as UNIX millisecond timestamp (as a JSON number).
|
||||
case millisecondsSince1970
|
||||
|
||||
/// Encode the `Date` as an ISO-8601-formatted string (in RFC 3339 format).
|
||||
@available(OSX 10.12, iOS 10.0, watchOS 3.0, tvOS 10.0, *)
|
||||
case iso8601
|
||||
|
||||
/// Encode the `Date` as a string formatted by the given formatter.
|
||||
case formatted(DateFormatter)
|
||||
|
||||
/// Encode the `Date` as a custom value encoded by the given closure.
|
||||
///
|
||||
/// If the closure fails to encode a value into the given encoder, the encoder will encode an empty automatic container in its place.
|
||||
case custom((Date, Encoder) throws -> Void)
|
||||
}
|
||||
|
||||
/// The strategy to use for encoding `Data` values.
|
||||
public enum DataEncodingStrategy {
|
||||
/// Defer to `Data` for choosing an encoding.
|
||||
case deferredToData
|
||||
|
||||
/// Encoded the `Data` as a Base64-encoded string. This is the default strategy.
|
||||
case base64
|
||||
|
||||
/// Encode the `Data` as a custom value encoded by the given closure.
|
||||
///
|
||||
/// If the closure fails to encode a value into the given encoder, the encoder will encode an empty automatic container in its place.
|
||||
case custom((Data, Encoder) throws -> Void)
|
||||
}
|
||||
|
||||
/// Options set on the top-level encoder to pass down the encoding hierarchy.
|
||||
struct _Options {
|
||||
let dateEncodingStrategy: DateEncodingStrategy?
|
||||
let dataEncodingStrategy: DataEncodingStrategy?
|
||||
let dateEncodingStrategy: FirebaseEncoder.DateEncodingStrategy?
|
||||
let dataEncodingStrategy: FirebaseEncoder.DataEncodingStrategy?
|
||||
let userInfo: [CodingUserInfoKey : Any]
|
||||
}
|
||||
|
||||
|
||||
71
CodableFirebase/FirebaseEncoder.swift
Normal file
71
CodableFirebase/FirebaseEncoder.swift
Normal file
@@ -0,0 +1,71 @@
|
||||
//
|
||||
// FirebaseEncoder.swift
|
||||
// CodableFirebase
|
||||
//
|
||||
// Created by Oleksii on 27/12/2017.
|
||||
// Copyright © 2017 ViolentOctopus. All rights reserved.
|
||||
//
|
||||
|
||||
import Foundation
|
||||
|
||||
open class FirebaseEncoder {
|
||||
/// The strategy to use for encoding `Date` values.
|
||||
public enum DateEncodingStrategy {
|
||||
/// Defer to `Date` for choosing an encoding. This is the default strategy.
|
||||
case deferredToDate
|
||||
|
||||
/// Encode the `Date` as a UNIX timestamp (as a JSON number).
|
||||
case secondsSince1970
|
||||
|
||||
/// Encode the `Date` as UNIX millisecond timestamp (as a JSON number).
|
||||
case millisecondsSince1970
|
||||
|
||||
/// Encode the `Date` as an ISO-8601-formatted string (in RFC 3339 format).
|
||||
@available(OSX 10.12, iOS 10.0, watchOS 3.0, tvOS 10.0, *)
|
||||
case iso8601
|
||||
|
||||
/// Encode the `Date` as a string formatted by the given formatter.
|
||||
case formatted(DateFormatter)
|
||||
|
||||
/// Encode the `Date` as a custom value encoded by the given closure.
|
||||
///
|
||||
/// If the closure fails to encode a value into the given encoder, the encoder will encode an empty automatic container in its place.
|
||||
case custom((Date, Encoder) throws -> Void)
|
||||
}
|
||||
|
||||
/// The strategy to use for encoding `Data` values.
|
||||
public enum DataEncodingStrategy {
|
||||
/// Defer to `Data` for choosing an encoding.
|
||||
case deferredToData
|
||||
|
||||
/// Encoded the `Data` as a Base64-encoded string. This is the default strategy.
|
||||
case base64
|
||||
|
||||
/// Encode the `Data` as a custom value encoded by the given closure.
|
||||
///
|
||||
/// If the closure fails to encode a value into the given encoder, the encoder will encode an empty automatic container in its place.
|
||||
case custom((Data, Encoder) throws -> Void)
|
||||
}
|
||||
|
||||
public init() {}
|
||||
|
||||
open var userInfo: [CodingUserInfoKey : Any] = [:]
|
||||
open var dateEncodingStrategy: DateEncodingStrategy = .deferredToDate
|
||||
open var dataEncodingStrategy: DataEncodingStrategy = .deferredToData
|
||||
|
||||
open func encode<Value : Encodable>(_ value: Value) throws -> Any {
|
||||
let options = _FirebaseEncoder._Options(
|
||||
dateEncodingStrategy: dateEncodingStrategy,
|
||||
dataEncodingStrategy: dataEncodingStrategy,
|
||||
userInfo: userInfo
|
||||
)
|
||||
let encoder = _FirebaseEncoder(options: options)
|
||||
guard let topLevel = try encoder.box_(value) else {
|
||||
throw EncodingError.invalidValue(value,
|
||||
EncodingError.Context(codingPath: [],
|
||||
debugDescription: "Top-level \(Value.self) did not encode any values."))
|
||||
}
|
||||
|
||||
return topLevel
|
||||
}
|
||||
}
|
||||
Reference in New Issue
Block a user