how to avoid adding the same data in Realm databas

2019-08-28 03:15发布

I have wishlistVC that has collection view like the picture below:

enter image description here

I have product realm model like this:

class Product : Object {

    @objc dynamic var productID : String = ""
    @objc dynamic var name : String = ""
    @objc dynamic var unitPrice: Double = 0.0
    @objc dynamic var quantity = 0
    @objc dynamic var descriptionProduct : String = ""
    @objc dynamic var hasBeenAddedToWishList : Bool = false
    @objc dynamic var hasBeenAddedToCart : Bool = false
    @objc dynamic var isNewProduct : Bool = false
    var imagePaths = List<String>()
}

and WishList realm model like this:

    class WishList : Object {
        @objc dynamic var userID: String = ""
        var products = List<Product>() // many to many relationship

   static func getWishListFromRealmDatabase() -> WishList {

        let userID = "1"
        let allWishList = RealmService.shared.realm.objects(WishList.self)
        let theWishList = allWishList.filter("userID CONTAINS[cd] %@", userID).first


        if let userWishList = theWishList {
            return userWishList
        } else {
            // WishList never setted up before in Realm database container
            // then create WishList in realm database

            let newWishList = WishList()
            newWishList.userID = userID
            newWishList.products = List<Product>()
            RealmService.shared.save(object: newWishList)
            return newWishList
        }
    }


    static func addProductToWishListRealmDatabase(userWishList: WishList, selectedProduct: Product) {

        // to check wheter the selected product from user is already in WishList or not
        if userWishList.products.filter("productID == %@", selectedProduct.productID).first == nil {

            RealmService.shared.save(expression: {
                selectedProduct.hasBeenAddedToWishList = true
                userWishList.products.append(selectedProduct)
            })

        }


    }

     }

when the user tap that love button, here is the code used to add product to WishList:

func addProductToWishListRealmDatabase(userWishList: WishList, selectedProduct: Product) {

        // to check wheter the selected product from user is already in WishList.products or not
        if userWishList.products.filter("productID == %@", selectedProduct.productID).first == nil {

            // write in realm database
            RealmService.shared.save(expression: { // <-- this is just a wrapper to avoid write do try catch block all over the place

                selectedProduct.hasBeenAddedToWishList = true
                userWishList.products.append(selectedProduct)


            })

        }


    }

and here is the full simplified code of my WishListVC:

class WishListVC : UIViewController {

    @IBOutlet weak var wishListCollectionView: UICollectionView!

    private var userWishList : WishList?
    private var products = List<Product>()
    private var selectedProduct : Product?

    override func viewDidLoad() {
        super.viewDidLoad()

    }

    override func viewWillAppear(_ animated: Bool) {
        super.viewWillAppear(animated)

        userWishList = WishList.getWishListFromRealmDatabase() // the definition is in the code above
        guard let userWishList = userWishList else {return}
        products = userWishList.products

    }



}

extension WishListVC : ListProductCellDelegate {

    func likeButtonDidTapped(at selectedIndexPath: IndexPath, productHasBeenLiked: Bool, collectionView: UICollectionView) {

        guard let userWishList = userWishList else {return}
        let selectedProduct = products[selectedIndexPath.item]

        if productHasBeenLiked {
            WishList.removeProductFromWishListRealmDatabase(userWishList: userWishList, selectedProduct: selectedProduct)
        } else {
            WishList.addProductToWishListRealmDatabase(userWishList: userWishList, selectedProduct: selectedProduct)
        }

        wishListCollectionView.reloadData()
        self.wishListCollectionView.isHidden = userWishList.products.isEmpty

    }

}

if I append a product to the wishlist model like the code above, it will affect to the Product.self in realm database, it will keep adding the product in 'Product Realm Database', as you can see in the image below, there are 9 data in Product, but as you can see some of the product have the same productID, there are 3 products that have 'a' as the productID .

enter image description here

so how to avoid adding the product that has the same productID in 'Product Realm Database' (Product.self) when I modify the WishList by appending the product to wishlist.products ?

I have also tried to add primary key using:

override static func primaryKey() -> String? {
        return "productID"
}

but It makes crash with message:

*** Terminating app due to uncaught exception 'RLMException', reason: 'Attempting to create an object of type 'Product' with an existing primary key value 'a'.'

it will throw error because I add productID = 'a'

what should I do ? how to append product to the WishList model but I also can avoid adding the same product that has the same productID to the Product Realm database model (Product.self) ?

do I use the wrong approach to add the product to the wishlist?

标签: ios swift realm
0条回答
登录 后发表回答