V1.30 notification
This commit is contained in:
@@ -0,0 +1,97 @@
|
||||
import datetime
|
||||
from firebase_admin import messaging, initialize_app, exceptions
|
||||
|
||||
class FCM:
|
||||
logo_url = 'https://workouttest.com/wp-content/uploads/2020/10/WT_long_logo.png'
|
||||
|
||||
# default constructor
|
||||
def __init__(self):
|
||||
# To learn more, visit the docs here:
|
||||
# https://cloud.google.com/docs/authentication/getting-started>
|
||||
default_app = initialize_app()
|
||||
|
||||
def send_to_multiple_token(self, title, body, registration_token, image_url = None):
|
||||
try:
|
||||
notification_image_url = image_url
|
||||
#if image_url == None:
|
||||
# notification_image_url = self.logo_url
|
||||
|
||||
message = messaging.MulticastMessage(
|
||||
notification=messaging.Notification(
|
||||
title=title,
|
||||
body=body,
|
||||
),
|
||||
android=messaging.AndroidConfig(
|
||||
ttl=datetime.timedelta(seconds=3600),
|
||||
priority='normal',
|
||||
notification=messaging.AndroidNotification(
|
||||
image=notification_image_url,
|
||||
),
|
||||
),
|
||||
apns=messaging.APNSConfig(
|
||||
payload=messaging.APNSPayload(
|
||||
aps=messaging.Aps(badge=1),
|
||||
),
|
||||
fcm_options= messaging.APNSFCMOptions(
|
||||
image=notification_image_url,
|
||||
)
|
||||
),
|
||||
tokens= registration_token,
|
||||
)
|
||||
response = messaging.send_multicast(message)
|
||||
# Response is a message ID string.
|
||||
print('Successfully sent message:', response);
|
||||
|
||||
except exceptions.FirebaseError as error:
|
||||
print('Error sending message:', error);
|
||||
except ValueError as value_error:
|
||||
print('Error sending message:', value_error);
|
||||
|
||||
|
||||
def send_to_token(self, title, body, image_url = None, registration_token = None):
|
||||
if registration_token == None:
|
||||
return "Registration token is null"
|
||||
try:
|
||||
#notification_image_url = image_url
|
||||
#if image_url == None:
|
||||
notification_image_url = self.logo_url
|
||||
registration_token = 'cOqNt8rzo074gbIkBSpCgW:APA91bEBuNi3iVzGKb4JhxqN2j80MoJbNptLHk2qsdeKBQz5grpHtrPPXvDqn5BJVVSaj1nwGPwgN7pi6FIApog_TTP3g1yobgmgpPN6udrYgzILlVPMvdGGFDSDh6gKlczhlTL9NEp0'
|
||||
|
||||
print(f'image: {notification_image_url}' )
|
||||
|
||||
message = messaging.Message(
|
||||
notification=messaging.Notification(
|
||||
title=title,
|
||||
body=body,
|
||||
),
|
||||
android=messaging.AndroidConfig(
|
||||
ttl=datetime.timedelta(seconds=3600),
|
||||
priority='normal',
|
||||
notification=messaging.AndroidNotification(
|
||||
image=notification_image_url,
|
||||
),
|
||||
),
|
||||
apns=messaging.APNSConfig(
|
||||
payload=messaging.APNSPayload(
|
||||
aps=messaging.Aps(badge=1),
|
||||
),
|
||||
fcm_options= messaging.APNSFCMOptions(
|
||||
image=notification_image_url,
|
||||
)
|
||||
),
|
||||
token= registration_token,
|
||||
)
|
||||
response = messaging.send(message)
|
||||
# Response is a message ID string.
|
||||
print('Successfully sent message:', response);
|
||||
rc = 'OK'
|
||||
|
||||
except exceptions.FirebaseError as error:
|
||||
print('Error sending message:', error);
|
||||
rc = error
|
||||
except ValueError as value_error:
|
||||
print('Error sending message:', value_error);
|
||||
rc = value_error
|
||||
|
||||
return rc
|
||||
|
||||
@@ -0,0 +1,76 @@
|
||||
import requests
|
||||
import logging
|
||||
from django.db import connections
|
||||
import datetime
|
||||
|
||||
from ..models.customer import Customer
|
||||
|
||||
|
||||
class Mautic:
|
||||
|
||||
def syncTrial(self):
|
||||
tenDays = datetime.datetime - datetime.timedelta(days=10)
|
||||
qs = Customer.objects.raw(
|
||||
'SELECT * from customer WHERE trial_date < "' + tenDays + '" and trial_date is not null')
|
||||
|
||||
def sync(self):
|
||||
logger = logging.getLogger(__name__)
|
||||
logger.info("Syncronising...")
|
||||
|
||||
last_synced_date = self.get_last_synced_date()
|
||||
|
||||
if len(last_synced_date) != 0:
|
||||
qs = Customer.objects.raw(
|
||||
'SELECT * from customer WHERE date_add > "' + last_synced_date + '" or synced_date is null')
|
||||
else:
|
||||
qs = Customer.objects.raw(
|
||||
'SELECT * from customer WHERE synced_date is null')
|
||||
|
||||
headers = {
|
||||
'content-type': "application/x-www-form-urlencoded",
|
||||
'cache-control': "no-cache"
|
||||
}
|
||||
index = 0
|
||||
for customer in qs:
|
||||
goal = customer.goal if customer.goal is not None else ""
|
||||
fitness_level = customer.fitness_level if customer.fitness_level is not None else ""
|
||||
data = "mauticform[email]=" + customer.email + \
|
||||
"&mauticform[f_name]=" + customer.name + \
|
||||
"&mauticform[firstname]=" + customer.firstname + \
|
||||
"&mauticform[goal]=" + goal + \
|
||||
"&mauticform[fitness_level]=" + fitness_level + \
|
||||
"&mauticform[subscribed]=" + str(customer.date_add) + \
|
||||
"&mauticform[database_id]=" + str(customer.customer_id) + \
|
||||
"&mauticform[formId]=1" + \
|
||||
"&mauticform[formName]=appsync"
|
||||
|
||||
print(data)
|
||||
|
||||
form_url = 'https://mautic.aitrainer.app/form/submit?formId=1'
|
||||
response = requests.post(form_url, data=data.encode('utf-8'), headers=headers)
|
||||
print(str(response.status_code))
|
||||
|
||||
if response.status_code == 200:
|
||||
with connections["live"].cursor() as cursor:
|
||||
cursor.execute("UPDATE customer SET synced_date = NOW() WHERE customer_id="
|
||||
+ str(customer.customer_id))
|
||||
#if index == 0:
|
||||
# break
|
||||
index = index + 1
|
||||
|
||||
logger.info("Syncronised customer count: " + str(index))
|
||||
|
||||
return True
|
||||
|
||||
def get_last_synced_date(self):
|
||||
qs = Customer.objects.raw('SELECT customer_id, max(synced_date) as synced_date from customer')
|
||||
for c in qs:
|
||||
if c.synced_date is None:
|
||||
return ""
|
||||
synced_date = c.synced_date.strftime('%Y-%m-%d')
|
||||
print(synced_date)
|
||||
return synced_date
|
||||
|
||||
def sync_frequent_users(self):
|
||||
print("SYNC FREQ USERS")
|
||||
return True
|
||||
@@ -0,0 +1,308 @@
|
||||
"""Server Side FCM sample.
|
||||
Firebase Cloud Messaging (FCM) can be used to send messages to clients on iOS,
|
||||
Android and Web.
|
||||
This sample uses FCM to send two types of messages to clients that are subscribed
|
||||
to the `news` topic. One type of message is a simple notification message (display message).
|
||||
The other is a notification message (display notification) with platform specific
|
||||
customizations. For example, a badge is added to messages that are sent to iOS devices.
|
||||
"""
|
||||
|
||||
import argparse
|
||||
import json
|
||||
import requests
|
||||
import datetime
|
||||
import os
|
||||
|
||||
from google.oauth2 import service_account
|
||||
from firebase_admin import messaging, initialize_app
|
||||
from aitrainer_backoffice.settings.prod import BASE_DIR
|
||||
|
||||
PROJECT_ID = 'aitrainer-af0ec'
|
||||
BASE_URL = 'https://fcm.googleapis.com'
|
||||
FCM_ENDPOINT = 'v1/projects/' + PROJECT_ID + '/messages:send'
|
||||
FCM_URL = BASE_URL + '/' + FCM_ENDPOINT
|
||||
SCOPES = ['https://www.googleapis.com/auth/firebase.messaging', 'https://www.googleapis.com/auth/cloud-platform', 'email']
|
||||
ASSET_ROOT = os.path.join(BASE_DIR, "asset")
|
||||
SERVER_KEY = 'AAAA18iNwog:APA91bFo_kDhK4Nd_zHAtyPj6D5CR_amV0aenNn9VPMMVz6j8mgyTCSr3J3IDD_U9duBe1AN35oAiWKp6LmDdJ5n2UQU6unfyUUmsFOSaDlEQZtYl6ZeIQ5XW52Fmkc29Xh62GZ4E-Ic'
|
||||
|
||||
# [START retrieve_access_token]
|
||||
def _get_access_token():
|
||||
"""Retrieve a valid access token that can be used to authorize requests.
|
||||
:return: Access token.
|
||||
"""
|
||||
|
||||
default_app = initialize_app()
|
||||
|
||||
access_token = default_app.credential.get_access_token()
|
||||
return access_token.access_token
|
||||
#return access_token_info.access_token
|
||||
# [END retrieve_access_token]
|
||||
|
||||
def _send_fcm_message(fcm_message):
|
||||
"""Send HTTP request to FCM with given message.
|
||||
Args:
|
||||
fcm_message: JSON object that will make up the body of the request.
|
||||
"""
|
||||
# [START use_access_token]
|
||||
headers = {
|
||||
'Authorization': 'Bearer ' + _get_access_token(),
|
||||
'Content-Type': 'application/json; UTF-8',
|
||||
}
|
||||
# [END use_access_token]
|
||||
resp = requests.post(FCM_URL, data=json.dumps(fcm_message), headers=headers)
|
||||
return resp
|
||||
|
||||
'''
|
||||
if resp.status_code == 200:
|
||||
print('Message sent to Firebase for delivery, response:')
|
||||
print(resp.text)
|
||||
else:
|
||||
print('Unable to send message to Firebase')
|
||||
print(resp.text)
|
||||
'''
|
||||
|
||||
def _build_common_message():
|
||||
"""Construct common notifiation message.
|
||||
Construct a JSON object that will be used to define the
|
||||
common parts of a notification message that will be sent
|
||||
to any app instance subscribed to the news topic.
|
||||
"""
|
||||
return {
|
||||
'message': {
|
||||
'topic': 'news',
|
||||
'notification': {
|
||||
'title': 'FCM Notification',
|
||||
'body': 'Notification from FCM'
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
def _build_override_message():
|
||||
"""Construct common notification message with overrides.
|
||||
Constructs a JSON object that will be used to customize
|
||||
the messages that are sent to iOS and Android devices.
|
||||
"""
|
||||
fcm_message = _build_common_message()
|
||||
|
||||
apns_override = {
|
||||
'payload': {
|
||||
'aps': {
|
||||
'badge': 1
|
||||
}
|
||||
},
|
||||
'headers': {
|
||||
'apns-priority': '10'
|
||||
}
|
||||
}
|
||||
|
||||
android_override = {
|
||||
'notification': {
|
||||
'click_action': 'android.intent.action.MAIN'
|
||||
}
|
||||
}
|
||||
|
||||
fcm_message['message']['android'] = android_override
|
||||
fcm_message['message']['apns'] = apns_override
|
||||
|
||||
return fcm_message
|
||||
|
||||
def send_to_token():
|
||||
# [START send_to_token]
|
||||
# This registration token comes from the client FCM SDKs.
|
||||
registration_token = 'fFjCZmrHREpRvxZMIKhNSI:APA91bH7cfctHFHbKxtQ5XGRlL26jgLLzo3a1x4hlPfZYi9WxrauMkdIBmqnIQnyD8Jc3xEs0gAsgNYNMLDEgdrHV3bbH4gvFHYUrYzOHZFr-2aVCsYF9otT8_fmAV380egGf5HiCIYd'
|
||||
|
||||
# See documentation on defining a message payload.
|
||||
message = messaging.Message(
|
||||
data={
|
||||
'score': '850',
|
||||
'time': '2:45',
|
||||
},
|
||||
token=registration_token,
|
||||
)
|
||||
|
||||
# Send a message to the device corresponding to the provided
|
||||
# registration token.
|
||||
response = messaging.send(message)
|
||||
# Response is a message ID string.
|
||||
print('Successfully sent message:', response)
|
||||
# [END send_to_token]
|
||||
|
||||
def send_fcm_to_token():
|
||||
# [START send_to_token]
|
||||
# This registration token comes from the client FCM SDKs.
|
||||
|
||||
'''
|
||||
headers = {
|
||||
'Content-Type': 'application/json',
|
||||
'Authorization': 'Bearer ' + _get_access_token(),
|
||||
}
|
||||
|
||||
# See documentation on defining a message payload.
|
||||
message = messaging.Message(
|
||||
data = _build_override_message(),
|
||||
token= registration_token,
|
||||
)
|
||||
'''
|
||||
|
||||
registration_token = ['fFjCZmrHREpRvxZMIKhNSI:APA91bH7cfctHFHbKxtQ5XGRlL26jgLLzo3a1x4hlPfZYi9WxrauMkdIBmqnIQnyD8Jc3xEs0gAsgNYNMLDEgdrHV3bbH4gvFHYUrYzOHZFr-2aVCsYF9otT8_fmAV380egGf5HiCIYd',
|
||||
'cOqNt8rzo074gbIkBSpCgW:APA91bEBuNi3iVzGKb4JhxqN2j80MoJbNptLHk2qsdeKBQz5grpHtrPPXvDqn5BJVVSaj1nwGPwgN7pi6FIApog_TTP3g1yobgmgpPN6udrYgzILlVPMvdGGFDSDh6gKlczhlTL9NEp0',
|
||||
'eUrsvYw9ekx0sr_R8pGTD8:APA91bHJKl1D9gLBz7xi0gILb7ng576DDnCvNba7MHqRaFn9MeeCSVLhEU1yC10b1v0KrZ4pVYgUqxkSv2t-Rh0mXtHR7ABGQENuGDfqjokWPNamXhp99Fuq66o3jnlXxSzRKe_aSCtk']
|
||||
|
||||
message = messaging.MulticastMessage(
|
||||
notification=messaging.Notification(
|
||||
title='$GOOG up 1.43% on the day',
|
||||
body='$GOOG gained 11.80 points to close at 835.67, up 1.43% on the day.',
|
||||
),
|
||||
android=messaging.AndroidConfig(
|
||||
ttl=datetime.timedelta(seconds=3600),
|
||||
priority='normal',
|
||||
notification=messaging.AndroidNotification(
|
||||
icon='stock_ticker_update',
|
||||
color='#f45342'
|
||||
),
|
||||
),
|
||||
apns=messaging.APNSConfig(
|
||||
payload=messaging.APNSPayload(
|
||||
aps=messaging.Aps(badge=42),
|
||||
),
|
||||
),
|
||||
tokens= registration_token,
|
||||
)
|
||||
|
||||
print(f'SEND FCM message {message}')
|
||||
response = messaging.send_multicast(message)
|
||||
|
||||
#data = json.dumps(message)
|
||||
|
||||
#print(f'SEND FCM message {FCM_URL} - Header {headers} - body: {data}')
|
||||
|
||||
#response = requests.post(FCM_URL, headers = headers, data=data)
|
||||
print(f'RESPONSE: {response}')
|
||||
|
||||
#response = _send_fcm_message(message)
|
||||
# Response is a message ID string.
|
||||
#print('Successfully sent message:', response)
|
||||
# [END send_to_token]
|
||||
|
||||
def send_to_topic():
|
||||
# [START send_to_topic]
|
||||
# The topic name can be optionally prefixed with "/topics/".
|
||||
topic = 'highScores'
|
||||
|
||||
# See documentation on defining a message payload.
|
||||
message = messaging.Message(
|
||||
data={
|
||||
'score': '850',
|
||||
'time': '2:45',
|
||||
},
|
||||
topic=topic,
|
||||
)
|
||||
|
||||
# Send a message to the devices subscribed to the provided topic.
|
||||
response = messaging.send(message)
|
||||
# Response is a message ID string.
|
||||
print('Successfully sent message:', response)
|
||||
# [END send_to_topic]
|
||||
|
||||
|
||||
|
||||
def send_to_condition():
|
||||
# [START send_to_condition]
|
||||
# Define a condition which will send to devices which are subscribed
|
||||
# to either the Google stock or the tech industry topics.
|
||||
condition = "'stock-GOOG' in topics || 'industry-tech' in topics"
|
||||
|
||||
# See documentation on defining a message payload.
|
||||
message = messaging.Message(
|
||||
notification=messaging.Notification(
|
||||
title='$GOOG up 1.43% on the day',
|
||||
body='$GOOG gained 11.80 points to close at 835.67, up 1.43% on the day.',
|
||||
),
|
||||
condition=condition,
|
||||
)
|
||||
|
||||
# Send a message to devices subscribed to the combination of topics
|
||||
# specified by the provided condition.
|
||||
response = messaging.send(message)
|
||||
# Response is a message ID string.
|
||||
print('Successfully sent message:', response)
|
||||
# [END send_to_condition]
|
||||
|
||||
|
||||
def send_dry_run():
|
||||
message = messaging.Message(
|
||||
data={
|
||||
'score': '850',
|
||||
'time': '2:45',
|
||||
},
|
||||
token='token',
|
||||
)
|
||||
|
||||
# [START send_dry_run]
|
||||
# Send a message in the dry run mode.
|
||||
response = messaging.send(message, dry_run=True)
|
||||
# Response is a message ID string.
|
||||
print('Dry run successful:', response)
|
||||
# [END send_dry_run]
|
||||
|
||||
|
||||
def android_message():
|
||||
# [START android_message]
|
||||
message = messaging.Message(
|
||||
android=messaging.AndroidConfig(
|
||||
ttl=datetime.timedelta(seconds=3600),
|
||||
priority='normal',
|
||||
notification=messaging.AndroidNotification(
|
||||
title='$GOOG up 1.43% on the day',
|
||||
body='$GOOG gained 11.80 points to close at 835.67, up 1.43% on the day.',
|
||||
icon='stock_ticker_update',
|
||||
color='#f45342'
|
||||
),
|
||||
),
|
||||
topic='industry-tech',
|
||||
)
|
||||
# [END android_message]
|
||||
return message
|
||||
|
||||
|
||||
def apns_message():
|
||||
# [START apns_message]
|
||||
message = messaging.Message(
|
||||
apns=messaging.APNSConfig(
|
||||
headers={'apns-priority': '10'},
|
||||
payload=messaging.APNSPayload(
|
||||
aps=messaging.Aps(
|
||||
alert=messaging.ApsAlert(
|
||||
title='$GOOG up 1.43% on the day',
|
||||
body='$GOOG gained 11.80 points to close at 835.67, up 1.43% on the day.',
|
||||
),
|
||||
badge=42,
|
||||
),
|
||||
),
|
||||
),
|
||||
topic='industry-tech',
|
||||
)
|
||||
# [END apns_message]
|
||||
return message
|
||||
|
||||
def main():
|
||||
parser = argparse.ArgumentParser()
|
||||
parser.add_argument('--message')
|
||||
args = parser.parse_args()
|
||||
if args.message and args.message == 'common-message':
|
||||
common_message = _build_common_message()
|
||||
print('FCM request body for message using common notification object:')
|
||||
print(json.dumps(common_message, indent=2))
|
||||
_send_fcm_message(common_message)
|
||||
elif args.message and args.message == 'override-message':
|
||||
override_message = _build_override_message()
|
||||
print('FCM request body for override message:')
|
||||
print(json.dumps(override_message, indent=2))
|
||||
_send_fcm_message(override_message)
|
||||
else:
|
||||
print('''Invalid command. Please use one of the following commands:
|
||||
python messaging.py --message=common-message
|
||||
python messaging.py --message=override-message''')
|
||||
|
||||
if __name__ == '__main__':
|
||||
main()
|
||||
@@ -0,0 +1,44 @@
|
||||
import datetime
|
||||
from .notification_hook import NotificationHook
|
||||
from ..models import notification as notif
|
||||
from ..models.notification import NotificationHistory
|
||||
from .fcm import FCM
|
||||
|
||||
class Notification:
|
||||
fcm = FCM()
|
||||
|
||||
def run(self):
|
||||
notification_queryset = notif.Notification.objects.using('live').raw('SELECT * from notification WHERE active = 1')
|
||||
|
||||
for notification in notification_queryset:
|
||||
if notification.schedule_date != None:
|
||||
pass
|
||||
elif notification.schedule_hook != None:
|
||||
hook = NotificationHook()
|
||||
try:
|
||||
hook_function = notification.schedule_hook
|
||||
hook_sql = notification.schedule_sql
|
||||
if hook_sql == None:
|
||||
customers = getattr(hook, hook_function)()
|
||||
else:
|
||||
customers = getattr(hook, hook_function)(hook_sql)
|
||||
|
||||
for customer in customers:
|
||||
if customer.firebase_reg_token != None:
|
||||
print(f'-- Notify Customer {customer.customer_id}')
|
||||
rc= self.fcm.send_to_token(notification.message_title, notification.message_body, notification.image_url, customer.firebase_reg_token)
|
||||
self.insert_history(notification=notification, customer=customer, rc=rc)
|
||||
|
||||
|
||||
except Exception as ex:
|
||||
print(f'Notification Hook {notification.schedule_hook} has no callback function: {ex}')
|
||||
|
||||
def insert_history(self, notification, customer, rc):
|
||||
history = NotificationHistory()
|
||||
history.pk = None
|
||||
history.notification = notification
|
||||
history.customer = customer
|
||||
history.response = rc
|
||||
history.notification_date = datetime.datetime.now()
|
||||
history.save()
|
||||
print(f'-- Notification History "{history}" has been saved')
|
||||
@@ -0,0 +1,16 @@
|
||||
from ..models.customer import Customer
|
||||
import datetime
|
||||
|
||||
class NotificationHook:
|
||||
def __init__(self) -> None:
|
||||
pass
|
||||
|
||||
def NotificationSelectAdmins(self):
|
||||
print(datetime.datetime.now(), " *** START automation NotificationSelectAdmins ")
|
||||
qs = Customer.objects.raw('SELECT customer_id, firebase_reg_token from customer WHERE admin = 1')
|
||||
return qs
|
||||
|
||||
def NotificationCommonSQL(self, sql):
|
||||
print(datetime.datetime.now(), " *** START automation NotificationCommonSQL ")
|
||||
qs = Customer.objects.raw(sql)
|
||||
return qs
|
||||
Reference in New Issue
Block a user