зеркало из https://github.com/mozilla/pjs.git
land OSX AB integration on the trunk, NPOB yet, patch by peterv, 203927
This commit is contained in:
Родитель
04ff180ea4
Коммит
05a705475d
|
@ -0,0 +1,76 @@
|
||||||
|
/* -*- Mode: C++; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
|
||||||
|
/* ***** BEGIN LICENSE BLOCK *****
|
||||||
|
* Version: MPL 1.1/GPL 2.0/LGPL 2.1
|
||||||
|
*
|
||||||
|
* The contents of this file are subject to the Mozilla Public License Version
|
||||||
|
* 1.1 (the "License"); you may not use this file except in compliance with
|
||||||
|
* the License. You may obtain a copy of the License at
|
||||||
|
* http://www.mozilla.org/MPL/
|
||||||
|
*
|
||||||
|
* Software distributed under the License is distributed on an "AS IS" basis,
|
||||||
|
* WITHOUT WARRANTY OF ANY KIND, either express or implied. See the License
|
||||||
|
* for the specific language governing rights and limitations under the
|
||||||
|
* License.
|
||||||
|
*
|
||||||
|
* The Original Code is mozilla.org code.
|
||||||
|
*
|
||||||
|
* The Initial Developer of the Original Code is
|
||||||
|
* Peter Van der Beken.
|
||||||
|
* Portions created by the Initial Developer are Copyright (C) 2004
|
||||||
|
* the Initial Developer. All Rights Reserved.
|
||||||
|
*
|
||||||
|
* Contributor(s):
|
||||||
|
* Peter Van der Beken <peterv@propagandism.org>
|
||||||
|
*
|
||||||
|
*
|
||||||
|
* Alternatively, the contents of this file may be used under the terms of
|
||||||
|
* either the GNU General Public License Version 2 or later (the "GPL"), or
|
||||||
|
* the GNU Lesser General Public License Version 2.1 or later (the "LGPL"),
|
||||||
|
* in which case the provisions of the GPL or the LGPL are applicable instead
|
||||||
|
* of those above. If you wish to allow use of your version of this file only
|
||||||
|
* under the terms of either the GPL or the LGPL, and not to allow others to
|
||||||
|
* use your version of this file under the terms of the MPL, indicate your
|
||||||
|
* decision by deleting the provisions above and replace them with the notice
|
||||||
|
* and other provisions required by the GPL or the LGPL. If you do not delete
|
||||||
|
* the provisions above, a recipient may use your version of this file under
|
||||||
|
* the terms of any one of the MPL, the GPL or the LGPL.
|
||||||
|
*
|
||||||
|
* ***** END LICENSE BLOCK ***** */
|
||||||
|
|
||||||
|
#ifndef nsAbOSXCard_h___
|
||||||
|
#define nsAbOSXCard_h___
|
||||||
|
|
||||||
|
#include "nsAbCardProperty.h"
|
||||||
|
#include "nsRDFResource.h"
|
||||||
|
|
||||||
|
#define NS_ABOSXCARD_URI_PREFIX NS_ABOSXCARD_PREFIX "://"
|
||||||
|
|
||||||
|
#define NS_IABOSXCARD_IID \
|
||||||
|
{ 0xa7e5b697, 0x772d, 0x4fb5, \
|
||||||
|
{ 0x81, 0x16, 0x23, 0xb7, 0x5a, 0xac, 0x94, 0x56 } }
|
||||||
|
|
||||||
|
class nsIAbOSXCard : public nsISupports
|
||||||
|
{
|
||||||
|
public:
|
||||||
|
NS_DEFINE_STATIC_IID_ACCESSOR(NS_IABOSXCARD_IID)
|
||||||
|
|
||||||
|
virtual nsresult Update(PRBool aNotify) = 0;
|
||||||
|
};
|
||||||
|
|
||||||
|
class nsAbOSXCard : public nsRDFResource,
|
||||||
|
public nsAbCardProperty,
|
||||||
|
public nsIAbOSXCard
|
||||||
|
{
|
||||||
|
public:
|
||||||
|
NS_DECL_ISUPPORTS_INHERITED
|
||||||
|
|
||||||
|
// nsIRDFResource method
|
||||||
|
NS_IMETHOD Init(const char *aUri);
|
||||||
|
|
||||||
|
nsresult Update(PRBool aNotify);
|
||||||
|
|
||||||
|
// this is needed so nsAbOSXUtils.mm can get at nsAbCardProperty
|
||||||
|
friend class nsAbOSXUtils;
|
||||||
|
};
|
||||||
|
|
||||||
|
#endif // nsAbOSXCard_h___
|
|
@ -0,0 +1,351 @@
|
||||||
|
/* -*- Mode: C++; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
|
||||||
|
/* ***** BEGIN LICENSE BLOCK *****
|
||||||
|
* Version: MPL 1.1/GPL 2.0/LGPL 2.1
|
||||||
|
*
|
||||||
|
* The contents of this file are subject to the Mozilla Public License Version
|
||||||
|
* 1.1 (the "License"); you may not use this file except in compliance with
|
||||||
|
* the License. You may obtain a copy of the License at
|
||||||
|
* http://www.mozilla.org/MPL/
|
||||||
|
*
|
||||||
|
* Software distributed under the License is distributed on an "AS IS" basis,
|
||||||
|
* WITHOUT WARRANTY OF ANY KIND, either express or implied. See the License
|
||||||
|
* for the specific language governing rights and limitations under the
|
||||||
|
* License.
|
||||||
|
*
|
||||||
|
* The Original Code is mozilla.org code.
|
||||||
|
*
|
||||||
|
* The Initial Developer of the Original Code is
|
||||||
|
* Peter Van der Beken.
|
||||||
|
* Portions created by the Initial Developer are Copyright (C) 2004
|
||||||
|
* the Initial Developer. All Rights Reserved.
|
||||||
|
*
|
||||||
|
* Contributor(s):
|
||||||
|
* Peter Van der Beken <peterv@propagandism.org>
|
||||||
|
*
|
||||||
|
*
|
||||||
|
* Alternatively, the contents of this file may be used under the terms of
|
||||||
|
* either the GNU General Public License Version 2 or later (the "GPL"), or
|
||||||
|
* the GNU Lesser General Public License Version 2.1 or later (the "LGPL"),
|
||||||
|
* in which case the provisions of the GPL or the LGPL are applicable instead
|
||||||
|
* of those above. If you wish to allow use of your version of this file only
|
||||||
|
* under the terms of either the GPL or the LGPL, and not to allow others to
|
||||||
|
* use your version of this file under the terms of the MPL, indicate your
|
||||||
|
* decision by deleting the provisions above and replace them with the notice
|
||||||
|
* and other provisions required by the GPL or the LGPL. If you do not delete
|
||||||
|
* the provisions above, a recipient may use your version of this file under
|
||||||
|
* the terms of any one of the MPL, the GPL or the LGPL.
|
||||||
|
*
|
||||||
|
* ***** END LICENSE BLOCK ***** */
|
||||||
|
|
||||||
|
#include "nsAbOSXCard.h"
|
||||||
|
#include "nsAbOSXDirectory.h"
|
||||||
|
#include "nsAbOSXUtils.h"
|
||||||
|
#include "nsAutoPtr.h"
|
||||||
|
#include "nsIAddrBookSession.h"
|
||||||
|
#include "nsServiceManagerUtils.h"
|
||||||
|
|
||||||
|
#include <AddressBook/AddressBook.h>
|
||||||
|
|
||||||
|
NS_IMPL_ISUPPORTS_INHERITED2(nsAbOSXCard,
|
||||||
|
nsRDFResource,
|
||||||
|
nsIAbCard,
|
||||||
|
nsIAbOSXCard)
|
||||||
|
|
||||||
|
#ifdef DEBUG
|
||||||
|
static ABPropertyType
|
||||||
|
GetPropertType(ABRecord *aCard, NSString *aProperty)
|
||||||
|
{
|
||||||
|
ABPropertyType propertyType = kABErrorInProperty;
|
||||||
|
if ([aCard isKindOfClass:[ABPerson class]])
|
||||||
|
propertyType = [ABPerson typeOfProperty:aProperty];
|
||||||
|
else if ([aCard isKindOfClass:[ABGroup class]])
|
||||||
|
propertyType = [ABGroup typeOfProperty:aProperty];
|
||||||
|
return propertyType;
|
||||||
|
}
|
||||||
|
#endif
|
||||||
|
|
||||||
|
static void
|
||||||
|
SetStringProperty(nsAbOSXCard *aCard, nsString &aValue, nsString &aMember,
|
||||||
|
const char *aMemberName, PRBool aNotify,
|
||||||
|
nsIAddrBookSession *aSession)
|
||||||
|
{
|
||||||
|
if (!aNotify) {
|
||||||
|
aMember = aValue;
|
||||||
|
}
|
||||||
|
else if (!aMember.Equals(aValue)) {
|
||||||
|
nsString oldValue(aMember);
|
||||||
|
aMember = aValue;
|
||||||
|
|
||||||
|
nsISupports *supports = NS_ISUPPORTS_CAST(nsRDFResource*, aCard);
|
||||||
|
aSession->NotifyItemPropertyChanged(supports, aMemberName,
|
||||||
|
oldValue.get(), aMember.get());
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
static void
|
||||||
|
SetStringProperty(nsAbOSXCard *aCard, NSString *aValue, nsString &aMember,
|
||||||
|
const char *aMemberName, PRBool aNotify,
|
||||||
|
nsIAddrBookSession *aSession)
|
||||||
|
{
|
||||||
|
nsAutoString value;
|
||||||
|
if (aValue)
|
||||||
|
AppendToString(aValue, value);
|
||||||
|
|
||||||
|
SetStringProperty(aCard, value, aMember, aMemberName, aNotify, aSession);
|
||||||
|
}
|
||||||
|
|
||||||
|
static void
|
||||||
|
MapStringProperty(nsAbOSXCard *aCard, ABRecord *aOSXCard, NSString *aProperty,
|
||||||
|
nsString &aMember, const char *aMemberName, PRBool aNotify,
|
||||||
|
nsIAddrBookSession *aSession)
|
||||||
|
{
|
||||||
|
NS_ASSERTION(aProperty, "This is bad! You asked for an unresolved symbol.");
|
||||||
|
NS_ASSERTION(GetPropertType(aOSXCard, aProperty) == kABStringProperty,
|
||||||
|
"Wrong type!");
|
||||||
|
|
||||||
|
SetStringProperty(aCard, [aOSXCard valueForProperty:aProperty], aMember,
|
||||||
|
aMemberName, aNotify, aSession);
|
||||||
|
}
|
||||||
|
|
||||||
|
static ABMutableMultiValue*
|
||||||
|
GetMultiValue(ABRecord *aCard, NSString *aProperty)
|
||||||
|
{
|
||||||
|
NS_ASSERTION(aProperty, "This is bad! You asked for an unresolved symbol.");
|
||||||
|
NS_ASSERTION(GetPropertType(aCard, aProperty) & kABMultiValueMask,
|
||||||
|
"Wrong type!");
|
||||||
|
|
||||||
|
return [aCard valueForProperty:aProperty];
|
||||||
|
}
|
||||||
|
|
||||||
|
static void
|
||||||
|
MapDate(nsAbOSXCard *aCard, NSDate *aDate, nsString &aYear,
|
||||||
|
const char *aYearName, nsString &aMonth, const char *aMonthName,
|
||||||
|
nsString &aDay, const char *aDayName, PRBool aNotify,
|
||||||
|
nsIAddrBookSession *aSession)
|
||||||
|
{
|
||||||
|
// XXX Should we pass a format and timezone?
|
||||||
|
NSCalendarDate *date = [aDate dateWithCalendarFormat:nil timeZone:nil];
|
||||||
|
|
||||||
|
nsAutoString value;
|
||||||
|
value.AppendInt([date yearOfCommonEra]);
|
||||||
|
SetStringProperty(aCard, value, aYear, aYearName, aNotify, aSession);
|
||||||
|
value.AppendInt([date monthOfYear]);
|
||||||
|
SetStringProperty(aCard, value, aMonth, aMonthName, aNotify, aSession);
|
||||||
|
value.AppendInt([date dayOfWeek]);
|
||||||
|
SetStringProperty(aCard, value, aDay, aDayName, aNotify, aSession);
|
||||||
|
}
|
||||||
|
|
||||||
|
static PRBool
|
||||||
|
MapMultiValue(nsAbOSXCard *aCard, ABRecord *aOSXCard,
|
||||||
|
const nsAbOSXPropertyMap &aMap, PRBool aNotify,
|
||||||
|
nsIAddrBookSession *aSession)
|
||||||
|
{
|
||||||
|
ABMultiValue *value = GetMultiValue(aOSXCard, aMap.mOSXProperty);
|
||||||
|
if (value) {
|
||||||
|
unsigned int j;
|
||||||
|
unsigned int count = [value count];
|
||||||
|
for (j = 0; j < count; ++j) {
|
||||||
|
if ([[value labelAtIndex:j] isEqualToString:aMap.mOSXLabel]) {
|
||||||
|
NSString *stringValue = (aMap.mOSXKey)
|
||||||
|
? [[value valueAtIndex:j] objectForKey:aMap.mOSXKey]
|
||||||
|
: [value valueAtIndex:j];
|
||||||
|
|
||||||
|
SetStringProperty(aCard, stringValue, aCard->*(aMap.mProperty),
|
||||||
|
aMap.mPropertyName, aNotify, aSession);
|
||||||
|
|
||||||
|
return PR_TRUE;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
return PR_FALSE;
|
||||||
|
}
|
||||||
|
|
||||||
|
NS_IMETHODIMP
|
||||||
|
nsAbOSXCard::Init(const char *aUri)
|
||||||
|
{
|
||||||
|
if (strncmp(aUri, NS_ABOSXCARD_URI_PREFIX,
|
||||||
|
sizeof(NS_ABOSXCARD_URI_PREFIX) - 1) != 0)
|
||||||
|
return NS_ERROR_FAILURE;
|
||||||
|
|
||||||
|
nsresult rv = nsRDFResource::Init(aUri);
|
||||||
|
NS_ENSURE_SUCCESS(rv, rv);
|
||||||
|
|
||||||
|
return Update(PR_FALSE);
|
||||||
|
}
|
||||||
|
|
||||||
|
nsresult
|
||||||
|
nsAbOSXCard::Update(PRBool aNotify)
|
||||||
|
{
|
||||||
|
ABAddressBook *addressBook = [ABAddressBook sharedAddressBook];
|
||||||
|
|
||||||
|
const char *uid = &((mURI.get())[16]);
|
||||||
|
ABRecord *card = [addressBook recordForUniqueId:[NSString stringWithUTF8String:uid]];
|
||||||
|
NS_ENSURE_TRUE(card, NS_ERROR_FAILURE);
|
||||||
|
|
||||||
|
nsCOMPtr<nsIAddrBookSession> abSession;
|
||||||
|
nsresult rv;
|
||||||
|
if (aNotify) {
|
||||||
|
abSession = do_GetService(NS_ADDRBOOKSESSION_CONTRACTID, &rv);
|
||||||
|
NS_ENSURE_SUCCESS(rv, rv);
|
||||||
|
}
|
||||||
|
|
||||||
|
if ([card isKindOfClass:[ABGroup class]]) {
|
||||||
|
m_IsMailList = PR_TRUE;
|
||||||
|
m_MailListURI.AssignLiteral(NS_ABOSXDIRECTORY_URI_PREFIX);
|
||||||
|
m_MailListURI.Append(uid);
|
||||||
|
MapStringProperty(this, card, kABGroupNameProperty, m_DisplayName,
|
||||||
|
"DisplayName", aNotify, abSession);
|
||||||
|
|
||||||
|
return NS_OK;
|
||||||
|
}
|
||||||
|
|
||||||
|
PRBool foundHome = PR_FALSE, foundWork = PR_FALSE;
|
||||||
|
|
||||||
|
PRUint32 i;
|
||||||
|
for (i = 0; i < nsAbOSXUtils::kPropertyMapSize; ++i) {
|
||||||
|
const nsAbOSXPropertyMap &propertyMap = nsAbOSXUtils::kPropertyMap[i];
|
||||||
|
if (!propertyMap.mOSXProperty)
|
||||||
|
continue;
|
||||||
|
|
||||||
|
if (propertyMap.mOSXLabel) {
|
||||||
|
if (MapMultiValue(this, card, propertyMap, aNotify,
|
||||||
|
abSession) && propertyMap.mOSXProperty == kABAddressProperty) {
|
||||||
|
if (propertyMap.mOSXLabel == kABAddressHomeLabel)
|
||||||
|
foundHome = PR_TRUE;
|
||||||
|
else
|
||||||
|
foundWork = PR_TRUE;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
MapStringProperty(this, card, propertyMap.mOSXProperty,
|
||||||
|
this->*(propertyMap.mProperty),
|
||||||
|
propertyMap.mPropertyName, aNotify, abSession);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
int flags = 0;
|
||||||
|
if (kABPersonFlags)
|
||||||
|
flags = [[card valueForProperty:kABPersonFlags] intValue];
|
||||||
|
|
||||||
|
#define SET_STRING(_value, _name, _notify, _session) \
|
||||||
|
SetStringProperty(this, _value, m_##_name, #_name, _notify, _session)
|
||||||
|
|
||||||
|
// If kABShowAsCompany is set we use the company name as display name.
|
||||||
|
if (flags & kABShowAsCompany) {
|
||||||
|
SET_STRING(m_Company, DisplayName, aNotify, abSession);
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
// Use the order used in the OS X address book to set DisplayName.
|
||||||
|
int order = flags & kABNameOrderingMask;
|
||||||
|
if (order == kABDefaultNameOrdering) {
|
||||||
|
order = [addressBook defaultNameOrdering];
|
||||||
|
}
|
||||||
|
|
||||||
|
nsAutoString displayName;
|
||||||
|
if (order == kABFirstNameFirst) {
|
||||||
|
displayName.Append(m_FirstName);
|
||||||
|
displayName.Append(' ');
|
||||||
|
displayName.Append(m_LastName);
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
displayName.Append(m_LastName);
|
||||||
|
displayName.Append(' ');
|
||||||
|
displayName.Append(m_FirstName);
|
||||||
|
}
|
||||||
|
SET_STRING(displayName, DisplayName, aNotify, abSession);
|
||||||
|
}
|
||||||
|
|
||||||
|
ABMultiValue *value = GetMultiValue(card, kABEmailProperty);
|
||||||
|
if (value) {
|
||||||
|
unsigned int count = [value count];
|
||||||
|
if (count > 0) {
|
||||||
|
unsigned int j = [value indexForIdentifier:[value primaryIdentifier]];
|
||||||
|
|
||||||
|
if (j < count)
|
||||||
|
SET_STRING([value valueAtIndex:j], PrimaryEmail, aNotify,
|
||||||
|
abSession);
|
||||||
|
|
||||||
|
// If j is 0 (first in the list) we want the second in the list
|
||||||
|
// (index 1), if j is anything else we want the first in the list
|
||||||
|
// (index 0).
|
||||||
|
j = (j == 0);
|
||||||
|
if (j < count)
|
||||||
|
SET_STRING([value valueAtIndex:j], SecondEmail, aNotify,
|
||||||
|
abSession);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// We map the first home address we can find and the first work address
|
||||||
|
// we can find. If we find none, we map the primary address to the home
|
||||||
|
// address.
|
||||||
|
if (!foundHome && !foundWork) {
|
||||||
|
value = GetMultiValue(card, kABAddressProperty);
|
||||||
|
if (value) {
|
||||||
|
unsigned int count = [value count];
|
||||||
|
unsigned int j = [value indexForIdentifier:[value primaryIdentifier]];
|
||||||
|
|
||||||
|
if (j < count) {
|
||||||
|
NSDictionary *address = [value valueAtIndex:j];
|
||||||
|
if (address) {
|
||||||
|
SET_STRING([address objectForKey:kABAddressStreetKey],
|
||||||
|
HomeAddress, aNotify, abSession);
|
||||||
|
SET_STRING([address objectForKey:kABAddressCityKey],
|
||||||
|
HomeCity, aNotify, abSession);
|
||||||
|
SET_STRING([address objectForKey:kABAddressStateKey],
|
||||||
|
HomeState, aNotify, abSession);
|
||||||
|
SET_STRING([address objectForKey:kABAddressZIPKey],
|
||||||
|
HomeZipCode, aNotify, abSession);
|
||||||
|
SET_STRING([address objectForKey:kABAddressCountryKey],
|
||||||
|
HomeCountry, aNotify, abSession);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
value = GetMultiValue(card, kABAIMInstantProperty);
|
||||||
|
if (value) {
|
||||||
|
unsigned int count = [value count];
|
||||||
|
if (count > 0) {
|
||||||
|
unsigned int j = [value indexForIdentifier:[value primaryIdentifier]];
|
||||||
|
|
||||||
|
if (j < count)
|
||||||
|
SET_STRING([value valueAtIndex:j], AimScreenName, aNotify,
|
||||||
|
abSession);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
#define MAP_DATE(_date, _name, _notify, _session) \
|
||||||
|
MapDate(this, _date, m_##_name##Year, #_name"Year", m_##_name##Month, \
|
||||||
|
#_name"Month", m_##_name##Day, #_name"Day", _notify, _session)
|
||||||
|
|
||||||
|
NSDate *date = [card valueForProperty:kABBirthdayProperty];
|
||||||
|
if (date)
|
||||||
|
MAP_DATE(date, Birth, aNotify, abSession);
|
||||||
|
|
||||||
|
if (kABOtherDatesProperty) {
|
||||||
|
value = GetMultiValue(card, kABOtherDatesProperty);
|
||||||
|
if (value) {
|
||||||
|
unsigned int j, count = [value count];
|
||||||
|
for (j = 0; j < count; ++j) {
|
||||||
|
if ([[value labelAtIndex:j] isEqualToString:kABAnniversaryLabel]) {
|
||||||
|
date = [value valueAtIndex:j];
|
||||||
|
if (date) {
|
||||||
|
MAP_DATE(date, Anniversary, aNotify, abSession);
|
||||||
|
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
#undef MAP_DATE
|
||||||
|
#undef SET_STRING
|
||||||
|
|
||||||
|
date = [card valueForProperty:kABModificationDateProperty];
|
||||||
|
if (date)
|
||||||
|
m_LastModDate = PRUint32([date timeIntervalSince1970]);
|
||||||
|
// XXX No way to notify about this?
|
||||||
|
|
||||||
|
return NS_OK;
|
||||||
|
}
|
|
@ -0,0 +1,96 @@
|
||||||
|
/* -*- Mode: C++; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
|
||||||
|
/* ***** BEGIN LICENSE BLOCK *****
|
||||||
|
* Version: MPL 1.1/GPL 2.0/LGPL 2.1
|
||||||
|
*
|
||||||
|
* The contents of this file are subject to the Mozilla Public License Version
|
||||||
|
* 1.1 (the "License"); you may not use this file except in compliance with
|
||||||
|
* the License. You may obtain a copy of the License at
|
||||||
|
* http://www.mozilla.org/MPL/
|
||||||
|
*
|
||||||
|
* Software distributed under the License is distributed on an "AS IS" basis,
|
||||||
|
* WITHOUT WARRANTY OF ANY KIND, either express or implied. See the License
|
||||||
|
* for the specific language governing rights and limitations under the
|
||||||
|
* License.
|
||||||
|
*
|
||||||
|
* The Original Code is mozilla.org code.
|
||||||
|
*
|
||||||
|
* The Initial Developer of the Original Code is
|
||||||
|
* Peter Van der Beken.
|
||||||
|
* Portions created by the Initial Developer are Copyright (C) 2004
|
||||||
|
* the Initial Developer. All Rights Reserved.
|
||||||
|
*
|
||||||
|
* Contributor(s):
|
||||||
|
* Peter Van der Beken <peterv@propagandism.org>
|
||||||
|
*
|
||||||
|
*
|
||||||
|
* Alternatively, the contents of this file may be used under the terms of
|
||||||
|
* either the GNU General Public License Version 2 or later (the "GPL"), or
|
||||||
|
* the GNU Lesser General Public License Version 2.1 or later (the "LGPL"),
|
||||||
|
* in which case the provisions of the GPL or the LGPL are applicable instead
|
||||||
|
* of those above. If you wish to allow use of your version of this file only
|
||||||
|
* under the terms of either the GPL or the LGPL, and not to allow others to
|
||||||
|
* use your version of this file under the terms of the MPL, indicate your
|
||||||
|
* decision by deleting the provisions above and replace them with the notice
|
||||||
|
* and other provisions required by the GPL or the LGPL. If you do not delete
|
||||||
|
* the provisions above, a recipient may use your version of this file under
|
||||||
|
* the terms of any one of the MPL, the GPL or the LGPL.
|
||||||
|
*
|
||||||
|
* ***** END LICENSE BLOCK ***** */
|
||||||
|
|
||||||
|
#include "nsAbOSXDirFactory.h"
|
||||||
|
#include "nsAbBaseCID.h"
|
||||||
|
#include "nsEnumeratorUtils.h"
|
||||||
|
#include "nsIAbDirectory.h"
|
||||||
|
#include "nsIRDFService.h"
|
||||||
|
#include "rdf.h"
|
||||||
|
#include "nsString.h"
|
||||||
|
#include "nsServiceManagerUtils.h"
|
||||||
|
#include "nsAbOSXDirectory.h"
|
||||||
|
|
||||||
|
NS_IMPL_ISUPPORTS1(nsAbOSXDirFactory, nsIAbDirFactory)
|
||||||
|
|
||||||
|
NS_IMETHODIMP
|
||||||
|
nsAbOSXDirFactory::CreateDirectory(nsIAbDirectoryProperties *aProperties,
|
||||||
|
nsISimpleEnumerator **aDirectories)
|
||||||
|
{
|
||||||
|
NS_ENSURE_ARG_POINTER(aProperties);
|
||||||
|
NS_ENSURE_ARG_POINTER(aDirectories);
|
||||||
|
|
||||||
|
*aDirectories = nsnull;
|
||||||
|
|
||||||
|
nsAutoString description;
|
||||||
|
nsresult rv = aProperties->GetDescription(description);
|
||||||
|
NS_ENSURE_SUCCESS(rv, rv);
|
||||||
|
|
||||||
|
nsCOMPtr<nsIRDFService> rdf =
|
||||||
|
do_GetService(NS_RDF_CONTRACTID "/rdf-service;1", &rv);
|
||||||
|
NS_ENSURE_SUCCESS(rv, rv);
|
||||||
|
|
||||||
|
// We hardcode the root to "moz-abosxdirectory:///".
|
||||||
|
nsCOMPtr<nsIRDFResource> resource;
|
||||||
|
rv = rdf->GetResource(NS_LITERAL_CSTRING(NS_ABOSXDIRECTORY_URI_PREFIX "/"),
|
||||||
|
getter_AddRefs(resource));
|
||||||
|
NS_ENSURE_SUCCESS(rv, rv);
|
||||||
|
|
||||||
|
nsCOMPtr<nsIAbDirectory> directory = do_QueryInterface(resource, &rv);
|
||||||
|
NS_ENSURE_SUCCESS(rv, rv);
|
||||||
|
|
||||||
|
rv = directory->SetDirName(description.get());
|
||||||
|
NS_ENSURE_SUCCESS(rv, rv);
|
||||||
|
|
||||||
|
nsCOMPtr<nsIAbOSXDirectory> osxDirectory =
|
||||||
|
do_QueryInterface(directory, &rv);
|
||||||
|
NS_ENSURE_SUCCESS(rv, rv);
|
||||||
|
|
||||||
|
rv = osxDirectory->AssertChildNodes();
|
||||||
|
NS_ENSURE_SUCCESS(rv, rv);
|
||||||
|
|
||||||
|
return NS_NewSingletonEnumerator(aDirectories, directory);
|
||||||
|
}
|
||||||
|
|
||||||
|
// No actual deletion, since you cannot create the address books from Mozilla.
|
||||||
|
NS_IMETHODIMP
|
||||||
|
nsAbOSXDirFactory::DeleteDirectory(nsIAbDirectory *aDirectory)
|
||||||
|
{
|
||||||
|
return NS_OK;
|
||||||
|
}
|
|
@ -0,0 +1,52 @@
|
||||||
|
/* -*- Mode: C++; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
|
||||||
|
/* ***** BEGIN LICENSE BLOCK *****
|
||||||
|
* Version: MPL 1.1/GPL 2.0/LGPL 2.1
|
||||||
|
*
|
||||||
|
* The contents of this file are subject to the Mozilla Public License Version
|
||||||
|
* 1.1 (the "License"); you may not use this file except in compliance with
|
||||||
|
* the License. You may obtain a copy of the License at
|
||||||
|
* http://www.mozilla.org/MPL/
|
||||||
|
*
|
||||||
|
* Software distributed under the License is distributed on an "AS IS" basis,
|
||||||
|
* WITHOUT WARRANTY OF ANY KIND, either express or implied. See the License
|
||||||
|
* for the specific language governing rights and limitations under the
|
||||||
|
* License.
|
||||||
|
*
|
||||||
|
* The Original Code is mozilla.org code.
|
||||||
|
*
|
||||||
|
* The Initial Developer of the Original Code is
|
||||||
|
* Peter Van der Beken.
|
||||||
|
* Portions created by the Initial Developer are Copyright (C) 2004
|
||||||
|
* the Initial Developer. All Rights Reserved.
|
||||||
|
*
|
||||||
|
* Contributor(s):
|
||||||
|
* Peter Van der Beken <peterv@propagandism.org>
|
||||||
|
*
|
||||||
|
*
|
||||||
|
* Alternatively, the contents of this file may be used under the terms of
|
||||||
|
* either the GNU General Public License Version 2 or later (the "GPL"), or
|
||||||
|
* the GNU Lesser General Public License Version 2.1 or later (the "LGPL"),
|
||||||
|
* in which case the provisions of the GPL or the LGPL are applicable instead
|
||||||
|
* of those above. If you wish to allow use of your version of this file only
|
||||||
|
* under the terms of either the GPL or the LGPL, and not to allow others to
|
||||||
|
* use your version of this file under the terms of the MPL, indicate your
|
||||||
|
* decision by deleting the provisions above and replace them with the notice
|
||||||
|
* and other provisions required by the GPL or the LGPL. If you do not delete
|
||||||
|
* the provisions above, a recipient may use your version of this file under
|
||||||
|
* the terms of any one of the MPL, the GPL or the LGPL.
|
||||||
|
*
|
||||||
|
* ***** END LICENSE BLOCK ***** */
|
||||||
|
|
||||||
|
#ifndef nsAbOSXDirFactory_h___
|
||||||
|
#define nsAbOSXDirFactory_h___
|
||||||
|
|
||||||
|
#include "nsIAbDirFactory.h"
|
||||||
|
|
||||||
|
class nsAbOSXDirFactory : public nsIAbDirFactory
|
||||||
|
{
|
||||||
|
public:
|
||||||
|
NS_DECL_ISUPPORTS
|
||||||
|
NS_DECL_NSIABDIRFACTORY
|
||||||
|
};
|
||||||
|
|
||||||
|
#endif // nsAbOSXDirFactory_h___
|
|
@ -0,0 +1,183 @@
|
||||||
|
/* -*- Mode: C++; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
|
||||||
|
/* ***** BEGIN LICENSE BLOCK *****
|
||||||
|
* Version: MPL 1.1/GPL 2.0/LGPL 2.1
|
||||||
|
*
|
||||||
|
* The contents of this file are subject to the Mozilla Public License Version
|
||||||
|
* 1.1 (the "License"); you may not use this file except in compliance with
|
||||||
|
* the License. You may obtain a copy of the License at
|
||||||
|
* http://www.mozilla.org/MPL/
|
||||||
|
*
|
||||||
|
* Software distributed under the License is distributed on an "AS IS" basis,
|
||||||
|
* WITHOUT WARRANTY OF ANY KIND, either express or implied. See the License
|
||||||
|
* for the specific language governing rights and limitations under the
|
||||||
|
* License.
|
||||||
|
*
|
||||||
|
* The Original Code is mozilla.org code.
|
||||||
|
*
|
||||||
|
* The Initial Developer of the Original Code is
|
||||||
|
* Peter Van der Beken.
|
||||||
|
* Portions created by the Initial Developer are Copyright (C) 2004
|
||||||
|
* the Initial Developer. All Rights Reserved.
|
||||||
|
*
|
||||||
|
* Contributor(s):
|
||||||
|
* Peter Van der Beken <peterv@propagandism.org>
|
||||||
|
*
|
||||||
|
*
|
||||||
|
* Alternatively, the contents of this file may be used under the terms of
|
||||||
|
* either the GNU General Public License Version 2 or later (the "GPL"), or
|
||||||
|
* the GNU Lesser General Public License Version 2.1 or later (the "LGPL"),
|
||||||
|
* in which case the provisions of the GPL or the LGPL are applicable instead
|
||||||
|
* of those above. If you wish to allow use of your version of this file only
|
||||||
|
* under the terms of either the GPL or the LGPL, and not to allow others to
|
||||||
|
* use your version of this file under the terms of the MPL, indicate your
|
||||||
|
* decision by deleting the provisions above and replace them with the notice
|
||||||
|
* and other provisions required by the GPL or the LGPL. If you do not delete
|
||||||
|
* the provisions above, a recipient may use your version of this file under
|
||||||
|
* the terms of any one of the MPL, the GPL or the LGPL.
|
||||||
|
*
|
||||||
|
* ***** END LICENSE BLOCK ***** */
|
||||||
|
|
||||||
|
#ifndef nsAbOSXDirectory_h___
|
||||||
|
#define nsAbOSXDirectory_h___
|
||||||
|
|
||||||
|
#include "nsAbBaseCID.h"
|
||||||
|
#include "nsAbDirectoryRDFResource.h"
|
||||||
|
#include "nsAbDirProperty.h"
|
||||||
|
#include "nsIAbDirectoryQuery.h"
|
||||||
|
#include "nsIAbDirectorySearch.h"
|
||||||
|
#include "nsAbDirSearchListener.h"
|
||||||
|
#include "nsTHashtable.h"
|
||||||
|
|
||||||
|
class nsIAddrBookSession;
|
||||||
|
|
||||||
|
#define NS_ABOSXDIRECTORY_URI_PREFIX NS_ABOSXDIRECTORY_PREFIX "://"
|
||||||
|
|
||||||
|
class nsIAbCardHashKey : public PLDHashEntryHdr
|
||||||
|
{
|
||||||
|
public:
|
||||||
|
typedef nsIAbCard* KeyType;
|
||||||
|
typedef const nsIAbCard* KeyTypePointer;
|
||||||
|
|
||||||
|
nsIAbCardHashKey(const nsIAbCard* key)
|
||||||
|
: mCard(NS_CONST_CAST(nsIAbCard*, key))
|
||||||
|
{
|
||||||
|
}
|
||||||
|
nsIAbCardHashKey(const nsIAbCardHashKey& toCopy)
|
||||||
|
: mCard(toCopy.mCard)
|
||||||
|
{
|
||||||
|
}
|
||||||
|
~nsIAbCardHashKey()
|
||||||
|
{
|
||||||
|
}
|
||||||
|
|
||||||
|
KeyType GetCard() const
|
||||||
|
{
|
||||||
|
return mCard;
|
||||||
|
}
|
||||||
|
KeyTypePointer GetKeyPointer() const
|
||||||
|
{
|
||||||
|
return mCard;
|
||||||
|
}
|
||||||
|
|
||||||
|
PRBool KeyEquals(KeyTypePointer aKey) const
|
||||||
|
{
|
||||||
|
return aKey == mCard;
|
||||||
|
}
|
||||||
|
|
||||||
|
static KeyTypePointer KeyToPointer(KeyType aKey)
|
||||||
|
{
|
||||||
|
return aKey;
|
||||||
|
}
|
||||||
|
static PLDHashNumber HashKey(KeyTypePointer aKey)
|
||||||
|
{
|
||||||
|
return NS_PTR_TO_INT32(aKey) >> 2;
|
||||||
|
}
|
||||||
|
enum { ALLOW_MEMMOVE = PR_TRUE };
|
||||||
|
|
||||||
|
private:
|
||||||
|
nsCOMPtr<nsIAbCard> mCard;
|
||||||
|
};
|
||||||
|
|
||||||
|
#define NS_IABOSXDIRECTORY_IID \
|
||||||
|
{ 0x87ee4bd9, 0x8552, 0x498f, \
|
||||||
|
{ 0x80, 0x85, 0x34, 0xf0, 0x2a, 0xbb, 0x56, 0x16 } }
|
||||||
|
|
||||||
|
class nsIAbOSXDirectory : public nsISupports
|
||||||
|
{
|
||||||
|
public:
|
||||||
|
NS_DEFINE_STATIC_IID_ACCESSOR(NS_IABOSXDIRECTORY_IID)
|
||||||
|
|
||||||
|
virtual nsresult AssertChildNodes() = 0;
|
||||||
|
virtual nsresult Update() = 0;
|
||||||
|
virtual nsresult AssertDirectory(nsIAddrBookSession *aSession,
|
||||||
|
nsIAbDirectory *aDirectory) = 0;
|
||||||
|
virtual nsresult AssertCard(nsIAddrBookSession *aSession,
|
||||||
|
nsIAbCard *aCard) = 0;
|
||||||
|
virtual nsresult UnassertDirectory(nsIAddrBookSession *aSession,
|
||||||
|
nsIAbDirectory *aDirectory) = 0;
|
||||||
|
virtual nsresult UnassertCard(nsIAddrBookSession *aSession,
|
||||||
|
nsIAbCard *aCard) = 0;
|
||||||
|
virtual void GetURI(nsACString &aURI) = 0;
|
||||||
|
};
|
||||||
|
|
||||||
|
class nsAbOSXDirectory : public nsAbDirectoryRDFResource,
|
||||||
|
public nsAbDirProperty,
|
||||||
|
public nsAbDirSearchListenerContext,
|
||||||
|
public nsIAbOSXDirectory
|
||||||
|
{
|
||||||
|
public:
|
||||||
|
~nsAbOSXDirectory();
|
||||||
|
|
||||||
|
NS_DECL_ISUPPORTS_INHERITED
|
||||||
|
|
||||||
|
// nsAbDirectoryRDFResource method
|
||||||
|
NS_IMETHOD Init(const char *aUri);
|
||||||
|
|
||||||
|
// nsAbDirProperty methods
|
||||||
|
NS_IMETHOD GetOperations(PRInt32 *aOperations);
|
||||||
|
NS_IMETHOD GetChildCards(nsIEnumerator **aCards);
|
||||||
|
NS_IMETHOD GetChildNodes(nsISimpleEnumerator **aNodes);
|
||||||
|
NS_IMETHOD HasCard(nsIAbCard *aCard, PRBool *aHasCard);
|
||||||
|
NS_IMETHOD HasDirectory(nsIAbDirectory *aDirectory, PRBool *aHasDirectory);
|
||||||
|
|
||||||
|
// nsAbDirSearchListenerContext methods
|
||||||
|
nsresult OnSearchFinished(PRInt32 aResult);
|
||||||
|
nsresult OnSearchFoundCard(nsIAbCard *aCard);
|
||||||
|
|
||||||
|
// nsIAbOSXDirectory
|
||||||
|
nsresult AssertChildNodes();
|
||||||
|
nsresult AssertDirectory(nsIAddrBookSession *aSession,
|
||||||
|
nsIAbDirectory *aDirectory);
|
||||||
|
nsresult AssertCard(nsIAddrBookSession *aSession,
|
||||||
|
nsIAbCard *aCard);
|
||||||
|
nsresult UnassertDirectory(nsIAddrBookSession *aSession,
|
||||||
|
nsIAbDirectory *aDirectory);
|
||||||
|
nsresult UnassertCard(nsIAddrBookSession *aSession,
|
||||||
|
nsIAbCard *aCard);
|
||||||
|
|
||||||
|
nsresult Update();
|
||||||
|
void GetURI(nsACString &aURI)
|
||||||
|
{
|
||||||
|
aURI = mURI;
|
||||||
|
}
|
||||||
|
|
||||||
|
private:
|
||||||
|
static nsresult GetEnumerator(nsISupportsArray *aArray,
|
||||||
|
nsIEnumerator **aEnumerator)
|
||||||
|
{
|
||||||
|
nsIBidirectionalEnumerator *enumerator;
|
||||||
|
nsresult rv = NS_NewISupportsArrayEnumerator(aArray,
|
||||||
|
&enumerator);
|
||||||
|
NS_ENSURE_SUCCESS(rv, rv);
|
||||||
|
|
||||||
|
*aEnumerator = enumerator;
|
||||||
|
|
||||||
|
return NS_OK;
|
||||||
|
}
|
||||||
|
nsresult FallbackSearch(nsIAbBooleanExpression *aExpression,
|
||||||
|
nsIEnumerator **aCards);
|
||||||
|
|
||||||
|
nsTHashtable<nsIAbCardHashKey> mCardList;
|
||||||
|
};
|
||||||
|
|
||||||
|
#endif // nsAbOSXDirectory_h___
|
|
@ -0,0 +1,897 @@
|
||||||
|
/* -*- Mode: C++; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
|
||||||
|
/* ***** BEGIN LICENSE BLOCK *****
|
||||||
|
* Version: MPL 1.1/GPL 2.0/LGPL 2.1
|
||||||
|
*
|
||||||
|
* The contents of this file are subject to the Mozilla Public License Version
|
||||||
|
* 1.1 (the "License"); you may not use this file except in compliance with
|
||||||
|
* the License. You may obtain a copy of the License at
|
||||||
|
* http://www.mozilla.org/MPL/
|
||||||
|
*
|
||||||
|
* Software distributed under the License is distributed on an "AS IS" basis,
|
||||||
|
* WITHOUT WARRANTY OF ANY KIND, either express or implied. See the License
|
||||||
|
* for the specific language governing rights and limitations under the
|
||||||
|
* License.
|
||||||
|
*
|
||||||
|
* The Original Code is mozilla.org code.
|
||||||
|
*
|
||||||
|
* The Initial Developer of the Original Code is
|
||||||
|
* Peter Van der Beken.
|
||||||
|
* Portions created by the Initial Developer are Copyright (C) 2004
|
||||||
|
* the Initial Developer. All Rights Reserved.
|
||||||
|
*
|
||||||
|
* Contributor(s):
|
||||||
|
* Peter Van der Beken <peterv@propagandism.org>
|
||||||
|
*
|
||||||
|
*
|
||||||
|
* Alternatively, the contents of this file may be used under the terms of
|
||||||
|
* either the GNU General Public License Version 2 or later (the "GPL"), or
|
||||||
|
* the GNU Lesser General Public License Version 2.1 or later (the "LGPL"),
|
||||||
|
* in which case the provisions of the GPL or the LGPL are applicable instead
|
||||||
|
* of those above. If you wish to allow use of your version of this file only
|
||||||
|
* under the terms of either the GPL or the LGPL, and not to allow others to
|
||||||
|
* use your version of this file under the terms of the MPL, indicate your
|
||||||
|
* decision by deleting the provisions above and replace them with the notice
|
||||||
|
* and other provisions required by the GPL or the LGPL. If you do not delete
|
||||||
|
* the provisions above, a recipient may use your version of this file under
|
||||||
|
* the terms of any one of the MPL, the GPL or the LGPL.
|
||||||
|
*
|
||||||
|
* ***** END LICENSE BLOCK ***** */
|
||||||
|
|
||||||
|
#include "nsAbOSXDirectory.h"
|
||||||
|
#include "nsAbOSXCard.h"
|
||||||
|
#include "nsAbOSXUtils.h"
|
||||||
|
#include "nsAbQueryStringToExpression.h"
|
||||||
|
#include "nsArrayEnumerator.h"
|
||||||
|
#include "nsAutoPtr.h"
|
||||||
|
#include "nsCOMArray.h"
|
||||||
|
#include "nsEnumeratorUtils.h"
|
||||||
|
#include "nsIAbDirectoryQueryProxy.h"
|
||||||
|
#include "nsIAddrBookSession.h"
|
||||||
|
#include "nsIRDFService.h"
|
||||||
|
#include "nsServiceManagerUtils.h"
|
||||||
|
|
||||||
|
#include <AddressBook/AddressBook.h>
|
||||||
|
|
||||||
|
static nsresult
|
||||||
|
ConvertToGroupResource(nsIRDFService *aRDFService, NSString *aUid,
|
||||||
|
nsIAbDirectory **aResult)
|
||||||
|
{
|
||||||
|
NS_ASSERTION(aUid, "No UID for group!.");
|
||||||
|
|
||||||
|
*aResult = nsnull;
|
||||||
|
|
||||||
|
nsCAutoString uri(NS_ABOSXDIRECTORY_URI_PREFIX);
|
||||||
|
AppendToCString(aUid, uri);
|
||||||
|
|
||||||
|
nsCOMPtr<nsIRDFResource> resource;
|
||||||
|
nsresult rv = aRDFService->GetResource(uri, getter_AddRefs(resource));
|
||||||
|
NS_ENSURE_SUCCESS(rv, rv);
|
||||||
|
|
||||||
|
return CallQueryInterface(resource, aResult);
|
||||||
|
}
|
||||||
|
|
||||||
|
static nsresult
|
||||||
|
ConvertToCard(nsIRDFService *aRDFService, ABRecord *aRecord,
|
||||||
|
nsIAbCard **aResult)
|
||||||
|
{
|
||||||
|
*aResult = nsnull;
|
||||||
|
|
||||||
|
NSString *uid = [aRecord uniqueId];
|
||||||
|
NS_ASSERTION(uid, "No UID for card!.");
|
||||||
|
if (!uid)
|
||||||
|
return NS_ERROR_FAILURE;
|
||||||
|
|
||||||
|
nsCAutoString uri(NS_ABOSXCARD_URI_PREFIX);
|
||||||
|
AppendToCString(uid, uri);
|
||||||
|
|
||||||
|
nsCOMPtr<nsIRDFResource> resource;
|
||||||
|
nsresult rv = aRDFService->GetResource(uri, getter_AddRefs(resource));
|
||||||
|
NS_ENSURE_SUCCESS(rv, rv);
|
||||||
|
|
||||||
|
return CallQueryInterface(resource, aResult);
|
||||||
|
}
|
||||||
|
|
||||||
|
static nsresult
|
||||||
|
Update(nsIRDFService *aRDFService, NSString *aUid)
|
||||||
|
{
|
||||||
|
ABAddressBook *addressBook = [ABAddressBook sharedAddressBook];
|
||||||
|
ABRecord *card = [addressBook recordForUniqueId:aUid];
|
||||||
|
if ([card isKindOfClass:[ABGroup class]]) {
|
||||||
|
nsCOMPtr<nsIAbDirectory> directory;
|
||||||
|
ConvertToGroupResource(aRDFService, aUid, getter_AddRefs(directory));
|
||||||
|
nsCOMPtr<nsIAbOSXDirectory> osxDirectory =
|
||||||
|
do_QueryInterface(directory);
|
||||||
|
|
||||||
|
osxDirectory->Update();
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
nsCOMPtr<nsIAbCard> abCard;
|
||||||
|
ConvertToCard(aRDFService, card, getter_AddRefs(abCard));
|
||||||
|
nsCOMPtr<nsIAbOSXCard> osxCard = do_QueryInterface(abCard);
|
||||||
|
|
||||||
|
osxCard->Update(PR_TRUE);
|
||||||
|
}
|
||||||
|
return NS_OK;
|
||||||
|
}
|
||||||
|
|
||||||
|
@interface ABChangedMonitor : NSObject
|
||||||
|
-(void)ABChanged:(NSNotification *)aNotification;
|
||||||
|
@end
|
||||||
|
|
||||||
|
@implementation ABChangedMonitor
|
||||||
|
-(void)ABChanged:(NSNotification *)aNotification
|
||||||
|
{
|
||||||
|
NSDictionary *changes = [aNotification userInfo];
|
||||||
|
|
||||||
|
nsresult rv;
|
||||||
|
nsCOMPtr<nsIRDFService> rdfService =
|
||||||
|
do_GetService("@mozilla.org/rdf/rdf-service;1", &rv);
|
||||||
|
NS_ENSURE_SUCCESS(rv, );
|
||||||
|
|
||||||
|
NSArray *inserted = [changes objectForKey:kABInsertedRecords];
|
||||||
|
if (inserted) {
|
||||||
|
nsCOMPtr<nsIRDFResource> resource;
|
||||||
|
rv = rdfService->GetResource(NS_LITERAL_CSTRING(NS_ABOSXDIRECTORY_URI_PREFIX"/"),
|
||||||
|
getter_AddRefs(resource));
|
||||||
|
NS_ENSURE_SUCCESS(rv, );
|
||||||
|
|
||||||
|
nsCOMPtr<nsIAbOSXDirectory> osxDirectory =
|
||||||
|
do_QueryInterface(resource, &rv);
|
||||||
|
NS_ENSURE_SUCCESS(rv, );
|
||||||
|
|
||||||
|
nsCOMPtr<nsIAddrBookSession> abSession =
|
||||||
|
do_GetService(NS_ADDRBOOKSESSION_CONTRACTID, &rv);
|
||||||
|
NS_ENSURE_SUCCESS(rv, );
|
||||||
|
|
||||||
|
unsigned int i, count = [inserted count];
|
||||||
|
for (i = 0; i < count; ++i) {
|
||||||
|
ABAddressBook *addressBook =
|
||||||
|
[ABAddressBook sharedAddressBook];
|
||||||
|
ABRecord *card =
|
||||||
|
[addressBook recordForUniqueId:[inserted objectAtIndex:i]];
|
||||||
|
if ([card isKindOfClass:[ABGroup class]]) {
|
||||||
|
nsCOMPtr<nsIAbDirectory> directory;
|
||||||
|
ConvertToGroupResource(rdfService, [inserted objectAtIndex:i],
|
||||||
|
getter_AddRefs(directory));
|
||||||
|
|
||||||
|
rv = osxDirectory->AssertDirectory(abSession, directory);
|
||||||
|
NS_ENSURE_SUCCESS(rv, );
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
nsCOMPtr<nsIAbCard> abCard;
|
||||||
|
ConvertToCard(rdfService, card, getter_AddRefs(abCard));
|
||||||
|
|
||||||
|
rv = osxDirectory->AssertCard(abSession, abCard);
|
||||||
|
NS_ENSURE_SUCCESS(rv, );
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
NSArray *updated = [changes objectForKey:kABUpdatedRecords];
|
||||||
|
if (updated) {
|
||||||
|
unsigned int i, count = [updated count];
|
||||||
|
for (i = 0; i < count; ++i) {
|
||||||
|
NSString *uid = [updated objectAtIndex:i];
|
||||||
|
Update(rdfService, uid);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
NSArray *deleted = [changes objectForKey:kABDeletedRecords];
|
||||||
|
if (deleted) {
|
||||||
|
nsCOMPtr<nsIRDFResource> resource;
|
||||||
|
rv = rdfService->GetResource(NS_LITERAL_CSTRING(NS_ABOSXDIRECTORY_URI_PREFIX"/"),
|
||||||
|
getter_AddRefs(resource));
|
||||||
|
NS_ENSURE_SUCCESS(rv, );
|
||||||
|
|
||||||
|
nsCOMPtr<nsIAbOSXDirectory> osxDirectory =
|
||||||
|
do_QueryInterface(resource, &rv);
|
||||||
|
NS_ENSURE_SUCCESS(rv, );
|
||||||
|
|
||||||
|
nsCOMPtr<nsIAddrBookSession> abSession =
|
||||||
|
do_GetService(NS_ADDRBOOKSESSION_CONTRACTID, &rv);
|
||||||
|
NS_ENSURE_SUCCESS(rv, );
|
||||||
|
|
||||||
|
unsigned int i, count = [deleted count];
|
||||||
|
for (i = 0; i < count; ++i) {
|
||||||
|
ABAddressBook *addressBook = [ABAddressBook sharedAddressBook];
|
||||||
|
NSString *recordClass =
|
||||||
|
[addressBook recordClassFromUniqueId:[deleted objectAtIndex:i]];
|
||||||
|
if ([recordClass isEqualToString:@"ABGroup"]) {
|
||||||
|
nsCOMPtr<nsIAbDirectory> directory;
|
||||||
|
ConvertToGroupResource(rdfService, [deleted objectAtIndex:i],
|
||||||
|
getter_AddRefs(directory));
|
||||||
|
|
||||||
|
rv = osxDirectory->UnassertDirectory(abSession, directory);
|
||||||
|
NS_ENSURE_SUCCESS(rv, );
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
nsCOMPtr<nsIAbCard> abCard;
|
||||||
|
ConvertToCard(rdfService, [deleted objectAtIndex:i],
|
||||||
|
getter_AddRefs(abCard));
|
||||||
|
|
||||||
|
rv = osxDirectory->UnassertCard(abSession, abCard);
|
||||||
|
NS_ENSURE_SUCCESS(rv, );
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if (!inserted && !updated && !deleted) {
|
||||||
|
// XXX This is supposed to mean "everything was updated", but we get
|
||||||
|
// this whenever something has changed, so not sure what to do.
|
||||||
|
}
|
||||||
|
}
|
||||||
|
@end
|
||||||
|
|
||||||
|
static nsresult
|
||||||
|
MapConditionString(nsIAbBooleanConditionString *aCondition, PRBool aNegate,
|
||||||
|
PRBool &aCanHandle, ABSearchElement **aResult)
|
||||||
|
{
|
||||||
|
aCanHandle = PR_FALSE;
|
||||||
|
|
||||||
|
nsAbBooleanConditionType conditionType = 0;
|
||||||
|
nsresult rv = aCondition->GetCondition(&conditionType);
|
||||||
|
NS_ENSURE_SUCCESS(rv, rv);
|
||||||
|
|
||||||
|
ABSearchComparison comparison;
|
||||||
|
switch (conditionType) {
|
||||||
|
case nsIAbBooleanConditionTypes::Contains:
|
||||||
|
{
|
||||||
|
if (!aNegate) {
|
||||||
|
comparison = kABContainsSubString;
|
||||||
|
aCanHandle = PR_TRUE;
|
||||||
|
}
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
case nsIAbBooleanConditionTypes::DoesNotContain:
|
||||||
|
{
|
||||||
|
if (aNegate) {
|
||||||
|
comparison = kABContainsSubString;
|
||||||
|
aCanHandle = PR_TRUE;
|
||||||
|
}
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
case nsIAbBooleanConditionTypes::Is:
|
||||||
|
{
|
||||||
|
comparison = aNegate ? kABNotEqual : kABEqual;
|
||||||
|
aCanHandle = PR_TRUE;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
case nsIAbBooleanConditionTypes::IsNot:
|
||||||
|
{
|
||||||
|
comparison = aNegate ? kABEqual : kABNotEqual;
|
||||||
|
aCanHandle = PR_TRUE;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
case nsIAbBooleanConditionTypes::BeginsWith:
|
||||||
|
{
|
||||||
|
if (!aNegate) {
|
||||||
|
comparison = kABPrefixMatch;
|
||||||
|
aCanHandle = PR_TRUE;
|
||||||
|
}
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
case nsIAbBooleanConditionTypes::EndsWith:
|
||||||
|
{
|
||||||
|
//comparison = kABSuffixMatch;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
case nsIAbBooleanConditionTypes::LessThan:
|
||||||
|
{
|
||||||
|
comparison = aNegate ? kABGreaterThanOrEqual : kABLessThan;
|
||||||
|
aCanHandle = PR_TRUE;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
case nsIAbBooleanConditionTypes::GreaterThan:
|
||||||
|
{
|
||||||
|
comparison = aNegate ? kABLessThanOrEqual : kABGreaterThan;
|
||||||
|
aCanHandle = PR_TRUE;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if (!aCanHandle)
|
||||||
|
return NS_OK;
|
||||||
|
|
||||||
|
nsXPIDLCString name;
|
||||||
|
rv = aCondition->GetName(getter_Copies(name));
|
||||||
|
NS_ENSURE_SUCCESS(rv, rv);
|
||||||
|
|
||||||
|
nsXPIDLString value;
|
||||||
|
rv = aCondition->GetValue(getter_Copies(value));
|
||||||
|
NS_ENSURE_SUCCESS(rv, rv);
|
||||||
|
|
||||||
|
PRUint32 length = value.Length();
|
||||||
|
|
||||||
|
PRUint32 i;
|
||||||
|
for (i = 0; i < nsAbOSXUtils::kPropertyMapSize; ++i) {
|
||||||
|
if (name.EqualsASCII(nsAbOSXUtils::kPropertyMap[i].mPropertyName)) {
|
||||||
|
*aResult =
|
||||||
|
[ABPerson searchElementForProperty:nsAbOSXUtils::kPropertyMap[i].mOSXProperty
|
||||||
|
label:nsAbOSXUtils::kPropertyMap[i].mOSXLabel
|
||||||
|
key:nsAbOSXUtils::kPropertyMap[i].mOSXKey
|
||||||
|
value:[NSString stringWithCharacters:value.get() length:length]
|
||||||
|
comparison:comparison];
|
||||||
|
|
||||||
|
return NS_OK;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if (name.EqualsLiteral("DisplayName") && comparison == kABContainsSubString) {
|
||||||
|
ABSearchElement *first =
|
||||||
|
[ABPerson searchElementForProperty:kABFirstNameProperty
|
||||||
|
label:nil
|
||||||
|
key:nil
|
||||||
|
value:[NSString stringWithCharacters:value.get() length:length]
|
||||||
|
comparison:comparison];
|
||||||
|
ABSearchElement *second =
|
||||||
|
[ABPerson searchElementForProperty:kABLastNameProperty
|
||||||
|
label:nil
|
||||||
|
key:nil
|
||||||
|
value:[NSString stringWithCharacters:value.get() length:length]
|
||||||
|
comparison:comparison];
|
||||||
|
ABSearchElement *third =
|
||||||
|
[ABGroup searchElementForProperty:kABGroupNameProperty
|
||||||
|
label:nil
|
||||||
|
key:nil
|
||||||
|
value:[NSString stringWithCharacters:value.get() length:length]
|
||||||
|
comparison:comparison];
|
||||||
|
|
||||||
|
*aResult = [ABSearchElement searchElementForConjunction:kABSearchOr children:[NSArray arrayWithObjects:first, second, third, nil]];
|
||||||
|
|
||||||
|
return NS_OK;
|
||||||
|
}
|
||||||
|
|
||||||
|
aCanHandle = PR_FALSE;
|
||||||
|
|
||||||
|
return NS_OK;
|
||||||
|
}
|
||||||
|
|
||||||
|
static nsresult
|
||||||
|
BuildSearchElements(nsIAbBooleanExpression *aExpression,
|
||||||
|
PRBool &aCanHandle,
|
||||||
|
ABSearchElement **aResult)
|
||||||
|
{
|
||||||
|
aCanHandle = PR_TRUE;
|
||||||
|
|
||||||
|
nsCOMPtr<nsISupportsArray> expressions;
|
||||||
|
nsresult rv = aExpression->GetExpressions(getter_AddRefs(expressions));
|
||||||
|
NS_ENSURE_SUCCESS(rv, rv);
|
||||||
|
|
||||||
|
nsAbBooleanOperationType operation;
|
||||||
|
rv = aExpression->GetOperation(&operation);
|
||||||
|
NS_ENSURE_SUCCESS(rv, rv);
|
||||||
|
|
||||||
|
PRUint32 count;
|
||||||
|
rv = expressions->Count(&count);
|
||||||
|
NS_ENSURE_SUCCESS(rv, rv);
|
||||||
|
|
||||||
|
NS_ASSERTION(count > 1 && operation != nsIAbBooleanOperationTypes::NOT,
|
||||||
|
"This doesn't make sense!");
|
||||||
|
|
||||||
|
NSMutableArray *array = nsnull;
|
||||||
|
if (count > 1)
|
||||||
|
array = [[NSMutableArray alloc] init];
|
||||||
|
|
||||||
|
PRUint32 i;
|
||||||
|
nsCOMPtr<nsIAbBooleanConditionString> condition;
|
||||||
|
nsCOMPtr<nsIAbBooleanExpression> subExpression;
|
||||||
|
for (i = 0; i < count; ++i) {
|
||||||
|
ABSearchElement *element = nsnull;
|
||||||
|
|
||||||
|
condition = do_QueryElementAt(expressions, i);
|
||||||
|
if (condition) {
|
||||||
|
rv = MapConditionString(condition, operation == nsIAbBooleanOperationTypes::NOT, aCanHandle, &element);
|
||||||
|
NS_ENSURE_SUCCESS(rv, rv);
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
subExpression = do_QueryElementAt(expressions, i);
|
||||||
|
if (subExpression) {
|
||||||
|
rv = BuildSearchElements(subExpression, aCanHandle, &element);
|
||||||
|
NS_ENSURE_SUCCESS(rv, rv);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if (!aCanHandle) {
|
||||||
|
return NS_OK;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (element) {
|
||||||
|
if (array)
|
||||||
|
[array addObject:element];
|
||||||
|
else
|
||||||
|
*aResult = element;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if (array) {
|
||||||
|
ABSearchConjunction conjunction = operation == nsIAbBooleanOperationTypes::AND ? kABSearchAnd : kABSearchOr;
|
||||||
|
*aResult = [ABSearchElement searchElementForConjunction:conjunction children:array];
|
||||||
|
[array release];
|
||||||
|
}
|
||||||
|
|
||||||
|
return NS_OK;
|
||||||
|
}
|
||||||
|
|
||||||
|
static PRBool
|
||||||
|
Search(nsIAbBooleanExpression *aExpression, NSArray **aResult)
|
||||||
|
{
|
||||||
|
PRBool canHandle = PR_FALSE;
|
||||||
|
ABSearchElement *searchElement;
|
||||||
|
nsresult rv = BuildSearchElements(aExpression, canHandle, &searchElement);
|
||||||
|
NS_ENSURE_SUCCESS(rv, PR_FALSE);
|
||||||
|
|
||||||
|
if (canHandle)
|
||||||
|
*aResult = [[ABAddressBook sharedAddressBook] recordsMatchingSearchElement:searchElement];
|
||||||
|
|
||||||
|
return canHandle;
|
||||||
|
}
|
||||||
|
|
||||||
|
static PRUint32 sObserverCount = 0;
|
||||||
|
static ABChangedMonitor *sObserver = nsnull;
|
||||||
|
|
||||||
|
nsAbOSXDirectory::~nsAbOSXDirectory()
|
||||||
|
{
|
||||||
|
if (--sObserverCount == 0) {
|
||||||
|
[[NSNotificationCenter defaultCenter] removeObserver:sObserver];
|
||||||
|
[sObserver release];
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
NS_IMPL_ISUPPORTS_INHERITED2(nsAbOSXDirectory,
|
||||||
|
nsAbDirectoryRDFResource,
|
||||||
|
nsIAbDirectory,
|
||||||
|
nsIAbOSXDirectory)
|
||||||
|
|
||||||
|
NS_IMETHODIMP
|
||||||
|
nsAbOSXDirectory::Init(const char *aUri)
|
||||||
|
{
|
||||||
|
ABAddressBook *addressBook = [ABAddressBook sharedAddressBook];
|
||||||
|
if (sObserverCount == 0) {
|
||||||
|
sObserver = [[ABChangedMonitor alloc] init];
|
||||||
|
[[NSNotificationCenter defaultCenter] addObserver:(ABChangedMonitor*)sObserver
|
||||||
|
selector:@selector(ABChanged:)
|
||||||
|
name:kABDatabaseChangedExternallyNotification
|
||||||
|
object:nil];
|
||||||
|
}
|
||||||
|
++sObserverCount;
|
||||||
|
|
||||||
|
nsresult rv = nsAbDirectoryRDFResource::Init(aUri);
|
||||||
|
NS_ENSURE_SUCCESS(rv, rv);
|
||||||
|
|
||||||
|
if (mURINoQuery.Length() > sizeof(NS_ABOSXDIRECTORY_URI_PREFIX)) {
|
||||||
|
nsCAutoString uid(Substring(mURINoQuery, sizeof(NS_ABOSXDIRECTORY_URI_PREFIX) - 1));
|
||||||
|
ABRecord *card = [addressBook recordForUniqueId:[NSString stringWithUTF8String:uid.get()]];
|
||||||
|
NS_ASSERTION([card isKindOfClass:[ABGroup class]], "Huh.");
|
||||||
|
|
||||||
|
m_IsMailList = PR_TRUE;
|
||||||
|
AppendToString([card valueForProperty:kABGroupNameProperty], m_DirName);
|
||||||
|
}
|
||||||
|
|
||||||
|
return NS_OK;
|
||||||
|
}
|
||||||
|
|
||||||
|
NS_IMETHODIMP
|
||||||
|
nsAbOSXDirectory::GetOperations(PRInt32 *aOperations)
|
||||||
|
{
|
||||||
|
*aOperations = nsIAbDirectory::opRead |
|
||||||
|
nsIAbDirectory::opSearch;
|
||||||
|
|
||||||
|
return NS_OK;
|
||||||
|
}
|
||||||
|
|
||||||
|
struct nsEnumeratorData
|
||||||
|
{
|
||||||
|
NSMutableArray *mCards;
|
||||||
|
nsIAbDirectory *mDirectory;
|
||||||
|
nsIAddrBookSession *mSession;
|
||||||
|
};
|
||||||
|
|
||||||
|
PLDHashOperator
|
||||||
|
Enumerator(nsIAbCardHashKey *aKey, void *aUserArg)
|
||||||
|
{
|
||||||
|
nsEnumeratorData *data = NS_STATIC_CAST(nsEnumeratorData*, aUserArg);
|
||||||
|
|
||||||
|
nsIAbCard *abCard = aKey->GetCard();
|
||||||
|
|
||||||
|
nsCOMPtr<nsIRDFResource> resource = do_QueryInterface(abCard);
|
||||||
|
|
||||||
|
const char* uri;
|
||||||
|
resource->GetValueConst(&uri);
|
||||||
|
NSString *uid = [NSString stringWithUTF8String:(uri + 21)];
|
||||||
|
|
||||||
|
unsigned int i, count = [data->mCards count];
|
||||||
|
for (i = 0; i < count; ++i) {
|
||||||
|
if ([[[data->mCards objectAtIndex:i] uniqueId] isEqualToString:uid]) {
|
||||||
|
[data->mCards removeObjectAtIndex:i];
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if (i == count) {
|
||||||
|
data->mSession->NotifyDirectoryItemDeleted(data->mDirectory, abCard);
|
||||||
|
|
||||||
|
return PL_DHASH_REMOVE;
|
||||||
|
}
|
||||||
|
|
||||||
|
return PL_DHASH_NEXT;
|
||||||
|
}
|
||||||
|
|
||||||
|
nsresult
|
||||||
|
nsAbOSXDirectory::Update()
|
||||||
|
{
|
||||||
|
nsresult rv;
|
||||||
|
nsCOMPtr<nsIAddrBookSession> abSession = do_GetService(NS_ADDRBOOKSESSION_CONTRACTID, &rv);
|
||||||
|
NS_ENSURE_SUCCESS(rv, rv);
|
||||||
|
|
||||||
|
if (mIsQueryURI) {
|
||||||
|
return NS_OK;
|
||||||
|
}
|
||||||
|
|
||||||
|
ABAddressBook *addressBook = [ABAddressBook sharedAddressBook];
|
||||||
|
|
||||||
|
NSArray *groups, *cards;
|
||||||
|
if (m_IsMailList) {
|
||||||
|
ABGroup *group = (ABGroup*)[addressBook recordForUniqueId:[NSString stringWithUTF8String:nsCAutoString(Substring(mURINoQuery, 21)).get()]];
|
||||||
|
groups = nil;
|
||||||
|
cards = [[group members] arrayByAddingObjectsFromArray:[group subgroups]];
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
groups = [addressBook groups];
|
||||||
|
cards = [[addressBook people] arrayByAddingObjectsFromArray:groups];
|
||||||
|
}
|
||||||
|
|
||||||
|
NSMutableArray *mutableArray = [NSMutableArray arrayWithArray:cards];
|
||||||
|
if (mCardList.IsInitialized()) {
|
||||||
|
nsEnumeratorData data = { mutableArray, this, abSession };
|
||||||
|
|
||||||
|
mCardList.EnumerateEntries(Enumerator, &data);
|
||||||
|
}
|
||||||
|
|
||||||
|
NSEnumerator *enumerator = [mutableArray objectEnumerator];
|
||||||
|
ABRecord *card;
|
||||||
|
nsCOMPtr<nsIAbCard> abCard;
|
||||||
|
while ((card = [enumerator nextObject])) {
|
||||||
|
rv = ConvertToCard(gRDFService, card, getter_AddRefs(abCard));
|
||||||
|
NS_ENSURE_SUCCESS(rv, rv);
|
||||||
|
|
||||||
|
AssertCard(abSession, abCard);
|
||||||
|
}
|
||||||
|
|
||||||
|
card = (ABRecord*)[addressBook recordForUniqueId:[NSString stringWithUTF8String:nsCAutoString(Substring(mURINoQuery, 21)).get()]];
|
||||||
|
NSString * stringValue = [card valueForProperty:kABGroupNameProperty];
|
||||||
|
if (![stringValue isEqualToString:WrapString(m_DirName)]) {
|
||||||
|
nsAutoString oldValue(m_DirName);
|
||||||
|
AssignToString(stringValue, m_DirName);
|
||||||
|
nsISupports *supports =
|
||||||
|
NS_ISUPPORTS_CAST(nsAbDirectoryRDFResource*, this);
|
||||||
|
abSession->NotifyItemPropertyChanged(supports, "DirName",
|
||||||
|
oldValue.get(), m_DirName.get());
|
||||||
|
}
|
||||||
|
|
||||||
|
if (groups) {
|
||||||
|
mutableArray = [NSMutableArray arrayWithArray:groups];
|
||||||
|
nsCOMPtr<nsIAbDirectory> directory;
|
||||||
|
if (m_AddressList) {
|
||||||
|
PRUint32 i, count;
|
||||||
|
m_AddressList->Count(&count);
|
||||||
|
for (i = 0; i < count; ++i) {
|
||||||
|
directory = do_QueryElementAt(m_AddressList, i);
|
||||||
|
nsCOMPtr<nsIAbOSXDirectory> osxDirectory =
|
||||||
|
do_QueryInterface(directory);
|
||||||
|
|
||||||
|
nsCAutoString uri;
|
||||||
|
osxDirectory->GetURI(uri);
|
||||||
|
uri.Cut(0, 21);
|
||||||
|
NSString *uid = [NSString stringWithUTF8String:uri.get()];
|
||||||
|
|
||||||
|
unsigned int j, arrayCount = [mutableArray count];
|
||||||
|
for (j = 0; j < arrayCount; ++j) {
|
||||||
|
if ([[[mutableArray objectAtIndex:j] uniqueId] isEqualToString:uid]) {
|
||||||
|
[mutableArray removeObjectAtIndex:j];
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if (j == arrayCount) {
|
||||||
|
UnassertDirectory(abSession, directory);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
enumerator = [mutableArray objectEnumerator];
|
||||||
|
while ((card = [enumerator nextObject])) {
|
||||||
|
rv = ConvertToGroupResource(gRDFService, [card uniqueId],
|
||||||
|
getter_AddRefs(directory));
|
||||||
|
NS_ENSURE_SUCCESS(rv, rv);
|
||||||
|
|
||||||
|
AssertDirectory(abSession, directory);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
return NS_OK;
|
||||||
|
}
|
||||||
|
|
||||||
|
nsresult
|
||||||
|
nsAbOSXDirectory::AssertChildNodes()
|
||||||
|
{
|
||||||
|
// Queries and mailing lists can't have childnodes.
|
||||||
|
if (mIsQueryURI || m_IsMailList) {
|
||||||
|
return NS_OK;
|
||||||
|
}
|
||||||
|
|
||||||
|
nsresult rv;
|
||||||
|
nsCOMPtr<nsIAddrBookSession> abSession =
|
||||||
|
do_GetService(NS_ADDRBOOKSESSION_CONTRACTID, &rv);
|
||||||
|
NS_ENSURE_SUCCESS(rv, rv);
|
||||||
|
|
||||||
|
NSArray *groups = [[ABAddressBook sharedAddressBook] groups];
|
||||||
|
|
||||||
|
unsigned int i, count = [groups count];
|
||||||
|
|
||||||
|
if (count > 0 && !m_AddressList) {
|
||||||
|
rv = NS_NewISupportsArray(getter_AddRefs(m_AddressList));
|
||||||
|
NS_ENSURE_SUCCESS(rv, rv);
|
||||||
|
}
|
||||||
|
|
||||||
|
nsCOMPtr<nsIAbDirectory> directory;
|
||||||
|
for (i = 0; i < count; ++i) {
|
||||||
|
rv = ConvertToGroupResource(gRDFService, [[groups objectAtIndex:i] uniqueId],
|
||||||
|
getter_AddRefs(directory));
|
||||||
|
NS_ENSURE_SUCCESS(rv, rv);
|
||||||
|
|
||||||
|
rv = AssertDirectory(abSession, directory);
|
||||||
|
NS_ENSURE_SUCCESS(rv, rv);
|
||||||
|
}
|
||||||
|
|
||||||
|
return NS_OK;
|
||||||
|
}
|
||||||
|
|
||||||
|
nsresult
|
||||||
|
nsAbOSXDirectory::AssertDirectory(nsIAddrBookSession *aSession,
|
||||||
|
nsIAbDirectory *aDirectory)
|
||||||
|
{
|
||||||
|
NS_ASSERTION(!m_AddressList || m_AddressList->IndexOf(aDirectory) < 0,
|
||||||
|
"Replacing?");
|
||||||
|
|
||||||
|
nsresult rv;
|
||||||
|
if (!m_AddressList) {
|
||||||
|
rv = NS_NewISupportsArray(getter_AddRefs(m_AddressList));
|
||||||
|
NS_ENSURE_SUCCESS(rv, rv);
|
||||||
|
}
|
||||||
|
|
||||||
|
rv = m_AddressList->AppendElement(aDirectory);
|
||||||
|
NS_ENSURE_SUCCESS(rv, rv);
|
||||||
|
|
||||||
|
return aSession->NotifyDirectoryItemAdded(this, aDirectory);
|
||||||
|
}
|
||||||
|
|
||||||
|
nsresult
|
||||||
|
nsAbOSXDirectory::AssertCard(nsIAddrBookSession *aSession,
|
||||||
|
nsIAbCard *aCard)
|
||||||
|
{
|
||||||
|
NS_ASSERTION(!mCardList.IsInitialized() || !mCardList.GetEntry(aCard),
|
||||||
|
"Replacing?");
|
||||||
|
|
||||||
|
if (!mCardList.IsInitialized() && !mCardList.Init()) {
|
||||||
|
return NS_ERROR_OUT_OF_MEMORY;
|
||||||
|
}
|
||||||
|
|
||||||
|
mCardList.PutEntry(aCard);
|
||||||
|
return aSession->NotifyDirectoryItemAdded(this, aCard);
|
||||||
|
}
|
||||||
|
|
||||||
|
nsresult
|
||||||
|
nsAbOSXDirectory::UnassertDirectory(nsIAddrBookSession *aSession,
|
||||||
|
nsIAbDirectory *aDirectory)
|
||||||
|
{
|
||||||
|
NS_ASSERTION(m_AddressList->IndexOf(aDirectory) >= 0, "Not found?");
|
||||||
|
|
||||||
|
nsresult rv = m_AddressList->RemoveElement(aDirectory);
|
||||||
|
NS_ENSURE_SUCCESS(rv, rv);
|
||||||
|
|
||||||
|
return aSession->NotifyDirectoryItemDeleted(this, aDirectory);
|
||||||
|
}
|
||||||
|
|
||||||
|
nsresult
|
||||||
|
nsAbOSXDirectory::UnassertCard(nsIAddrBookSession *aSession,
|
||||||
|
nsIAbCard *aCard)
|
||||||
|
{
|
||||||
|
NS_ASSERTION(mCardList.GetEntry(aCard), "Not found?");
|
||||||
|
|
||||||
|
mCardList.RemoveEntry(aCard);
|
||||||
|
return aSession->NotifyDirectoryItemDeleted(this, aCard);
|
||||||
|
}
|
||||||
|
|
||||||
|
NS_IMETHODIMP
|
||||||
|
nsAbOSXDirectory::GetChildNodes(nsISimpleEnumerator **aNodes)
|
||||||
|
{
|
||||||
|
NS_ENSURE_ARG_POINTER(aNodes);
|
||||||
|
|
||||||
|
// Queries don't have childnodes.
|
||||||
|
if (mIsQueryURI || !m_AddressList) {
|
||||||
|
return NS_NewEmptyEnumerator(aNodes);
|
||||||
|
}
|
||||||
|
|
||||||
|
return NS_NewArrayEnumerator(aNodes, m_AddressList);
|
||||||
|
}
|
||||||
|
|
||||||
|
NS_IMETHODIMP
|
||||||
|
nsAbOSXDirectory::GetChildCards(nsIEnumerator **aCards)
|
||||||
|
{
|
||||||
|
NS_ENSURE_ARG_POINTER(aCards);
|
||||||
|
|
||||||
|
ABAddressBook *addressBook = [ABAddressBook sharedAddressBook];
|
||||||
|
|
||||||
|
nsresult rv;
|
||||||
|
NSArray *cards;
|
||||||
|
if (mIsQueryURI) {
|
||||||
|
nsCOMPtr<nsIAbBooleanExpression> expression;
|
||||||
|
rv = nsAbQueryStringToExpression::Convert(mQueryString.get(),
|
||||||
|
getter_AddRefs(expression));
|
||||||
|
NS_ENSURE_SUCCESS(rv, rv);
|
||||||
|
|
||||||
|
PRBool canHandle = !m_IsMailList && Search(expression, &cards);
|
||||||
|
if (!canHandle) {
|
||||||
|
return FallbackSearch(expression, aCards);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
if (m_IsMailList) {
|
||||||
|
ABGroup *group = (ABGroup*)[addressBook recordForUniqueId:[NSString stringWithUTF8String:nsCAutoString(Substring(mURINoQuery, 21)).get()]];
|
||||||
|
cards = [[group members] arrayByAddingObjectsFromArray:[group subgroups]];
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
cards = [[addressBook people] arrayByAddingObjectsFromArray:[addressBook groups]];
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// Fill the results array and update the card list
|
||||||
|
// Also update the address list and notify any changes.
|
||||||
|
unsigned int nbCards = [cards count];
|
||||||
|
if (nbCards > 0) {
|
||||||
|
if (mCardList.IsInitialized()) {
|
||||||
|
mCardList.Clear();
|
||||||
|
}
|
||||||
|
else if (!mCardList.Init()) {
|
||||||
|
return NS_ERROR_OUT_OF_MEMORY;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
nsCOMPtr<nsISupportsArray> cardList;
|
||||||
|
rv = NS_NewISupportsArray(getter_AddRefs(cardList));
|
||||||
|
NS_ENSURE_SUCCESS(rv, rv);
|
||||||
|
|
||||||
|
unsigned int i;
|
||||||
|
nsCOMPtr<nsIAbCard> card;
|
||||||
|
for (i = 0; i < nbCards; ++i) {
|
||||||
|
rv = ConvertToCard(gRDFService, [cards objectAtIndex:i],
|
||||||
|
getter_AddRefs(card));
|
||||||
|
NS_ENSURE_SUCCESS(rv, rv);
|
||||||
|
|
||||||
|
rv = cardList->AppendElement(card);
|
||||||
|
NS_ENSURE_SUCCESS(rv, rv);
|
||||||
|
|
||||||
|
mCardList.PutEntry(card);
|
||||||
|
}
|
||||||
|
|
||||||
|
return GetEnumerator(cardList, aCards);
|
||||||
|
}
|
||||||
|
|
||||||
|
NS_IMETHODIMP
|
||||||
|
nsAbOSXDirectory::HasCard(nsIAbCard *aCard, PRBool *aHasCard)
|
||||||
|
{
|
||||||
|
NS_ENSURE_ARG_POINTER(aCard);
|
||||||
|
NS_ENSURE_ARG_POINTER(aHasCard);
|
||||||
|
|
||||||
|
*aHasCard = mCardList.IsInitialized() && mCardList.GetEntry(aCard);
|
||||||
|
|
||||||
|
return NS_OK;
|
||||||
|
}
|
||||||
|
|
||||||
|
NS_IMETHODIMP
|
||||||
|
nsAbOSXDirectory::HasDirectory(nsIAbDirectory *aDirectory,
|
||||||
|
PRBool *aHasDirectory)
|
||||||
|
{
|
||||||
|
NS_ENSURE_ARG_POINTER(aDirectory);
|
||||||
|
NS_ENSURE_ARG_POINTER(aHasDirectory);
|
||||||
|
|
||||||
|
*aHasDirectory = m_AddressList && m_AddressList->IndexOf(aDirectory) >= 0;
|
||||||
|
|
||||||
|
return NS_OK;
|
||||||
|
}
|
||||||
|
|
||||||
|
nsresult
|
||||||
|
nsAbOSXDirectory::OnSearchFinished(PRInt32 aResult)
|
||||||
|
{
|
||||||
|
return NS_OK;
|
||||||
|
}
|
||||||
|
|
||||||
|
nsresult
|
||||||
|
nsAbOSXDirectory::OnSearchFoundCard(nsIAbCard *aCard)
|
||||||
|
{
|
||||||
|
nsresult rv;
|
||||||
|
if (!m_AddressList) {
|
||||||
|
rv = NS_NewISupportsArray(getter_AddRefs(m_AddressList));
|
||||||
|
NS_ENSURE_SUCCESS(rv, rv);
|
||||||
|
}
|
||||||
|
|
||||||
|
if (!mCardList.IsInitialized() && !mCardList.Init()) {
|
||||||
|
return NS_ERROR_OUT_OF_MEMORY;
|
||||||
|
}
|
||||||
|
|
||||||
|
rv = m_AddressList->AppendElement(aCard);
|
||||||
|
NS_ENSURE_SUCCESS(rv, rv);
|
||||||
|
|
||||||
|
mCardList.PutEntry(aCard);
|
||||||
|
|
||||||
|
return NS_OK;
|
||||||
|
}
|
||||||
|
|
||||||
|
nsresult
|
||||||
|
nsAbOSXDirectory::FallbackSearch(nsIAbBooleanExpression *aExpression,
|
||||||
|
nsIEnumerator **aCards)
|
||||||
|
{
|
||||||
|
nsresult rv;
|
||||||
|
|
||||||
|
if (mCardList.IsInitialized())
|
||||||
|
mCardList.Clear();
|
||||||
|
else if (!mCardList.Init())
|
||||||
|
return NS_ERROR_OUT_OF_MEMORY;
|
||||||
|
|
||||||
|
if (m_AddressList) {
|
||||||
|
m_AddressList->Clear();
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
rv = NS_NewISupportsArray(getter_AddRefs(m_AddressList));
|
||||||
|
NS_ENSURE_SUCCESS(rv, rv);
|
||||||
|
}
|
||||||
|
|
||||||
|
nsCOMPtr<nsIAbDirectoryQueryArguments> arguments =
|
||||||
|
do_CreateInstance(NS_ABDIRECTORYQUERYARGUMENTS_CONTRACTID, &rv);
|
||||||
|
NS_ENSURE_SUCCESS(rv, rv);
|
||||||
|
|
||||||
|
rv = arguments->SetExpression(aExpression);
|
||||||
|
NS_ENSURE_SUCCESS(rv, rv);
|
||||||
|
|
||||||
|
// Set the return properties to
|
||||||
|
// return nsIAbCard interfaces
|
||||||
|
const char* property = "card:nsIAbCard";
|
||||||
|
rv = arguments->SetReturnProperties(1, &property);
|
||||||
|
NS_ENSURE_SUCCESS(rv, rv);
|
||||||
|
|
||||||
|
// Don't search the subdirectories. If the current directory is a mailing
|
||||||
|
// list, it won't have any subdirectories. If the current directory is an
|
||||||
|
// addressbook, searching both it and the subdirectories (the mailing
|
||||||
|
// lists), will yield duplicate results because every entry in a mailing
|
||||||
|
// list will be an entry in the parent addressbook.
|
||||||
|
rv = arguments->SetQuerySubDirectories(PR_FALSE);
|
||||||
|
NS_ENSURE_SUCCESS(rv, rv);
|
||||||
|
|
||||||
|
// Set the the query listener
|
||||||
|
nsCOMPtr<nsIAbDirectoryQueryResultListener> queryListener =
|
||||||
|
new nsAbDirSearchListener(this);
|
||||||
|
if (!queryListener)
|
||||||
|
return NS_ERROR_OUT_OF_MEMORY;
|
||||||
|
|
||||||
|
// Get the directory without the query
|
||||||
|
nsCOMPtr<nsIRDFResource> resource;
|
||||||
|
rv = gRDFService->GetResource(mURINoQuery, getter_AddRefs(resource));
|
||||||
|
NS_ENSURE_SUCCESS(rv, rv);
|
||||||
|
|
||||||
|
nsCOMPtr<nsIAbDirectory> directory = do_QueryInterface(resource, &rv);
|
||||||
|
NS_ENSURE_SUCCESS(rv, rv);
|
||||||
|
|
||||||
|
// Initiate the proxy query with the no query directory
|
||||||
|
nsCOMPtr<nsIAbDirectoryQueryProxy> queryProxy =
|
||||||
|
do_CreateInstance(NS_ABDIRECTORYQUERYPROXY_CONTRACTID, &rv);
|
||||||
|
NS_ENSURE_SUCCESS(rv, rv);
|
||||||
|
|
||||||
|
rv = queryProxy->Initiate(directory);
|
||||||
|
NS_ENSURE_SUCCESS(rv, rv);
|
||||||
|
|
||||||
|
PRInt32 context = 0;
|
||||||
|
rv = queryProxy->DoQuery(arguments, queryListener, -1, 0, &context);
|
||||||
|
NS_ENSURE_SUCCESS(rv, rv);
|
||||||
|
|
||||||
|
return GetEnumerator(m_AddressList, aCards);
|
||||||
|
}
|
|
@ -0,0 +1,71 @@
|
||||||
|
/* -*- Mode: C++; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
|
||||||
|
/* ***** BEGIN LICENSE BLOCK *****
|
||||||
|
* Version: MPL 1.1/GPL 2.0/LGPL 2.1
|
||||||
|
*
|
||||||
|
* The contents of this file are subject to the Mozilla Public License Version
|
||||||
|
* 1.1 (the "License"); you may not use this file except in compliance with
|
||||||
|
* the License. You may obtain a copy of the License at
|
||||||
|
* http://www.mozilla.org/MPL/
|
||||||
|
*
|
||||||
|
* Software distributed under the License is distributed on an "AS IS" basis,
|
||||||
|
* WITHOUT WARRANTY OF ANY KIND, either express or implied. See the License
|
||||||
|
* for the specific language governing rights and limitations under the
|
||||||
|
* License.
|
||||||
|
*
|
||||||
|
* The Original Code is mozilla.org code.
|
||||||
|
*
|
||||||
|
* The Initial Developer of the Original Code is
|
||||||
|
* Peter Van der Beken.
|
||||||
|
* Portions created by the Initial Developer are Copyright (C) 2006
|
||||||
|
* the Initial Developer. All Rights Reserved.
|
||||||
|
*
|
||||||
|
* Contributor(s):
|
||||||
|
* Peter Van der Beken <peterv@propagandism.org>
|
||||||
|
*
|
||||||
|
*
|
||||||
|
* Alternatively, the contents of this file may be used under the terms of
|
||||||
|
* either the GNU General Public License Version 2 or later (the "GPL"), or
|
||||||
|
* the GNU Lesser General Public License Version 2.1 or later (the "LGPL"),
|
||||||
|
* in which case the provisions of the GPL or the LGPL are applicable instead
|
||||||
|
* of those above. If you wish to allow use of your version of this file only
|
||||||
|
* under the terms of either the GPL or the LGPL, and not to allow others to
|
||||||
|
* use your version of this file under the terms of the MPL, indicate your
|
||||||
|
* decision by deleting the provisions above and replace them with the notice
|
||||||
|
* and other provisions required by the GPL or the LGPL. If you do not delete
|
||||||
|
* the provisions above, a recipient may use your version of this file under
|
||||||
|
* the terms of any one of the MPL, the GPL or the LGPL.
|
||||||
|
*
|
||||||
|
* ***** END LICENSE BLOCK ***** */
|
||||||
|
|
||||||
|
#ifndef nsAbOSXUtils_h___
|
||||||
|
#define nsAbOSXUtils_h___
|
||||||
|
|
||||||
|
#include <Foundation/NSString.h>
|
||||||
|
#include "nscore.h"
|
||||||
|
|
||||||
|
class nsString;
|
||||||
|
class nsCString;
|
||||||
|
class nsAbCardProperty;
|
||||||
|
|
||||||
|
NSString *WrapString(const nsString &aString);
|
||||||
|
void AppendToString(const NSString *aString, nsString &aResult);
|
||||||
|
void AssignToString(const NSString *aString, nsString &aResult);
|
||||||
|
void AppendToCString(const NSString *aString, nsCString &aResult);
|
||||||
|
|
||||||
|
struct nsAbOSXPropertyMap
|
||||||
|
{
|
||||||
|
NSString * const mOSXProperty;
|
||||||
|
NSString * const mOSXLabel;
|
||||||
|
NSString * const mOSXKey;
|
||||||
|
nsString nsAbCardProperty::*mProperty;
|
||||||
|
const char *mPropertyName;
|
||||||
|
};
|
||||||
|
|
||||||
|
class nsAbOSXUtils
|
||||||
|
{
|
||||||
|
public:
|
||||||
|
static const nsAbOSXPropertyMap kPropertyMap[];
|
||||||
|
static const PRUint32 kPropertyMapSize;
|
||||||
|
};
|
||||||
|
|
||||||
|
#endif // nsAbOSXUtils_h___
|
|
@ -0,0 +1,147 @@
|
||||||
|
/* -*- Mode: C++; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
|
||||||
|
/* ***** BEGIN LICENSE BLOCK *****
|
||||||
|
* Version: MPL 1.1/GPL 2.0/LGPL 2.1
|
||||||
|
*
|
||||||
|
* The contents of this file are subject to the Mozilla Public License Version
|
||||||
|
* 1.1 (the "License"); you may not use this file except in compliance with
|
||||||
|
* the License. You may obtain a copy of the License at
|
||||||
|
* http://www.mozilla.org/MPL/
|
||||||
|
*
|
||||||
|
* Software distributed under the License is distributed on an "AS IS" basis,
|
||||||
|
* WITHOUT WARRANTY OF ANY KIND, either express or implied. See the License
|
||||||
|
* for the specific language governing rights and limitations under the
|
||||||
|
* License.
|
||||||
|
*
|
||||||
|
* The Original Code is mozilla.org code.
|
||||||
|
*
|
||||||
|
* The Initial Developer of the Original Code is
|
||||||
|
* Peter Van der Beken.
|
||||||
|
* Portions created by the Initial Developer are Copyright (C) 2006
|
||||||
|
* the Initial Developer. All Rights Reserved.
|
||||||
|
*
|
||||||
|
* Contributor(s):
|
||||||
|
* Peter Van der Beken <peterv@propagandism.org>
|
||||||
|
*
|
||||||
|
*
|
||||||
|
* Alternatively, the contents of this file may be used under the terms of
|
||||||
|
* either the GNU General Public License Version 2 or later (the "GPL"), or
|
||||||
|
* the GNU Lesser General Public License Version 2.1 or later (the "LGPL"),
|
||||||
|
* in which case the provisions of the GPL or the LGPL are applicable instead
|
||||||
|
* of those above. If you wish to allow use of your version of this file only
|
||||||
|
* under the terms of either the GPL or the LGPL, and not to allow others to
|
||||||
|
* use your version of this file under the terms of the MPL, indicate your
|
||||||
|
* decision by deleting the provisions above and replace them with the notice
|
||||||
|
* and other provisions required by the GPL or the LGPL. If you do not delete
|
||||||
|
* the provisions above, a recipient may use your version of this file under
|
||||||
|
* the terms of any one of the MPL, the GPL or the LGPL.
|
||||||
|
*
|
||||||
|
* ***** END LICENSE BLOCK ***** */
|
||||||
|
|
||||||
|
#include "nsAbOSXUtils.h"
|
||||||
|
#include "nsString.h"
|
||||||
|
#include "nsAbOSXCard.h"
|
||||||
|
|
||||||
|
#include <AddressBook/AddressBook.h>
|
||||||
|
|
||||||
|
NSString*
|
||||||
|
WrapString(const nsString &aString)
|
||||||
|
{
|
||||||
|
PRUnichar* chars = NS_CONST_CAST(PRUnichar*, aString.get());
|
||||||
|
|
||||||
|
return [NSString stringWithCharacters:chars
|
||||||
|
length:aString.Length()];
|
||||||
|
}
|
||||||
|
|
||||||
|
void
|
||||||
|
AppendToString(const NSString *aString, nsString &aResult)
|
||||||
|
{
|
||||||
|
if (aString) {
|
||||||
|
const char *chars = [aString UTF8String];
|
||||||
|
if (chars) {
|
||||||
|
AppendUTF8toUTF16(chars, aResult);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
void
|
||||||
|
AssignToString(const NSString *aString, nsString &aResult)
|
||||||
|
{
|
||||||
|
if (aString) {
|
||||||
|
const char *chars = [aString UTF8String];
|
||||||
|
if (chars) {
|
||||||
|
CopyUTF8toUTF16(chars, aResult);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
void
|
||||||
|
AppendToCString(const NSString *aString, nsCString &aResult)
|
||||||
|
{
|
||||||
|
if (aString) {
|
||||||
|
const char *chars = [aString UTF8String];
|
||||||
|
if (chars) {
|
||||||
|
aResult.Append(chars);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// Some properties can't be easily mapped back and forth.
|
||||||
|
#define DONT_MAP(moz_name, osx_property, osx_label, osx_key)
|
||||||
|
|
||||||
|
#define DEFINE_PROPERTY(moz_name, osx_property, osx_label, osx_key) \
|
||||||
|
{ osx_property, osx_label, osx_key, &nsAbOSXCard::m_##moz_name, #moz_name },
|
||||||
|
|
||||||
|
const nsAbOSXPropertyMap nsAbOSXUtils::kPropertyMap[] = {
|
||||||
|
DEFINE_PROPERTY(FirstName, kABFirstNameProperty, nil, nil)
|
||||||
|
DEFINE_PROPERTY(LastName, kABLastNameProperty, nil, nil)
|
||||||
|
DONT_MAP("DisplayName", nil, nil, nil)
|
||||||
|
DEFINE_PROPERTY(PhoneticFirstName, kABFirstNamePhoneticProperty, nil, nil)
|
||||||
|
DEFINE_PROPERTY(PhoneticLastName, kABLastNamePhoneticProperty, nil, nil)
|
||||||
|
DEFINE_PROPERTY(NickName, kABNicknameProperty, nil, nil)
|
||||||
|
DONT_MAP(PrimaryEmail, kABEmailProperty, nil, nil)
|
||||||
|
DONT_MAP(SecondEmail, kABEmailProperty, nil, nil)
|
||||||
|
DEFINE_PROPERTY(WorkPhone, kABPhoneProperty, kABPhoneWorkLabel, nil)
|
||||||
|
DEFINE_PROPERTY(HomePhone, kABPhoneProperty, kABPhoneHomeLabel, nil)
|
||||||
|
DEFINE_PROPERTY(FaxNumber, kABPhoneProperty, kABPhoneWorkFAXLabel, nil)
|
||||||
|
DEFINE_PROPERTY(PagerNumber, kABPhoneProperty, kABPhonePagerLabel, nil)
|
||||||
|
DEFINE_PROPERTY(CellularNumber, kABPhoneProperty, kABPhoneMobileLabel, nil)
|
||||||
|
DEFINE_PROPERTY(HomeAddress, kABAddressProperty, kABAddressHomeLabel,
|
||||||
|
kABAddressStreetKey)
|
||||||
|
DEFINE_PROPERTY(HomeCity, kABAddressProperty, kABAddressHomeLabel,
|
||||||
|
kABAddressCityKey)
|
||||||
|
DEFINE_PROPERTY(HomeState, kABAddressProperty, kABAddressHomeLabel,
|
||||||
|
kABAddressStateKey)
|
||||||
|
DEFINE_PROPERTY(HomeZipCode, kABAddressProperty, kABAddressHomeLabel,
|
||||||
|
kABAddressZIPKey)
|
||||||
|
DEFINE_PROPERTY(HomeCountry, kABAddressProperty, kABAddressHomeLabel,
|
||||||
|
kABAddressCountryKey)
|
||||||
|
DEFINE_PROPERTY(WorkAddress, kABAddressProperty, kABAddressWorkLabel,
|
||||||
|
kABAddressStreetKey)
|
||||||
|
DEFINE_PROPERTY(WorkCity, kABAddressProperty, kABAddressWorkLabel,
|
||||||
|
kABAddressCityKey)
|
||||||
|
DEFINE_PROPERTY(WorkState, kABAddressProperty, kABAddressWorkLabel,
|
||||||
|
kABAddressStateKey)
|
||||||
|
DEFINE_PROPERTY(WorkZipCode, kABAddressProperty, kABAddressWorkLabel,
|
||||||
|
kABAddressZIPKey)
|
||||||
|
DEFINE_PROPERTY(WorkCountry, kABAddressProperty, kABAddressWorkLabel,
|
||||||
|
kABAddressCountryKey)
|
||||||
|
DEFINE_PROPERTY(JobTitle, kABJobTitleProperty, nil, nil)
|
||||||
|
DEFINE_PROPERTY(Department, kABDepartmentProperty, nil, nil)
|
||||||
|
DEFINE_PROPERTY(Company, kABOrganizationProperty, nil, nil)
|
||||||
|
DONT_MAP(_AimScreenName, kABAIMInstantProperty, nil, nil)
|
||||||
|
DEFINE_PROPERTY(WebPage1, kABHomePageProperty, nil, nil)
|
||||||
|
DONT_MAP(WebPage2, kABHomePageProperty, nil, nil)
|
||||||
|
DONT_MAP(BirthYear, "birthyear", nil, nil)
|
||||||
|
DONT_MAP(BirthMonth, "birthmonth", nil, nil)
|
||||||
|
DONT_MAP(BirthDay, "birthday", nil, nil)
|
||||||
|
DONT_MAP(Custom1, "custom1", nil, nil)
|
||||||
|
DONT_MAP(Custom2, "custom2", nil, nil)
|
||||||
|
DONT_MAP(Custom3, "custom3", nil, nil)
|
||||||
|
DONT_MAP(Custom4, "custom4", nil, nil)
|
||||||
|
DEFINE_PROPERTY(Note, kABNoteProperty, nil, nil)
|
||||||
|
DONT_MAP("PreferMailFormat", nil, nil, nil)
|
||||||
|
DONT_MAP("LastModifiedDate", modifytimestamp, nil, nil)
|
||||||
|
};
|
||||||
|
|
||||||
|
const PRUint32 nsAbOSXUtils::kPropertyMapSize =
|
||||||
|
NS_ARRAY_LENGTH(nsAbOSXUtils::kPropertyMap);
|
Загрузка…
Ссылка в новой задаче