Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Support for FCM v1 API #361

Merged
merged 9 commits into from
Feb 15, 2024
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
23 changes: 19 additions & 4 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -78,11 +78,26 @@ For either type, it can accept:
### gcm

This sends messages via Google/Firebase Cloud Messaging (GCM/FCM)
and hence can be used to deliver notifications to Android apps. It
expects the 'api_key' parameter to contain the 'Server key',
which can be acquired from Firebase Console at:
`https://console.firebase.google.com/project/<PROJECT NAME>/settings/cloudmessaging/`
and hence can be used to deliver notifications to Android apps.

The expected configuration depends on which version of the firebase api you
wish to use.

For legacy API, it expects:

- the `api_key` parameter to contain the `Server key`,
which can be acquired from Firebase Console at:
`https://console.firebase.google.com/project/<PROJECT NAME>/settings/cloudmessaging/`

For API v1, it expects:

- the `api_version` parameter to contain `v1`
- the `project_id` parameter to contain the `Project ID`,
which can be acquired from Firebase Console at:
`https://console.cloud.google.com/project/<PROJECT NAME>/settings/general/`
- the `service_account_file` parameter to contain the path to the service account file,
which can be acquired from Firebase Console at:
`https://console.firebase.google.com/project/<PROJECT NAME>/settings/serviceaccounts/adminsdk`

Using an HTTP Proxy for outbound traffic
----------------------------------------
Expand Down
1 change: 1 addition & 0 deletions changelog.d/361.feature
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
Adds the ability to use the new FCM v1 API.
31 changes: 26 additions & 5 deletions docs/applications.md
Original file line number Diff line number Diff line change
Expand Up @@ -211,7 +211,14 @@ may be useful for reference.

### Firebase Cloud Messaging

The client will receive a message with an FCM `data` payload with this structure:
The client will receive a message with an FCM `data` payload with a structure depending on the api version used:

Please note that fields may be truncated if they are large, so that they fit
within FCM's limit.
Please also note that some fields will be unavailable if you registered a pusher
with `event_id_only` format.

#### Legacy API

```json
{
Expand All @@ -232,10 +239,24 @@ The client will receive a message with an FCM `data` payload with this structure
}
```

Please note that fields may be truncated if they are large, so that they fit
within FCM's limit.
Please also note that some fields will be unavailable if you registered a pusher
with `event_id_only` format.
#### API v1

```json
{
"event_id": "$3957tyerfgewrf384",
"type": "m.room.message",
"sender": "@exampleuser:example.org",
"room_name": "Mission Control",
"room_alias": "#exampleroom:example.org",
"sender_display_name": "Major Tom",
"content_msgtype": "m.text",
"content_body": "I'm floating in a most peculiar way."
"room_id": "!slw48wfj34rtnrf:example.org",
"prio": "high",
"unread": "2",
"missed_calls": "1"
}
```

### WebPush

Expand Down
2 changes: 1 addition & 1 deletion docs/troubleshooting.md
Original file line number Diff line number Diff line change
Expand Up @@ -207,7 +207,7 @@ EOF
```


## Example of an FCM request
## Example of an FCM request (Legacy API)

HTTP data sent to `https://fcm.googleapis.com/fcm/send`:

Expand Down
1 change: 1 addition & 0 deletions pyproject.toml
Original file line number Diff line number Diff line change
Expand Up @@ -78,6 +78,7 @@ dependencies = [
"attrs>=19.2.0",
"cryptography>=2.6.1",
"idna>=2.8",
"google-auth>=2.27.0",
"jaeger-client>=4.0.0",
"matrix-common==1.3.0",
"opentracing>=2.2.0",
Expand Down
Empty file added stubs/google/__init__.pyi
Empty file.
3 changes: 3 additions & 0 deletions stubs/google/auth/__init__.pyi
Original file line number Diff line number Diff line change
@@ -0,0 +1,3 @@
from google.auth._default import default

__all__ = ["default"]
15 changes: 15 additions & 0 deletions stubs/google/auth/_default.pyi
Original file line number Diff line number Diff line change
@@ -0,0 +1,15 @@
from typing import Optional

from google.auth.transport.requests import Request

class Credentials:
token = "token"

def refresh(self, request: Request) -> None: ...

def default(
scopes: Optional[list[str]] = None,
request: Optional[str] = None,
quota_project_id: Optional[int] = None,
default_scopes: Optional[list[str]] = None,
) -> tuple[Credentials, Optional[str]]: ...
3 changes: 3 additions & 0 deletions stubs/google/auth/transport/__init__.pyi
Original file line number Diff line number Diff line change
@@ -0,0 +1,3 @@
from google.auth.transport.requests import Request

__all__ = ["Request"]
1 change: 1 addition & 0 deletions stubs/google/auth/transport/requests.pyi
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
class Request: ...
3 changes: 3 additions & 0 deletions stubs/google/oauth2/__init__.pyi
Original file line number Diff line number Diff line change
@@ -0,0 +1,3 @@
from google.oauth2.service_account import Credentials

__all__ = ["Credentials"]
16 changes: 16 additions & 0 deletions stubs/google/oauth2/service_account.pyi
Original file line number Diff line number Diff line change
@@ -0,0 +1,16 @@
from typing import Optional

from google.auth.transport.requests import Request

class Credentials:
token = "token"

def refresh(self, request: Request) -> None: ...
@staticmethod
def from_service_account_file(
service_account_file: str,
scopes: Optional[list[str]] = None,
request: Optional[str] = None,
quota_project_id: Optional[int] = None,
default_scopes: Optional[list[str]] = None,
) -> Credentials: ...
7 changes: 5 additions & 2 deletions sygnal.yaml.sample
Original file line number Diff line number Diff line change
Expand Up @@ -205,9 +205,12 @@ apps:

# This is an example GCM/FCM push configuration.
#
#com.example.myapp.android:
#im.vector.app:
# type: gcm
# api_key: your_api_key_for_gcm
# #api_key:
# api_version: v1
# project_id: project-id
# service_account_file: /path/to/service_account.json
#
# # This is the maximum number of connections to GCM servers at any one time
# # the default is 20.
Expand Down
12 changes: 12 additions & 0 deletions sygnal/exceptions.py
Original file line number Diff line number Diff line change
Expand Up @@ -39,6 +39,18 @@ def __init__(self, *args: object, custom_retry_delay: Optional[int] = None) -> N
self.custom_retry_delay = custom_retry_delay


class NotificationQuotaDispatchException(Exception):
"""
To be used by pushkins for errors that are do to exceeding the quota
limits and are hopefully temporary, so the request should possibly be
retried soon.
"""

def __init__(self, *args: object, custom_retry_delay: Optional[int] = None) -> None:
super().__init__(*args)
self.custom_retry_delay = custom_retry_delay


class ProxyConnectError(ConnectError):
"""
Exception raised when we are unable to start a connection using a HTTP proxy
Expand Down
Loading
Loading