(20241228) Started making provisions for disabling payment gateway accounts when the gateway says that the credentials are invalid. Am stuck at one place, though.
This commit is contained in:
@@ -149,6 +149,7 @@ async def safaricom_m_pesa_express_callback(
|
|||||||
# ┛┗┗┻┗┻ ┗┛┗┛┗ ┛┗┗
|
# ┛┗┗┻┗┻ ┗┛┗┛┗ ┛┗┗
|
||||||
|
|
||||||
client_response = await current_app.safaricom_mpesa_express_controller.handle_payment_callback(
|
client_response = await current_app.safaricom_mpesa_express_controller.handle_payment_callback(
|
||||||
|
sql_conn = current_app.sql_writer,
|
||||||
mongo_data_conn = current_app.data_mongo,
|
mongo_data_conn = current_app.data_mongo,
|
||||||
inbound_data = inbound_data,
|
inbound_data = inbound_data,
|
||||||
inbound_headers = inbound_headers
|
inbound_headers = inbound_headers
|
||||||
|
|||||||
@@ -180,6 +180,7 @@ async def request_payment(
|
|||||||
# For Safaricom's M-Pesa Express client:
|
# For Safaricom's M-Pesa Express client:
|
||||||
if auth_token.client == "safaricomMPesaExpress":
|
if auth_token.client == "safaricomMPesaExpress":
|
||||||
response = await current_app.safaricom_mpesa_express_controller.request_payment(
|
response = await current_app.safaricom_mpesa_express_controller.request_payment(
|
||||||
|
sql_conn = current_app.sql_writer,
|
||||||
mongo_data_conn = current_app.data_mongo,
|
mongo_data_conn = current_app.data_mongo,
|
||||||
auth_token = auth_token,
|
auth_token = auth_token,
|
||||||
user_info = CoreUserInfoModel(**kwargs["session_info"]),
|
user_info = CoreUserInfoModel(**kwargs["session_info"]),
|
||||||
|
|||||||
@@ -139,6 +139,7 @@ class AllPaymentsController(PaymentsController):
|
|||||||
|
|
||||||
async def request_payment(
|
async def request_payment(
|
||||||
self,
|
self,
|
||||||
|
sql_conn: AsyncMySQL,
|
||||||
mongo_data_conn: AsyncMongo,
|
mongo_data_conn: AsyncMongo,
|
||||||
auth_token: CoreAuthTokenModel,
|
auth_token: CoreAuthTokenModel,
|
||||||
user_info: CoreUserInfoModel,
|
user_info: CoreUserInfoModel,
|
||||||
@@ -147,6 +148,8 @@ class AllPaymentsController(PaymentsController):
|
|||||||
|
|
||||||
"""
|
"""
|
||||||
To request payment from someone through a payment gateway.
|
To request payment from someone through a payment gateway.
|
||||||
|
:param sql_conn: Only needed when a payment gateway says that the credentials are invalid and the account needs
|
||||||
|
to be disabled.
|
||||||
:param mongo_data_conn: The database connection to use to perform this activity.
|
:param mongo_data_conn: The database connection to use to perform this activity.
|
||||||
:param auth_token: The token that has to be used to fetch the data.
|
:param auth_token: The token that has to be used to fetch the data.
|
||||||
:param user_info: The info. of your user, so that you can identify who requested the payment.
|
:param user_info: The info. of your user, so that you can identify who requested the payment.
|
||||||
@@ -158,17 +161,21 @@ class AllPaymentsController(PaymentsController):
|
|||||||
|
|
||||||
async def handle_payment_callback(
|
async def handle_payment_callback(
|
||||||
self,
|
self,
|
||||||
|
sql_conn: AsyncMySQL,
|
||||||
mongo_data_conn: AsyncMongo,
|
mongo_data_conn: AsyncMongo,
|
||||||
inbound_data: dict
|
inbound_data: dict,
|
||||||
):
|
inbound_headers: dict
|
||||||
|
) -> PaymentRequestOneResult:
|
||||||
|
|
||||||
"""
|
"""
|
||||||
Whenever the payment gateway sends an update about a requested payment, we use this method to update our records
|
Whenever the payment gateway sends an update about a requested payment, we use this method to update our records
|
||||||
as per the specification of the third-party payment gateway.
|
as per the specification of the third-party payment gateway.
|
||||||
|
:param sql_conn: Only needed when a payment gateway says that the credentials are invalid and the account needs
|
||||||
|
to be disabled.
|
||||||
:param mongo_data_conn: The database connection to use to perform this activity.
|
:param mongo_data_conn: The database connection to use to perform this activity.
|
||||||
:param inbound_data: The data sent by the payment gateway in their update.
|
:param inbound_data: The data sent by the payment gateway in their update.
|
||||||
|
:param inbound_headers: The headers sent by the payment gateway in their update.
|
||||||
:return: ??
|
:return: A structured response about the process of updating the payment event.
|
||||||
"""
|
"""
|
||||||
|
|
||||||
raise NotImplementedError
|
raise NotImplementedError
|
||||||
|
|||||||
@@ -47,7 +47,11 @@ from controllers_v2.core.auth_token import CoreAuthTokenController
|
|||||||
from models.core.user import CoreUserInfoModel
|
from models.core.user import CoreUserInfoModel
|
||||||
from models.core.auth_token import CoreAuthTokenModel
|
from models.core.auth_token import CoreAuthTokenModel
|
||||||
from models.core.payment import CorePaymentModel, PaymentEvent, CustomerDetails
|
from models.core.payment import CorePaymentModel, PaymentEvent, CustomerDetails
|
||||||
from models.api.finstitutions.payments.request import PGPaymentRequestData, PaymentRequestOneResult
|
from models.api.finstitutions.payments.request import (
|
||||||
|
PGPaymentRequestData,
|
||||||
|
PaymentRequestOneResult,
|
||||||
|
PaymentCallbackResult
|
||||||
|
)
|
||||||
|
|
||||||
# To work with MongoDB:
|
# To work with MongoDB:
|
||||||
from bson import ObjectId
|
from bson import ObjectId
|
||||||
@@ -270,6 +274,34 @@ class PaymentsController(CoreAuthTokenController, ABC):
|
|||||||
# we return it as our data model:
|
# we return it as our data model:
|
||||||
return CorePaymentModel(**record)
|
return CorePaymentModel(**record)
|
||||||
|
|
||||||
|
async def get_payment_by_client_reference_id(
|
||||||
|
self,
|
||||||
|
mongo_data_conn: AsyncMongo,
|
||||||
|
client_reference_id: str
|
||||||
|
) -> CorePaymentModel | None:
|
||||||
|
|
||||||
|
"""
|
||||||
|
Gets one payment detail if you know its payment id.
|
||||||
|
:param mongo_data_conn: The instance of the database connector to use for the operation.
|
||||||
|
:param client_reference_id: The way the client identifies this payment. You need to pass this only on the first
|
||||||
|
event. Typically, when you initiate the payment request.
|
||||||
|
:return: The contents of that one payment detail in a structured format.
|
||||||
|
"""
|
||||||
|
|
||||||
|
# We fetch the whole payload of that one message:
|
||||||
|
record = await mongo_data_conn.find_one(
|
||||||
|
collection = self.PAYMENTS_COLLECTION,
|
||||||
|
filter = {"clientPaymentReferenceId": client_reference_id},
|
||||||
|
raise_exception = True
|
||||||
|
)
|
||||||
|
|
||||||
|
# If no such message was found:
|
||||||
|
if record is None: return None
|
||||||
|
|
||||||
|
# If a record was found,
|
||||||
|
# we return it as our data model:
|
||||||
|
return CorePaymentModel(**record)
|
||||||
|
|
||||||
# ┳┳ ┓ ┏┓
|
# ┳┳ ┓ ┏┓
|
||||||
# ┃┃┏┓┏┫┏┓╋┏┓ ┃┃┏┓┓┏┏┳┓┏┓┏┓╋┏
|
# ┃┃┏┓┏┫┏┓╋┏┓ ┃┃┏┓┓┏┏┳┓┏┓┏┓╋┏
|
||||||
# ┗┛┣┛┗┻┗┻┗┗ ┣┛┗┻┗┫┛┗┗┗ ┛┗┗┛
|
# ┗┛┣┛┗┻┗┻┗┗ ┣┛┗┻┗┫┛┗┗┗ ┛┗┗┛
|
||||||
@@ -466,6 +498,7 @@ class PaymentsController(CoreAuthTokenController, ABC):
|
|||||||
@abstractmethod
|
@abstractmethod
|
||||||
async def request_payment(
|
async def request_payment(
|
||||||
self,
|
self,
|
||||||
|
sql_conn: AsyncMySQL,
|
||||||
mongo_data_conn: AsyncMongo,
|
mongo_data_conn: AsyncMongo,
|
||||||
auth_token: CoreAuthTokenModel,
|
auth_token: CoreAuthTokenModel,
|
||||||
user_info: CoreUserInfoModel,
|
user_info: CoreUserInfoModel,
|
||||||
@@ -474,6 +507,8 @@ class PaymentsController(CoreAuthTokenController, ABC):
|
|||||||
|
|
||||||
"""
|
"""
|
||||||
To request payment from someone through a payment gateway.
|
To request payment from someone through a payment gateway.
|
||||||
|
:param sql_conn: Only needed when a payment gateway says that the credentials are invalid and the account needs
|
||||||
|
to be disabled.
|
||||||
:param mongo_data_conn: The database connection to use to perform this activity.
|
:param mongo_data_conn: The database connection to use to perform this activity.
|
||||||
:param auth_token: The token that has to be used to fetch the data.
|
:param auth_token: The token that has to be used to fetch the data.
|
||||||
:param user_info: The info. of your user, so that you can identify who requested the payment.
|
:param user_info: The info. of your user, so that you can identify who requested the payment.
|
||||||
@@ -486,18 +521,21 @@ class PaymentsController(CoreAuthTokenController, ABC):
|
|||||||
@abstractmethod
|
@abstractmethod
|
||||||
async def handle_payment_callback(
|
async def handle_payment_callback(
|
||||||
self,
|
self,
|
||||||
|
sql_conn: AsyncMySQL,
|
||||||
mongo_data_conn: AsyncMongo,
|
mongo_data_conn: AsyncMongo,
|
||||||
inbound_data: dict,
|
inbound_data: dict,
|
||||||
inbound_headers: dict
|
inbound_headers: dict
|
||||||
) -> None:
|
) -> PaymentCallbackResult:
|
||||||
|
|
||||||
"""
|
"""
|
||||||
Whenever the payment gateway sends an update about a requested payment, we use this method to update our records
|
Whenever the payment gateway sends an update about a requested payment, we use this method to update our records
|
||||||
as per the specification of the third-party payment gateway.
|
as per the specification of the third-party payment gateway.
|
||||||
|
:param sql_conn: Only needed when a payment gateway says that the credentials are invalid and the account needs
|
||||||
|
to be disabled.
|
||||||
:param mongo_data_conn: The database connection to use to perform this activity.
|
:param mongo_data_conn: The database connection to use to perform this activity.
|
||||||
:param inbound_data: The data sent by the payment gateway in their update.
|
:param inbound_data: The data sent by the payment gateway in their update.
|
||||||
:param inbound_headers: The headers sent by the payment gateway in their update.
|
:param inbound_headers: The headers sent by the payment gateway in their update.
|
||||||
:return: ??
|
:return: A structured response about the process of updating the payment event.
|
||||||
"""
|
"""
|
||||||
|
|
||||||
pass
|
pass
|
||||||
|
|||||||
@@ -168,6 +168,7 @@ class SafaricomMPesaExpressPaymentsController(PaymentsController):
|
|||||||
|
|
||||||
async def request_payment(
|
async def request_payment(
|
||||||
self,
|
self,
|
||||||
|
sql_conn: AsyncMySQL,
|
||||||
mongo_data_conn: AsyncMongo,
|
mongo_data_conn: AsyncMongo,
|
||||||
auth_token: CoreAuthTokenModel,
|
auth_token: CoreAuthTokenModel,
|
||||||
user_info: CoreUserInfoModel,
|
user_info: CoreUserInfoModel,
|
||||||
@@ -176,6 +177,8 @@ class SafaricomMPesaExpressPaymentsController(PaymentsController):
|
|||||||
|
|
||||||
"""
|
"""
|
||||||
To request payment from someone through a payment gateway.
|
To request payment from someone through a payment gateway.
|
||||||
|
:param sql_conn: Only needed when a payment gateway says that the credentials are invalid and the account needs
|
||||||
|
to be disabled.
|
||||||
:param mongo_data_conn: The database connection to use to perform this activity.
|
:param mongo_data_conn: The database connection to use to perform this activity.
|
||||||
:param auth_token: The token that has to be used to fetch the data.
|
:param auth_token: The token that has to be used to fetch the data.
|
||||||
:param user_info: The info. of your user, so that you can identify who requested the payment.
|
:param user_info: The info. of your user, so that you can identify who requested the payment.
|
||||||
@@ -249,6 +252,7 @@ class SafaricomMPesaExpressPaymentsController(PaymentsController):
|
|||||||
|
|
||||||
async def handle_payment_callback(
|
async def handle_payment_callback(
|
||||||
self,
|
self,
|
||||||
|
sql_conn: AsyncMySQL,
|
||||||
mongo_data_conn: AsyncMongo,
|
mongo_data_conn: AsyncMongo,
|
||||||
inbound_data: dict,
|
inbound_data: dict,
|
||||||
inbound_headers: dict
|
inbound_headers: dict
|
||||||
@@ -257,6 +261,8 @@ class SafaricomMPesaExpressPaymentsController(PaymentsController):
|
|||||||
"""
|
"""
|
||||||
Whenever the payment gateway sends an update about a requested payment, we use this method to update our records
|
Whenever the payment gateway sends an update about a requested payment, we use this method to update our records
|
||||||
as per the specification of the third-party payment gateway.
|
as per the specification of the third-party payment gateway.
|
||||||
|
:param sql_conn: Only needed when a payment gateway says that the credentials are invalid and the account needs
|
||||||
|
to be disabled.
|
||||||
:param mongo_data_conn: The database connection to use to perform this activity.
|
:param mongo_data_conn: The database connection to use to perform this activity.
|
||||||
:param inbound_data: The data sent by the payment gateway in their update.
|
:param inbound_data: The data sent by the payment gateway in their update.
|
||||||
:param inbound_headers: The headers sent by the payment gateway in their update.
|
:param inbound_headers: The headers sent by the payment gateway in their update.
|
||||||
@@ -334,6 +340,24 @@ class SafaricomMPesaExpressPaymentsController(PaymentsController):
|
|||||||
client_reference_id = pg_reference_id
|
client_reference_id = pg_reference_id
|
||||||
)
|
)
|
||||||
|
|
||||||
|
# In case the payment collector's credentials have changed,
|
||||||
|
# we mark his account as disabled:
|
||||||
|
# if pg_result_code in [2001]:
|
||||||
|
# payment = await self.get_payment_by_client_reference_id(
|
||||||
|
# mongo_data_conn = mongo_data_conn,
|
||||||
|
# client_reference_id = pg_reference_id
|
||||||
|
# )
|
||||||
|
# auth_token = await self.get_token_from_id(
|
||||||
|
# mongo_data_conn = mongo_data_conn,
|
||||||
|
# token_id = payment.tokenId
|
||||||
|
# )
|
||||||
|
# auth_token.status = "disabled"
|
||||||
|
# await self.set_token(
|
||||||
|
# sql_conn = sql_conn,
|
||||||
|
# mongo_data_conn = mongo_data_conn,
|
||||||
|
# auth_token = auth_token
|
||||||
|
# )
|
||||||
|
|
||||||
# Done here:
|
# Done here:
|
||||||
if event_note_success:
|
if event_note_success:
|
||||||
result.success = True
|
result.success = True
|
||||||
|
|||||||
Reference in New Issue
Block a user