from app.api.schemas.user_update import UserUpdateSchema from app.utils.logger import logger from app.api.services.base_service import BaseService from marshmallow import ValidationError from app.extensions import db from app.models import Members, MembersActions, MembersProfile, Payments, MembersProducts, ProvisionActions, \ ProductsContacts from app.api.helpers.response_helper import ResponseHelper from app.api.schemas.user import UserSchema from app.api.schemas.start_profile import StartProfileSchema from app.api.schemas.profile_links import ProfileLinksSchema # from sendgrid import SendGridAPIClient # from sendgrid.helpers.mail import Mail import datetime import jwt import random from app.config import Config from app.notifications.mail_factory import send_email_factory class AccountService(BaseService): JWT_SECRET_KEY = Config.JWT_SECRET_KEY SEND_EMAIL_FROM = Config.SEND_EMAIL_FROM SEND_EMAIL_PASS = Config.SEND_EMAIL_PASS THIS_SITE_URL = Config.THIS_SITE_URL @staticmethod def process_bar_request(data): bar_data = { "last_update": datetime.datetime.utcnow(), "top_bar": [ {"id": "1", "description": "Contacts", "last_update": "10-10-2010 11:00 AM", "value": random.randint(0, 10), "data_span": 'Last 2 months', "link": "#", "extra_style": ''}, {"id": "2", "description": "Site Traffic", "last_update": "10-10-2010 11:30 AM", "value": random.randint(0, 10), "data_span": 'Past 12 hours', "link": "#", "extra_style": ''}, {"id": "3", "description": "Appointments", "last_update": "10-12-2010 11:30 AM", "value": random.randint(0, 10), "data_span": 'Last 14 days', "link": "#", "extra_style": ''}, {"id": "4", "description": "Upgrade Account", "last_update": "10-12-2010 11:30 AM", "value": "Free Trial", "data_span": 'End: 10/10/2025', "link": "/subscription", "extra_style": " billing "} ] } return ResponseHelper.success(data=bar_data) @staticmethod def process_bar_data(data): try: with db.session.begin(): validated_data = AccountService.validate_data(data, UserSchema()) user_token = validated_data.get('token') uid = str(validated_data.get('uid')) member_data = Members.get_member_by_uid(uid) logger.error(f"Member_Data ID ::: {member_data.id}") member_id = member_data.id option_name = member_data.option_name # "Free Trial" if option_name is not None and option_name != "": next_bill = f"Bill: {member_data.next_billing}" view_sub = "Account" bill_style = " next_billing " else: option_name = "Free Trial" next_bill = f"Ends: {member_data.trial_end}" view_sub = "Upgrade Account" bill_style = " billing " # int(member_data.id) contacts_count = ProductsContacts.get_member_contact_count(member_id,90) # contacts_count = 0 # random.randint(0, 10) appointments_count = 0 site_traffic_count = 0 bar_data = { "last_update": datetime.datetime.utcnow(), "top_bar": [ {"id": "1", "description": "Contacts", "last_update": "10-10-2010 11:00 AM", "value": contacts_count, "data_span": 'Last 2 months', "link": "/contacts", "extra_style": ''}, {"id": "2", "description": "Appointments", "last_update": "10-12-2010 11:30 AM", "value": appointments_count, "data_span": 'Last 14 days', "link": "/appointments", "extra_style": ''}, {"id": "3", "description": "Site Traffic", "last_update": "10-10-2010 11:30 AM", "value": site_traffic_count, "data_span": 'Past 12 hours', "link": "/traffic", "extra_style": ''}, {"id": "4", "description": view_sub, "last_update": "10-12-2010 11:30 AM", "value": option_name, "data_span": next_bill, "link": "/subscription", "extra_style": bill_style} ] } return ResponseHelper.success(data=bar_data) except ValidationError as err: logger.error(f"Validation Error: {getattr(err, 'messages', str(err))}") db.session.rollback() return ResponseHelper.unprocessable_entity(result_description="Validation exception") except ValueError as err: logger.error(f"{getattr(err, 'messages', str(err))}") db.session.rollback() return ResponseHelper.error(result_description=str(err)) except Exception as e: logger.error(f"An error occurred: {str(e)}", exc_info=True) db.session.rollback() return ResponseHelper.internal_server_error() def process_action_request(data): try: with db.session.begin(): validated_data = AccountService.validate_data(data, UserSchema()) user_token = validated_data.get('token') uid = str(validated_data.get('uid')) member_data = Members.get_member_by_uid(uid) member_actions = MembersActions.get_recent_member_actions(member_data.id) member_actions_data = [] if member_actions: for t in member_actions: member_actions_data.append({ 'id': t.id, 'uid': t.uid, 'member_id': t.member_id, 'member_uid': t.member_uid, 'action_label': t.action_label, 'action_name': t.action_name, 'status_description': t.status_description, 'status': t.status, 'added': t.added, 'updated': t.updated }) action_data = { "recent_actions": member_actions_data, "last_update": datetime.datetime.utcnow(), "initial": random.randint(0, 10), "processing": random.randint(0, 10), "verifying": random.randint(0, 10), "completed": random.randint(0, 10) } # logger.info(f"Member Actions : {action_data}") return ResponseHelper.success(data=action_data) except ValidationError as err: logger.error(f"Validation Error: {getattr(err, 'messages', str(err))}") db.session.rollback() return ResponseHelper.unprocessable_entity(result_description="Validation exception") except ValueError as err: logger.error(f"{getattr(err, 'messages', str(err))}") db.session.rollback() return ResponseHelper.error(result_description=str(err)) except Exception as e: logger.error(f"An error occurred: {str(e)}", exc_info=True) db.session.rollback() return ResponseHelper.internal_server_error() @staticmethod def process_request(data): try: with db.session.begin(): validated_data = AccountService.validate_data(data, UserSchema()) user_token = validated_data.get('token') uid = str(validated_data.get('uid')) member = Members.get_member_by_uid(uid) # Simulate processing response_data = { "member_id": member.id, "uid": str(uid), "username": member.username, "account_name": member.account_name, "profile_completed": member.profile_completed, "firstname": member.firstname, "lastname": member.lastname, "email": member.email, "room": member.uid, "picture": 'https://media.mermsemr.com/media/show/merms-profile', "token": user_token } return ResponseHelper.success(data=response_data) except ValidationError as err: logger.error(f"Validation Error: {getattr(err, 'messages', str(err))}") db.session.rollback() return ResponseHelper.unprocessable_entity(result_description="Validation exception") except ValueError as err: logger.error(f"{getattr(err, 'messages', str(err))}") db.session.rollback() return ResponseHelper.error(result_description=str(err)) except Exception as e: logger.error(f"An error occurred: {str(e)}", exc_info=True) db.session.rollback() return ResponseHelper.internal_server_error() @staticmethod def process_startprofile(data): try: with db.session.begin(): validated_data = AccountService.validate_data(data, StartProfileSchema()) user_token = validated_data.get('token') uid = str(validated_data.get('uid')) practice = str(validated_data.get('practice')) specialization = str(validated_data.get('specialization')) introduction = str(validated_data.get('introduction')) url_name = str(validated_data.get('url_name')) # verify is anybody is using this url name urlNammeData = MembersProfile.get_any_member_profile_by_url_name(url_name) if urlNammeData: return { "error": 'Duplicate url name', "error_message": 'Try another url name', "url_name": url_name, }, 400 profile_uid = '' profile_completed = None member = Members.get_member_by_uid(uid) if member: # Simulate processing member_data = { "member_id": member.id, "uid": str(uid), "username": member.username, "account_name": member.account_name, "firstname": member.firstname, "lastname": member.lastname, "email": member.email, "room": member.uid, "token": user_token } current_profile = MembersProfile.get_member_profile_by_member_id(member.id) if current_profile is not None: profile_uid = current_profile.uid profile_completed = member.profile_completed else: profile_result = MembersProfile.create_member_profile(member.id, practice, specialization, introduction, url_name) if profile_result: profile_uid = profile_result.uid current_profile = MembersProfile.get_member_profile_by_member_id(member.id) if profile_uid is not None and profile_uid != '' and current_profile is not None: profile_completed = Members.set_member_profile_completed(member_data['uid']) result_data = { "profile_completed": profile_completed, "profile_uid": profile_uid, "last_update": datetime.datetime.utcnow() } return ResponseHelper.success(data=result_data) except ValidationError as err: logger.error(f"Validation Error: {getattr(err, 'messages', str(err))}") db.session.rollback() return ResponseHelper.unprocessable_entity(result_description="Validation exception") except ValueError as err: logger.error(f"{getattr(err, 'messages', str(err))}") db.session.rollback() return ResponseHelper.error(result_description=str(err)) except Exception as e: logger.error(f"An error occurred: {str(e)}", exc_info=True) db.session.rollback() return ResponseHelper.internal_server_error() @staticmethod def process_calendar(data): try: with db.session.begin(): validated_data = AccountService.validate_data(data, UserSchema()) user_token = validated_data.get('token') uid = str(validated_data.get('uid')) member = Members.get_member_by_uid(uid) if not member: return { "error": 'Invalid Request', "uid": uid, }, 400 member_id = member.id dList = [] # LET get the ptovison actions prov_actions = ProvisionActions.get_provision_action_calendar_member_id(member_id=member_id, limit=100) if prov_actions: for prov_action in prov_actions: new_l = {"uid": prov_action.uid, "title": prov_action.action, "start": prov_action.added, "category": 3} dList.append(new_l) member_actions = MembersActions.get_recent_member_calendar_actions_member_id(member_id=member_id, limit=100) if member_actions: for member_action in member_actions: new_l = {"uid": member_action.uid, "title": member_action.action_label, "start": member_action.added, "category": 1} dList.append(new_l) # sample_range = random.randint(20, 60) # for x in range(sample_range): # timeMin = random.randint(1440, 2880) # calDate = datetime.datetime.utcnow() + datetime.timedelta(minutes=timeMin * random.randint(0, 20)) # new_l = {"uid": "425611f2-c692-4404-b93d-76ca7a5ce7" + str(x), # "title": "Calendar Random Item on " + str(x), "start": calDate, # "category": random.randint(1, 4)} # dList.append(new_l) calendar_data = { "last_update": datetime.datetime.utcnow(), "category": [ { "cid": "1", "description": "Health Check" }, { "cid": "2", "description": "Product Updates" }, { "cid": "3", "description": "Provisioning" }, { "cid": "4", "description": "Contacts" } ], "list": dList } return ResponseHelper.success(data=calendar_data) except ValidationError as err: logger.error(f"Validation Error: {getattr(err, 'messages', str(err))}") db.session.rollback() return ResponseHelper.unprocessable_entity(result_description="Validation exception") except ValueError as err: logger.error(f"{getattr(err, 'messages', str(err))}") db.session.rollback() return ResponseHelper.error(result_description=str(err)) except Exception as e: logger.error(f"An error occurred: {str(e)}", exc_info=True) db.session.rollback() return ResponseHelper.internal_server_error() @staticmethod def process_payments_data(data): try: with db.session.begin(): validated_data = AccountService.validate_data(data, UserSchema()) user_token = validated_data.get('token') uid = str(validated_data.get('uid')) member_data = Members.get_member_by_uid(uid) member_payments = Payments.get_member_payments_by_member_id(member_data.id) member_payments_data = [] for t in member_payments: member_payments_data.append({ 'id': t.id, 'uid': t.uid, 'option_name': t.option_name, 'option_type': t.option_type, 'payment_uid': t.payment_uid, 'amount': round(t.amount * 0.01, 2), 'status': t.status, 'added': t.added }) action_data = { "member_payments": member_payments_data, "last_update": datetime.datetime.utcnow(), } # logger.info(f"Member Actions : {action_data}") return ResponseHelper.success(data=action_data) except ValidationError as err: logger.error(f"Validation Error: {getattr(err, 'messages', str(err))}") db.session.rollback() return ResponseHelper.unprocessable_entity(result_description="Validation exception") except ValueError as err: logger.error(f"{getattr(err, 'messages', str(err))}") db.session.rollback() return ResponseHelper.error(result_description=str(err)) except Exception as e: logger.error(f"An error occurred: {str(e)}", exc_info=True) db.session.rollback() return ResponseHelper.internal_server_error() @staticmethod def process_profile_data(data): try: with db.session.begin(): validated_data = AccountService.validate_data(data, UserSchema()) user_token = validated_data.get('token') uid = str(validated_data.get('uid')) member_data = Members.get_member_by_uid(uid) file_url = BaseService.get_profile_picture_url(member_data.profile_picture) personal_data = { "firstname": member_data.firstname, "lastname": member_data.lastname, "account_name": member_data.account_name, "email": member_data.email, "phone": member_data.phone, "full_address": member_data.full_address, "picture": 'https://media.mermsemr.com/media/show/merms-profile' if file_url == '' else file_url, "country": member_data.country, } external_links = { "facebook_url": "facebook.com", "twitter_url": "twitter.com", "blogger_url": "blogger.com", "google_url": "google.com", "linked_url": "linkedin.com", "website_url": "www.mysite.com", } profile_data = { "personal_data": personal_data, "external_links": external_links, } return ResponseHelper.success(data=profile_data) except ValidationError as err: logger.error(f"Validation Error: {getattr(err, 'messages', str(err))}") db.session.rollback() return ResponseHelper.unprocessable_entity(result_description="Validation exception") except ValueError as err: logger.error(f"{getattr(err, 'messages', str(err))}") db.session.rollback() return ResponseHelper.error(result_description=str(err)) except Exception as e: logger.error(f"An error occurred: {str(e)}", exc_info=True) db.session.rollback() return ResponseHelper.internal_server_error() @staticmethod def update_profile_data(data): try: with db.session.begin(): validated_data = AccountService.validate_data(data, UserUpdateSchema()) user_token = validated_data.get('token') uid = str(validated_data.get('uid')) member_data = Members.get_member_by_uid(uid) if member_data: firstname = str(validated_data.get('firstname')) lastname = str(validated_data.get('lastname')) account_name = str(validated_data.get('account_name')) phone = str(validated_data.get('phone')) full_address = str(validated_data.get('full_address')) # email = str(validated_data.get('email')) profile_data = { "firstname": firstname, "lastname": lastname, "account_name": account_name, "phone": phone, "full_address": full_address, # "email": email, } Members.set_member_update_profile(uid, profile_data) # Read the saved data member_data = Members.get_member_by_uid(uid) personal_data = { "firstname": member_data.firstname, "lastname": member_data.lastname, "account_name": member_data.account_name, "email": member_data.email, "phone": member_data.phone, "full_address": member_data.full_address, "country": member_data.country, } external_links = { "facebook_url": "facebook.com", "twitter_url": "twitter.com", "blogger_url": "blogger.com", "google_url": "google.com", "linked_url": "linkedin.com", "website_url": "www.mysite.com", } profile_data = { "personal_data": personal_data, "external_links": external_links, } return ResponseHelper.success(data=profile_data) except ValidationError as err: logger.error(f"Validation Error: {getattr(err, 'messages', str(err))}") db.session.rollback() return ResponseHelper.unprocessable_entity(result_description="Validation exception") except ValueError as err: logger.error(f"{getattr(err, 'messages', str(err))}") db.session.rollback() return ResponseHelper.error(result_description=str(err)) except Exception as e: logger.error(f"An error occurred: {str(e)}", exc_info=True) db.session.rollback() return ResponseHelper.internal_server_error() @staticmethod def update_profile_link_data(data): try: with db.session.begin(): url_list = data["url_list"] data.pop("url_list") validated_data = AccountService.validate_data(data, ProfileLinksSchema()) user_token = validated_data.get('token') uid = str(validated_data.get('uid')) member_data = Members.get_member_by_uid(uid) if member_data: for key in url_list.keys(): url_list_value = url_list[key] logger.info(f"URL LIST : {key} : {url_list_value}") external_links = { "facebook_url": "https://facebook.com", "twitter_url": "twitter.com", "blogger_url": "blogger.com", "google_url": "google.com", "linked_url": "linkedin.com", "website_url": "www.mysite.com", } profile_data = { "external_links": external_links, } return ResponseHelper.success(data=profile_data) except ValidationError as err: logger.error(f"Validation Error: {getattr(err, 'messages', str(err))}") db.session.rollback() return ResponseHelper.unprocessable_entity(result_description="Validation exception") except ValueError as err: logger.error(f"{getattr(err, 'messages', str(err))}") db.session.rollback() return ResponseHelper.error(result_description=str(err)) except Exception as e: logger.error(f"An error occurred: {str(e)}", exc_info=True) db.session.rollback() return ResponseHelper.internal_server_error() @staticmethod def process_test_email(data): logger.info(f"Email Test Enter 001", exc_info=True) send_email_factory( to_email="ameye@chiefsoft.com", subject="Test from Merms", html_content="Hello from AWS SES" ) logger.info(f"Email Test", exc_info=True)