Skip to content
Snippets Groups Projects
Commit 94d06466 authored by geant-release-service's avatar geant-release-service
Browse files

Finished release 0.16.

parents 709a092a 3a833c15
Branches
Tags 0.16
No related merge requests found
......@@ -2,6 +2,12 @@
All notable changes to this project will be documented in this file.
## [0.16] - 2025-02-12
- Exclude void invoices from possbile error report
- Limit max invoice due date and set maximum date for allowing bank transfers
...
## [0.9] - 2025-02-12
- added repeated confirm click prevention
- added emails sent out when a payment is received with no associated order
......
......@@ -5,5 +5,7 @@
"STRIPE_TAX_RATE_ID": "txr_1QeddlDSpyjzuj5pPwUcMwTd",
"VISIT_API_KEY": "<visit api key>",
"VISIT_EXPO_ID": "18lm2fafttito",
"SEND_ERROR_EMAILS_TO": []
"SEND_ERROR_EMAILS_TO": [],
"MAX_INVOICE_DUE_DATE": "2025-05-23",
"MAX_BANK_TRANSFER_ALLOWED_DATE": "2025-05-12"
}
\ No newline at end of file
......@@ -2,7 +2,7 @@ from setuptools import setup, find_packages
setup(
name="stripe-checkout",
version="0.15",
version="0.16",
author="GEANT",
author_email="swd@geant.org",
description="Stripe custom checkout support service",
......
......@@ -43,6 +43,8 @@ class PossibleErrorReporter(CSVReporter):
yield obj
unseen_invoices: dict[str, list[dict]] = {}
for obj_id, obj in data["stripe"].items():
if obj["status"] in ("draft", "void"):
continue
email = obj["customer_email"]
if obj_id.startswith("in_") and email not in seen:
unseen_invoices.setdefault(email, []).append(obj)
......@@ -105,6 +107,13 @@ reporter = PossibleErrorReporter([VISITOR_SERIALIZER], get_data=get_all_data)
def main():
import logging
import pathlib
import stripe
from django.conf import settings
from stripe_checkout.config import load_config
load_config("config.json", settings=settings)
stripe.api_key = settings.STRIPE_API_KEY
logger = logging.getLogger()
logging.basicConfig(level=logging.INFO)
......
from __future__ import annotations
import datetime
import functools
import logging
import time
......@@ -72,6 +73,33 @@ def parse_address(visit_address: dict, organization: str):
}
def get_invoice_days_until_due(max_days=30):
max_invoice_due_date = getattr(settings, "MAX_INVOICE_DUE_DATE", None)
if not max_invoice_due_date:
return max_days
days_until_max_due_date = (
datetime.date.fromisoformat(max_invoice_due_date) - datetime.date.today()
).days
return max(min(days_until_max_due_date, max_days), 0)
def _is_bank_transfer_allowed():
max_bank_transfer_allowed_date = getattr(
settings, "MAX_BANK_TRANSFER_ALLOWED_DATE", None
)
if not max_bank_transfer_allowed_date:
return True
return datetime.date.today() <= datetime.date.fromisoformat(
max_bank_transfer_allowed_date
)
def get_allowed_payment_methods():
if _is_bank_transfer_allowed():
return ["card", "customer_balance"]
return ["card"]
def create_invoice(
shopping_cart: ShoppingCart,
customer_id,
......@@ -98,8 +126,8 @@ def create_invoice(
invoice = stripe.Invoice.create(
customer=customer_id,
collection_method="send_invoice",
payment_settings={"payment_method_types": ["card", "customer_balance"]},
days_until_due=30,
payment_settings={"payment_method_types": get_allowed_payment_methods()},
days_until_due=get_invoice_days_until_due(),
custom_fields=custom_fields,
rendering={"template": settings.STRIPE_INVOICE_TEMPLATE_ID},
metadata=metadata,
......
import datetime
import pytest
import stripe
from stripe_checkout.stripe_checkout.stripe_ import get_or_create_customer
from stripe_checkout.stripe_checkout.stripe_ import (
get_allowed_payment_methods,
get_invoice_days_until_due,
get_or_create_customer,
)
@pytest.mark.parametrize(
......@@ -95,3 +100,44 @@ def test_updates_visitor_with_address(default_visitor, mock_stripe):
new_address = stripe.Customer.modify.call_args.kwargs["address"]
non_empty = {key: val for key, val in new_address.items() if val}
assert non_empty == {"country": "BE"}
@pytest.mark.parametrize(
"max_due_date_in_days, expected_days_until_due",
[
(None, 30),
(31, 30),
(30, 30),
(29, 29),
(1, 1),
(0, 0),
(-1, 0),
],
)
def test_invoice_due_date(max_due_date_in_days, expected_days_until_due, settings):
if max_due_date_in_days is not None:
max_due_date = datetime.date.today() + datetime.timedelta(
days=max_due_date_in_days
)
settings.MAX_INVOICE_DUE_DATE = max_due_date.isoformat()
assert get_invoice_days_until_due() == expected_days_until_due
@pytest.mark.parametrize(
"days_until_max_bank_transfer_date, expected_payment_methods",
[
(None, ["card", "customer_balance"]),
(1, ["card", "customer_balance"]),
(0, ["card", "customer_balance"]),
(-1, ["card"]),
],
)
def test_get_allowed_payment_methods(
days_until_max_bank_transfer_date, expected_payment_methods, settings
):
if days_until_max_bank_transfer_date is not None:
max_bank_transfer_date = datetime.date.today() + datetime.timedelta(
days=days_until_max_bank_transfer_date
)
settings.MAX_BANK_TRANSFER_ALLOWED_DATE = max_bank_transfer_date.isoformat()
assert get_allowed_payment_methods() == expected_payment_methods
0% Loading or .
You are about to add 0 people to the discussion. Proceed with caution.
Please register or to comment