import iso3166
import tornado.web
-from . import auth
from . import base
SKUS = {
}
DEFAULT_SKU = "IPFIRE-DONATION"
-class DonateHandler(auth.CacheMixin, base.BaseHandler):
+class DonateHandler(base.BaseHandler):
def get(self):
- country = self.current_country_code
+ if self.current_user:
+ country = self.current_user.country_code
+ else:
+ country = self.current_country_code
# Get defaults
- first_name = self.get_argument("first_name", None)
- last_name = self.get_argument("last_name", None)
amount = self.get_argument_float("amount", None)
currency = self.get_argument("currency", None)
frequency = self.get_argument("frequency", None)
frequency = "one-time"
self.render("donate/donate.html", countries=iso3166.countries,
- country=country, first_name=first_name, last_name=last_name,
- amount=amount, currency=currency, frequency=frequency)
+ country=country, amount=amount, currency=currency, frequency=frequency)
@base.ratelimit(minutes=15, requests=5)
async def post(self):
+ type = self.get_argument("type")
+ if not type in ("individual", "organization"):
+ raise tornado.web.HTTPError(400, "type is of an invalid value: %s" % type)
+
amount = self.get_argument("amount")
currency = self.get_argument("currency", "EUR")
frequency = self.get_argument("frequency")
- # Collect donor information
- donor = {
+ organization = None
+ locale = self.get_browser_locale()
+
+ # Get organization information
+ if type == "organization":
+ organization = {
+ "name" : self.get_argument("organization"),
+ "vat_number" : self.get_argument("vat_number", None),
+ }
+
+ # Collect person information
+ person = {
"email" : self.get_argument("email"),
"title" : self.get_argument("title"),
"first_name" : self.get_argument("first_name"),
"last_name" : self.get_argument("last_name"),
+ "locale" : locale.code,
}
# Collect address information
# Send everything to Zeiterfassung
try:
- # Search for person or create a new one
- response = await self.backend.zeiterfassung.send_request(
- "/api/v1/persons/search", **donor
- )
-
- if not response:
- response = await self.backend.zeiterfassung.send_request(
- "/api/v1/persons/create", **donor, **address
- )
+ # Create a new organization
+ if organization:
+ organization = await self._create_organization(organization, address)
- # Store person number
- person = response.get("number")
+ # Create a person
+ person = await self._create_person(person, address, organization)
# Create a new order
order = await self._create_order(person=person, currency=currency)
# Add donation to the order
- await self._create_donation(order, frequency, amount, currency)
+ await self._create_donation(order, frequency, amount, currency,
+ vat_included=(type == "individual"))
# Submit the order
needs_payment = await self._submit_order(order)
except Exception:
raise
+ async def _create_organization(self, organization, address):
+ # Check if we have an existing organization
+ response = await self.backend.zeiterfassung.send_request(
+ "/api/v1/organizations/search", **organization,
+ )
+
+ # Update details if we found a match
+ if response:
+ number = response.get("number")
+
+ # Update name
+ await self.backend.zeiterfassung.send_request(
+ "/api/v1/organizations/%s/name" % number, **organization
+ )
+
+ # Update VAT number
+ vat_number = organization.get("vat_number", None)
+ if vat_number:
+ await self.backend.zeiterfassung.send_request(
+ "/api/v1/organizations/%s/vat-number" % number, vat_number=vat_number,
+ )
+
+ # Update address
+ await self.backend.zeiterfassung.send_request(
+ "/api/v1/organizations/%s/address" % number, **address,
+ )
+
+ return number
+
+ # Otherwise we will create a new one
+ response = await self.backend.zeiterfassung.send_request(
+ "/api/v1/organizations/create", **organization, **address,
+ )
+
+ # Return the organization's number
+ return response.get("number")
+
+ async def _create_person(self, person, address, organization=None):
+ """
+ Searches for a matching person or creates a new one
+ """
+ # Check if we have an existing person
+ response = await self.backend.zeiterfassung.send_request(
+ "/api/v1/persons/search", **person
+ )
+
+ # Update details if we found a match
+ if response:
+ number = response.get("number")
+
+ # Update name
+ await self.backend.zeiterfassung.send_request(
+ "/api/v1/persons/%s/name" % number, **person,
+ )
+
+ # Update address
+ await self.backend.zeiterfassung.send_request(
+ "/api/v1/persons/%s/address" % number, **address,
+ )
+
+ return number
+
+ # If not, we will create a new one
+ response = await self.backend.zeiterfassung.send_request(
+ "/api/v1/persons/create", organization=organization, **person, **address
+ )
+
+ # Return the persons's number
+ return response.get("number")
+
async def _create_order(self, person, currency=None):
"""
Creates a new order and returns its ID
# Return the order number
return response.get("number")
- async def _create_donation(self, order, frequency, amount, currency):
+ async def _create_donation(self, order, frequency, amount, currency,
+ vat_included=False):
"""
Creates a new donation
"""
# Set the price
await self.backend.zeiterfassung.send_request(
"/api/v1/orders/%s/products/%s/price" % (order, sku),
- price=amount, currency=currency,
+ price=amount, currency=currency, vat_included=vat_included,
)
async def _submit_order(self, order):