git subrepo pull vendor/registripe
Also update vendored_requirements to make sure we pull this in. subrepo: subdir: "vendor/registripe" merged: "9fc3645" upstream: origin: "git@gitlab.com:tchaypo/registrasion-stripe.git" branch: "lca2018" commit: "9fc3645" git-subrepo: version: "0.3.1" origin: "???" commit: "???"
This commit is contained in:
		
							parent
							
								
									6eaddfc1d8
								
							
						
					
					
						commit
						660690c5cf
					
				
					 27 changed files with 474 additions and 233 deletions
				
			
		
							
								
								
									
										89
									
								
								vendor/registripe/.gitignore
									
										
									
									
										vendored
									
									
										Normal file
									
								
							
							
						
						
									
										89
									
								
								vendor/registripe/.gitignore
									
										
									
									
										vendored
									
									
										Normal file
									
								
							|  | @ -0,0 +1,89 @@ | ||||||
|  | # Byte-compiled / optimized / DLL files | ||||||
|  | __pycache__/ | ||||||
|  | *.py[cod] | ||||||
|  | *$py.class | ||||||
|  | 
 | ||||||
|  | # C extensions | ||||||
|  | *.so | ||||||
|  | 
 | ||||||
|  | # Distribution / packaging | ||||||
|  | .Python | ||||||
|  | env/ | ||||||
|  | build/ | ||||||
|  | develop-eggs/ | ||||||
|  | dist/ | ||||||
|  | downloads/ | ||||||
|  | eggs/ | ||||||
|  | .eggs/ | ||||||
|  | lib/ | ||||||
|  | lib64/ | ||||||
|  | parts/ | ||||||
|  | sdist/ | ||||||
|  | var/ | ||||||
|  | *.egg-info/ | ||||||
|  | .installed.cfg | ||||||
|  | *.egg | ||||||
|  | 
 | ||||||
|  | # PyInstaller | ||||||
|  | #  Usually these files are written by a python script from a template | ||||||
|  | #  before PyInstaller builds the exe, so as to inject date/other infos into it. | ||||||
|  | *.manifest | ||||||
|  | *.spec | ||||||
|  | 
 | ||||||
|  | # Installer logs | ||||||
|  | pip-log.txt | ||||||
|  | pip-delete-this-directory.txt | ||||||
|  | 
 | ||||||
|  | # Unit test / coverage reports | ||||||
|  | htmlcov/ | ||||||
|  | .tox/ | ||||||
|  | .coverage | ||||||
|  | .coverage.* | ||||||
|  | .cache | ||||||
|  | nosetests.xml | ||||||
|  | coverage.xml | ||||||
|  | *,cover | ||||||
|  | .hypothesis/ | ||||||
|  | 
 | ||||||
|  | # Translations | ||||||
|  | *.mo | ||||||
|  | *.pot | ||||||
|  | 
 | ||||||
|  | # Django stuff: | ||||||
|  | *.log | ||||||
|  | local_settings.py | ||||||
|  | 
 | ||||||
|  | # Flask stuff: | ||||||
|  | instance/ | ||||||
|  | .webassets-cache | ||||||
|  | 
 | ||||||
|  | # Scrapy stuff: | ||||||
|  | .scrapy | ||||||
|  | 
 | ||||||
|  | # Sphinx documentation | ||||||
|  | docs/_build/ | ||||||
|  | 
 | ||||||
|  | # PyBuilder | ||||||
|  | target/ | ||||||
|  | 
 | ||||||
|  | # IPython Notebook | ||||||
|  | .ipynb_checkpoints | ||||||
|  | 
 | ||||||
|  | # pyenv | ||||||
|  | .python-version | ||||||
|  | 
 | ||||||
|  | # celery beat schedule file | ||||||
|  | celerybeat-schedule | ||||||
|  | 
 | ||||||
|  | # dotenv | ||||||
|  | .env | ||||||
|  | 
 | ||||||
|  | # virtualenv | ||||||
|  | venv/ | ||||||
|  | ENV/ | ||||||
|  | 
 | ||||||
|  | # Spyder project settings | ||||||
|  | .spyderproject | ||||||
|  | 
 | ||||||
|  | # Rope project settings | ||||||
|  | .ropeproject | ||||||
							
								
								
									
										4
									
								
								vendor/registripe/.gitrepo
									
										
									
									
										vendored
									
									
								
							
							
						
						
									
										4
									
								
								vendor/registripe/.gitrepo
									
										
									
									
										vendored
									
									
								
							|  | @ -6,6 +6,6 @@ | ||||||
| [subrepo] | [subrepo] | ||||||
| 	remote = git@gitlab.com:tchaypo/registrasion-stripe.git | 	remote = git@gitlab.com:tchaypo/registrasion-stripe.git | ||||||
| 	branch = lca2018 | 	branch = lca2018 | ||||||
| 	commit = 5ebd58154006e63d390c5feadafb9a19769c7455 | 	commit = 9fc364586b2246801979da690bdf2387b8f53e42 | ||||||
| 	parent = 5789cbd05e06742f4f7d5dfaf02c92cc8be6bfad | 	parent = 6eaddfc1d8dd08dfeaaf7101a827974c977f23f4 | ||||||
| 	cmdver = 0.3.1 | 	cmdver = 0.3.1 | ||||||
|  |  | ||||||
							
								
								
									
										2
									
								
								vendor/registripe/README.md
									
										
									
									
										vendored
									
									
										Normal file
									
								
							
							
						
						
									
										2
									
								
								vendor/registripe/README.md
									
										
									
									
										vendored
									
									
										Normal file
									
								
							|  | @ -0,0 +1,2 @@ | ||||||
|  | # registrasion-stripe | ||||||
|  | Provides Credit Card processing for Registrasion using the Stripe API. | ||||||
							
								
								
									
										223
									
								
								vendor/registripe/forms.py
									
										
									
									
										vendored
									
									
								
							
							
						
						
									
										223
									
								
								vendor/registripe/forms.py
									
										
									
									
										vendored
									
									
								
							|  | @ -1,223 +0,0 @@ | ||||||
| import copy |  | ||||||
| from registripe import models |  | ||||||
| 
 |  | ||||||
| from django import forms |  | ||||||
| from django.core.urlresolvers import reverse |  | ||||||
| from django.db.models import F, Q |  | ||||||
| from django.forms import widgets |  | ||||||
| from django.utils import timezone |  | ||||||
| 
 |  | ||||||
| from django_countries import countries |  | ||||||
| from django_countries.fields import LazyTypedChoiceField |  | ||||||
| from django_countries.widgets import CountrySelectWidget |  | ||||||
| 
 |  | ||||||
| 
 |  | ||||||
| class NoRenderWidget(forms.widgets.HiddenInput): |  | ||||||
| 
 |  | ||||||
|     def render(self, name, value, attrs=None): |  | ||||||
|         return "<!-- no widget: " + name + " -->" |  | ||||||
| 
 |  | ||||||
| 
 |  | ||||||
| def secure_striped(field): |  | ||||||
|     ''' Calls stripe() with secure=True. ''' |  | ||||||
|     return striped(field, True) |  | ||||||
| 
 |  | ||||||
| 
 |  | ||||||
| def striped(field, secure=False): |  | ||||||
| 
 |  | ||||||
|     oldwidget = field.widget |  | ||||||
|     field.widget = StripeWidgetProxy(oldwidget, secure) |  | ||||||
|     return field |  | ||||||
| 
 |  | ||||||
| 
 |  | ||||||
| class StripeWidgetProxy(widgets.Widget): |  | ||||||
| 
 |  | ||||||
|     def __init__(self, underlying, secure=False): |  | ||||||
|         self.underlying = underlying |  | ||||||
|         self.secure = secure |  | ||||||
| 
 |  | ||||||
|     def __deepcopy__(self, memo): |  | ||||||
|         copy_underlying = copy.deepcopy(self.underlying, memo) |  | ||||||
|         return type(self)(copy_underlying, self.secure) |  | ||||||
| 
 |  | ||||||
|     def __getattribute__(self, attr): |  | ||||||
|         spr = super(StripeWidgetProxy, self).__getattribute__ |  | ||||||
|         if attr in ("underlying", "render", "secure", "__deepcopy__"): |  | ||||||
|             return spr(attr) |  | ||||||
|         else: |  | ||||||
|             return getattr(self.underlying, attr) |  | ||||||
| 
 |  | ||||||
|     def render(self, name, value, attrs=None): |  | ||||||
| 
 |  | ||||||
|         if not attrs: |  | ||||||
|             attrs = {} |  | ||||||
| 
 |  | ||||||
|         attrs["data-stripe"] = name |  | ||||||
| 
 |  | ||||||
|         if self.secure: |  | ||||||
|             name = "" |  | ||||||
| 
 |  | ||||||
|         return self.underlying.render(name, value, attrs=attrs) |  | ||||||
| 
 |  | ||||||
| 
 |  | ||||||
| class CreditCardForm(forms.Form): |  | ||||||
| 
 |  | ||||||
|     required_css_class = 'label-required' |  | ||||||
| 
 |  | ||||||
|     def _media(self): |  | ||||||
|         js = ( |  | ||||||
|             'https://js.stripe.com/v2/', |  | ||||||
|             reverse("registripe_pubkey"), |  | ||||||
|         ) |  | ||||||
| 
 |  | ||||||
|         return forms.Media(js=js) |  | ||||||
| 
 |  | ||||||
|     media = property(_media) |  | ||||||
| 
 |  | ||||||
|     number = secure_striped(forms.CharField( |  | ||||||
|         required=False, |  | ||||||
|         label="Credit card Number", |  | ||||||
|         help_text="Your credit card number, with or without spaces.", |  | ||||||
|         max_length=255, |  | ||||||
|     )) |  | ||||||
|     exp_month = secure_striped(forms.IntegerField( |  | ||||||
|         required=False, |  | ||||||
|         label="Card expiry month", |  | ||||||
|         min_value=1, |  | ||||||
|         max_value=12, |  | ||||||
|     )) |  | ||||||
|     exp_year = secure_striped(forms.IntegerField( |  | ||||||
|         required=False, |  | ||||||
|         label="Card expiry year", |  | ||||||
|         help_text="The expiry year for your card in 4-digit form", |  | ||||||
|         min_value=timezone.now().year, |  | ||||||
|     )) |  | ||||||
|     cvc = secure_striped(forms.CharField( |  | ||||||
|         required=False, |  | ||||||
|         min_length=3, |  | ||||||
|         max_length=4, |  | ||||||
|     )) |  | ||||||
| 
 |  | ||||||
|     stripe_token = forms.CharField( |  | ||||||
|         max_length=255, |  | ||||||
|         # required=True, |  | ||||||
|         widget=NoRenderWidget(), |  | ||||||
|     ) |  | ||||||
| 
 |  | ||||||
|     name = striped(forms.CharField( |  | ||||||
|         required=True, |  | ||||||
|         label="Cardholder name", |  | ||||||
|         help_text="The cardholder's name, as it appears on the credit card", |  | ||||||
|         max_length=255, |  | ||||||
|     )) |  | ||||||
|     address_line1 = striped(forms.CharField( |  | ||||||
|         required=True, |  | ||||||
|         label="Cardholder account address, line 1", |  | ||||||
|         max_length=255, |  | ||||||
|     )) |  | ||||||
|     address_line2 = striped(forms.CharField( |  | ||||||
|         required=False, |  | ||||||
|         label="Cardholder account address, line 2", |  | ||||||
|         max_length=255, |  | ||||||
|     )) |  | ||||||
|     address_city = striped(forms.CharField( |  | ||||||
|         required=True, |  | ||||||
|         label="Cardholder account city", |  | ||||||
|         max_length=255, |  | ||||||
|     )) |  | ||||||
|     address_state = striped(forms.CharField( |  | ||||||
|         required=True, |  | ||||||
|         max_length=255, |  | ||||||
|         label="Cardholder account state or province", |  | ||||||
|     )) |  | ||||||
|     address_zip = striped(forms.CharField( |  | ||||||
|         required=True, |  | ||||||
|         max_length=255, |  | ||||||
|         label="Cardholder account postal code", |  | ||||||
|     )) |  | ||||||
|     address_country = striped(LazyTypedChoiceField( |  | ||||||
|         label="Cardholder account country", |  | ||||||
|         choices=countries, |  | ||||||
|         widget=CountrySelectWidget, |  | ||||||
|     )) |  | ||||||
| 
 |  | ||||||
| 
 |  | ||||||
| class StripeRefundForm(forms.Form): |  | ||||||
| 
 |  | ||||||
|     required_css_class = 'label-required' |  | ||||||
| 
 |  | ||||||
|     def __init__(self, *args, **kwargs): |  | ||||||
|         ''' |  | ||||||
| 
 |  | ||||||
|         Arguments: |  | ||||||
|             user (User): The user whose charges we should filter to. |  | ||||||
|             min_value (Decimal): The minimum value of the charges we should |  | ||||||
|                 show (currently, credit notes can only be cashed out in full.) |  | ||||||
| 
 |  | ||||||
|         ''' |  | ||||||
|         user = kwargs.pop('user', None) |  | ||||||
|         min_value = kwargs.pop('min_value', None) |  | ||||||
|         super(StripeRefundForm, self).__init__(*args, **kwargs) |  | ||||||
| 
 |  | ||||||
|         payment_field = self.fields['payment'] |  | ||||||
|         qs = payment_field.queryset |  | ||||||
| 
 |  | ||||||
|         if user: |  | ||||||
|             qs = qs.filter( |  | ||||||
|                 charge__customer__user=user, |  | ||||||
|             ) |  | ||||||
| 
 |  | ||||||
|         if min_value is not None: |  | ||||||
|             # amount >= amount_to_refund + amount_refunded |  | ||||||
|             # No refunds yet |  | ||||||
|             q1 = ( |  | ||||||
|                 Q(charge__amount_refunded__isnull=True) & |  | ||||||
|                 Q(charge__amount__gte=min_value) |  | ||||||
|             ) |  | ||||||
|             # There are some refunds |  | ||||||
|             q2 = ( |  | ||||||
|                 Q(charge__amount_refunded__isnull=False) & |  | ||||||
|                 Q(charge__amount__gte=( |  | ||||||
|                     F("charge__amount_refunded") + min_value)) |  | ||||||
|             ) |  | ||||||
|             qs = qs.filter(q1 | q2) |  | ||||||
| 
 |  | ||||||
|         payment_field.queryset = qs |  | ||||||
| 
 |  | ||||||
|     payment = forms.ModelChoiceField( |  | ||||||
|         required=True, |  | ||||||
|         queryset=models.StripePayment.objects.all(), |  | ||||||
|     ) |  | ||||||
| 
 |  | ||||||
| 
 |  | ||||||
| '''{ |  | ||||||
| From stripe.js details: |  | ||||||
| 
 |  | ||||||
| Card details: |  | ||||||
| 
 |  | ||||||
| The first argument to createToken is a JavaScript object containing credit |  | ||||||
| card data entered by the user. It should contain the following required |  | ||||||
| members: |  | ||||||
| 
 |  | ||||||
| number: card number as a string without any separators |  | ||||||
| (e.g., "4242424242424242") |  | ||||||
| exp_month: two digit number representing the card's expiration month |  | ||||||
| (e.g., 12) |  | ||||||
| exp_year: two or four digit number representing the card's expiration year |  | ||||||
| (e.g., 2017) |  | ||||||
| (The expiration date can also be passed as a single string.) |  | ||||||
| 
 |  | ||||||
| cvc: optional, but we highly recommend you provide it to help prevent fraud. |  | ||||||
| This is the card's security code, as a string (e.g., "123"). |  | ||||||
| The following fields are entirely optional and cannot result in a token |  | ||||||
| creation failure: |  | ||||||
| 
 |  | ||||||
| name: cardholder name |  | ||||||
| address_line1: billing address line 1 |  | ||||||
| address_line2: billing address line 2 |  | ||||||
| address_city: billing address city |  | ||||||
| address_state: billing address state |  | ||||||
| address_zip: billing postal code as a string (e.g., "94301") |  | ||||||
| address_country: billing address country |  | ||||||
| } |  | ||||||
| ''' |  | ||||||
							
								
								
									
										3
									
								
								vendor/registripe/registripe/admin.py
									
										
									
									
										vendored
									
									
										Normal file
									
								
							
							
						
						
									
										3
									
								
								vendor/registripe/registripe/admin.py
									
										
									
									
										vendored
									
									
										Normal file
									
								
							|  | @ -0,0 +1,3 @@ | ||||||
|  | from django.contrib import admin | ||||||
|  | 
 | ||||||
|  | # Register your models here. | ||||||
							
								
								
									
										120
									
								
								vendor/registripe/registripe/forms.py
									
										
									
									
										vendored
									
									
										Normal file
									
								
							
							
						
						
									
										120
									
								
								vendor/registripe/registripe/forms.py
									
										
									
									
										vendored
									
									
										Normal file
									
								
							|  | @ -0,0 +1,120 @@ | ||||||
|  | import copy | ||||||
|  | from registripe import models | ||||||
|  | 
 | ||||||
|  | from django import forms | ||||||
|  | from django.core.urlresolvers import reverse | ||||||
|  | import functools | ||||||
|  | 
 | ||||||
|  | from django import forms | ||||||
|  | from django.core.urlresolvers import reverse | ||||||
|  | from django.core.exceptions import ValidationError | ||||||
|  | from django.db.models import F, Q | ||||||
|  | from django.forms import widgets | ||||||
|  | from django.utils import timezone | ||||||
|  | 
 | ||||||
|  | from django_countries import countries | ||||||
|  | from django_countries.fields import LazyTypedChoiceField | ||||||
|  | from django_countries.widgets import CountrySelectWidget | ||||||
|  | 
 | ||||||
|  | from pinax.stripe import models as pinax_stripe_models | ||||||
|  | 
 | ||||||
|  | 
 | ||||||
|  | class StripeCardElement(forms.widgets.TextInput): | ||||||
|  | 
 | ||||||
|  |     def render(self, name, value, attrs=None): | ||||||
|  |         element = ''' | ||||||
|  |             <div class="registrasion-stripe-element" id='%s' style='"-moz-appearance: textfield; -webkit-appearance: textfield;     appearance: field;"'>Please wait.</div>''' % (name, ) | ||||||
|  | 
 | ||||||
|  |         script = ''' | ||||||
|  |             <script type='text/javascript'> | ||||||
|  |                 window.addEventListener('load', function(event){ | ||||||
|  |                     stripeify('%s'); | ||||||
|  |                 }); | ||||||
|  |             </script>''' % (name) | ||||||
|  |         return element + script | ||||||
|  | 
 | ||||||
|  | 
 | ||||||
|  | class StripeTokenWidget(forms.widgets.HiddenInput): | ||||||
|  | 
 | ||||||
|  |     def render(self, name, value, attrs=None): | ||||||
|  | 
 | ||||||
|  |         return ''' | ||||||
|  |             <div class='registrasion-stripe-token' style='display:none;' | ||||||
|  |             data-input-id='%s' | ||||||
|  |             ></div> | ||||||
|  |         ''' % (name, ) | ||||||
|  | 
 | ||||||
|  | 
 | ||||||
|  | class CreditCardForm(forms.Form): | ||||||
|  | 
 | ||||||
|  |     required_css_class = 'label-required' | ||||||
|  | 
 | ||||||
|  |     def _media(self): | ||||||
|  |         js = ( | ||||||
|  |             'https://js.stripe.com/v3/', | ||||||
|  |             reverse("registripe_form_handler"), | ||||||
|  |         ) | ||||||
|  | 
 | ||||||
|  |         return forms.Media(js=js) | ||||||
|  | 
 | ||||||
|  |     media = property(_media) | ||||||
|  | 
 | ||||||
|  |     card = forms.CharField( | ||||||
|  |         required=False, | ||||||
|  |         label="Credit card", | ||||||
|  |         max_length=255, | ||||||
|  |         widget=StripeCardElement() | ||||||
|  |     ) | ||||||
|  | 
 | ||||||
|  |     stripe_token = forms.CharField( | ||||||
|  |         max_length=255, | ||||||
|  |         #required=True, | ||||||
|  |         widget=StripeTokenWidget(), | ||||||
|  |     ) | ||||||
|  | 
 | ||||||
|  | 
 | ||||||
|  | class StripeRefundForm(forms.Form): | ||||||
|  | 
 | ||||||
|  |     def __init__(self, *args, **kwargs): | ||||||
|  |         ''' | ||||||
|  | 
 | ||||||
|  |         Arguments: | ||||||
|  |             user (User): The user whose charges we should filter to. | ||||||
|  |             min_value (Decimal): The minimum value of the charges we should | ||||||
|  |                 show (currently, credit notes can only be cashed out in full.) | ||||||
|  | 
 | ||||||
|  |         ''' | ||||||
|  |         user = kwargs.pop('user', None) | ||||||
|  |         min_value = kwargs.pop('min_value', None) | ||||||
|  |         super(StripeRefundForm, self).__init__(*args, **kwargs) | ||||||
|  | 
 | ||||||
|  |         payment_field = self.fields['payment'] | ||||||
|  |         qs = payment_field.queryset | ||||||
|  | 
 | ||||||
|  |         if user: | ||||||
|  |             qs = qs.filter( | ||||||
|  |                 charge__customer__user=user, | ||||||
|  |             ) | ||||||
|  | 
 | ||||||
|  |         if min_value is not None: | ||||||
|  |             # amount >= amount_to_refund + amount_refunded | ||||||
|  |             # No refunds yet | ||||||
|  |             q1 = ( | ||||||
|  |                 Q(charge__amount_refunded__isnull=True) & | ||||||
|  |                 Q(charge__amount__gte=min_value) | ||||||
|  |             ) | ||||||
|  |             # There are some refunds | ||||||
|  |             q2 = ( | ||||||
|  |                 Q(charge__amount_refunded__isnull=False) & | ||||||
|  |                 Q(charge__amount__gte=( | ||||||
|  |                     F("charge__amount_refunded") + min_value) | ||||||
|  |                 ) | ||||||
|  |             ) | ||||||
|  |             qs = qs.filter(q1 | q2) | ||||||
|  | 
 | ||||||
|  |         payment_field.queryset = qs | ||||||
|  | 
 | ||||||
|  |     payment = forms.ModelChoiceField( | ||||||
|  |         required=True, | ||||||
|  |         queryset=models.StripePayment.objects.all(), | ||||||
|  |     ) | ||||||
|  | @ -9,7 +9,6 @@ class StripePayment(commerce.PaymentBase): | ||||||
| 
 | 
 | ||||||
|     charge = models.ForeignKey(Charge) |     charge = models.ForeignKey(Charge) | ||||||
| 
 | 
 | ||||||
| 
 |  | ||||||
| class StripeCreditNoteRefund(commerce.CreditNoteRefund): | class StripeCreditNoteRefund(commerce.CreditNoteRefund): | ||||||
| 
 | 
 | ||||||
|     charge = models.ForeignKey(Charge) |     charge = models.ForeignKey(Charge) | ||||||
							
								
								
									
										13
									
								
								vendor/registripe/registripe/templates/registrasion/stripe/credit_card_payment.html
									
										
									
									
										vendored
									
									
										Normal file
									
								
							
							
						
						
									
										13
									
								
								vendor/registripe/registripe/templates/registrasion/stripe/credit_card_payment.html
									
										
									
									
										vendored
									
									
										Normal file
									
								
							|  | @ -0,0 +1,13 @@ | ||||||
|  | {% extends "registrasion/stripe/credit_card_payment_.html" %} | ||||||
|  | 
 | ||||||
|  | {% comment %} | ||||||
|  |   Blocks that you can override: | ||||||
|  | 
 | ||||||
|  |   - balance_due | ||||||
|  | 
 | ||||||
|  |   You MUST include the following in your template: | ||||||
|  |   - {{ form.media.js }} | ||||||
|  |   - the payment form, where the form's id="payent-form" | ||||||
|  |   - there is a div with id="payment-errors" | ||||||
|  | 
 | ||||||
|  | {% endcomment %} | ||||||
							
								
								
									
										55
									
								
								vendor/registripe/registripe/templates/registrasion/stripe/credit_card_payment_.html
									
										
									
									
										vendored
									
									
										Normal file
									
								
							
							
						
						
									
										55
									
								
								vendor/registripe/registripe/templates/registrasion/stripe/credit_card_payment_.html
									
										
									
									
										vendored
									
									
										Normal file
									
								
							|  | @ -0,0 +1,55 @@ | ||||||
|  | {% extends "registrasion/base.html" %} | ||||||
|  | {% load registrasion_tags %} | ||||||
|  | 
 | ||||||
|  | {% block title %}Credit card payment for invoice #{{ invoice.id}}{% endblock %} | ||||||
|  | {% block heading %}Credit card payment for invoice #{{ invoice.id}}{% endblock %} | ||||||
|  | {% block lede %} | ||||||
|  |   Credit card payments are processed by <a href="https://stripe.com">Stripe</a>. | ||||||
|  |   We do not store any of your credit card data locally, but instead Stripe will securely tokenise your card details. To allow this, you must allow JavaScript from <code>js.stripe.com</code>. | ||||||
|  | {% endblock %} | ||||||
|  | 
 | ||||||
|  | {% block content %} | ||||||
|  | 
 | ||||||
|  |   {% block balance_due_outer %} | ||||||
|  |     <div class="alert alert-info"> | ||||||
|  |       <p> | ||||||
|  |         {% block balance_due %} | ||||||
|  |           You have ${{ invoice.balance_due }} remaining to pay on this invoice. | ||||||
|  |         {% endblock %} | ||||||
|  |       </p> | ||||||
|  |     </div> | ||||||
|  |   {% endblock %} | ||||||
|  | 
 | ||||||
|  |   <div class="panel panel-primary"> | ||||||
|  |     <div class="panel-heading"> | ||||||
|  |       <h3 class="panel-title">Card details</h3> | ||||||
|  |     </div> | ||||||
|  |     <form id="payment-form" method="post"> | ||||||
|  | 
 | ||||||
|  |       <div class="panel-body"> | ||||||
|  |         {% csrf_token %} | ||||||
|  |         {% include "registrasion/form.html" %} | ||||||
|  |       </div> | ||||||
|  | 
 | ||||||
|  |       <div class="panel-footer"> | ||||||
|  |         <input id="pay" class="btn btn-primary" type="submit" value="Pay {{ invoice.balance_due }}" /> | ||||||
|  |         <a class="btn btn-default" href='{% url "invoice" invoice.id invoice.user.attendee.access_code %}'>Return to invoice</a> | ||||||
|  |       </div> | ||||||
|  | 
 | ||||||
|  |     </form> | ||||||
|  |   </div> | ||||||
|  | 
 | ||||||
|  |   {% block form_scripts %} | ||||||
|  |     {% block add_form_control_class_script %} | ||||||
|  |       <script> | ||||||
|  |         elements = document.getElementsByClassName("registrasion-stripe-element"); | ||||||
|  |         Array.prototype.forEach.call(elements, function(element) { | ||||||
|  |           element.setAttribute("class", "{% block form_control_class %}form-control{% endblock %}"); | ||||||
|  |         }); | ||||||
|  |       </script> | ||||||
|  |     {% endblock %} | ||||||
|  | 
 | ||||||
|  |     {{ form.media.js }} | ||||||
|  |   {% endblock %} | ||||||
|  | 
 | ||||||
|  | {% endblock %} | ||||||
							
								
								
									
										68
									
								
								vendor/registripe/registripe/templates/registrasion/stripe/js/form_handler.js
									
										
									
									
										vendored
									
									
										Normal file
									
								
							
							
						
						
									
										68
									
								
								vendor/registripe/registripe/templates/registrasion/stripe/js/form_handler.js
									
										
									
									
										vendored
									
									
										Normal file
									
								
							|  | @ -0,0 +1,68 @@ | ||||||
|  | var stripe = Stripe('{{ PINAX_STRIPE_PUBLIC_KEY }}'); | ||||||
|  | var elements = stripe.elements(); | ||||||
|  | 
 | ||||||
|  | function stripeify(elementId) { | ||||||
|  |   var element = elements.create(elementId); | ||||||
|  |   element.mount('#' + elementId); | ||||||
|  | 
 | ||||||
|  |   var htmlElement = document.getElementById(elementId); | ||||||
|  |   var errors = elementId + "-errors"; | ||||||
|  |   htmlElement.insertAdjacentHTML("afterend", "<div id='" + errors + "' role='alert' class='help-block'></div>"); | ||||||
|  |   var displayError = document.getElementById(errors); | ||||||
|  | 
 | ||||||
|  |   //Handle real-time validation errors from the card Element.
 | ||||||
|  |   element.addEventListener('change', function(event) { | ||||||
|  |     toggleErrorMessage(displayError, event.error); | ||||||
|  |   }); | ||||||
|  | 
 | ||||||
|  |   // Create a token or display an error when the form is submitted.
 | ||||||
|  |   var paymentForm = document.getElementById('payment-form'); | ||||||
|  |   paymentForm.addEventListener('submit', function(event) { | ||||||
|  |     event.preventDefault(); | ||||||
|  | 
 | ||||||
|  |     stripe.createToken(element).then(function(result) { | ||||||
|  |       if (result.error) { | ||||||
|  |         // Inform the user if there was an error
 | ||||||
|  |         toggleErrorMessage(displayError, result.error); | ||||||
|  |       } else { | ||||||
|  |         // Send the token to your server
 | ||||||
|  |         stripeTokenHandler(result.token); | ||||||
|  |       } | ||||||
|  |     }); | ||||||
|  |   }); | ||||||
|  | } | ||||||
|  | 
 | ||||||
|  | function toggleErrorMessage(errorElement, maybeError) { | ||||||
|  |   errorClass = inputErrorClassName(); | ||||||
|  |   if (maybeError) { | ||||||
|  |     errorElement.textContent = maybeError.message; | ||||||
|  |     errorElement.parentNode.classList.add(errorClass); | ||||||
|  |   } else { | ||||||
|  |     errorElement.textContent = ''; | ||||||
|  |     errorElement.parentNode.classList.remove(errorClass); | ||||||
|  |   } | ||||||
|  | } | ||||||
|  | 
 | ||||||
|  | 
 | ||||||
|  | function inputErrorClassName() { | ||||||
|  |   return {% block form_control_error_class %}"has-error"{% endblock %}; | ||||||
|  | } | ||||||
|  | 
 | ||||||
|  | 
 | ||||||
|  | function stripeTokenHandler(token) { | ||||||
|  |   // Insert the token ID into the form so it gets submitted to the server
 | ||||||
|  | 
 | ||||||
|  |   var form = document.getElementById('payment-form'); | ||||||
|  |   tokenHolder = form.getElementsByClassName('registrasion-stripe-token')[0]; | ||||||
|  |   inputId = tokenHolder.dataset.inputId; | ||||||
|  | 
 | ||||||
|  |   var hiddenInput = document.createElement('input'); | ||||||
|  |   hiddenInput.setAttribute('type', 'hidden'); | ||||||
|  |   hiddenInput.setAttribute('name', inputId); | ||||||
|  |   hiddenInput.setAttribute('value', token.id); | ||||||
|  | 
 | ||||||
|  |   tokenHolder.appendChild(hiddenInput); | ||||||
|  | 
 | ||||||
|  |   // Submit the form
 | ||||||
|  |   form.submit(); | ||||||
|  | } | ||||||
							
								
								
									
										6
									
								
								vendor/registripe/registripe/templates/registrasion/stripe/link_to_payment.html
									
										
									
									
										vendored
									
									
										Normal file
									
								
							
							
						
						
									
										6
									
								
								vendor/registripe/registripe/templates/registrasion/stripe/link_to_payment.html
									
										
									
									
										vendored
									
									
										Normal file
									
								
							|  | @ -0,0 +1,6 @@ | ||||||
|  | {% extends "registrasion/stripe/link_to_payment_.html" %} | ||||||
|  | 
 | ||||||
|  | {% comment %} | ||||||
|  |   Blocks that you can override: | ||||||
|  | 
 | ||||||
|  | {% endcomment %} | ||||||
							
								
								
									
										7
									
								
								vendor/registripe/registripe/templates/registrasion/stripe/link_to_payment_.html
									
										
									
									
										vendored
									
									
										Normal file
									
								
							
							
						
						
									
										7
									
								
								vendor/registripe/registripe/templates/registrasion/stripe/link_to_payment_.html
									
										
									
									
										vendored
									
									
										Normal file
									
								
							|  | @ -0,0 +1,7 @@ | ||||||
|  | {% comment %} | ||||||
|  |   This is used in the default credit_note.html file to display Stripe funcationality if the app is loaded. | ||||||
|  | {% endcomment %} | ||||||
|  | 
 | ||||||
|  | {% block content %} | ||||||
|  |   <a class="btn btn-primary" href='{% url "registripe_card" invoice_id access_code %}'>Pay this invoice with Stripe</a> | ||||||
|  | {% endblock %} | ||||||
							
								
								
									
										6
									
								
								vendor/registripe/registripe/templates/registrasion/stripe/link_to_refunds.html
									
										
									
									
										vendored
									
									
										Normal file
									
								
							
							
						
						
									
										6
									
								
								vendor/registripe/registripe/templates/registrasion/stripe/link_to_refunds.html
									
										
									
									
										vendored
									
									
										Normal file
									
								
							|  | @ -0,0 +1,6 @@ | ||||||
|  | {% extends "registrasion/stripe/link_to_refunds_.html" %} | ||||||
|  | 
 | ||||||
|  | {% comment %} | ||||||
|  |   Blocks that you can override: | ||||||
|  | 
 | ||||||
|  | {% endcomment %} | ||||||
							
								
								
									
										9
									
								
								vendor/registripe/registripe/templates/registrasion/stripe/link_to_refunds_.html
									
										
									
									
										vendored
									
									
										Normal file
									
								
							
							
						
						
									
										9
									
								
								vendor/registripe/registripe/templates/registrasion/stripe/link_to_refunds_.html
									
										
									
									
										vendored
									
									
										Normal file
									
								
							|  | @ -0,0 +1,9 @@ | ||||||
|  | {% comment %} | ||||||
|  |   This is used in the default invoice.html file to display Stripe funcationality if the app is loaded. | ||||||
|  | {% endcomment %} | ||||||
|  | 
 | ||||||
|  | {% block content %} | ||||||
|  |   <h3>Stripe Refund</h3> | ||||||
|  | 
 | ||||||
|  |   <p><a href="{% url 'registripe_refund' credit_note_id %}">View Stripe refund options</a></p> | ||||||
|  | {% endblock %} | ||||||
							
								
								
									
										6
									
								
								vendor/registripe/registripe/templates/registrasion/stripe/refund.html
									
										
									
									
										vendored
									
									
										Normal file
									
								
							
							
						
						
									
										6
									
								
								vendor/registripe/registripe/templates/registrasion/stripe/refund.html
									
										
									
									
										vendored
									
									
										Normal file
									
								
							|  | @ -0,0 +1,6 @@ | ||||||
|  | {% extends "registrasion/stripe/refund_.html" %} | ||||||
|  | 
 | ||||||
|  | {% comment %} | ||||||
|  |   Blocks that you can override: | ||||||
|  | 
 | ||||||
|  | {% endcomment %} | ||||||
							
								
								
									
										24
									
								
								vendor/registripe/registripe/templates/registrasion/stripe/refund_.html
									
										
									
									
										vendored
									
									
										Normal file
									
								
							
							
						
						
									
										24
									
								
								vendor/registripe/registripe/templates/registrasion/stripe/refund_.html
									
										
									
									
										vendored
									
									
										Normal file
									
								
							|  | @ -0,0 +1,24 @@ | ||||||
|  | {% extends "registrasion/base.html" %} | ||||||
|  | {% load registrasion_tags %} | ||||||
|  | 
 | ||||||
|  | {% block title %}Stripe refunds for credit note #{{ credit_note.id}}{% endblock %} | ||||||
|  | {% block heading %}Stripe refunds for credit note #{{ credit_note.id}}{% endblock %} | ||||||
|  | {% block lede %} | ||||||
|  |   Currently credit notes can only be cashed out in full in a single | ||||||
|  |   transaction. If you need to cash out to multiple small payments, you will | ||||||
|  |   need to manually invoke the refunds from the Stripe Dashboard. | ||||||
|  | {% endblock %} | ||||||
|  | 
 | ||||||
|  | 
 | ||||||
|  | {% block content %} | ||||||
|  | 
 | ||||||
|  |   <p>This credit note is valued at ${{ credit_note.value }}.</p> | ||||||
|  | 
 | ||||||
|  |   <h3>Available refunds</h3> | ||||||
|  | 
 | ||||||
|  |   <form method="post"> | ||||||
|  |     {% csrf_token %} | ||||||
|  |     {% include "registrasion/form.html" %} | ||||||
|  |     <input id="submit" class="btn btn-primary" type="submit" value="Refund {{ credit_note.value }} to payment source" /> | ||||||
|  |   </form> | ||||||
|  | {% endblock %} | ||||||
							
								
								
									
										3
									
								
								vendor/registripe/registripe/tests.py
									
										
									
									
										vendored
									
									
										Normal file
									
								
							
							
						
						
									
										3
									
								
								vendor/registripe/registripe/tests.py
									
										
									
									
										vendored
									
									
										Normal file
									
								
							|  | @ -0,0 +1,3 @@ | ||||||
|  | from django.test import TestCase | ||||||
|  | 
 | ||||||
|  | # Create your tests here. | ||||||
|  | @ -7,9 +7,8 @@ from pinax.stripe.views import Webhook | ||||||
| 
 | 
 | ||||||
| urlpatterns = [ | urlpatterns = [ | ||||||
|     url(r"^card/([0-9]*)/$", views.card, name="registripe_card"), |     url(r"^card/([0-9]*)/$", views.card, name="registripe_card"), | ||||||
|     url(r"^card/([0-9]*)/([0-9A-Za-z]*)/$", views.card, |     url(r"^card/([0-9]*)/([0-9A-Za-z]*)/$", views.card, name="registripe_card"), | ||||||
|         name="registripe_card"), |     url(r"^form_handler.js", views.form_handler, name="registripe_form_handler"), | ||||||
|     url(r"^pubkey/$", views.pubkey_script, name="registripe_pubkey"), |  | ||||||
|     url(r"^refund/([0-9]*)/$", views.refund, name="registripe_refund"), |     url(r"^refund/([0-9]*)/$", views.refund, name="registripe_refund"), | ||||||
|     url(r"^webhook/$", Webhook.as_view(), name="pinax_stripe_webhook"), |     url(r"^webhook/$", Webhook.as_view(), name="pinax_stripe_webhook"), | ||||||
| ] | ] | ||||||
|  | @ -1,5 +1,7 @@ | ||||||
| from registripe import forms | from registripe import forms | ||||||
| from registripe import models | from registripe import models | ||||||
|  | import forms | ||||||
|  | import models | ||||||
| 
 | 
 | ||||||
| from django.core.exceptions import ValidationError | from django.core.exceptions import ValidationError | ||||||
| from django.conf import settings | from django.conf import settings | ||||||
|  | @ -14,6 +16,8 @@ from registrasion.controllers.credit_note import CreditNoteController | ||||||
| from registrasion.controllers.invoice import InvoiceController | from registrasion.controllers.invoice import InvoiceController | ||||||
| 
 | 
 | ||||||
| from pinax.stripe import actions | from pinax.stripe import actions | ||||||
|  | from pinax.stripe.actions import refunds as pinax_stripe_actions_refunds | ||||||
|  | from registrasion.models import commerce | ||||||
| 
 | 
 | ||||||
| from stripe.error import StripeError | from stripe.error import StripeError | ||||||
| 
 | 
 | ||||||
|  | @ -28,8 +32,19 @@ def _staff_only(user): | ||||||
|     return user.is_staff |     return user.is_staff | ||||||
| 
 | 
 | ||||||
| 
 | 
 | ||||||
| def pubkey_script(request): | def form_handler(request): | ||||||
|     ''' Returns a JS snippet that sets the Stripe public key for Stripe.js. ''' |     ''' Renders a js file to process Stripe payments. ''' | ||||||
|  | 
 | ||||||
|  |     data = { | ||||||
|  |         "PINAX_STRIPE_PUBLIC_KEY": settings.PINAX_STRIPE_PUBLIC_KEY, | ||||||
|  |     } | ||||||
|  | 
 | ||||||
|  |     return render( | ||||||
|  |         request, | ||||||
|  |         "registrasion/stripe/js/form_handler.js", | ||||||
|  |         data, | ||||||
|  |         content_type="text/javascript", | ||||||
|  |     ) | ||||||
| 
 | 
 | ||||||
|     script_template = "Stripe.setPublishableKey('%s');" |     script_template = "Stripe.setPublishableKey('%s');" | ||||||
|     script = script_template % settings.PINAX_STRIPE_PUBLIC_KEY |     script = script_template % settings.PINAX_STRIPE_PUBLIC_KEY | ||||||
|  | @ -65,7 +80,7 @@ def card(request, invoice_id, access_code=None): | ||||||
| 
 | 
 | ||||||
|     if request.POST and form.is_valid(): |     if request.POST and form.is_valid(): | ||||||
|         try: |         try: | ||||||
|             inv.validate_allowed_to_pay() |             inv.validate_allowed_to_pay()  # Verify that we're allowed to do this. | ||||||
|             process_card(request, form, inv) |             process_card(request, form, inv) | ||||||
|             return to_invoice |             return to_invoice | ||||||
|         except StripeError as e: |         except StripeError as e: | ||||||
|  | @ -185,7 +200,7 @@ def process_refund(cn, form): | ||||||
|             "the credit note." |             "the credit note." | ||||||
|         ) |         ) | ||||||
| 
 | 
 | ||||||
|     refund = actions.refunds.create(charge, to_refund) # noqa |     refund = actions.refunds.create(charge, to_refund) | ||||||
| 
 | 
 | ||||||
|     models.StripeCreditNoteRefund.objects.create( |     models.StripeCreditNoteRefund.objects.create( | ||||||
|         parent=cn.credit_note, |         parent=cn.credit_note, | ||||||
							
								
								
									
										4
									
								
								vendor/registripe/requirements.txt
									
										
									
									
										vendored
									
									
										Normal file
									
								
							
							
						
						
									
										4
									
								
								vendor/registripe/requirements.txt
									
										
									
									
										vendored
									
									
										Normal file
									
								
							|  | @ -0,0 +1,4 @@ | ||||||
|  | django-countries==4.0 | ||||||
|  | pinax-stripe==3.2.1 | ||||||
|  | requests>=2.11.1 | ||||||
|  | stripe==1.38.0 | ||||||
							
								
								
									
										35
									
								
								vendor/registripe/setup.py
									
										
									
									
										vendored
									
									
										Normal file
									
								
							
							
						
						
									
										35
									
								
								vendor/registripe/setup.py
									
										
									
									
										vendored
									
									
										Normal file
									
								
							|  | @ -0,0 +1,35 @@ | ||||||
|  | #!/usr/bin/env python | ||||||
|  | import os | ||||||
|  | from setuptools import setup, find_packages | ||||||
|  | 
 | ||||||
|  | import registripe | ||||||
|  | 
 | ||||||
|  | 
 | ||||||
|  | def read_file(filename): | ||||||
|  |     """Read a file into a string.""" | ||||||
|  |     path = os.path.abspath(os.path.dirname(__file__)) | ||||||
|  |     filepath = os.path.join(path, filename) | ||||||
|  |     try: | ||||||
|  |         return open(filepath).read() | ||||||
|  |     except IOError: | ||||||
|  |         return '' | ||||||
|  | 
 | ||||||
|  | setup( | ||||||
|  |     name="registrasion-stripe", | ||||||
|  |     author="Christopher Neugebauer", | ||||||
|  |     author_email="_@chrisjrn.com", | ||||||
|  |     version=registripe.__version__, | ||||||
|  |     description="Stripe-based payments for the Registrasion conference registration package.", | ||||||
|  |     url="http://github.com/chrisjrn/registrasion-stripe/", | ||||||
|  |     packages=find_packages(), | ||||||
|  |     include_package_data=True, | ||||||
|  |     classifiers=( | ||||||
|  |         "Development Status :: 3 - Alpha", | ||||||
|  |         "Programming Language :: Python", | ||||||
|  |         "Framework :: Django", | ||||||
|  |         "Intended Audience :: Developers", | ||||||
|  |         "Natural Language :: English", | ||||||
|  |         "License :: OSI Approved :: Apache Software License", | ||||||
|  |     ), | ||||||
|  |     install_requires=read_file("requirements.txt").splitlines(), | ||||||
|  | ) | ||||||
|  | @ -1 +1,2 @@ | ||||||
| vendor/registrasion | vendor/registrasion | ||||||
|  | vendor/registripe | ||||||
|  |  | ||||||
		Loading…
	
	Add table
		
		Reference in a new issue
	
	 James Polley
						James Polley