skip to Main Content

Firebase Android library has Exclude annotation which allows to ignore a property when saving/retrieving object to and from database.

Is there a similar property wrapper for Swift FirebaseFirestoreSwift library?

As far as I can see DocumentId annotation has equivalent property wrapper in Swift library.

What is the best way to exclude property from database in Codable object in Swift anyway?

2

Answers


  1. Chosen as BEST ANSWER

    I've created such wrapper. It makes code more concise. It indeed deals with Codable, and should work fine with Firebase Coder as good as with any other one (such as JSONEncoder/Decoder). Let me modestly present

    @CodableExcluded

    import Foundation
    
    @propertyWrapper
    public struct CodableExcluded<Wrapped> {
        public var wrappedValue: Wrapped?
        
        public init(wrappedValue: Wrapped?) {
            self.wrappedValue = wrappedValue
        }
    }
    
    extension CodableExcluded: Encodable {
        public func encode(to encoder: Encoder) throws {
            // Do nothing. Actually this is never called due to empty `encode<Wrapped>` func in `KeyedEncodingContainer`
        }
    }
    
    extension CodableExcluded: Decodable {
        public init(from decoder: Decoder) throws {
            self.wrappedValue = nil
        }
    }
    
    extension KeyedDecodingContainer {
        public func decode<Wrapped>(_ type: CodableExcluded<Wrapped>.Type, forKey key: Self.Key) throws -> CodableExcluded<Wrapped> {
            CodableExcluded(wrappedValue: nil)
        }
    }
    
    extension KeyedEncodingContainer {
        public mutating func encode<Wrapped>(_ value: CodableExcluded<Wrapped>, forKey key: KeyedEncodingContainer<K>.Key) throws {
            // Do nothing.
        }
    }
    

    Usage

    struct Test: Codable {
        var codedString = "This will be included during encoding and decoded back."
        @CodableExcluded var nonCodedString: String? = "This will NOT be included when encodig and assigned `nil` when decoded from decoded."
    }
    
    let data = try JSONEncoder().encode(Test())
    print(String(data: data, encoding: .utf8) ?? "")
    
    let obj = try JSONDecoder().decode(Test.self, from: data)
    print(obj)
    

  2. Using CodingKeys is the default mechanism to fine-tune Codable’s mapping. If you’re interested in how Codable works in general, check out this excellent book: Flight School Guide to Swift Codable and this Hacking with Swift article: Codable cheat sheet – Hacking with Swift.

    The Firebase documentation has a comprehensive guide for using Codable with Firestore: Map Cloud Firestore data with Swift Codable, which talks about customising the mapping in this section:

    Any property that is not listed as a case on the respective CodingKeys enum will be ignored during the mapping process. This can actually be convenient if we specifically want to exclude some of the properties from being mapped.

    If you find anything missing in this guide, please let us know so we can add it.

    Login or Signup to reply.
Please signup or login to give your own answer.
Back To Top
Search