10f4e1ab773d4d52bfb85a9ad2f050ead3b8b4e49Fred Quintana/*
20f4e1ab773d4d52bfb85a9ad2f050ead3b8b4e49Fred Quintana * Copyright (C) 2009 The Android Open Source Project
30f4e1ab773d4d52bfb85a9ad2f050ead3b8b4e49Fred Quintana *
40f4e1ab773d4d52bfb85a9ad2f050ead3b8b4e49Fred Quintana * Licensed under the Apache License, Version 2.0 (the "License");
50f4e1ab773d4d52bfb85a9ad2f050ead3b8b4e49Fred Quintana * you may not use this file except in compliance with the License.
60f4e1ab773d4d52bfb85a9ad2f050ead3b8b4e49Fred Quintana * You may obtain a copy of the License at
70f4e1ab773d4d52bfb85a9ad2f050ead3b8b4e49Fred Quintana *
80f4e1ab773d4d52bfb85a9ad2f050ead3b8b4e49Fred Quintana *      http://www.apache.org/licenses/LICENSE-2.0
90f4e1ab773d4d52bfb85a9ad2f050ead3b8b4e49Fred Quintana *
100f4e1ab773d4d52bfb85a9ad2f050ead3b8b4e49Fred Quintana * Unless required by applicable law or agreed to in writing, software
110f4e1ab773d4d52bfb85a9ad2f050ead3b8b4e49Fred Quintana * distributed under the License is distributed on an "AS IS" BASIS,
120f4e1ab773d4d52bfb85a9ad2f050ead3b8b4e49Fred Quintana * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
130f4e1ab773d4d52bfb85a9ad2f050ead3b8b4e49Fred Quintana * See the License for the specific language governing permissions and
140f4e1ab773d4d52bfb85a9ad2f050ead3b8b4e49Fred Quintana * limitations under the License
150f4e1ab773d4d52bfb85a9ad2f050ead3b8b4e49Fred Quintana */
160f4e1ab773d4d52bfb85a9ad2f050ead3b8b4e49Fred Quintana
170f4e1ab773d4d52bfb85a9ad2f050ead3b8b4e49Fred Quintanapackage android.provider;
180f4e1ab773d4d52bfb85a9ad2f050ead3b8b4e49Fred Quintana
190f4e1ab773d4d52bfb85a9ad2f050ead3b8b4e49Fred Quintanaimport android.net.Uri;
200f4e1ab773d4d52bfb85a9ad2f050ead3b8b4e49Fred Quintanaimport android.content.ContentProviderClient;
210f4e1ab773d4d52bfb85a9ad2f050ead3b8b4e49Fred Quintanaimport android.content.ContentValues;
220f4e1ab773d4d52bfb85a9ad2f050ead3b8b4e49Fred Quintanaimport android.content.ContentProviderOperation;
23c4516a7b62de525e3d6d5e76851bdfaf12c11f05Fred Quintanaimport android.content.ContentUris;
240f4e1ab773d4d52bfb85a9ad2f050ead3b8b4e49Fred Quintanaimport android.accounts.Account;
250f4e1ab773d4d52bfb85a9ad2f050ead3b8b4e49Fred Quintanaimport android.database.Cursor;
260f4e1ab773d4d52bfb85a9ad2f050ead3b8b4e49Fred Quintanaimport android.os.RemoteException;
27c4516a7b62de525e3d6d5e76851bdfaf12c11f05Fred Quintanaimport android.util.Pair;
280f4e1ab773d4d52bfb85a9ad2f050ead3b8b4e49Fred Quintana
290f4e1ab773d4d52bfb85a9ad2f050ead3b8b4e49Fred Quintana/**
300f4e1ab773d4d52bfb85a9ad2f050ead3b8b4e49Fred Quintana * The ContentProvider contract for associating data with ana data array account.
310f4e1ab773d4d52bfb85a9ad2f050ead3b8b4e49Fred Quintana * This may be used by providers that want to store this data in a standard way.
320f4e1ab773d4d52bfb85a9ad2f050ead3b8b4e49Fred Quintana */
330f4e1ab773d4d52bfb85a9ad2f050ead3b8b4e49Fred Quintanapublic class SyncStateContract {
340f4e1ab773d4d52bfb85a9ad2f050ead3b8b4e49Fred Quintana    public interface Columns extends BaseColumns {
350f4e1ab773d4d52bfb85a9ad2f050ead3b8b4e49Fred Quintana        /**
360f4e1ab773d4d52bfb85a9ad2f050ead3b8b4e49Fred Quintana         * A reference to the name of the account to which this data belongs
370f4e1ab773d4d52bfb85a9ad2f050ead3b8b4e49Fred Quintana         * <P>Type: STRING</P>
380f4e1ab773d4d52bfb85a9ad2f050ead3b8b4e49Fred Quintana         */
390f4e1ab773d4d52bfb85a9ad2f050ead3b8b4e49Fred Quintana        public static final String ACCOUNT_NAME = "account_name";
400f4e1ab773d4d52bfb85a9ad2f050ead3b8b4e49Fred Quintana
410f4e1ab773d4d52bfb85a9ad2f050ead3b8b4e49Fred Quintana        /**
420f4e1ab773d4d52bfb85a9ad2f050ead3b8b4e49Fred Quintana         * A reference to the type of the account to which this data belongs
430f4e1ab773d4d52bfb85a9ad2f050ead3b8b4e49Fred Quintana         * <P>Type: STRING</P>
440f4e1ab773d4d52bfb85a9ad2f050ead3b8b4e49Fred Quintana         */
450f4e1ab773d4d52bfb85a9ad2f050ead3b8b4e49Fred Quintana        public static final String ACCOUNT_TYPE = "account_type";
460f4e1ab773d4d52bfb85a9ad2f050ead3b8b4e49Fred Quintana
470f4e1ab773d4d52bfb85a9ad2f050ead3b8b4e49Fred Quintana        /**
480f4e1ab773d4d52bfb85a9ad2f050ead3b8b4e49Fred Quintana         * The sync data associated with this account.
490f4e1ab773d4d52bfb85a9ad2f050ead3b8b4e49Fred Quintana         * <P>Type: NONE</P>
500f4e1ab773d4d52bfb85a9ad2f050ead3b8b4e49Fred Quintana         */
510f4e1ab773d4d52bfb85a9ad2f050ead3b8b4e49Fred Quintana        public static final String DATA = "data";
520f4e1ab773d4d52bfb85a9ad2f050ead3b8b4e49Fred Quintana    }
530f4e1ab773d4d52bfb85a9ad2f050ead3b8b4e49Fred Quintana
540f4e1ab773d4d52bfb85a9ad2f050ead3b8b4e49Fred Quintana    public static class Constants implements Columns {
550f4e1ab773d4d52bfb85a9ad2f050ead3b8b4e49Fred Quintana        public static final String CONTENT_DIRECTORY = "syncstate";
560f4e1ab773d4d52bfb85a9ad2f050ead3b8b4e49Fred Quintana    }
570f4e1ab773d4d52bfb85a9ad2f050ead3b8b4e49Fred Quintana
580f4e1ab773d4d52bfb85a9ad2f050ead3b8b4e49Fred Quintana    public static final class Helpers {
59c4516a7b62de525e3d6d5e76851bdfaf12c11f05Fred Quintana        private static final String[] DATA_PROJECTION = new String[]{Columns.DATA, Columns._ID};
600f4e1ab773d4d52bfb85a9ad2f050ead3b8b4e49Fred Quintana        private static final String SELECT_BY_ACCOUNT =
610f4e1ab773d4d52bfb85a9ad2f050ead3b8b4e49Fred Quintana                Columns.ACCOUNT_NAME + "=? AND " + Columns.ACCOUNT_TYPE + "=?";
620f4e1ab773d4d52bfb85a9ad2f050ead3b8b4e49Fred Quintana
630f4e1ab773d4d52bfb85a9ad2f050ead3b8b4e49Fred Quintana        /**
640f4e1ab773d4d52bfb85a9ad2f050ead3b8b4e49Fred Quintana         * Get the sync state that is associated with the account or null.
650f4e1ab773d4d52bfb85a9ad2f050ead3b8b4e49Fred Quintana         * @param provider the {@link ContentProviderClient} that is to be used to communicate
660f4e1ab773d4d52bfb85a9ad2f050ead3b8b4e49Fred Quintana         * with the {@link android.content.ContentProvider} that contains the sync state.
670f4e1ab773d4d52bfb85a9ad2f050ead3b8b4e49Fred Quintana         * @param uri the uri of the sync state
680f4e1ab773d4d52bfb85a9ad2f050ead3b8b4e49Fred Quintana         * @param account the {@link Account} whose sync state should be returned
690f4e1ab773d4d52bfb85a9ad2f050ead3b8b4e49Fred Quintana         * @return the sync state or null if there is no sync state associated with the account
700f4e1ab773d4d52bfb85a9ad2f050ead3b8b4e49Fred Quintana         * @throws RemoteException if there is a failure communicating with the remote
710f4e1ab773d4d52bfb85a9ad2f050ead3b8b4e49Fred Quintana         * {@link android.content.ContentProvider}
720f4e1ab773d4d52bfb85a9ad2f050ead3b8b4e49Fred Quintana         */
730f4e1ab773d4d52bfb85a9ad2f050ead3b8b4e49Fred Quintana        public static byte[] get(ContentProviderClient provider, Uri uri,
740f4e1ab773d4d52bfb85a9ad2f050ead3b8b4e49Fred Quintana                Account account) throws RemoteException {
750f4e1ab773d4d52bfb85a9ad2f050ead3b8b4e49Fred Quintana            Cursor c = provider.query(uri, DATA_PROJECTION, SELECT_BY_ACCOUNT,
76ffd0cb04f97e62d286d185c520580d81a9c328b1Fred Quintana                    new String[]{account.name, account.type}, null);
770f4e1ab773d4d52bfb85a9ad2f050ead3b8b4e49Fred Quintana            try {
780f4e1ab773d4d52bfb85a9ad2f050ead3b8b4e49Fred Quintana                if (c.moveToNext()) {
790f4e1ab773d4d52bfb85a9ad2f050ead3b8b4e49Fred Quintana                    return c.getBlob(c.getColumnIndexOrThrow(Columns.DATA));
800f4e1ab773d4d52bfb85a9ad2f050ead3b8b4e49Fred Quintana                }
810f4e1ab773d4d52bfb85a9ad2f050ead3b8b4e49Fred Quintana            } finally {
820f4e1ab773d4d52bfb85a9ad2f050ead3b8b4e49Fred Quintana                c.close();
830f4e1ab773d4d52bfb85a9ad2f050ead3b8b4e49Fred Quintana            }
840f4e1ab773d4d52bfb85a9ad2f050ead3b8b4e49Fred Quintana            return null;
850f4e1ab773d4d52bfb85a9ad2f050ead3b8b4e49Fred Quintana        }
860f4e1ab773d4d52bfb85a9ad2f050ead3b8b4e49Fred Quintana
870f4e1ab773d4d52bfb85a9ad2f050ead3b8b4e49Fred Quintana        /**
880f4e1ab773d4d52bfb85a9ad2f050ead3b8b4e49Fred Quintana         * Assigns the data array as the sync state for the given account.
890f4e1ab773d4d52bfb85a9ad2f050ead3b8b4e49Fred Quintana         * @param provider the {@link ContentProviderClient} that is to be used to communicate
900f4e1ab773d4d52bfb85a9ad2f050ead3b8b4e49Fred Quintana         * with the {@link android.content.ContentProvider} that contains the sync state.
910f4e1ab773d4d52bfb85a9ad2f050ead3b8b4e49Fred Quintana         * @param uri the uri of the sync state
920f4e1ab773d4d52bfb85a9ad2f050ead3b8b4e49Fred Quintana         * @param account the {@link Account} whose sync state should be set
930f4e1ab773d4d52bfb85a9ad2f050ead3b8b4e49Fred Quintana         * @param data the byte[] that contains the sync state
940f4e1ab773d4d52bfb85a9ad2f050ead3b8b4e49Fred Quintana         * @throws RemoteException if there is a failure communicating with the remote
950f4e1ab773d4d52bfb85a9ad2f050ead3b8b4e49Fred Quintana         * {@link android.content.ContentProvider}
960f4e1ab773d4d52bfb85a9ad2f050ead3b8b4e49Fred Quintana         */
970f4e1ab773d4d52bfb85a9ad2f050ead3b8b4e49Fred Quintana        public static void set(ContentProviderClient provider, Uri uri,
980f4e1ab773d4d52bfb85a9ad2f050ead3b8b4e49Fred Quintana                Account account, byte[] data) throws RemoteException {
990f4e1ab773d4d52bfb85a9ad2f050ead3b8b4e49Fred Quintana            ContentValues values = new ContentValues();
1000f4e1ab773d4d52bfb85a9ad2f050ead3b8b4e49Fred Quintana            values.put(Columns.DATA, data);
101ffd0cb04f97e62d286d185c520580d81a9c328b1Fred Quintana            values.put(Columns.ACCOUNT_NAME, account.name);
102ffd0cb04f97e62d286d185c520580d81a9c328b1Fred Quintana            values.put(Columns.ACCOUNT_TYPE, account.type);
1030f4e1ab773d4d52bfb85a9ad2f050ead3b8b4e49Fred Quintana            provider.insert(uri, values);
1040f4e1ab773d4d52bfb85a9ad2f050ead3b8b4e49Fred Quintana        }
1050f4e1ab773d4d52bfb85a9ad2f050ead3b8b4e49Fred Quintana
106c4516a7b62de525e3d6d5e76851bdfaf12c11f05Fred Quintana        public static Uri insert(ContentProviderClient provider, Uri uri,
107c4516a7b62de525e3d6d5e76851bdfaf12c11f05Fred Quintana                Account account, byte[] data) throws RemoteException {
108c4516a7b62de525e3d6d5e76851bdfaf12c11f05Fred Quintana            ContentValues values = new ContentValues();
109c4516a7b62de525e3d6d5e76851bdfaf12c11f05Fred Quintana            values.put(Columns.DATA, data);
110c4516a7b62de525e3d6d5e76851bdfaf12c11f05Fred Quintana            values.put(Columns.ACCOUNT_NAME, account.name);
111c4516a7b62de525e3d6d5e76851bdfaf12c11f05Fred Quintana            values.put(Columns.ACCOUNT_TYPE, account.type);
112c4516a7b62de525e3d6d5e76851bdfaf12c11f05Fred Quintana            return provider.insert(uri, values);
113c4516a7b62de525e3d6d5e76851bdfaf12c11f05Fred Quintana        }
114c4516a7b62de525e3d6d5e76851bdfaf12c11f05Fred Quintana
115c4516a7b62de525e3d6d5e76851bdfaf12c11f05Fred Quintana        public static void update(ContentProviderClient provider, Uri uri, byte[] data)
116c4516a7b62de525e3d6d5e76851bdfaf12c11f05Fred Quintana                throws RemoteException {
117c4516a7b62de525e3d6d5e76851bdfaf12c11f05Fred Quintana            ContentValues values = new ContentValues();
118c4516a7b62de525e3d6d5e76851bdfaf12c11f05Fred Quintana            values.put(Columns.DATA, data);
119c4516a7b62de525e3d6d5e76851bdfaf12c11f05Fred Quintana            provider.update(uri, values, null, null);
120c4516a7b62de525e3d6d5e76851bdfaf12c11f05Fred Quintana        }
121c4516a7b62de525e3d6d5e76851bdfaf12c11f05Fred Quintana
122c4516a7b62de525e3d6d5e76851bdfaf12c11f05Fred Quintana        public static Pair<Uri, byte[]> getWithUri(ContentProviderClient provider, Uri uri,
123c4516a7b62de525e3d6d5e76851bdfaf12c11f05Fred Quintana                Account account) throws RemoteException {
124c4516a7b62de525e3d6d5e76851bdfaf12c11f05Fred Quintana            Cursor c = provider.query(uri, DATA_PROJECTION, SELECT_BY_ACCOUNT,
125c4516a7b62de525e3d6d5e76851bdfaf12c11f05Fred Quintana                    new String[]{account.name, account.type}, null);
126c4516a7b62de525e3d6d5e76851bdfaf12c11f05Fred Quintana            try {
127c4516a7b62de525e3d6d5e76851bdfaf12c11f05Fred Quintana                if (c.moveToNext()) {
128c4516a7b62de525e3d6d5e76851bdfaf12c11f05Fred Quintana                    long rowId = c.getLong(1);
129c4516a7b62de525e3d6d5e76851bdfaf12c11f05Fred Quintana                    byte[] blob = c.getBlob(c.getColumnIndexOrThrow(Columns.DATA));
130c4516a7b62de525e3d6d5e76851bdfaf12c11f05Fred Quintana                    return Pair.create(ContentUris.withAppendedId(uri, rowId), blob);
131c4516a7b62de525e3d6d5e76851bdfaf12c11f05Fred Quintana                }
132c4516a7b62de525e3d6d5e76851bdfaf12c11f05Fred Quintana            } finally {
133c4516a7b62de525e3d6d5e76851bdfaf12c11f05Fred Quintana                c.close();
134c4516a7b62de525e3d6d5e76851bdfaf12c11f05Fred Quintana            }
135c4516a7b62de525e3d6d5e76851bdfaf12c11f05Fred Quintana            return null;
136c4516a7b62de525e3d6d5e76851bdfaf12c11f05Fred Quintana        }
137c4516a7b62de525e3d6d5e76851bdfaf12c11f05Fred Quintana
1380f4e1ab773d4d52bfb85a9ad2f050ead3b8b4e49Fred Quintana        /**
1390f4e1ab773d4d52bfb85a9ad2f050ead3b8b4e49Fred Quintana         * Creates and returns a ContentProviderOperation that assigns the data array as the
1400f4e1ab773d4d52bfb85a9ad2f050ead3b8b4e49Fred Quintana         * sync state for the given account.
1410f4e1ab773d4d52bfb85a9ad2f050ead3b8b4e49Fred Quintana         * @param uri the uri of the sync state
1420f4e1ab773d4d52bfb85a9ad2f050ead3b8b4e49Fred Quintana         * @param account the {@link Account} whose sync state should be set
1430f4e1ab773d4d52bfb85a9ad2f050ead3b8b4e49Fred Quintana         * @param data the byte[] that contains the sync state
1440f4e1ab773d4d52bfb85a9ad2f050ead3b8b4e49Fred Quintana         * @return the new ContentProviderOperation that assigns the data array as the
1450f4e1ab773d4d52bfb85a9ad2f050ead3b8b4e49Fred Quintana         * account's sync state
1460f4e1ab773d4d52bfb85a9ad2f050ead3b8b4e49Fred Quintana         */
1470f4e1ab773d4d52bfb85a9ad2f050ead3b8b4e49Fred Quintana        public static ContentProviderOperation newSetOperation(Uri uri,
1480f4e1ab773d4d52bfb85a9ad2f050ead3b8b4e49Fred Quintana                Account account, byte[] data) {
1490f4e1ab773d4d52bfb85a9ad2f050ead3b8b4e49Fred Quintana            ContentValues values = new ContentValues();
1500f4e1ab773d4d52bfb85a9ad2f050ead3b8b4e49Fred Quintana            values.put(Columns.DATA, data);
1510f4e1ab773d4d52bfb85a9ad2f050ead3b8b4e49Fred Quintana            return ContentProviderOperation
1520f4e1ab773d4d52bfb85a9ad2f050ead3b8b4e49Fred Quintana                    .newInsert(uri)
153ffd0cb04f97e62d286d185c520580d81a9c328b1Fred Quintana                    .withValue(Columns.ACCOUNT_NAME, account.name)
154ffd0cb04f97e62d286d185c520580d81a9c328b1Fred Quintana                    .withValue(Columns.ACCOUNT_TYPE, account.type)
1550f4e1ab773d4d52bfb85a9ad2f050ead3b8b4e49Fred Quintana                    .withValues(values)
1560f4e1ab773d4d52bfb85a9ad2f050ead3b8b4e49Fred Quintana                    .build();
1570f4e1ab773d4d52bfb85a9ad2f050ead3b8b4e49Fred Quintana        }
158c4516a7b62de525e3d6d5e76851bdfaf12c11f05Fred Quintana
159c4516a7b62de525e3d6d5e76851bdfaf12c11f05Fred Quintana        /**
160c4516a7b62de525e3d6d5e76851bdfaf12c11f05Fred Quintana         * Creates and returns a ContentProviderOperation that assigns the data array as the
161c4516a7b62de525e3d6d5e76851bdfaf12c11f05Fred Quintana         * sync state for the given account.
162c4516a7b62de525e3d6d5e76851bdfaf12c11f05Fred Quintana         * @param uri the uri of the specific sync state to set
163c4516a7b62de525e3d6d5e76851bdfaf12c11f05Fred Quintana         * @param data the byte[] that contains the sync state
164c4516a7b62de525e3d6d5e76851bdfaf12c11f05Fred Quintana         * @return the new ContentProviderOperation that assigns the data array as the
165c4516a7b62de525e3d6d5e76851bdfaf12c11f05Fred Quintana         * account's sync state
166c4516a7b62de525e3d6d5e76851bdfaf12c11f05Fred Quintana         */
167c4516a7b62de525e3d6d5e76851bdfaf12c11f05Fred Quintana        public static ContentProviderOperation newUpdateOperation(Uri uri, byte[] data) {
168c4516a7b62de525e3d6d5e76851bdfaf12c11f05Fred Quintana            ContentValues values = new ContentValues();
169c4516a7b62de525e3d6d5e76851bdfaf12c11f05Fred Quintana            values.put(Columns.DATA, data);
170c4516a7b62de525e3d6d5e76851bdfaf12c11f05Fred Quintana            return ContentProviderOperation
171c4516a7b62de525e3d6d5e76851bdfaf12c11f05Fred Quintana                    .newUpdate(uri)
172c4516a7b62de525e3d6d5e76851bdfaf12c11f05Fred Quintana                    .withValues(values)
173c4516a7b62de525e3d6d5e76851bdfaf12c11f05Fred Quintana                    .build();
174c4516a7b62de525e3d6d5e76851bdfaf12c11f05Fred Quintana        }
1750f4e1ab773d4d52bfb85a9ad2f050ead3b8b4e49Fred Quintana    }
1760f4e1ab773d4d52bfb85a9ad2f050ead3b8b4e49Fred Quintana}
177