nuovo / vCard-parser

Easier and more concise vCard (.vcf) parser for PHP
http://nuovo.lv/
MIT License
123 stars 54 forks source link

Addresses from Apple Addressbook cannot be parsed #9

Closed gopeter closed 11 years ago

gopeter commented 11 years ago

I try to parse vcards from Apple Addressbook, but

foreach ($vCard -> ADR as $Address) { // do something }

doesn't work, cause Apples vcards looks like:

item1.ADR;type=HOME:;;Street;Foo;;00000;Bar item2.ADR;type=HOME:;;Street;Foo;;00000;Bar

Any suggestions? :)

jrast commented 11 years ago

The example you posted is not in the vCard-Format. Have a look at the vCard-Format here: http://en.wikipedia.org/wiki/VCard

gopeter commented 11 years ago

Unfortunately, Apple Addressbook produces exactly such vCards. I've exported a vCard, opened it in TextEdit and got this:

BEGIN:VCARD VERSION:3.0 PRODID:-//Apple Inc.//Address Book 6.1.2//EN N:lastname;firstname;;; FN:firstname lastname item1.ADR;type=WORK;type=pref:;;street;city;;zip;country item1.X-ABADR:de CATEGORIES:Default Address Book,CategoryXY UID:b1341197-52bb-4c6a-8d2a-9e9c4d3b570f X-ABUID:28E7998F-D09C-4233-B268-4FA8173174E7:ABPerson END:VCARD

jrast commented 11 years ago

Ok, i see the problem. Apple Adressbook uses Groups for some Properties. Seems to be OK according to this RCF: http://tools.ietf.org/html/rfc6350#section-3.3

gopeter commented 11 years ago

Little bit of dirty code helps me solving the problem

// loop each group of addresses (i have only 2 addresses in one vcard)
for ($i = 1; $i <= 2; $i++) {

    // get field identifier. $single_vcard is our vCard Object
    $address_field = "item$i.ADR";
    $address_raw = $single_vcard -> $address_field;

    // get raw address informations
    $address = $address_raw[0]['Value'];

    // call a vCard function to parse raw address informations to an array with semantic keys
    $address = vCard::ParseStructuredValue($address,'adr');

    // get first type value (work, home, office, ...), cause we dont need the "pref" value, that apples addressbook create
    $type = $address_raw[0]['Type'][0];

    // save vars to array
    $contacts["address_$i"]['address_type'] = $type;
    $contacts["address_$i"]['address_street'] = $address['StreetAddress'];
    $contacts["address_$i"]['address_zip'] = $address['PostalCode'];
    $contacts["address_$i"]['address_city'] = $address['Locality'];
    $contacts["address_$i"]['address_country'] = $address['Country'];
}
pilsetnieks commented 11 years ago

I made some changes so that those itemized elements aren't completely ignored so it is now possible to get that data, too. However those Apple Address Book extensions aren't supported and are ignored for now (the elements starting with X-AB...)