Building Custom Gateway
1. Gateway Settings Doctype
Create gateway settings doctype extending standard controller pattern:
class CustomGatewaySettings(Document):
supported_currencies = ("USD", "EUR", "GBP")
def on_update(self):
create_payment_gateway(
"Custom Gateway",
settings="Custom Gateway Settings",
controller=self.name
)
call_hook_method("payment_gateway_enabled", gateway="Custom Gateway")
def validate_transaction_currency(self, currency):
if currency not in self.supported_currencies:
frappe.throw(_("Currency {0} not supported").format(currency))
def get_payment_url(self, **kwargs):
return f"https://checkout.customgateway.com/pay?{urlencode(kwargs)}"
2. Doctype JSON Configuration
{
"doctype": "DocType",
"name": "Custom Gateway Settings",
"fields": [
{"fieldname": "api_key", "fieldtype": "Data", "label": "API Key"},
{"fieldname": "api_secret", "fieldtype": "Password", "label": "API Secret"},
{"fieldname": "use_sandbox", "fieldtype": "Check", "label": "Use Sandbox"}
]
}
3. Checkout Template
Create checkout page template:
{% extends "templates/web.html" %}
{% block page_content %}
<form id="payment-form" action="{{ callback_url }}" method="POST">
<input type="hidden" name="token" value="{{ token }}">
<button type="submit">Pay {{ amount }} {{ currency }}</button>
</form>
{% endblock %}
4. Callback Handler
@frappe.whitelist(allow_guest=True)
def handle_callback():
token = frappe.form_dict.token
integration_request = frappe.get_doc("Integration Request", token)
# Verify payment with gateway
payment_status = verify_payment_with_gateway(token)
integration_request.update_status(
data={"transaction_id": payment_status.txn_id},
status="Completed" if payment_status.success else "Failed"
)
# Trigger callback on reference document
data = json.loads(integration_request.data)
if data.get("reference_doctype"):
doc = frappe.get_doc(data["reference_doctype"], data["reference_docname"])
doc.run_method("on_payment_authorized", "Completed")
5. App Hooks Configuration
# custom_gateway/hooks.py
doctype_js = {
"Custom Gateway Settings": "custom_gateway/js/settings.js"
}
payment_gateway_controller = {
"Custom Gateway": "custom_gateway.controllers.get_controller"
}
Last updated 2 months ago
Was this helpful?