0

I am getting json data from an api call and persisting it in room db. The data saves successfully and I'm able to show it in my recyclerview correctly.

The problem occurs when I re-open the app. As the data is from a network call, the same data is re-fetched and again re-saved in the database.

Here's my code for fetching and saving data to room database:

    private void saveAllProducts() {
    AndroidNetworking.get(Constants.ALL_PRODUCTS_ENDPOINT)
            .setTag("Find All Products")
            .setPriority(Priority.HIGH)
            .build()
            .getAsJSONObject(new JSONObjectRequestListener() {
                @Override
                public void onResponse(JSONObject response) {
                    Log.d(TAG, "All Products Response:\t" + response.toString());
                    saveProductsList = new ArrayList<>();

                    try {
                        JSONObject jsonObject = new JSONObject(response.toString());
                        JSONArray data = jsonObject.getJSONArray("products");

                        for (int d = 0; d < data.length(); d++) {
                            JSONObject allProductsObject = data.getJSONObject(d);

                            String id = allProductsObject.getString("_id");
                            String title = allProductsObject.getString("title");
                            String slug = allProductsObject.getString("slug");
                            String price = allProductsObject.getString("price");
                            String desc = allProductsObject.getString("desc");
                            String category = allProductsObject.getString("category");
                            String image = allProductsObject.getString("image");

                            Products products = new Products();
                            products.setProductId(id);
                            products.setProductName(title);
                            products.setProductDesc(desc);
                            products.setCategory(category);
                            products.setProductPrice(price);
                            products.setImage(image);

                            saveProductsList.clear();
                            saveProductsList.add(products);

                            Log.d(TAG, "Saved List Size:\t" + saveProductsList.size());

                        }


                    } catch (JSONException e) {
                        e.printStackTrace();
                    }

                    /**
                     *  Code block to save products
                     * */

                    ProductsDatabase database = 
  ProductsDatabase.getInstance(getBaseContext());

  database.getProductsDAO().insertAllProducts(saveProductsList);


                }

                @Override
                public void onError(ANError anError) {

                }
            });
}

I want to update the database with new data each time but also not duplicating existing data. Is it possible to count and remove the duplicates in the list before saving to room? How can I solve this? Thanks

Here's my DAO interface:

@Dao
public interface ProductsDAO {

     @Query("Select * from products")
     List<Products> getAllProducts();

     @Query("Select * from products where category = :category LIMIT 1")
     Products findByCategory(String category);

     @Insert(onConflict = OnConflictStrategy.IGNORE)
     void insertAllProducts(List<Products> productsList);

 }

1 Answers1

1

In your, Dao add onConflictin the insert method

@Insert(onConflict = OnConflictStrategy.REPLACE)
public void insertProduct(Product product);

this way if the product with the same id is added with different data will be updated. and you will not end up with duplicate rows.

  • consider using OnConflictStrategy.IGNORE if it's guaranteed that a product with the same id won't change.
humazed
  • 74,687
  • 32
  • 99
  • 138
  • I have edited the question. Please take another look. Thanks –  Mar 05 '18 at 00:22
  • I have observed that ur dao interface uses directly the model but I'm using a list of the model class. If I change mine, will it still save more than one object of my model class? –  Mar 05 '18 at 00:31
  • no, I think it's the same, make sure to clear the app data before retying. – humazed Mar 05 '18 at 00:33
  • I have done that, but when I reload that activity then the entries are duplicated. –  Mar 05 '18 at 00:48
  • Is there a way to compare and filter the values in the list itself or return a boolean value in the function to save products? –  Mar 05 '18 at 00:49
  • I don't understand is the reason for duplication is it because you reinsert the data or the List already has duplicates. if it's the latter then my answer doesn't apply. – humazed Mar 05 '18 at 00:53
  • take a look at https://stackoverflow.com/questions/203984/how-do-i-remove-repeated-elements-from-arraylist if your problem that the list already contains duplicates. – humazed Mar 05 '18 at 00:57
  • I have changed my doa interface to reflect yours. The problem I think is with the activity lifecycle. When the activity is resumed/restarted, the network call is made again and then only this happens. How do I control the network call times or some other way? –  Mar 05 '18 at 00:58