AddressBook Framework Bindings for PyObjC
pyobjc-framework-addressbook provides Pythonic wrappers for the macOS AddressBook framework, allowing Python applications to interact with contact data. It is part of the larger PyObjC project, which bridges Python and Objective-C. The current version is 12.1 and new releases generally align with macOS SDK updates and Python version support changes.
Warnings
- breaking PyObjC has dropped support for older Python versions in recent major releases. Version 12.0 dropped support for Python 3.9, and version 11.0 dropped support for Python 3.8. Ensure your Python environment meets the 'requires_python' specification (>=3.10).
- breaking The AddressBook framework itself has been deprecated by Apple since macOS 10.11. For new development, it is strongly recommended to use the Contacts framework (available via `pyobjc-framework-Contacts`) instead.
- breaking The `IMServicePlugIn` framework bindings were entirely removed in PyObjC 10.0, as the framework was deprecated in macOS 10.13 and removed in macOS 14.
- gotcha In PyObjC 10.3, the behavior around `__init__` when a Python class relies on PyObjC's provided `__new__` for Objective-C object instantiation changed, preventing `__init__` from being called. While PyObjC 10.3.1 partially reverted this for user-implemented `__new__` methods, code relying on the `__new__` provided by PyObjC still cannot use `__init__`.
- gotcha Using `os.fspath()` with Cocoa URLs (like `NSURL` or `CFURLRef`) that *do not* refer to local filesystem paths will raise a `TypeError`. This functionality was improved in PyObjC 10.1 to enable standard Python filesystem APIs for *local* paths.
- gotcha As of PyObjC 12.1, Key-Value Observation (KVO) usage is automatically disabled for subclasses of `NSProxy` defined in Python to prevent unexpected behavior.
Install
-
pip install pyobjc-framework-addressbook
Imports
- ABAddressBook
from AddressBook import ABAddressBook
- ABPerson
from AddressBook import ABPerson
Quickstart
from AddressBook import ABAddressBook, ABPerson
def get_first_person_name():
try:
# On modern macOS, you might need to grant permission to access contacts.
# This code will likely prompt for permission the first time it's run.
book = ABAddressBook.sharedAddressBook() #
people = book.people() #
if people.count() > 0:
person = people[0] #
display_name = person.displayName() #
return display_name
else:
return "No contacts found."
except Exception as e:
return f"An error occurred: {e}"
if __name__ == '__main__':
print(f"First contact's display name: {get_first_person_name()}")