Note that unlike other application components, calls on to the 29 | * IBinder interface returned here may not happen on the main thread 30 | * of the process. More information about the main thread can be found in 31 | * Processes and 32 | * Threads.
33 | * 34 | * @param intent The Intent that was used to bind to this service, 35 | * as given to {@link Context#bindService 36 | * Context.bindService}. Note that any extras that were included with 37 | * the Intent at that point will not be seen here. 38 | * @return Return an IBinder through which clients can call on to the 39 | * service. 40 | */ 41 | @Nullable 42 | @Override 43 | public IBinder onBind(Intent intent) { 44 | return mAuthenticator.getIBinder(); 45 | } 46 | } 47 | -------------------------------------------------------------------------------- /app/src/main/java/com/amrendra/codefiesta/CodeFiestaApplication.java: -------------------------------------------------------------------------------- 1 | package com.amrendra.codefiesta; 2 | 3 | import android.app.Application; 4 | 5 | import com.amrendra.codefiesta.sync.CodeFiestaSyncAdapter; 6 | import com.amrendra.codefiesta.utils.AppUtils; 7 | import com.amrendra.codefiesta.utils.Debug; 8 | import com.amrendra.codefiesta.utils.UserPreferences; 9 | import com.crashlytics.android.Crashlytics; 10 | import com.google.android.gms.analytics.GoogleAnalytics; 11 | import com.google.android.gms.analytics.Tracker; 12 | import io.fabric.sdk.android.Fabric; 13 | 14 | /** 15 | * Created by Amrendra Kumar on 05/04/16. 16 | */ 17 | public class CodeFiestaApplication extends Application { 18 | 19 | private Tracker mTracker; 20 | 21 | @Override 22 | public void onCreate() { 23 | super.onCreate(); 24 | Fabric.with(this, new Crashlytics()); 25 | AppUtils.cacheResources(this); 26 | getDefaultTracker(); 27 | checkAndSync(); 28 | } 29 | 30 | public void checkAndSync() { 31 | long lastSyncTime = UserPreferences.getInstance(this) 32 | .readValue(AppUtils.LAST_SYNC_PERFORMED, AppUtils 33 | .LAST_SYNC_PERFORMED_DEFAULT_VALUE); 34 | 35 | long currTime = System.currentTimeMillis() / 1000; 36 | if (currTime - lastSyncTime > AppUtils.SIX_HOURS) { 37 | CodeFiestaSyncAdapter.syncImmediately(this); 38 | } 39 | } 40 | 41 | public static void shouldNotHappen(String msg) { 42 | Debug.e(msg, false); 43 | } 44 | 45 | synchronized public Tracker getDefaultTracker() { 46 | if (mTracker == null) { 47 | GoogleAnalytics analytics = GoogleAnalytics.getInstance(this); 48 | // To enable debug logging use: adb shell setprop log.tag.GAv4 DEBUG 49 | mTracker = analytics.newTracker(R.xml.global_tracker); 50 | } 51 | return mTracker; 52 | } 53 | } 54 | -------------------------------------------------------------------------------- /app/src/main/res/layout/selection_fragment.xml: -------------------------------------------------------------------------------- 1 |Note that unlike other application components, calls on to the 34 | * IBinder interface returned here may not happen on the main thread 35 | * of the process. More information about the main thread can be found in 36 | * Processes and 37 | * Threads.
38 | * 39 | * @param intent The Intent that was used to bind to this service, 40 | * as given to {@link Context#bindService 41 | * Context.bindService}. Note that any extras that were included with 42 | * the Intent at that point will not be seen here. 43 | * @return Return an IBinder through which clients can call on to the 44 | * service. 45 | */ 46 | @Nullable 47 | @Override 48 | public IBinder onBind(Intent intent) { 49 | return mCodeFiestaSyncAdapter.getSyncAdapterBinder(); 50 | } 51 | } 52 | -------------------------------------------------------------------------------- /app/src/main/res/menu/menu_nav.xml: -------------------------------------------------------------------------------- 1 | -------------------------------------------------------------------------------- /app/src/test/java/com/amrendra/codefiesta/utils/DateUtilsTest.java: -------------------------------------------------------------------------------- 1 | package com.amrendra.codefiesta.utils; 2 | 3 | import junit.framework.Assert; 4 | 5 | import org.junit.After; 6 | import org.junit.Before; 7 | import org.junit.Test; 8 | 9 | import java.util.TimeZone; 10 | 11 | /** 12 | * Created by Amrendra Kumar on 09/04/16. 13 | */ 14 | public class DateUtilsTest { 15 | 16 | String timeStr[] = { 17 | "2016-04-08T18:30:00", 18 | "2016-04-08T08:30:00", 19 | "2016-04-11T09:30:00", 20 | "2016-04-01T09:32:00", 21 | }; 22 | 23 | String timeStrGMT[] = { 24 | "2016-04-08 18:30:00", 25 | "2016-04-08 08:30:00", 26 | "2016-04-11 09:30:00", 27 | "2016-04-01 09:32:00", 28 | }; 29 | 30 | String timeStrIST[] = { 31 | "2016-04-09 00:00:00", 32 | "2016-04-08 14:00:00", 33 | "2016-04-11 15:00:00", 34 | "2016-04-01 15:02:00", 35 | }; 36 | 37 | long epochTimes[] = { 38 | 1460140200, 39 | 1460104200, 40 | 1460367000, 41 | 1459503120, 42 | }; 43 | 44 | @Before 45 | public void setUp() throws Exception { 46 | } 47 | 48 | @After 49 | public void tearDown() throws Exception { 50 | 51 | } 52 | 53 | @Test 54 | public void testGetEpochTime() throws Exception { 55 | for (int i = 0; i < timeStr.length; i++) { 56 | long t = DateUtils.getEpochTime(timeStr[i]); 57 | Assert.assertEquals("Epoch time different", epochTimes[i], t); 58 | } 59 | } 60 | 61 | @Test 62 | public void testEpochToDateTimeGMT() throws Exception { 63 | for (int i = 0; i < epochTimes.length; i++) { 64 | String t = DateUtils.epochToDateTimeGmt(epochTimes[i]); 65 | Assert.assertEquals("Epoch time different", timeStrGMT[i], t); 66 | } 67 | } 68 | 69 | @Test 70 | public void testEpochToDateTimeLocal() throws Exception { 71 | TimeZone.setDefault(TimeZone.getTimeZone("IST")); 72 | for (int i = 0; i < epochTimes.length; i++) { 73 | String t = DateUtils.epochToDateTimeLocal(epochTimes[i]); 74 | Assert.assertEquals("Epoch time different", timeStrIST[i], t); 75 | } 76 | } 77 | 78 | } -------------------------------------------------------------------------------- /app/src/main/java/com/amrendra/codefiesta/model/Meta.java: -------------------------------------------------------------------------------- 1 | package com.amrendra.codefiesta.model; 2 | 3 | import android.os.Parcel; 4 | import android.os.Parcelable; 5 | 6 | import com.google.gson.annotations.SerializedName; 7 | 8 | /** 9 | * Created by Amrendra Kumar on 06/04/16. 10 | */ 11 | public class Meta implements Parcelable { 12 | 13 | int limit; 14 | String next; 15 | int offset; 16 | String previous; 17 | 18 | @SerializedName("total_count") 19 | long totalCount; 20 | 21 | 22 | protected Meta(Parcel in) { 23 | limit = in.readInt(); 24 | next = in.readString(); 25 | offset = in.readInt(); 26 | previous = in.readString(); 27 | totalCount = in.readLong(); 28 | } 29 | 30 | public static final Creator CREATOR = new Creator() { 31 | @Override 32 | public Meta createFromParcel(Parcel in) { 33 | return new Meta(in); 34 | } 35 | 36 | @Override 37 | public Meta[] newArray(int size) { 38 | return new Meta[size]; 39 | } 40 | }; 41 | 42 | public int getLimit() { 43 | return limit; 44 | } 45 | 46 | public void setLimit(int limit) { 47 | this.limit = limit; 48 | } 49 | 50 | public String getNext() { 51 | return next; 52 | } 53 | 54 | public void setNext(String next) { 55 | this.next = next; 56 | } 57 | 58 | public int getOffset() { 59 | return offset; 60 | } 61 | 62 | public void setOffset(int offset) { 63 | this.offset = offset; 64 | } 65 | 66 | public String getPrevious() { 67 | return previous; 68 | } 69 | 70 | public void setPrevious(String previous) { 71 | this.previous = previous; 72 | } 73 | 74 | public long getTotalCount() { 75 | return totalCount; 76 | } 77 | 78 | public void setTotalCount(long totalCount) { 79 | this.totalCount = totalCount; 80 | } 81 | 82 | @Override 83 | public int describeContents() { 84 | return 0; 85 | } 86 | 87 | @Override 88 | public void writeToParcel(Parcel dest, int flags) { 89 | dest.writeInt(limit); 90 | dest.writeString(next); 91 | dest.writeInt(offset); 92 | dest.writeString(previous); 93 | dest.writeLong(totalCount); 94 | } 95 | } 96 | -------------------------------------------------------------------------------- /app/src/main/java/com/amrendra/codefiesta/utils/CalendarUtils.java: -------------------------------------------------------------------------------- 1 | package com.amrendra.codefiesta.utils; 2 | 3 | import android.content.Context; 4 | import android.database.Cursor; 5 | import android.provider.CalendarContract; 6 | 7 | /** 8 | * Created by Amrendra Kumar on 24/04/16. 9 | */ 10 | public class CalendarUtils { 11 | public static long getCalendarId(Context mContext) { 12 | Debug.c(); 13 | String[] projection = new String[]{CalendarContract.Calendars._ID, CalendarContract 14 | .Calendars.NAME, CalendarContract.Calendars.ACCOUNT_NAME, CalendarContract 15 | .Calendars.CALENDAR_TIME_ZONE}; 16 | 17 | try { 18 | Cursor cursor = mContext.getContentResolver().query( 19 | CalendarContract.Calendars.CONTENT_URI, 20 | projection, 21 | null, 22 | null, 23 | null); 24 | if (cursor != null) { 25 | try { 26 | if (cursor.moveToFirst()) { 27 | int id = cursor.getInt(cursor.getColumnIndex(CalendarContract.Calendars 28 | ._ID)); 29 | String name = cursor.getString(cursor.getColumnIndex(CalendarContract 30 | .Calendars 31 | .NAME)); 32 | String accountName = cursor.getString(cursor.getColumnIndex(CalendarContract 33 | .Calendars 34 | .ACCOUNT_NAME)); 35 | String timezone = cursor.getString(cursor.getColumnIndex(CalendarContract 36 | .Calendars 37 | .CALENDAR_TIME_ZONE)); 38 | Debug.i("id: " + id + " name: " + name + " accName: " + accountName + " zone: " + 39 | "" + timezone, false); 40 | return id; 41 | } else { 42 | return AppUtils.STATUS_CALENDAR_NO_ACCOUNT; 43 | } 44 | } finally { 45 | cursor.close(); 46 | } 47 | } 48 | } catch (SecurityException ex) { 49 | ex.printStackTrace(); 50 | } 51 | return AppUtils.STATUS_CALENDAR_PERMISSION_ERROR; 52 | } 53 | } 54 | -------------------------------------------------------------------------------- /app/src/main/res/layout-sw600dp/activity_main.xml: -------------------------------------------------------------------------------- 1 | 2 |