Exchangelib is a Python client for Microsoft Exchange Web Services (EWS), providing programmatic access to Exchange mailboxes, calendars, contacts, and tasks. It supports autodiscovery, various authentication methods (NTLM, OAuth), and aims to be a comprehensive, easy-to-use interface for EWS. The current version is 5.6.0, with a release cadence that responds to bug fixes, feature requests, and EWS changes.
pip install exchangelibVerified import paths — ran on the pinned version, not inferred.
This quickstart demonstrates how to connect to an Exchange mailbox using email/password credentials and autodiscovery. It then fetches and prints the subjects of the 5 most recent unread items in the inbox. It uses environment variables for security to avoid hardcoding sensitive information.
Migrate authentication logic to use `exchangelib.Credentials` directly. For custom protocols, ensure `auth_type` and other parameters are correctly passed to `Protocol`.
Update any code that references `protocol.ews_url` (for autodiscover URL) to `protocol.autodiscover_url` and `protocol.service_endpoint` (for service endpoint URL) to `protocol.ews_url`.
Always use `exchangelib.EWSTimeZone` when creating or modifying datetime objects that interact with Exchange. Ensure your local system's timezone is correctly configured if relying on `tzlocal`.
Use iterators or specify a maximum number of items when querying large folders (e.g., `folder.all().order_by('-datetime_received')[:100]`). For complex queries, use `folder.filter().iterator()`.If autodiscovery fails, explicitly provide the `ews_url` when creating a `Configuration` object, then pass that configuration to the `Account`. Example: `config = Configuration(server='outlook.office365.com', credentials=credentials, ews_url='https://outlook.office365.com/EWS/Exchange.asmx')`.
Manually specify the EWS server URL and disable autodiscover. You can often find the EWS URL in Outlook's connection settings or through your IT administrator. ```python from exchangelib import Credentials, Account, Configuration creds = Credentials(username='your_username@your_domain.com', password='your_password') config = Configuration(server='your.exchange.server.com', credentials=creds) # e.g., 'outlook.office365.com' or a specific EWS URL account = Account(primary_smtp_address='your_username@your_domain.com', config=config, autodiscover=False) ```
First, double-check your username and password, including the format (e.g., `DOMAIN\username` vs. `user@domain.com`). If using Office 365, consider switching to OAuth2 authentication as Basic Auth is largely deprecated.
```python
from exchangelib import Credentials, Account, OAUTH2, OAuth2Credentials
# For NTLM/Basic Auth (if supported by your server)
# creds = Credentials(username='DOMAIN\username', password='your_password')
# For Office 365 / OAuth2
# Requires prior Azure AD app registration to get client_id, client_secret, and tenant_id
ocreds = OAuth2Credentials(
client_id='your_client_id',
client_secret='your_client_secret',
tenant_id='your_tenant_id', # or 'organizations' or 'common'
access_token='your_initial_access_token' # This needs to be refreshed externally
)
account = Account(primary_smtp_address='user@example.com', credentials=ocreds, autodiscover=True, access_type=OAUTH2)
```To fix this, you can either explicitly trust the certificate by providing its path to `exchangelib` or, as a last resort for testing (not recommended for production), disable SSL verification. ```python from exchangelib import DELEGATE, Account, Credentials, Configuration from exchangelib.protocol import BaseProtocol, NoVerifyHTTPAdapter import ssl # Option 1: Provide path to CA bundle (recommended) # BaseProtocol.HTTP_ADAPTER_CLS.ssl_context = ssl.create_default_context(cafile='/path/to/your/ca_bundle.pem') # Option 2: Disable SSL verification (use with caution, for testing only) BaseProtocol.HTTP_ADAPTER_CLS = NoVerifyHTTPAdapter creds = Credentials(username='user@example.com', password='your_password') account = Account(primary_smtp_address='user@example.com', credentials=creds, autodiscover=True) ```
Always use `exchangelib.EWSTimeZone` and `exchangelib.EWSDateTime` when working with dates and times that will be sent to or received from Exchange.
```python
from exchangelib import EWSDateTime, EWSTimeZone
from datetime import datetime
# Correct way to create a timezone-aware EWSDateTime
tz = EWSTimeZone.localzone() # or EWSTimeZone.timezone('Europe/Copenhagen')
now = EWSDateTime.now(tz=tz)
# If you have a standard datetime object and need to convert it:
standard_dt = datetime.now(tz=pytz.utc) # Example with pytz
ews_tz = EWSTimeZone.from_timezone(standard_dt.tzinfo)
news_dt = EWSDateTime(standard_dt.year, standard_dt.month, standard_dt.day,
standard_dt.hour, standard_dt.minute, standard_dt.second,
tzinfo=news_tz)
```Ensure `exchangelib` is installed in your environment using pip. If using a virtual environment, activate it first. If deploying with PyInstaller, ensure PyInstaller is correctly configured to include `exchangelib` as a hidden import if necessary. ```bash pip install exchangelib # If using PyInstaller and encountering issues, you might need: pyinstaller --hidden-import exchangelib your_script.py ```