package de.bitdroid.flooding.ods.data;

import android.content.ContentProviderClient;
import android.content.ContentProviderOperation;
import android.content.ContentValues;
import android.content.OperationApplicationException;
import android.database.Cursor;
import android.os.RemoteException;

import org.json.JSONArray;
import org.json.JSONException;
import org.json.JSONObject;

import java.util.ArrayList;

import de.bitdroid.flooding.utils.Log;


final class Processor {

	private final ContentProviderClient provider;
	private final OdsSource source;

	public Processor(ContentProviderClient provider, OdsSource source) {
		this.provider = provider;
		this.source = source;
	}


	public void processGetAll(String jsonString) 
			throws RemoteException, JSONException, OperationApplicationException {

		// delete all entries
		int deleteCount = provider.delete(source.toUri(), null, null);
		Log.debug("Removed " + deleteCount + " rows");

		// insert new entries
		ArrayList<ContentProviderOperation> operations = new ArrayList<ContentProviderOperation>();
		JSONArray json = new JSONArray(jsonString);
		Log.debug("Fetched " + json.length() + " items from server");
		for (int i = 0; i < json.length(); i++) {
			ContentProviderOperation operation = insertIntoProvider(json.getJSONObject(i));
			if (operation != null) operations.add(operation);
			if (operations.size() >= 100) {
				provider.applyBatch(operations);
				operations.clear();
			}
		}

		if (operations.size() > 0) provider.applyBatch(operations);
	}


	private ContentProviderOperation insertIntoProvider(JSONObject object) 
			throws RemoteException, JSONException {

		String serverId = object.optString("_id", null);
		ContentValues data = source.saveData(object);
		data.put(OdsSource.COLUMN_SERVER_ID, serverId);
		data.put(OdsSource.COLUMN_SYNC_STATUS, SyncStatus.SYNCED.toString());

		// query if already present
		Cursor cursor = null;
		try {
			cursor = provider.query(
					source.toUri(),
					new String[] { OdsSource.COLUMN_ID, OdsSource.COLUMN_SERVER_ID },
					OdsSource.COLUMN_SERVER_ID + " = ?",
					new String[] { serverId },
					null);

			// update data 
			if (cursor.getCount() >= 1) {
				cursor.moveToFirst();
				String id = cursor.getString(0);
				data.put(OdsSource.COLUMN_ID, id);

				if (cursor.getCount() > 1) {
					Log.warning("Found multiple objects in db with server id " + serverId);
				}

				return ContentProviderOperation
					.newUpdate(source.toUri())
					.withValues(data)
					.build();

			// insert new data
			} else {
				return ContentProviderOperation
					.newInsert(source.toUri())
					.withValues(data)
					.build();
			}
		} finally {
			if (cursor != null) cursor.close();
		}
	}

}

@@ -804,147 +804,8 @@
  %7B%0A%0A
-%09%09// delete all entries%0A%09%09int deleteCount = provider.delete(source.toUri(), null, null);%0A%09%09Log.debug(%22Removed %22 + deleteCount + %22 rows%22);%0A%0A
 %09%09//
@@ -824,16 +824,16 @@
 entries%0A
+
 %09%09ArrayL
@@ -1498,16 +1498,145 @@
 tion %7B%0A%0A
+%09%09// this is a hack that updates pegelonline data only, since ODS does currently%0A%09%09// (as of 29/07/14) not support updating data%0A
 %09%09String
@@ -1669,18 +1669,13 @@
 ng(%22
-_
+uu
 id%22
-, null
 );%0A%09
@@ -2195,22 +2195,19 @@
 ();%0A%09%09%09%09
-Str
 in
-g
+t
  id = cu
@@ -2214,22 +2214,19 @@
 rsor.get
-String
+Int
 (0);%0A%09%09%09
@@ -2407,32 +2407,32 @@
 oviderOperation%0A
-
 %09%09%09%09%09.newUpdate(
@@ -2439,32 +2439,117 @@
 source.toUri())%0A
+%09%09%09%09%09.withSelection(OdsSource.COLUMN_ID + %22=?%22, new String%5B%5D %7B String.valueOf(id) %7D)%0A
 %09%09%09%09%09.withValues

update ods data instead of deleting and fetching it