This is a fork of the original integration by @PTST which has now been archived.
This integration enables:
- Getting and creating calendar events from O365.
- Getting emails from your inbox.
- Sending emails via the notify.o365_email service.
- Getting presence from Teams (not for personal accounts)
- Getting the latest chat message from Teams (not for personal accounts)
This project would not be possible without the wonderful python-o365 project.
I work on this integration because I like things to work well for myself and others. Whilst I have now made significant changes to the integration, it would not be as it stands today without the major work to create it put in by @PTST. Please don't feel you are obligated to donate, but of course it is appreciated.
To allow authentication you first need to register your application at Azure App Registrations:
-
Login at Azure Portal (App Registrations). Personal accounts may receive an authentication notification that can be ignored.
-
Create a new App Registration. Give it a name. In Supported account types, choose "Accounts in any organizational directory and personal Microsoft accounts (e.g. Skype, Xbox, Outlook.com)", if you are using a personal account. Click Register
-
Click Add a Redirect URI. Click Add a platform. Select Web. Set redirect URI to:
https://login.microsoftonline.com/common/oauth2/nativeclient
, leave the other fields blank and click Configure.When using the alternate auth flow, which requires internet access to HA, please see the Authentication section.
NOTE: The default authentication method has changed from version 3.2.0. The default is now to use the method which does not require access to your HA instance from the internet. If you previously did not set alt_auth_flow or had it set to False, please set alt_auth_method to True and remove alt_auth_flow from your config. This will only impact people re-authenticating.
If you are using Multi-factor Authentication (MFA), you may find you also need to add "https://login.microsoftonline.com/organizations/oauth2/v2.0/authorize" to your redirect URIs.
-
From the Overview page, write down the Application (client) ID. You will need this value for the configuration.yaml.
-
Under "Certificates & secrets", generate a new client secret. Set the expiration as desired. This appears to be limited to 2 years. Write down the Value of the client secret now. It will be hidden later on. If you lose track of the secret return here to generate a new one.
-
Under "API Permissions" click Add a permission, then Microsoft Graph, then Delegated permission, and add the following permissions:
- offline_access - Maintain access to data you have given it access to
- Calendars.Read - Read user calendars
- Users.Read - Sign in and read user profile
If you are creating an email_sensor or a query_sensor you will need:
- Mail.Read - Read access to user mail
If you are creating a status_sensor you will need:
- Presence.Read - Read user's presence information (Not for personal accounts)
If you are creating a chat_sensor you will need:
- Chat.Read - Read user chat messages (Not for personal accounts)
If 'enable_update' is set to True, (it defaults to False for multi-account installs and True for other installs so as not to break existing installs), then the following permissions are also required (you can always remove permissions later):
- Calendars.ReadWrite - Read and write user calendars
- Mail.ReadWrite - Read and write access to user mail
- Mail.Send - Send mail as a user
- Install this integration:
- Recommended - Home Assistant Community Store (HACS) or
- Manually - Copy these files to custom_components/o365/.
- Add o365 configuration to configuration.yaml using the Configuration example below.
- Restart your Home Assistant instance. Note: if Home Assistant give the error "module not found", try restarting home assistant once more.
- Authenticate to establish link between this integration and Azure app
- A persistent token will be created in the hidden directory config/.O365-token-cache
- The o365_calendars_<account_name>.yaml (or o365_calendars.yaml for secondary configuration method) will be created under the config directory
- Configure Calendars
Two formats are possible. The first format shown below is the preferred layout since it is setup for improved security and allows for multiple accounts to be configured.
# Example configuration.yaml entry for multiple accounts
o365:
accounts:
- account_name: Account1
client_secret: "xx.xxxxxxxxxxxxxxxxxxxxxxxxxxxx"
client_id: "xxxxxx-xxxx-xxxx-xxxx-xxxxxxxxxx"
enable_update: True
email_sensor:
- name: inbox
max_items: 2
is_unread: True
download_attachments: False
query_sensors:
- name: "Example"
folder: "Inbox/Test_Inbox" #Default is Inbox
from: "[email protected]"
subject_contains: "Example subject"
has_attachment: True
max_items: 2
is_unread: True
status_sensors: # Cannot be used for personal accounts
- name: "User Teams Status"
chat_sensors: # Cannot be used for personal accounts
- name: "User Chat"
- account_name: Account2
client_secret: "xx.xxxxxxxxxxxxxxxxxxxxxxxxxxxx"
client_id: "xxxxxx-xxxx-xxxx-xxxx-xxxxxxxxxx"
# Example configuration.yaml entry for single account
o365:
client_secret: "xx.xxxxxxxxxxxxxxxxxxxxxxxxxxxx"
client_id: "xxxxxx-xxxx-xxxx-xxxx-xxxxxxxxxx"
enable_update: False
email_sensor:
- name: inbox
max_items: 2
is_unread: True
download_attachments: False
query_sensors:
- name: "Example"
folder: "Inbox/Test_Inbox" #Default is Inbox
from: "[email protected]"
subject_contains: "Example subject"
has_attachment: True
max_items: 2
is_unread: True
status_sensors: # Cannot be used for personal accounts
- name: "User Teams Status"
chat_sensors: # Cannot be used for personal accounts
- name: "User Chat"
Key | Type | Required | Description |
---|---|---|---|
account_name |
string |
True |
Uniquely identifying name for the account. Calendars entity names will be suffixed with this. e.g calendar.calendar_account1 |
client_id |
string |
True |
Client ID from your O365 application. |
client_secret |
string |
True |
Client Secret from your O365 application. |
alt_auth_method |
boolean |
False |
If False (default), authentication is not dependent on internet access to your HA instance. See Authentication |
enable_update |
boolean |
False |
If True (default is False), this will enable the various services that allow the sending of emails and updates to calendars |
track_new_calendar |
boolean |
False |
If True (default), will automatically generate a calendar_entity when a new calendar is detected. The system scans for new calendars only on startup. |
email_sensors |
list<email_sensors> |
False |
List of email_sensor config entries |
query_sensors |
list<query_sensors> |
False |
List of query_sensor config entries |
status_sensors |
list<status_sensors> |
False |
List of status_sensor config entries. Not for use on personal accounts |
Key | Type | Required | Description |
---|---|---|---|
client_id |
string |
True |
Client ID from your O365 application. |
client_secret |
string |
True |
Client Secret from your O365 application. |
alt_auth_method |
boolean |
False |
If False (default), authentication is not dependent on internet access to your HA instance. See Authentication |
enable_update |
boolean |
False |
If True (default is True), this will enable the various services that allow the sending of emails and updates to calendars |
track_new_calendar |
boolean |
False |
If True (default), will automatically generate a calendar_entity when a new calendar is detected. The system scans for new calendars only on startup. |
email_sensors |
list<email_sensors> |
False |
List of email_sensor config entries |
query_sensors |
list<query_sensors> |
False |
List of query_sensor config entries |
status_sensors |
list<status_sensors> |
False |
List of status_sensor config entries. Not for use on personal accounts |
Key | Type | Required | Description |
---|---|---|---|
name |
string |
True |
The name of the sensor. |
folder |
string |
False |
Mail folder to monitor, for nested calendars seperate with '/' ex. "Inbox/SubFolder/FinalFolder" Default is Inbox |
max_items |
integer |
False |
Max number of items to retrieve (default 5) |
is_unread |
boolean |
False |
True=Only get unread, False=Only get read, Not set=Get all |
download_attachments |
boolean |
False |
True=Download attachments, False=Don't download attachments |
Key | Type | Required | Description |
---|---|---|---|
name |
string |
True |
The name of the sensor. |
folder |
string |
False |
Mail folder to monitor, for nested calendars seperate with '/' ex. "Inbox/SubFolder/FinalFolder" Default is Inbox |
max_items |
integer |
False |
Max number of items to retrieve (default 5) |
is_unread |
boolean |
False |
True=Only get unread, False=Only get read, Not set=Get all |
from |
string |
False |
Only retrieve emails from this email address |
has_attachment |
boolean |
False |
True=Only get emails with attachments, False=Only get emails without attachments, Not set=Get all |
importance |
string |
False |
Only get items with 'low'/'normal'/'high' importance |
subject_contains |
string |
False |
Only get emails where the subject contains this string (Mutually exclusive with subject_is ) |
subject_is |
string |
False |
Only get emails where the subject equals exactly this string (Mutually exclusive with subject_contains ) |
download_attachments |
boolean |
False |
True=Download attachments, False=Don't download attachments |
Key | Type | Required | Description |
---|---|---|---|
name |
string |
True |
The name of the sensor. |
Key | Type | Required | Description |
---|---|---|---|
name |
string |
True |
The name of the sensor. |
NOTE: The default authentication method has changed from version 3.2.0. The default is now to use the method which does not require access to your HA instance from the internet. If you previously did not set alt_auth_flow or had it set to False, please set alt_auth_method to True and remove alt_auth_flow from your config. This will only impact people re-authenticating.
After setting up configuration.yaml and restarting home assistant a persistent notification will be created.
- Click on this notification.
- Click the "Link O365 account" link.
- Login on the microsoft page.
- Copy the url from the browser url bar.
- Insert into the "Returned Url" field. and click Submit.
- That's it.
This requires the alt_auth_method to be set to True and the redirect uri in your Azure app set to https://<your_home_assistant_url_or_local_ip>/api/o365
. Note: if you use Nabu Casa for remote support, use that URL as the base.
After setting up configuration.yaml with the key set to True and restarting home assistant a persisten notification will be created.
- Click on this notification.
- Click the "Link O365 account" link.
- Login on the microsoft page; when prompted, authorize the app you created
- Close the window when the message "Success! This window can be closed" appears.
- That's it.
The integration uses an external o365_calendars_<account_name>.yaml file (or o365_calendars.yaml for secondary configuration method).
- cal_id: xxxx
entities:
- device_id: work_calendar
end_offset: 24
name: My Work Calendar
start_offset: 0
track: true
- cal_id: xxxx
entities:
- device_id: birthdays
end_offset: 24
name: Birthdays
start_offset: 0
track: true
Key | Type | Required | Description |
---|---|---|---|
cal_id |
string |
True |
O365 generated unique ID, DO NOT CHANGE |
entities |
list<entity> |
True |
List of entities (see below) to generate from this calendar |
Key | Type | Required | Description |
---|---|---|---|
device_id |
string |
True |
The entity_id will be "calendar.{device_id}" |
name |
string |
True |
The name of your sensor that you’ll see in the frontend. |
track |
boolean |
True |
True=Create calendar entity. False=Don't create entity |
search |
string |
False |
Only get events if subject contains this string |
start_offset |
integer |
False |
Number of hours to offset the start time to search for events for (negative numbers to offset into the past). |
end_offset |
integer |
False |
Number of hours to offset the end time to search for events for (negative numbers to offset into the past). |
Key | Type | Required | Description |
---|---|---|---|
message |
string |
True |
The email body |
title |
string |
False |
The email subject |
data |
dict<data> |
False |
Addional attributes - see table below |
Key | Type | Required | Description |
---|---|---|---|
target |
string |
False |
recipient of the email, if not set will use the configured account's email address |
message_is_html |
boolean |
False |
Is the message formatted as html |
photos |
list<string> |
False |
Filepaths or urls of pictures to embed into the email body |
attachments |
list<string> |
False |
Filepaths to attach to email |
zip_attachments |
boolean |
False |
Zip files from attachments into a zip file before sending |
zip_name |
string |
False |
Name of the generated zip file |
service: notify.o365_email
data:
message: The garage door has been open for 10 minutes.
title: Your Garage Door Friend
data:
message_is_html: true
attachments:
- "/config/documents/sendfile.txt"
zip_attachments: true
zip_name: "zipfile.zip"
photos:
- "/config/documents/image.jpg"
Create an event in the specified calendar - All paremeters are shown in the available parameter list on the Developer Tools/Services tab.
Modify an event in the specified calendar - All paremeters are shown in the available parameter list on the Developer Tools/Services tab.
Remove an event in the specified calendar - All paremeters are shown in the available parameter list on the Developer Tools/Services tab.
Respond to an event in the specified calendar - All paremeters are shown in the available parameter list on the Developer Tools/Services tab.
Scan for new calendars and add to o365_calendars.yaml - No parameters.
The status of the calendar sensor indicates (on/off) whether there is an event on at the current time. The message
, all_day
, start_time
, end_time
, location
, description
and offset_reached
attributes provide details of the current of next event. A non all-day event is favoured over all_day events.
The data
attribute provides an array of events for the period defined by the start_offset
and end_offset
in o365_calendars_<account_name>.yaml. Individual array elements can be accessed using the notation {{ states.calendar.calendar_<account_name>.attributes.data[0...n] }}
- The reply URL specified in the request does not match the reply URLs configured for the application.
- Please ensure that you have configured base_url in your http config https://www.home-assistant.io/integrations/http/#base_url and that you have added the correct reply url to your Azure app
- Client is public so neither 'client_assertion' nor 'client_secret' should be presented.
- Application {x} is not configured as a multi-tenant application.
- In your azure app go to Manifest, find the key "signInAudience", change its value to "AzureADandPersonalMicrosoftAccount"
- Platform error sensor.office365calendar - No module named '{x}'
-
This is a known home assistant issue, all that's needed to fix this should be another restart of your home assistant server. If this does not work, please try installing the component in this order:
1. Install the component. 2. Restart home assistant. 3. Then add the sensor to your configuration.yaml 4. Restart home assistant again.
-
Please note that any changes made to your Azure app settings takes a few minutes to propagate. Please wait around 5 minutes between changes to your settings and any auth attemps from Home Assistant