2010-06-02 12 views
9

Me enfrenté al problema de actualizar/insertar contactos en Android 2.0+. No hay problema para insertar un nuevo contacto cuando la libreta de teléfonos está vacía pero cuando lo hice 2da vez algunos archivos como TEL, EMAIL se duplican y se disparan, etc. pero N, FN, ORG están bien (una copia).Usando ContentProviderOperation para actualizar e insertar contactos

Después de recibir consejos de otro miembro de este foro, primero actualicé un contacto y luego ContentProviderResult [] devolvió uri con nulo, luego realicé una acción de inserción y fue , pero después de eso hice una actualización y agregué todos los contactos en uno - obtuve 1 contacto inscrito 3 que existía en la guía telefónica. Este fue dañado, los campos de contacto son aleatoriamente construidos.

Configuré la cuenta de Google.

Código:

ArrayList<ContentProviderOperation> ops = new ArrayList<ContentProviderOperation>(); 
    ops.add(ContentProviderOperation.newUpdate(ContactsContract.RawContacts.CONTENT_URI) 
    .withValue(RawContacts.AGGREGATION_MODE, RawContacts.AGGREGATION_MODE_DISABLED) 
    .withValue(ContactsContract.RawContacts.ACCOUNT_TYPE, accountType) 
    .withValue(ContactsContract.RawContacts.ACCOUNT_NAME, accountName) 
    .build()); 

// add name 
ContentProviderOperation.Builder builder = ContentProviderOperation.newUpdate(ContactsContract.Data.CONTENT_URI); 
    builder.withValueBackReference(ContactsContract.Data.RAW_CONTACT_ID, 0); 
    builder.withValue(ContactsContract.Data.MIMETYPE, 
    ContactsContract.CommonDataKinds.StructuredName.CONTENT_ITEM_TYPE); 
builder.withValue(ContactsContract.CommonDataKinds.StructuredName.PHONETIC_FAMILY_NAME, name); 

// phones 
ContentProviderOperation.Builder builder = ContentProviderOperation.newUpdate(ContactsContract.Data.CONTENT_URI); 
    builder.withValueBackReference(ContactsContract.Data.RAW_CONTACT_ID, 0); 
    builder.withValue(ContactsContract.Data.MIMETYPE, 
    ContactsContract.CommonDataKinds.Phone.CONTENT_ITEM_TYPE); 
    builder.withValue(ContactsContract.CommonDataKinds.Phone.NUMBER, phoneValue); 
    builder.withValue(ContactsContract.CommonDataKinds.Phone.TYPE, phoneType); 
    builder.withValue(ContactsContract.CommonDataKinds.Phone.LABEL, phoneLabel);   
    ops.add(builder.build()); 

// emails ... 
// orgs ... 

try { 

    ContentProviderResult[] result = mContentResolver.applyBatch(ContactsContract.AUTHORITY, ops); 
} 
    } catch (Exception e) { 
    Log.e(LOG_TAG, "Exception while contact updating: " + e.getMessage()); 
    } 

¿Qué está mal en esta solución? ¿Cómo funciona el motor de agregación de trabajo?

Estaré encantado de ayudar.

Bogus

Respuesta

1

me encontré con los mismos problem.I piensan que debería funcionar de esta manera

opt.add(ContentProviderOperation.newUpdate(ContactsContract.Contacts.CONTENT_URI) 
       .withSelection(ContactsContract.Contacts._ID, new String[]{entity.getPeople()}) 
       .withValue(ContactsContract.Contacts.DISPLAY_NAME, "daerba") 
       .build() 
     ); 

Pero salió mal y informar de esto.

android.database.sqlite.SQLiteException: bind o el índice de la columna de gama

Creo que debe haber una selección para actualizar un contact.So la withSelection es importante decir la ContentResolver cuales contacto para actualizar.

Esperando que esto pueda dar alguna pista.

+4

withSelection requires parameters denoted with '?' para la Cadena []
es decir .withSelection (ContractsContract.Contacts._ID + "=?", new String [] {"5"})
Si no tiene ningún '?' s allí, no hay nada para unir los valores String [] a ... –

+0

@wiseideal Gracias por el puntero en la dirección correcta. TheSelection fue seguramente mi problema. – Bwire

0

está redefiniendo el constructor sin agregarlo a operaciones, por lo tanto, los datos nunca se envían para los nombres, lo que explica por qué su agregación es tan extraña.

// add name 
ContentProviderOperation.Builder builder = ContentProviderOperation.newUpdate(ContactsContract.Data.CONTENT_URI); 

// phones 
ContentProviderOperation.Builder builder = ContentProviderOperation.newUpdate(ContactsContract.Data.CONTENT_URI); 

también se debe a la legibilidad yo prefiero usar el siguiente formato cuando se trata de lotes más pequeños ....

ArrayList<ContentProviderOperation> batchOp = new ArrayList<ContentProviderOperation>(); 
batchOp.add(ContentProviderOperation.newUpdate(ContactsContract.RawContacts.CONTENT_URI) 
      .withValue(ContactsContract.RawContacts.ACCOUNT_NAME, accountName) 
      .withValue(ContactsContract.RawContacts.ACCOUNT_TYPE, accountType).build()); 
1

Debe proporcionar una cláusula donde para cada ContentProviderOperation si usted quiere hacer una actualización , Vea here y here.

Cuestiones relacionadas