Coverage for functions \ flipdare \ message \ summary_message.py: 100%
69 statements
« prev ^ index » next coverage.py v7.13.0, created at 2026-05-08 12:22 +1000
« prev ^ index » next coverage.py v7.13.0, created at 2026-05-08 12:22 +1000
1#!/usr/bin/env python
2# Copyright (c) 2026 Flipdare Pty Ltd. All rights reserved.
3#
4# This file is part of Flipdare's proprietary software and contains
5# confidential and copyrighted material. Unauthorised copying,
6# modification, distribution, or use of this file is strictly
7# prohibited without prior written permission from Flipdare Pty Ltd.
8#
9# This software includes third-party components licensed under MIT,
10# BSD, and Apache 2.0 licences. See THIRD_PARTY_NOTICES for details.
11#
14from __future__ import annotations
16from enum import StrEnum
17from typing import NotRequired, TypedDict
19from flipdare.generated.shared.backend.summary_email_entry_type import SummaryEmailEntryType
21__all__ = ["SummaryMessage", "SummaryContext"]
24class SummarySingleContext(TypedDict):
25 # Standard keys
26 from_name: NotRequired[str]
27 description: NotRequired[str]
28 group_name: NotRequired[str]
29 accepted_name: NotRequired[str]
30 comment: NotRequired[str]
33class SummaryManyContext(TypedDict):
34 # Summary keys
35 names: NotRequired[str] # e.g. "Alex, Jordan, and Sam"
36 count: NotRequired[int]
39SummaryContext = SummarySingleContext | SummaryManyContext
41# fmt: off
42class SummaryMessage(StrEnum):
43 # fields
44 # - from_name: str
45 # - description: str (for dares)
46 # - group_name: str (for group dares)
47 # - accepted_name: str (for accepted dares/group dares)
49 # friend request
50 SINGLE_FRIEND_REQUEST = "{FROM_NAME} has sent you a friend request."
51 SINGLE_FRIEND_REQUEST_ACCEPTED = "{FROM_NAME} accepted your friend request."
52 # friend misc
53 SINGLE_NEW_FOLLOWER = "{FROM_NAME} started following you."
54 SINGLE_NEW_LIKE = "{FROM_NAME} liked your dare."
55 SINGLE_NEW_VIEW = "{FROM_NAME} viewed your dare."
56 SINGLE_CHAT_COMMENT = "{FROM_NAME} commented in your chat: {COMMENT}"
57 # dare
58 SINGLE_DARE_REQUEST = "{FROM_NAME} sent you a dare: {DESCRIPTION}"
59 SINGLE_DARE_ACCEPTED = "{ACCEPTED_NAME} accepted your dare: {DESCRIPTION}"
60 SINGLE_DARE_COMPLETED = "{ACCEPTED_NAME} completed your dare: {DESCRIPTION}"
61 # group dare
62 SINGLE_GROUP_DARE_SENT = "{FROM_NAME} sent a dare to {GROUP_NAME}: {DESCRIPTION}"
63 SINGLE_GROUP_DARE_ACCEPTED = "{ACCEPTED_NAME} accepted a dare in {GROUP_NAME}: {DESCRIPTION}"
64 SINGLE_GROUP_DARE_COMPLETED = "{ACCEPTED_NAME} completed a dare in {GROUP_NAME}: {DESCRIPTION}"
65 # group
66 SINGLE_GROUP_REQUEST = "{FROM_NAME} invited you to join {GROUP_NAME}."
67 SINGLE_GROUP_REQUEST_ACCEPTED = "{FROM_NAME} accepted your invitation to {GROUP_NAME}."
68 # pledge
69 SINGLE_PLEDGE_PROCESSED = "A pledge was processed for your dare."
70 SINGLE_PLEDGE_FAILED = "A pledge payment failed for your dare."
71 SINGLE_PLEDGE_PAYMENT_NOTICE = "The community has voted! Your payment to dare {DESCRIPTION} is due soon."
72 SINGLE_PLEDGE_PAYMENT_COMPLETE = "Your payment to dare {DESCRIPTION} has been completed successfully."
73 SINGLE_PLEDGE_PAYMENT_FAILED = "Your payment to dare {DESCRIPTION} has failed. Please update your payment information."
75 # friend request
76 MANY_FRIEND_REQUEST = "{NAMES} have sent you friend requests."
77 MANY_FRIEND_REQUEST_ACCEPTED = "{NAMES} accepted your friend requests."
78 # friend misc
79 MANY_NEW_FOLLOWER = "{NAMES} started following you."
80 MANY_NEW_LIKE = "{NAMES} liked your dares."
81 MANY_NEW_VIEW = "{NAMES} viewed your dares."
82 MANY_CHAT_COMMENT = "{COUNT} new comments in your chats."
83 # dare
84 MANY_DARE_REQUEST = "{COUNT} new dares were sent to you."
85 MANY_DARE_ACCEPTED = "{COUNT} of your dares were accepted."
86 MANY_DARE_COMPLETED = "{COUNT} of your dares were completed."
87 # group dare
88 MANY_GROUP_DARE_SENT = "{COUNT} new dares were sent to your groups."
89 MANY_GROUP_DARE_ACCEPTED = "{COUNT} dares were accepted in your groups."
90 MANY_GROUP_DARE_COMPLETED = "{COUNT} dares were completed in your groups."
91 # group
92 MANY_GROUP_REQUEST = "You have {COUNT} new group invitations."
93 MANY_GROUP_REQUEST_ACCEPTED = "{COUNT} people accepted your group invitations."
94 # pledge
95 MANY_PLEDGE_PROCESSED = "{COUNT} pledges were processed for your dares."
96 MANY_PLEDGE_FAILED = "{COUNT} pledge payments failed for your dares."
97 MANY_PLEDGE_PAYMENT_NOTICE = "The community has voted! You have {COUNT} upcoming pledge payments duesoon."
98 MANY_PLEDGE_PAYMENT_COMPLETE = "You have successfully completed {COUNT} pledge payments."
99 MANY_PLEDGE_PAYMENT_FAILED = "{COUNT} of your pledge payments have failed. Please update your payment information."
101 def formatted(self,ctx : SummaryContext) -> str:
102 upper_context = {k.upper(): v for k, v in ctx.items()}
103 return self.value.format(**upper_context)
105 @staticmethod
106 def from_entry(entry_type: SummaryEmailEntryType, ctx: SummaryContext) -> str:
107 if 'names' not in ctx and 'count' not in ctx:
108 mapping = SummaryMessage.single_mappings()
109 else:
110 mapping = SummaryMessage.many_mapping()
112 return mapping[entry_type].formatted(ctx)
114 @staticmethod
115 def single_mappings() -> dict[SummaryEmailEntryType, SummaryMessage]:
116 return {
117 SummaryEmailEntryType.FRIEND_REQUEST: SummaryMessage.SINGLE_FRIEND_REQUEST,
118 SummaryEmailEntryType.FRIEND_REQUEST_ACCEPTED: SummaryMessage.SINGLE_FRIEND_REQUEST_ACCEPTED,
119 SummaryEmailEntryType.NEW_FOLLOWER: SummaryMessage.SINGLE_NEW_FOLLOWER,
120 SummaryEmailEntryType.NEW_LIKE: SummaryMessage.SINGLE_NEW_LIKE,
121 SummaryEmailEntryType.NEW_VIEW: SummaryMessage.SINGLE_NEW_VIEW,
122 SummaryEmailEntryType.DARE_REQUEST: SummaryMessage.SINGLE_DARE_REQUEST,
123 SummaryEmailEntryType.DARE_ACCEPTED: SummaryMessage.SINGLE_DARE_ACCEPTED,
124 SummaryEmailEntryType.DARE_COMPLETED: SummaryMessage.SINGLE_DARE_COMPLETED,
125 SummaryEmailEntryType.GROUP_REQUEST: SummaryMessage.SINGLE_GROUP_REQUEST,
126 SummaryEmailEntryType.GROUP_REQUEST_ACCEPTED: SummaryMessage.SINGLE_GROUP_REQUEST_ACCEPTED,
127 SummaryEmailEntryType.GROUP_DARE_SENT: SummaryMessage.SINGLE_GROUP_DARE_SENT,
128 SummaryEmailEntryType.GROUP_DARE_ACCEPTED: SummaryMessage.SINGLE_GROUP_DARE_ACCEPTED,
129 SummaryEmailEntryType.GROUP_DARE_COMPLETED: SummaryMessage.SINGLE_GROUP_DARE_COMPLETED,
130 SummaryEmailEntryType.PLEDGE_PROCESSED: SummaryMessage.SINGLE_PLEDGE_PROCESSED,
131 SummaryEmailEntryType.PLEDGE_FAILED: SummaryMessage.SINGLE_PLEDGE_FAILED,
132 SummaryEmailEntryType.PLEDGE_PAYMENT_NOTICE: SummaryMessage.SINGLE_PLEDGE_PAYMENT_NOTICE,
133 SummaryEmailEntryType.PLEDGE_PAYMENT_COMPLETE: SummaryMessage.SINGLE_PLEDGE_PAYMENT_COMPLETE,
134 SummaryEmailEntryType.PLEDGE_PAYMENT_FAILED: SummaryMessage.SINGLE_PLEDGE_PAYMENT_FAILED,
135 SummaryEmailEntryType.CHAT_COMMENT: SummaryMessage.SINGLE_CHAT_COMMENT,
136 }
138 @staticmethod
139 def many_mapping() -> dict[SummaryEmailEntryType, SummaryMessage]:
140 return {
141 SummaryEmailEntryType.FRIEND_REQUEST: SummaryMessage.MANY_FRIEND_REQUEST,
142 SummaryEmailEntryType.FRIEND_REQUEST_ACCEPTED: SummaryMessage.MANY_FRIEND_REQUEST_ACCEPTED,
143 SummaryEmailEntryType.NEW_FOLLOWER: SummaryMessage.MANY_NEW_FOLLOWER,
144 SummaryEmailEntryType.NEW_LIKE: SummaryMessage.MANY_NEW_LIKE,
145 SummaryEmailEntryType.NEW_VIEW: SummaryMessage.MANY_NEW_VIEW,
146 SummaryEmailEntryType.DARE_REQUEST: SummaryMessage.MANY_DARE_REQUEST,
147 SummaryEmailEntryType.DARE_ACCEPTED: SummaryMessage.MANY_DARE_ACCEPTED,
148 SummaryEmailEntryType.DARE_COMPLETED: SummaryMessage.MANY_DARE_COMPLETED,
149 SummaryEmailEntryType.GROUP_REQUEST: SummaryMessage.MANY_GROUP_REQUEST,
150 SummaryEmailEntryType.GROUP_REQUEST_ACCEPTED: SummaryMessage.MANY_GROUP_REQUEST_ACCEPTED,
151 SummaryEmailEntryType.GROUP_DARE_SENT: SummaryMessage.MANY_GROUP_DARE_SENT,
152 SummaryEmailEntryType.GROUP_DARE_ACCEPTED: SummaryMessage.MANY_GROUP_DARE_ACCEPTED,
153 SummaryEmailEntryType.GROUP_DARE_COMPLETED: SummaryMessage.MANY_GROUP_DARE_COMPLETED,
154 SummaryEmailEntryType.PLEDGE_PROCESSED: SummaryMessage.MANY_PLEDGE_PROCESSED,
155 SummaryEmailEntryType.PLEDGE_FAILED: SummaryMessage.MANY_PLEDGE_FAILED,
156 SummaryEmailEntryType.PLEDGE_PAYMENT_NOTICE: SummaryMessage.MANY_PLEDGE_PAYMENT_NOTICE,
157 SummaryEmailEntryType.PLEDGE_PAYMENT_COMPLETE: SummaryMessage.MANY_PLEDGE_PAYMENT_COMPLETE,
158 SummaryEmailEntryType.PLEDGE_PAYMENT_FAILED: SummaryMessage.MANY_PLEDGE_PAYMENT_FAILED,
159 SummaryEmailEntryType.CHAT_COMMENT: SummaryMessage.MANY_CHAT_COMMENT,
160 }
163# fmt: on