[add]: appId and apiKey validation

This commit is contained in:
VivianDee
2025-03-21 10:42:07 +01:00
parent c71995c9c5
commit 0f6d2b1219
6 changed files with 65 additions and 28 deletions
-1
View File
@@ -1,3 +1,2 @@
# Byte-compiled / optimized / DLL files
__pycache__/
.env
+6
View File
@@ -125,3 +125,9 @@ TypeError: require_api_key() missing 1 required positional argument: 'f'
2025-03-21 09:16:24,496 - INFO - before_request middleware triggered
2025-03-21 09:16:24,496 - INFO - Processing Disbursement request
2025-03-21 09:16:24,498 - ERROR - Validation Error: {'productId': ['Missing data for required field.'], 'debtId': ['Missing data for required field.'], 'collectAmountMgtFee': ['Missing data for required field.'], 'collectAmountVAT': ['Missing data for required field.'], 'provideAmount': ['Missing data for required field.'], 'requestId': ['Missing data for required field.'], 'collectAmountInsurance': ['Missing data for required field.'], 'countryId': ['Missing data for required field.'], 'channel': ['Unknown field.'], '$type': ['Unknown field.'], 'msisdn': ['Unknown field.'], 'countryCode': ['Unknown field.'], 'lienAmount': ['Unknown field.']}
2025-03-21 09:40:40,601 - ERROR - Unauthorized access: Invalid API key.
2025-03-21 09:41:09,390 - INFO - Processing Disbursement request
2025-03-21 09:41:09,396 - ERROR - Validation Error: {'requestId': ['Missing data for required field.'], 'productId': ['Missing data for required field.'], 'collectAmountMgtFee': ['Missing data for required field.'], 'collectAmountVAT': ['Missing data for required field.'], 'provideAmount': ['Missing data for required field.'], 'countryId': ['Missing data for required field.'], 'debtId': ['Missing data for required field.'], 'collectAmountInsurance': ['Missing data for required field.'], 'channel': ['Unknown field.'], 'lienAmount': ['Unknown field.'], '$type': ['Unknown field.'], 'msisdn': ['Unknown field.'], 'countryCode': ['Unknown field.']}
2025-03-21 09:41:13,582 - ERROR - Unauthorized access: Missing App-ID.
2025-03-21 09:41:16,993 - INFO - Processing Disbursement request
2025-03-21 09:41:16,995 - ERROR - Validation Error: {'requestId': ['Missing data for required field.'], 'productId': ['Missing data for required field.'], 'collectAmountMgtFee': ['Missing data for required field.'], 'collectAmountVAT': ['Missing data for required field.'], 'provideAmount': ['Missing data for required field.'], 'countryId': ['Missing data for required field.'], 'debtId': ['Missing data for required field.'], 'collectAmountInsurance': ['Missing data for required field.'], 'channel': ['Unknown field.'], 'lienAmount': ['Unknown field.'], '$type': ['Unknown field.'], 'msisdn': ['Unknown field.'], 'countryCode': ['Unknown field.']}
+1
View File
@@ -1 +1,2 @@
from .verify_api_key import require_api_key
from .app_id_checker import require_app_id
+17 -11
View File
@@ -1,20 +1,26 @@
from functools import wraps
from flask import request
from app.helpers.response_helper import ResponseHelper
from app.utils.logger import logger
import os
VALID_APP_IDS = os.getenv("VALID_APP_ID", "")
# Load valid App-IDs from environment variables (comma-separated list)
VALID_APP_ID = os.getenv("VALID_APP_ID", "app1,app2,app3").split(",")
def require_app_id():
"""Middleware to check if App-ID is present and valid."""
app_id = request.headers.get("App-ID")
def require_app_id(f):
"""Decorator to enforce App-ID validation."""
@wraps(f)
def decorated_function(*args, **kwargs):
app_id = request.headers.get("App-ID")
if not app_id:
logger.error("Unauthorized access: Missing App-ID.")
return ResponseHelper.unauthorized("Missing App-ID")
if not app_id:
logger.error("Unauthorized access: Missing App-ID.")
return ResponseHelper.unauthorized("Missing App-ID")
if app_id not in VALID_APP_IDS:
logger.error(f"Unauthorized access: Invalid App-ID {app_id}.")
return ResponseHelper.unauthorized("Invalid App-ID")
if app_id not in VALID_APP_ID:
logger.error(f"Unauthorized access: Invalid App-ID {app_id}.")
return ResponseHelper.unauthorized("Invalid App-ID")
return None
return f(*args, **kwargs)
return decorated_function
+18 -12
View File
@@ -1,20 +1,26 @@
from functools import wraps
from flask import request
from app.helpers.response_helper import ResponseHelper
from app.utils.logger import logger
import os
# Define a valid API key (store securely in environment variables)
VALID_API_KEY = "your-secure-api-key"
# Load valid API key from environment variables (fallback for testing)
VALID_API_KEY = os.getenv("VALID_API_KEY", "test-api-key-12345")
def require_api_key():
"""Middleware to check if API key is present and valid."""
api_key = request.headers.get("X-API-KEY")
def require_api_key(f):
"""Decorator to enforce API key authentication."""
@wraps(f)
def decorated_function(*args, **kwargs):
api_key = request.headers.get("X-API-KEY")
if not api_key:
logger.error("Unauthorized access: Missing API key.")
return ResponseHelper.unauthorized("Missing API key")
if not api_key:
logger.error("Unauthorized access: Missing API key.")
return ResponseHelper.unauthorized("Missing API key")
if api_key != VALID_API_KEY:
logger.error("Unauthorized access: Invalid API key.")
return ResponseHelper.unauthorized("Invalid API key")
if api_key != VALID_API_KEY:
logger.error("Unauthorized access: Invalid API key.")
return ResponseHelper.unauthorized("Invalid API key")
return None
return f(*args, **kwargs)
return decorated_function
+23 -4
View File
@@ -12,20 +12,23 @@ from app.blueprints import (
)
from app.utils.logger import logger
from app.middlewares import require_api_key
from app.middlewares import require_app_id
api = Blueprint("api", __name__)
@api.before_request
def require_api_key_middleware():
"""Middleware applied globally to all API routes in this blueprint"""
return require_api_key()
# @api.before_request
# def require_api_key_middleware():
# """Middleware applied globally to all API routes in this blueprint"""
# return require_api_key()
# RACCheck Endpoint
@api.route('/RACCheck', methods=['POST'])
@require_api_key
@require_app_id
def rac_check():
data = request.get_json()
# logger.info(f"RACCheck request received: {data}")
@@ -34,6 +37,8 @@ def rac_check():
# Disbursement Endpoint
@api.route('/Disbursement', methods=['POST'])
@require_api_key
@require_app_id
def disbursement():
data = request.get_json()
# logger.info(f"Disbursement request received: {data}")
@@ -42,6 +47,8 @@ def disbursement():
# CollectLoan Endpoint
@api.route('/CollectLoan', methods=['POST'])
@require_api_key
@require_app_id
def collect_loan():
data = request.get_json()
# logger.info(f"CollectLoan request received: {data}")
@@ -50,6 +57,8 @@ def collect_loan():
# TransactionVerify Endpoint
@api.route('/TransactionVerify', methods=['POST'])
@require_api_key
@require_app_id
def transaction_verify():
data = request.get_json()
# logger.info(f"TransactionVerify request received: {data}")
@@ -58,6 +67,8 @@ def transaction_verify():
# PenalCharge Endpoint
@api.route('/PenalCharge', methods=['POST'])
@require_api_key
@require_app_id
def penal_charge():
data = request.get_json()
# logger.info(f"PenalCharge request received: {data}")
@@ -66,6 +77,8 @@ def penal_charge():
# RevokeEnableConsent Endpoint
@api.route('/RevokeEnableConsent', methods=['POST'])
@require_api_key
@require_app_id
def revoke_enable_consent():
data = request.get_json()
# logger.info(f"RevokeEnableConsent request received: {data}")
@@ -74,6 +87,8 @@ def revoke_enable_consent():
# TokenValidation Endpoint
@api.route('/TokenValidation', methods=['POST'])
@require_api_key
@require_app_id
def token_validation():
data = request.get_json()
# logger.info(f"TokenValidation request received: {data}")
@@ -82,6 +97,8 @@ def token_validation():
# LienCheck Endpoint
@api.route('/LienCheck', methods=['POST'])
@require_api_key
@require_app_id
def lien_check():
data = request.get_json()
# logger.info(f"LienCheck request received: {data}")
@@ -90,6 +107,8 @@ def lien_check():
# NewTransactionCheck Endpoint
@api.route('/NewTransactionCheck', methods=['POST'])
@require_api_key
@require_app_id
def new_transaction_check():
data = request.get_json()
# logger.info(f"NewTransactionCheck request received: {data}")