Skip to content

Commit a4548b2

Browse files
committed
now account manager example can update contacts.
1 parent 75b9f44 commit a4548b2

File tree

4 files changed

+117
-9
lines changed

4 files changed

+117
-9
lines changed

account-manager-example/AndroidManifest.xml

+3-2
Original file line numberDiff line numberDiff line change
@@ -24,9 +24,9 @@
2424
<category android:name="android.intent.category.LAUNCHER" />
2525
</intent-filter>
2626
</activity>
27-
<service android:name=".core.ExampleAuthenticatationService">
27+
<service android:name=".core.ExampleAuthenticatationService" android:process=":auth">
2828
<intent-filter>
29-
<action android:name="android.accounts.AccountAuthenticator"></action>
29+
<action android:name="android.accounts.AccountAuthenticator" />
3030
</intent-filter>
3131
<meta-data android:name="android.accounts.AccountAuthenticator" android:resource="@xml/authenticator" />
3232
</service>
@@ -35,6 +35,7 @@
3535
<action android:name="android.content.SyncAdapter" />
3636
</intent-filter>
3737
<meta-data android:name="android.content.SyncAdapter" android:resource="@xml/syncadapter" />
38+
<meta-data android:name="android.provider.CONTACTS_STRUCTURE" android:resource="@xml/contacts" />
3839
</service>
3940
</application>
4041
</manifest>
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,8 @@
1+
<ContactsSource xmlns:android="http://schemas.android.com/apk/res/android">
2+
<ContactsDataKind
3+
android:icon="@drawable/ic_launcher"
4+
android:mimeType="vnd.android.cursor.item/vnd.net.yuki24.examples.profile"
5+
android:summaryColumn="data2"
6+
android:detailColumn="data3"
7+
android:detailSocialSummary="true" />
8+
</ContactsSource>

account-manager-example/src/net/yuki24/examples/AccountManager/AccountManagerExampleActivity.java

-5
Original file line numberDiff line numberDiff line change
@@ -1,16 +1,11 @@
11
package net.yuki24.examples.AccountManager;
22

33
import java.util.ArrayList;
4-
5-
import net.yuki24.examples.AccountManager.authenticator.ExampleAccountAuthenticator;
6-
74
import android.accounts.Account;
85
import android.accounts.AccountAuthenticatorActivity;
96
import android.accounts.AccountManager;
10-
import android.app.Activity;
117
import android.content.Intent;
128
import android.os.Bundle;
13-
import android.provider.SyncStateContract.Constants;
149

1510
public class AccountManagerExampleActivity extends AccountAuthenticatorActivity {
1611
@Override

account-manager-example/src/net/yuki24/examples/AccountManager/core/ContactsSyncAdapterService.java

+106-2
Original file line numberDiff line numberDiff line change
@@ -1,16 +1,29 @@
11
package net.yuki24.examples.AccountManager.core;
22

3+
import java.util.ArrayList;
4+
import java.util.HashMap;
35
import android.accounts.Account;
46
import android.accounts.OperationCanceledException;
57
import android.app.Service;
68
import android.content.AbstractThreadedSyncAdapter;
79
import android.content.ContentProviderClient;
10+
import android.content.ContentProviderOperation;
811
import android.content.ContentResolver;
12+
import android.content.ContentUris;
913
import android.content.Context;
1014
import android.content.Intent;
1115
import android.content.SyncResult;
16+
import android.database.Cursor;
17+
import android.net.Uri;
1218
import android.os.Bundle;
1319
import android.os.IBinder;
20+
import android.provider.BaseColumns;
21+
import android.provider.ContactsContract;
22+
import android.provider.ContactsContract.CommonDataKinds.StructuredName;
23+
import android.provider.ContactsContract.Data;
24+
import android.provider.ContactsContract.RawContacts;
25+
import android.provider.ContactsContract.RawContacts.Entity;
26+
import android.provider.ContactsContract.CommonDataKinds.Phone;
1427
import android.util.Log;
1528

1629
public class ContactsSyncAdapterService extends Service {
@@ -35,6 +48,8 @@ public void onPerformSync(Account account, Bundle extras, String authority, Cont
3548
try {
3649
ContactsSyncAdapterService.performSync(mContext, account, extras, authority, provider, syncResult);
3750
} catch (OperationCanceledException e) {
51+
// TODO Auto-generated catch block
52+
e.printStackTrace();
3853
}
3954
}
4055
}
@@ -51,10 +66,99 @@ private SyncAdapterImpl getSyncAdapter() {
5166
return sSyncAdapter;
5267
}
5368

54-
private static void performSync(Context context, Account account, Bundle extras, String authority, ContentProviderClient provider, SyncResult syncResult)
55-
throws OperationCanceledException {
69+
private static void performSync(Context context, Account account, Bundle extras, String authority,
70+
ContentProviderClient provider, SyncResult syncResult) throws OperationCanceledException {
5671
mContentResolver = context.getContentResolver();
5772
Log.i(TAG, "performSync: " + account.toString());
73+
5874
//This is where the magic will happen!
75+
HashMap<String, Long> localContacts = new HashMap<String, Long>();
76+
mContentResolver = context.getContentResolver();
77+
78+
// Load the local example contacts
79+
Uri rawContactUri = RawContacts.CONTENT_URI.buildUpon()
80+
.appendQueryParameter(RawContacts.ACCOUNT_NAME, account.name)
81+
.appendQueryParameter(RawContacts.ACCOUNT_TYPE, account.type)
82+
.build();
83+
Cursor c1 = mContentResolver.query(rawContactUri, new String[]{BaseColumns._ID, RawContacts.SYNC1}, null, null, null);
84+
while (c1.moveToNext()) { localContacts.put(c1.getString(1), c1.getLong(0)); }
85+
86+
ArrayList<ContentProviderOperation> operationList = new ArrayList<ContentProviderOperation>();
87+
try {
88+
// Here comes the actual update of contacts
89+
if (!localContacts.containsKey("example"))
90+
addContact(account, "Account Example", "example");
91+
else
92+
updateContactStatus(operationList, localContacts.get("example"));
93+
94+
if(operationList.size() > 0) mContentResolver.applyBatch(ContactsContract.AUTHORITY, operationList);
95+
} catch (Exception e) {
96+
// TODO Auto-generated catch block
97+
e.printStackTrace();
98+
}
99+
}
100+
101+
private static void addContact(Account account, String name, String username) {
102+
ArrayList<ContentProviderOperation> operationList = new ArrayList<ContentProviderOperation>();
103+
104+
// Create our RawContact
105+
ContentProviderOperation.Builder builder = ContentProviderOperation.newInsert(RawContacts.CONTENT_URI);
106+
builder.withValue(RawContacts.ACCOUNT_NAME, account.name);
107+
builder.withValue(RawContacts.ACCOUNT_TYPE, account.type);
108+
builder.withValue(RawContacts.SYNC1, username);
109+
operationList.add(builder.build());
110+
111+
// Create a Data record of common type 'StructuredName' for our RawContact
112+
builder = ContentProviderOperation.newInsert(Data.CONTENT_URI);
113+
builder.withValueBackReference(StructuredName.RAW_CONTACT_ID, 0);
114+
builder.withValue(Data.MIMETYPE, StructuredName.CONTENT_ITEM_TYPE);
115+
builder.withValue(StructuredName.DISPLAY_NAME, name);
116+
operationList.add(builder.build());
117+
118+
// Create a Data record of phone number
119+
builder = ContentProviderOperation.newInsert(Data.CONTENT_URI);
120+
builder.withValueBackReference(StructuredName.RAW_CONTACT_ID, 0);
121+
builder.withValue(Data.MIMETYPE, Phone.CONTENT_ITEM_TYPE);
122+
builder.withValue(Phone.NUMBER, "819012345678");
123+
operationList.add(builder.build());
124+
125+
// Create a Data record of custom type to display a link to the sample profile
126+
builder = ContentProviderOperation.newInsert(Data.CONTENT_URI);
127+
builder.withValueBackReference(Data.RAW_CONTACT_ID, 0);
128+
builder.withValue(Data.MIMETYPE, "vnd.android.cursor.item/vnd.net.yuki24.examples.profile");
129+
builder.withValue(Data.DATA2, "Yuki24 example Profile");
130+
builder.withValue(Data.DATA3, "View profile");
131+
builder.withValue(Data.DATA4, username);
132+
operationList.add(builder.build());
133+
134+
try {
135+
mContentResolver.applyBatch(ContactsContract.AUTHORITY, operationList);
136+
} catch (Exception e) {
137+
e.printStackTrace();
138+
}
139+
}
140+
141+
private static void updateContactStatus(ArrayList<ContentProviderOperation> operationList, long rawContactId) {
142+
Uri rawContactUri = ContentUris.withAppendedId(RawContacts.CONTENT_URI, rawContactId);
143+
Uri entityUri = Uri.withAppendedPath(rawContactUri, Entity.CONTENT_DIRECTORY);
144+
Cursor c = mContentResolver.query(entityUri, new String[]{RawContacts.SOURCE_ID, Entity.DATA_ID, Entity.MIMETYPE, Entity.DATA1}, null, null, null);
145+
146+
try {
147+
while(c.moveToNext()) {
148+
if (!c.isNull(1)) continue;
149+
150+
String mimeType = c.getString(2);
151+
if (mimeType.equals(Phone.CONTENT_ITEM_TYPE)) {
152+
ContentProviderOperation.Builder builder = ContentProviderOperation.newUpdate(Data.CONTENT_URI);
153+
builder.withSelection(BaseColumns._ID + " = ?", new String[]{c.getString(1)});
154+
builder.withValue(Phone.NUMBER, "819087654321");
155+
operationList.add(builder.build());
156+
} else if (mimeType.equals("vnd.android.cursor.item/vnd.net.yuki24.examples.profile")) {
157+
// Log.i(TAG, "update own profile.");
158+
}
159+
}
160+
} finally {
161+
c.close();
162+
}
59163
}
60164
}

0 commit comments

Comments
 (0)