package de.bitdroid.flooding.ods;

import java.io.IOException;
import java.util.HashSet;
import java.util.Map;
import java.util.Set;

import android.content.Context;
import android.content.SharedPreferences;

import com.google.android.gms.gcm.GoogleCloudMessaging;

import de.bitdroid.flooding.R;
import de.bitdroid.flooding.utils.Log;


final class GcmUtils {

	private static final String 
		PATH_NOTIFICATIONS = "notifications",
		PATH_REGISTER = "register",
		PATH_UNREGISTER = "unregister";

	private static final String
		PARAM_CLIENTID = "regId",
		PARAM_SOURCE = "source";

	private static final String PREFS_NAME = "GcmUtilities";
	private static final String PREFS_KEY_CLIENTID = "clientId";



	static void registerSource(Context context, OdsSource source) throws GcmException {
		sourceRegistrationHelper(context, source, true);
	}


	static void unregisterSource(Context context, OdsSource source) throws GcmException {
		sourceRegistrationHelper(context, source, false);
	}


	private static void sourceRegistrationHelper(
			Context context,
			OdsSource source,
			boolean register) throws GcmException {

		if (context == null || source == null)
			throw new NullPointerException("params cannot be null");

		try {
			// register with google
			String clientId = getClientId(context);
			if (clientId == null) {
				clientId = GoogleCloudMessaging
						.getInstance(context)
						.register(getSenderId(context));
				SharedPreferences.Editor editor = getSharedPreferences(context).edit();
				editor.putString(PREFS_KEY_CLIENTID, clientId);
				editor.commit();
			}

			// register on ods server
			RestCall.Builder builder = new RestCall.Builder(
					RestCall.RequestType.POST,
					OdsSourceManager.getInstance(context).getOdsServerName())
				.parameter(PARAM_CLIENTID, clientId)
				.parameter(PARAM_SOURCE, source.getSourceId())
				.path(PATH_NOTIFICATIONS);

			if (register) builder.path(PATH_REGISTER);
			else builder.path(PATH_UNREGISTER);

			builder.build().execute();
		} catch (IOException io) {
			Log.warning(android.util.Log.getStackTraceString(io));
			throw new GcmException(io);
		} catch (RestException re) {
			Log.warning(android.util.Log.getStackTraceString(re));
			throw new GcmException(re);
		}

		SharedPreferences.Editor editor = getSharedPreferences(context).edit();
		if (register) editor.putString(source.toString(), "");
		else {
			SharedPreferences prefs = getSharedPreferences(context);
			if (prefs.getAll().size() == 2) editor.clear();
			else editor.remove(source.toString());
		}
		editor.commit();
	}


	static boolean isSourceRegistered(Context context, OdsSource source) {
		if (context == null || source == null) 
			throw new NullPointerException("params cannot be null");

		return getSharedPreferences(context).contains(source.toString());
	}


	static Set<OdsSource> getRegisteredSources(Context context) {
		Set<OdsSource> sources = new HashSet<OdsSource>();
		Map<String,?> values = getSharedPreferences(context).getAll();
		for (String key : values.keySet()) {
			if (key.equals(PREFS_KEY_CLIENTID)) continue;
			sources.add(OdsSource.fromString(key));
		}
		return sources;
	}


	private static SharedPreferences getSharedPreferences(Context context) {
		return context.getSharedPreferences(PREFS_NAME, Context.MODE_PRIVATE);
	}


	private static String getSenderId(Context context) {
		return context.getString(R.string.GOOGLE_API_KEY);
	}


	private static String getClientId(Context context) {
		// TODO 
		// - Reregister source on app version change
		return getSharedPreferences(context).getString(PREFS_KEY_CLIENTID, null);
	}


	private GcmUtils() { }
}

@@ -200,16 +200,119 @@
 erences;
+%0Aimport android.content.pm.PackageInfo;%0Aimport android.content.pm.PackageManager.NameNotFoundException;
 %0A%0Aimport
@@ -761,24 +761,27 @@
 inal String 
+%0A%09%09
 PREFS_KEY_CL
@@ -799,16 +799,56 @@
 lientId%22
+,%0A%09%09PREFS_KEY_APP_VERSION = %22appVersion%22
 ;%0A%0A%0A%0A%09st
@@ -1699,16 +1699,82 @@
 entId);%0A
+%09%09%09%09editor.putInt(PREFS_KEY_APP_VERSION, getAppVersion(context));%0A
 %09%09%09%09edit
@@ -3277,16 +3277,53 @@
 LIENTID)
+ %7C%7C key.equals(PREFS_KEY_APP_VERSION)
 ) contin
@@ -3720,142 +3720,578 @@
 %7B%0A%09%09
-// TODO %0A%09%09// - Reregister source on app version change%0A%09%09return getSharedPreferences(context).getString(PREFS_KEY_CLIENTID, null);%0A%09%7D
+SharedPreferences prefs = getSharedPreferences(context);%0A%0A%09%09int savedVersion = prefs.getInt(PREFS_KEY_APP_VERSION, Integer.MIN_VALUE);%0A%09%09int currentVersion = getAppVersion(context);%0A%09%09if (savedVersion %3C currentVersion) return null;%0A%0A%09%09return prefs.getString(PREFS_KEY_CLIENTID, null);%0A%09%7D%0A%0A%0A%09private static int getAppVersion(Context context) %7B%0A%09%09try %7B%0A%09%09%09PackageInfo info = context%0A%09%09%09%09.getPackageManager()%0A%09%09%09%09.getPackageInfo(context.getPackageName(), 0);%0A%09%09%09return info.versionCode;%0A%09%09%7D catch (NameNotFoundException nnfe) %7B%0A%09%09%09throw new RuntimeException(nnfe);%0A%09%09%7D%0A%09%7D%0A%09
 %0A%0A%0A%09

clear client id on app upgrade in GcmUtils