Пример #1
0
    def account_billing(self, request):
        if request.method == 'POST':
            form = BillingAddressForm(request.POST)
        else:
            form = BillingAddressForm()

        form.configure(request)

        if form.is_valid():
            data = form.cleaned_data

            request.user.first_name = data.get('first_name')
            request.user.last_name = data.get('last_name')
            request.user.save()

            profile = get_customer_model().objects.get(user=request.user)
            profile.title       = data.get('title')
            profile.company     = data.get('company')
            profile.address1    = data.get('address1')
            profile.address2    = data.get('address2')
            profile.address3    = data.get('address3')
            profile.city        = data.get('city')
            profile.county      = data.get('county')
            profile.postcode    = data.get('postcode')
            profile.country     = data.get('country')

            profile.save()

            messages.success(request, 'Your delivery address has been changed.')
            return HttpResponseRedirect(reverse('shop.account.index'))

        return {
            'account_section': True,
            'form': form
        }
Пример #2
0
    def account_details(self, request):
        if request.method == 'POST':
            form = ChangeDetailsForm(request.POST)
        else:
            form = ChangeDetailsForm()

        form.configure(request)

        if form.is_valid():
            data = form.cleaned_data

            u = request.user
            p = get_customer_model().objects.get(user=u)

            if request.settings.mailchimp_enabled:
                # subscription details
                ms = MailSnake(request.settings.mailchimp_api)
                person_name = [data.get('first_name'), data.get('last_name')]
                merge_vars = {'FNAME': ' '.join(person_name)}

                # unsubscribe if email changed or we no longer want to be subscribed
                if 'email_address' in form.changed_data or ('newsletter' in form.changed_data and not data.get('newsletter')):
                    try:
                        ms.listUnsubscribe(id=request.settings.mailchimp_list_id, email_address=u.email)
                    except:
                        pass

                # subscribe if newsletter subscription changed or email was changed
                if ('email_address' in form.changed_data or 'newsletter' in form.changed_data) and data.get('newsletter'):
                    try:
                        ms.listSubscribe(id=request.settings.mailchimp_list_id, email_address=data.get('email_address'), merge_vars=merge_vars)
                    except:
                        pass

                # update newletter state in profile
                p.newsletter = data.get('newsletter')

            # update personal details on user record
            u.first_name = data.get('first_name')
            u.last_name = data.get('last_name')
            u.email = data.get('email_address')
            u.save()

            # update personal details on profile record
            p.title = data.get('title')
            p.first_name = data.get('first_name')
            p.last_name = data.get('last_name')
            p.telephone = data.get('phone')
            p.email = data.get('email_address')
            p.save()

            # success message and redirect to dashboard
            messages.success(request, 'Your details have been changed.')
            return HttpResponseRedirect(reverse('shop.account.index'))


        return {
            'account_section': True,
            'form': form
        }
Пример #3
0
    def clean_email_address(self):
        email = self.cleaned_data['email_address']

        if 'email_address' in self.changed_data:
            if get_customer_model().objects.filter(email=email).count(
            ) > 0 or get_user_model().objects.filter(email=email).count() > 0:
                raise forms.ValidationError(
                    'An account with the given email address already exists.')
        return email
Пример #4
0
        def _wrapped_view(request, *args, **kwargs):
            # authenticated users are free to continue
            if request.user.is_authenticated():
                if get_customer_model().objects.filter(
                        user=request.user).count() == 1:
                    return view_func(request, *args, **kwargs)

            # otherwise we redirect to checkout login page
            return HttpResponseRedirect(reverse('shop.account.login'))
Пример #5
0
    def clean_email(self):
        """
        Make sure that the email is not taken if the user checked signup.
        """
        signup = self.cleaned_data.get('signup', False)
        email = self.cleaned_data.get('email', None)

        if signup == True:
            if get_customer_model().objects.filter(email=email).count() > 0:
                raise forms.ValidationError(
                    'Email address already used. Please provide a different email address for signing up for a new account.'
                )

        return email
Пример #6
0
    def account_index(self, request):
        profile = get_customer_model().objects.get(user=request.user)
        orders = get_order_model().objects.get_processing_orders(user=request.user)[:3]
        try:
            address = request.user.delivery_addresses.all()[0]
        except IndexError:
            address = None

        return {
            'account_section': True,
            'profile': profile,
            'orders': orders,
            'address': address
        }
Пример #7
0
    def configure(self, request):
        self._request = request
        u = self._request.user
        p = get_customer_model().objects.get(user=u)

        self.fields['first_name'].initial = u.first_name
        self.fields['last_name'].initial = u.last_name
        self.fields['email_address'].initial = u.email

        self.fields['title'].initial = p.title
        self.fields['phone'].initial = p.telephone
        self.fields['newsletter'].initial = p.newsletter

        if not request.settings.mailchimp_enabled:
            self.remove_field('newsletter')
Пример #8
0
    def configure(self, request):
        self._request = request
        u = self._request.user
        p = get_customer_model().objects.get(user=u)

        self.fields['first_name'].initial = u.first_name
        self.fields['last_name'].initial = u.last_name
        self.fields['title'].initial = p.title
        self.fields['company'].initial = p.company

        self.fields['address1'].initial = p.address1
        self.fields['address2'].initial = p.address2
        self.fields['address3'].initial = p.address3
        self.fields['city'].initial = p.city
        self.fields['county'].initial = p.county
        self.fields['postcode'].initial = p.postcode
        self.fields['country'].initial = p.country

        if 'cubane.postcode' not in settings.INSTALLED_APPS:
            self.remove_field('postcode_lookup')
Пример #9
0
        def _wrapped_view(request, *args, **kwargs):
            # authenticated users are free to continue
            if request.user.is_authenticated():
                if get_customer_model().objects.filter(
                        user_id=request.user.id).count() == 1:
                    return view_func(request, *args, **kwargs)

            # Do we provide guest checkout?
            if request.settings.guest_checkout:
                # AnonymousUser need to provide an email
                if request.user.is_anonymous():
                    if request.session.get(settings.GUEST_USER_SESSION_VAR,
                                           None) != None:
                        return view_func(request, *args, **kwargs)

                # otherwise we redirect to checkout login page
                return HttpResponseRedirect(reverse('shop.order.login'))
            else:
                # No guest checkout -> Go to account registration/login
                return HttpResponseRedirect(
                    reverse('shop.account.login') + '?checkout=1')
Пример #10
0
def complete(request):
    """
    (3) Final checkout step, where the order is actually created from the basket.
    """
    basket = Basket(request)

    # redirect back to a previous step if we missed anything...
    next = get_next_checkout_step(request, basket, CurrentPage.COMPLETE())
    if next:
        return HttpResponseRedirect(next)

    # state or county
    if 'state' in basket.billing_address:
        county = basket.billing_address.get('state')
    else:
        county = basket.billing_address.get('county')

    # create account if requested
    if basket.signup:
        # create user account
        md5 = hashlib.md5()
        md5.update(basket.signup.get('email'))
        email = basket.signup.get('email')

        if User.objects.filter(email=email).count() > 0:
            messages.warning(
                request,
                'There is already an account with this email: %s.' % email)
            return HttpResponseRedirect(reverse('shop.account.login'))
        user = User.objects.create(username=md5.hexdigest()[:30],
                                   first_name=basket.signup.get('first_name'),
                                   last_name=basket.signup.get('last_name'),
                                   email=email)

        # replace username with user id and set password
        user.username = unicode(user.id)
        user.set_password(basket.signup.get('password'))
        user.save()

        # create profile
        get_customer_model().objects.create(
            user=user,
            first_name=user.first_name,
            last_name=user.last_name,
            email=user.email,
            title=basket.billing_address.get('title'),
            address1=basket.billing_address.get('address1'),
            address2=basket.billing_address.get('address2'),
            address3=basket.billing_address.get('address3'),
            city=basket.billing_address.get('city'),
            county=county,
            postcode=basket.billing_address.get('postcode'),
            country=basket.billing_address.get('country'),
            telephone=basket.billing_address.get('telephone'),
            newsletter=basket.newsletter)

        # log user in
        login_user_without_password(request, user)
        basket.signup = None
    else:
        if request.user.is_anonymous():
            user = None
        else:
            user = request.user

        # if specified, copy relevant information to customer's profile
        if user != None and basket.update_profile:
            user.first_name = basket.billing_address.get('first_name')
            user.last_name = basket.billing_address.get('last_name')
            user.save()

            customer = get_customer_model().objects.get(user=user)
            customer.address1 = basket.billing_address.get('address1')
            customer.address2 = basket.billing_address.get('address2')
            customer.address3 = basket.billing_address.get('address3')
            customer.city = basket.billing_address.get('city')
            customer.county = county
            customer.postcode = basket.billing_address.get('postcode')
            customer.country = basket.billing_address.get('country')
            customer.telephone = basket.billing_address.get('telephone')
            customer.save()

    # create single order
    order = get_order_model().create_from_basket(request, basket, user)

    # mailchimp
    if request.settings.mailchimp_enabled and basket.newsletter:
        email = basket.billing_address.get('email')
        first_name = basket.billing_address.get('first_name')
        last_name = basket.billing_address.get('last_name')
        person_name = (first_name, last_name)
        merge_vars = {'FNAME': " ".join(person_name)}
        ms = MailSnake(request.settings.mailchimp_api)
        try:
            ms.listSubscribe(id=request.settings.mailchimp_list_id,
                             email_address=email,
                             merge_vars=merge_vars)
        except:
            pass

    # redirect to order status page (payment from there...)
    basket.save()
    return HttpResponseRedirect(
        reverse('shop.order.status', args=[order.secret_id]))
Пример #11
0
class ChangeDetailsForm(BaseForm):
    _name = SectionField(
        label='Personal Details',
        help_text='These details are also used on your delivery address')

    title = forms.ChoiceField(required=True,
                              choices=get_customer_model().TITLE_CHOICES)

    first_name = forms.CharField(label='First Name',
                                 max_length=30,
                                 required=True,
                                 widget=forms.TextInput(attrs={
                                     'size': '40',
                                     'class': 'text'
                                 }))

    last_name = forms.CharField(label='Last Name',
                                max_length=30,
                                required=True,
                                widget=forms.TextInput(attrs={
                                    'size': '40',
                                    'class': 'text'
                                }))

    phone = forms.CharField(
        label='Phone',
        max_length=40,
        required=True,
        help_text='We may give you a call regarding your order if required.')

    email_address = forms.EmailField(
        label='Email',
        help_text='This E-mail address is also your username for this website',
        widget=EmailInput)

    newsletter = forms.BooleanField(
        label='',
        required=False,
        initial=False,
        help_text='Yes, subscribe me to the newsletter.')

    def configure(self, request):
        self._request = request
        u = self._request.user
        p = get_customer_model().objects.get(user=u)

        self.fields['first_name'].initial = u.first_name
        self.fields['last_name'].initial = u.last_name
        self.fields['email_address'].initial = u.email

        self.fields['title'].initial = p.title
        self.fields['phone'].initial = p.telephone
        self.fields['newsletter'].initial = p.newsletter

        if not request.settings.mailchimp_enabled:
            self.remove_field('newsletter')

    def clean(self):
        d = super(ChangeDetailsForm, self).clean()
        return clean_address(self, d)

    def clean_email_address(self):
        email = self.cleaned_data['email_address']

        if 'email_address' in self.changed_data:
            if get_customer_model().objects.filter(email=email).count(
            ) > 0 or get_user_model().objects.filter(email=email).count() > 0:
                raise forms.ValidationError(
                    'An account with the given email address already exists.')
        return email
Пример #12
0
 def clean_email(self):
     email = self.cleaned_data['email']
     # check customer and admin
     if get_customer_model().objects.filter(email=email).count() > 0 or get_user_model().objects.filter(email=email).count() > 0:
         raise forms.ValidationError('An account with the given email address already exists. If you forgot your password, please use the password forgotten function.')
     return email
Пример #13
0
class SignupForm(BaseForm):
    __name = SectionField(label='Your Name')

    title = forms.ChoiceField(
        required=True,
        choices=get_customer_model().TITLE_CHOICES
    )

    first_name = forms.CharField(
        label='First Name',
        max_length=30,
        required=True,
        widget=forms.TextInput(attrs={'size':'40', 'class': 'text'})
    )

    last_name = forms.CharField(
        label='Last Name',
        max_length=30,
        required=True,
        widget=forms.TextInput(attrs={'size':'40', 'class': 'text'})
    )

    country = forms.ModelChoiceField(
        required=True,
        empty_label=None,
        initial='GB',
        queryset=Country.objects.all()
    )

    __account = SectionField(label='Account Name and Password')

    email = forms.EmailField(
        label='Email', max_length=255,
        required=True,
        help_text='This E-mail address is also your username for this website',
        widget=EmailInput
    )

    password = forms.CharField(
        label='Password',
        #min_length=6,
        max_length=255,
        required=True,
        help_text='Your password must be at least 6 characters in length.',
        widget=forms.PasswordInput(render_value=True)
    )

    password_confirm = forms.CharField(
        label='Confirm Password',
        min_length=6,
        max_length=255,
        required=True,
        help_text='Confirm your password.',
        widget=forms.PasswordInput(render_value=True)
    )

    _newsletter = SectionField(label='Newsletter (Optional)')

    newsletter = forms.BooleanField(
        label='',
        required=False,
        initial=False,
        help_text='Yes, subscribe me to the newsletter.'
    )

    # init the captchas
    captcha = captchas.get_captcha_widget() if settings.CAPTCHA else None
    captcha_hash = forms.CharField(max_length=255, widget=forms.HiddenInput, required=False) if hasattr(settings, 'CAPTCHA') and not hasattr(settings, 'CAPTCHA_SECRET_KEY') else None

    checkout = forms.BooleanField(required=False, initial=False, widget=forms.HiddenInput)


    def clean(self):
        d = super(SignupForm, self).clean()

        # clean captcha
        if not hasattr(settings, 'CAPTCHA_SECRET_KEY') and hasattr(settings, 'CAPTCHA'):
            captchas.clean_captcha_data(d, self)

        return d


    def configure(self, request):
        self._request = request

        if not self._request.settings.mailchimp_enabled:
            self.remove_field('newsletter')


    def clean_email(self):
        email = self.cleaned_data['email']
        # check customer and admin
        if get_customer_model().objects.filter(email=email).count() > 0 or get_user_model().objects.filter(email=email).count() > 0:
            raise forms.ValidationError('An account with the given email address already exists. If you forgot your password, please use the password forgotten function.')
        return email


    def clean_password_confirm(self):
        """
        Password confirm must match password.
        """
        password = self.cleaned_data.get('password', None)
        password_confirm = self.cleaned_data.get('password_confirm', None)

        if password != password_confirm:
            raise forms.ValidationError('Password confirmation is required to match password.')

        return password_confirm
Пример #14
0
    def configure(self, request, basket):
        self._request = request
        self._basket = basket

        fields_list = [
            'email', 'signup', 'password', 'password_confirm', 'survey'
        ]

        if request.settings.has_survey:
            self.fields['survey'].choices = [('', '-------')] + [
                (o, o) for o in request.settings.get_survey_options()
            ]
        else:
            del self.fields['survey']

        if not request.settings.mailchimp_enabled:
            del self.fields['newsletter']

        # finance option
        self.fields[
            'finance_option'].queryset = basket.get_finance_options_queryset()

        # terms and condition
        if not request.settings.has_terms:
            del self.fields['terms']
        else:
            self.fields['terms'].help_text = mark_safe(
                'I have read and agree to the <a href="' +
                request.settings.get_terms() +
                '" target="_blank">terms and conditions</a>.')

        # collect additional delivery address options from customer's profile
        # (only available if we are allowed to edit the delivery address)
        if basket.can_edit_delivery_address and not request.user.is_anonymous(
        ):
            addresses = [(x.id, unicode(x))
                         for x in request.user.delivery_addresses.all()]
            self.fields['deliver_to'].choices += addresses

        if not request.user.is_anonymous():
            # authenticated user with a valid profile do not need to fill out
            # all the information but we pre fill out the majority of the
            # fields...
            self.fields['first_name'].initial = request.user.first_name
            self.fields['last_name'].initial = request.user.last_name

            try:
                p = get_customer_model().objects.get(user=request.user)

                self.fields['title'].initial = p.title
                self.fields['address1'].initial = p.address1
                self.fields['address2'].initial = p.address2
                self.fields['address3'].initial = p.address3
                self.fields['city'].initial = p.city
                self.fields['county'].initial = p.county
                self.fields['postcode'].initial = p.postcode
                self.fields['country'].initial = p.country
                self.fields['telephone'].initial = p.telephone

                if p.newsletter:
                    if 'newsletter' in self.fields:
                        del self.fields['newsletter']
                    if '_newsletter' in self.fields:
                        del self.fields['_newsletter']

                for field in fields_list:
                    if field in self.fields:
                        del self.fields[field]
            except get_customer_model().DoesNotExist:
                pass
        else:
            # guests need to fill out the entire form, copy only the email
            self.fields['email'].initial = request.session.get(
                settings.GUEST_USER_SESSION_VAR, '')
            del self.fields['update_profile']

        # billing address changable?
        if not basket.can_edit_billing_address:
            for field in self.ADDRESS_FIELD_NAMES:
                del self.fields[field]

        # delivery address changeable?
        if not basket.can_edit_delivery_address:
            self.fields[
                'deliver_to'].choices = self.DELIVERY_CHOICES_RESTRICTED
            for field in self.ADDRESS_FIELD_NAMES:
                del self.fields['delivery_%s' % field]

        # free delivery to
        if basket.can_have_free_delivery_to():
            self.fields['deliver_to'].choices = [
                (DeliveryAddressFrom.FREE_DELIVERY_TO,
                 'Free delivery to %s' % basket.get_free_delivery_to())
            ] + self.fields['deliver_to'].choices
        else:
            del self.fields['delivery_code']

        # special requirements
        if not request.settings.special_requirements:
            del self.fields['special_req']
Пример #15
0
class BillingAddressForm(BaseForm):
    postcode_lookup = PostcodeLookupField(label='Find Address',
                                          address1='id_address1',
                                          address2='id_address2',
                                          address3='id_address3',
                                          address4=None,
                                          locality=None,
                                          city='id_city',
                                          county='id_county',
                                          postcode='id_postcode',
                                          custom_css='text')

    __name = SectionField(label='Name')

    title = forms.ChoiceField(required=True,
                              choices=get_customer_model().TITLE_CHOICES)

    first_name = forms.CharField(label='First Name',
                                 max_length=30,
                                 required=True,
                                 widget=forms.TextInput(attrs={
                                     'size': '40',
                                     'class': 'text'
                                 }))

    last_name = forms.CharField(label='Last Name',
                                max_length=30,
                                required=True,
                                widget=forms.TextInput(attrs={
                                    'size': '40',
                                    'class': 'text'
                                }))

    __address = SectionField(label='Address')

    company = forms.CharField(label='Company',
                              max_length=255,
                              required=False,
                              widget=forms.TextInput(attrs={
                                  'size': '40',
                                  'class': 'text'
                              }))

    address1 = forms.CharField(label='Address 1',
                               max_length=255,
                               required=True,
                               widget=forms.TextInput(attrs={
                                   'size': '40',
                                   'class': 'text'
                               }))

    address2 = forms.CharField(label='Address 2',
                               max_length=255,
                               required=False,
                               widget=forms.TextInput(attrs={
                                   'size': '40',
                                   'class': 'text'
                               }))

    address3 = forms.CharField(label='Address 3',
                               max_length=255,
                               required=False,
                               widget=forms.TextInput(attrs={
                                   'size': '40',
                                   'class': 'text'
                               }))

    city = forms.CharField(max_length=255,
                           required=True,
                           widget=forms.TextInput(attrs={
                               'size': '40',
                               'class': 'text'
                           }))

    country = forms.ModelChoiceField(required=True,
                                     empty_label=None,
                                     initial='GB',
                                     queryset=Country.objects.all())

    county = forms.CharField(required=True,
                             max_length=255,
                             widget=forms.TextInput(attrs={
                                 'size': '40',
                                 'class': 'text'
                             }))

    postcode = forms.CharField(max_length=10,
                               required=True,
                               widget=forms.TextInput(attrs={
                                   'size': '10',
                                   'class': 'text'
                               }))

    def configure(self, request):
        self._request = request
        u = self._request.user
        p = get_customer_model().objects.get(user=u)

        self.fields['first_name'].initial = u.first_name
        self.fields['last_name'].initial = u.last_name
        self.fields['title'].initial = p.title
        self.fields['company'].initial = p.company

        self.fields['address1'].initial = p.address1
        self.fields['address2'].initial = p.address2
        self.fields['address3'].initial = p.address3
        self.fields['city'].initial = p.city
        self.fields['county'].initial = p.county
        self.fields['postcode'].initial = p.postcode
        self.fields['country'].initial = p.country

        if 'cubane.postcode' not in settings.INSTALLED_APPS:
            self.remove_field('postcode_lookup')

    def clean(self):
        d = super(BillingAddressForm, self).clean()
        return clean_address(self, d)
Пример #16
0
def delivery(request):
    """
    (1) Start to checkout by confirming the delivery address.
    The customer is required to login for checkout first (see login).
    """
    basket = Basket(request)
    if basket.is_empty():
        return HttpResponseRedirect('/')

    # if the basket contains collection only products,
    # force click and collect
    if basket.is_collection_only():
        basket.set_click_and_collect(True)

    if request.method == 'POST':
        form = DeliveryAddressFrom(request.POST)
    else:
        billing = basket.billing_address if basket.billing_address else {}
        delivery = basket.delivery_address if basket.delivery_address else {}

        profile = None
        default = {}
        user = request.user
        if not user.is_anonymous():
            try:
                profile = get_customer_model().objects.get(user=user)
                default = {
                    'title': profile.title,
                    'first_name': user.first_name,
                    'last_name': user.last_name,
                    'email': user.email,
                    'telephone': profile.telephone
                }

                if basket.has_billing_address():
                    default.update({
                        'company': profile.company,
                        'address1': profile.address1,
                        'address2': profile.address2,
                        'address3': profile.address3,
                        'city': profile.city,
                        'country': profile.country,
                        'county': profile.county,
                        'postcode': profile.postcode
                    })
            except get_customer_model().DoesNotExist:
                pass
        else:
            default = {
                'email': request.session.get(settings.GUEST_USER_SESSION_VAR),
                'country': 'GB'
            }

        def _get(name, data, fallback=None):
            v = data.get(name)
            if v is None and fallback is not None:
                v = fallback.get(name)
            return v

        form = DeliveryAddressFrom(
            initial={
                'title':
                _get('title', billing, default),
                'first_name':
                _get('first_name', billing, default),
                'last_name':
                _get('last_name', billing, default),
                'email':
                _get('email', billing, default),
                'telephone':
                _get('telephone', billing, default),
                'company':
                _get('company', billing, default),
                'address1':
                _get('address1', billing, default),
                'address2':
                _get('address2', billing, default),
                'address3':
                _get('address3', billing, default),
                'city':
                _get('city', billing, default),
                'country':
                _get('country', billing, default),
                'county':
                _get('county', billing, default),
                'postcode':
                _get('postcode', billing, default),
                'deliver_to':
                DeliveryAddressFrom.DELIVERY_COLLECTION if basket.
                is_click_and_collect(
                ) else DeliveryAddressFrom.DELIVERY_BILLING_ADDRESS,
                'free_name':
                _get('free_name', delivery),
                'delivery_name':
                _get('name', delivery),
                'delivery_company':
                _get('company', delivery),
                'delivery_address1':
                _get('address1', delivery),
                'delivery_address2':
                _get('address2', delivery),
                'delivery_address3':
                _get('address3', delivery),
                'delivery_city':
                _get('city', delivery),
                'delivery_country':
                _get('country', delivery, default),
                'delivery_county':
                _get('county', delivery),
                'delivery_postcode':
                _get('postcode', delivery),
                'finance_option':
                basket.finance_option,
                'loan_deposit':
                basket.loan_deposit,
                'newsletter':
                basket.newsletter,
                'terms':
                basket.terms,
                'special_req':
                basket.special_req,
                'survey':
                basket.survey,
                'signup':
                basket.signup != None,
                'password':
                basket.signup.get('password') if basket.signup else None,
                'password_confirm':
                basket.signup.get('password') if basket.signup else None,
                'update_profile':
                basket.update_profile
            })

    form.configure(request, basket)
    current_page = CurrentPage.DELIVERY_ADDRESS()

    if request.method == 'POST' and form.is_valid():
        d = form.cleaned_data

        if 'email' in d:
            email = d.get('email')
        else:
            email = request.user.email

        # keep initial address information if we are not allowed to change the
        # billing address
        if not basket.can_edit_billing_address:
            for field in [
                    'company', 'address1', 'address2', 'address3', 'city',
                    'country', 'county', 'postcode'
            ]:
                d[field] = basket.billing_address.get(field)

        # save billing address
        basket.set_billing_address(title=d.get('title'),
                                   first_name=d.get('first_name'),
                                   last_name=d.get('last_name'),
                                   email=email,
                                   telephone=d.get('telephone'),
                                   company=d.get('company'),
                                   address1=d.get('address1'),
                                   address2=d.get('address2'),
                                   address3=d.get('address3'),
                                   city=d.get('city'),
                                   country=d.get('country'),
                                   county=d.get('county'),
                                   postcode=d.get('postcode'))

        # get delivery method
        deliver_to = d.get('deliver_to',
                           DeliveryAddressFrom.DELIVERY_BILLING_ADDRESS)

        basket.set_click_and_collect(
            deliver_to == DeliveryAddressFrom.DELIVERY_COLLECTION
            or basket.is_collection_only())
        basket.set_free_delivery_to(False)

        if deliver_to == DeliveryAddressFrom.FREE_DELIVERY_TO:
            location = basket.get_normalized_free_delivery_to_address()

            basket.set_delivery_address(name=d.get('delivery_free_name'),
                                        company=location.get('title'),
                                        address1=location.get('address1'),
                                        address2=location.get('address2'),
                                        address3=location.get('address3'),
                                        city=location.get('city'),
                                        country=location.get('country'),
                                        county=location.get('county'),
                                        postcode=location.get('postcode'))
            basket.set_free_delivery_to(True)
        elif deliver_to == DeliveryAddressFrom.DELIVERY_BILLING_ADDRESS:
            # deliver to my billing address
            basket.set_delivery_address(
                name='%s %s' % (d.get('first_name'), d.get('last_name')),
                company=d.get('company'),
                address1=d.get('address1'),
                address2=d.get('address2'),
                address3=d.get('address3'),
                city=d.get('city'),
                country=d.get('country'),
                county=d.get('county'),
                postcode=d.get('postcode'))
        elif deliver_to == DeliveryAddressFrom.DELIVERY_NEW_ADDRESS:
            # enter new delivery address
            basket.set_delivery_address(name=d.get('delivery_name'),
                                        company=d.get('delivery_company'),
                                        address1=d.get('delivery_address1'),
                                        address2=d.get('delivery_address2'),
                                        address3=d.get('delivery_address3'),
                                        city=d.get('delivery_city'),
                                        country=d.get('delivery_country'),
                                        county=d.get('delivery_county'),
                                        postcode=d.get('delivery_postcode'))

            # create a new record for the customer's profile
            if not request.user.is_anonymous():
                n = DeliveryAddress.objects.filter(
                    user=request.user,
                    address1=d.get('delivery_address1'),
                    address2=d.get('delivery_address2'),
                    address3=d.get('delivery_address3'),
                    city=d.get('delivery_city'),
                    country=d.get('delivery_country'),
                    county=d.get('delivery_county'),
                    postcode=d.get('delivery_postcode')).count()

                if n == 0:
                    address = DeliveryAddress()
                    address.user = request.user
                    address.name = d.get('delivery_name')
                    address.company = d.get('delivery_company')
                    address.address1 = d.get('delivery_address1')
                    address.address2 = d.get('delivery_address2')
                    address.address3 = d.get('delivery_address3')
                    address.city = d.get('delivery_city')
                    address.country = d.get('delivery_country')
                    address.county = d.get('delivery_county')
                    address.postcode = d.get('delivery_postcode')
                    address.save()
        else:
            if not basket.is_click_and_collect():
                # delivery to one of my delivery addresses taken from my profile
                delivery_address = DeliveryAddress.objects.get(
                    user=request.user, pk=deliver_to)
                basket.set_delivery_address(name=delivery_address.name,
                                            company=delivery_address.company,
                                            address1=delivery_address.address1,
                                            address2=delivery_address.address2,
                                            address3=delivery_address.address3,
                                            city=delivery_address.city,
                                            country=delivery_address.country,
                                            county=delivery_address.county,
                                            postcode=delivery_address.postcode)

        is_loan_available = settings.SHOP_LOAN_ENABLED and 'finance_option' in d and 'loan_deposit' in d

        if is_loan_available and deliver_to == DeliveryAddressFrom.DELIVERY_NEW_ADDRESS:
            # deliver to my billing address as it is required by law if finance option is chosen
            if d.get('finance_option'):
                basket.set_delivery_address(
                    name='%s %s' % (d.get('first_name'), d.get('last_name')),
                    company=d.get('company'),
                    address1=d.get('address1'),
                    address2=d.get('address2'),
                    address3=d.get('address3'),
                    city=d.get('city'),
                    country=d.get('country'),
                    county=d.get('county'),
                    postcode=d.get('postcode'))

        # loan application
        if is_loan_available:
            basket.set_finance_option(d.get('finance_option'))
            basket.set_loan_deposit(d.get('loan_deposit'))
        else:
            basket.set_finance_option(None)
            basket.set_loan_deposit(None)

        # newsletter
        if request.settings.mailchimp_enabled and 'newsletter' in d and d.get(
                'newsletter'):
            basket.newsletter = True

        # terms and conditions
        if request.settings.has_terms and 'terms' in d and d.get('terms'):
            basket.terms = True

        # special requiremenets
        basket.special_req = d.get('special_req')

        # survey
        basket.survey = d.get('survey') if 'survey' in d else None

        # signup?
        if d.get('signup', False) == True:
            basket.set_signup(email=d.get('email'),
                              first_name=d.get('first_name'),
                              last_name=d.get('last_name'),
                              password=d.get('password'))
        else:
            basket.clear_signup()

        # default delivery address?
        if 'update_profile' in d and d.get('update_profile'):
            basket.update_profile = True

        # next...
        next = next_checkout_step(request, basket, current_page)
        basket.save()
        return next

    # generate list of available delivery addresses from customer's profile
    if request.user.is_anonymous():
        delivery_addresses = []
    else:
        delivery_addresses = [{
            'id': i,
            'iso': addr.country.iso
        } for i, addr in enumerate(request.user.delivery_addresses.all(),
                                   start=3)]

    return {
        'basket': basket,
        'form': form,
        'delivery_addresses': to_json(delivery_addresses)
    }
Пример #17
0
 def get_customer_model(self):
     """
     Return the model for a shop customer.
     """
     return get_customer_model()
Пример #18
0
    def account_signup(self, request):
        email = request.session.get(settings.SIGNUP_EMAIL_SESSION_VAR, None)
        if email == '':
            raise Http404('Missing email address.')

        checkout = request.GET.get('checkout', False) == '1'
        form_class = self.get_account_signup_form()
        if request.method == 'POST':
            form = form_class(request.POST, initial={'checkout': checkout})
        else:
            form = form_class(initial={
                'email': email,
                'checkout': checkout
            })

        form.configure(request)

        if request.method == 'POST':
            captcha = validate_captcha(request)
            if not captcha:
                messages.add_message(request, messages.ERROR,
                    'Please tick the checkbox at the bottom of the form to prevent SPAM.'
                )

            if form.is_valid() and captcha:
                d = form.cleaned_data

                # create user account
                md5 = hashlib.md5()
                md5.update(d['email'])
                user = User.objects.create(
                    username = md5.hexdigest()[:30],
                    first_name = d['first_name'],
                    last_name = d['last_name'],
                    email = d['email']
                )

                # replace username with user id, set password and add user to list of customers
                user.username = unicode(user.id)
                user.set_password(d['password'])

                user.save()

                # create customer
                newsletter = 0
                if request.settings.mailchimp_enabled:
                    if d['newsletter']:
                        person_name = (d['first_name'],d['last_name'])
                        merge_vars = {'FNAME': " ".join(person_name)}
                        ms = MailSnake(request.settings.mailchimp_api)
                        try:
                            ms.listSubscribe(id=request.settings.mailchimp_list_id, email_address=d['email'], merge_vars=merge_vars)
                        except:
                            pass
                        newsletter = d['newsletter']
                customer = get_customer_model().objects.create(
                    user=user,
                    first_name = d['first_name'],
                    last_name = d['last_name'],
                    email=d['email'],
                    title=d['title'],
                    address1='',
                    city='',
                    county='',
                    postcode='',
                    country=d['country'],
                    telephone='',
                    newsletter=newsletter
                )

                # log customer in
                login_user_without_password(request, user)

                # go to dashboard or deliver page
                messages.success(request, 'Thank you for signing up with us.')
                if d['checkout']:
                    response = HttpResponseRedirect(reverse('shop.order.delivery'))
                else:
                    response = HttpResponseRedirect(reverse('shop.account.index'))

                response.set_cookie('cubaneShopLogin', '1')
                return response

        return {
            'account_section': True,
            'is_signup_page': True,
            'form': form
        }
Пример #19
0
class CustomerView(ModelView):
    template_path = 'cubane/ishop/merchant/customers/'
    namespace = 'cubane.ishop.customers'
    model = get_customer_model()

    patterns = [
        view_url(r'change-password/$',
                 view='change_password',
                 name='change_password'),
    ]

    listing_actions = [('[Change Password]', 'change_password', 'single')]

    shortcut_actions = [
        'change_password',
    ]

    def __init__(self, *args, **kwargs):
        if not settings.SHOP_CHANGE_CUSTOMER_PASSWORD_ENABLED:
            self.shortcut_actions = []
            self.listing_actions = []
        super(CustomerView, self).__init__(*args, **kwargs)

    def _get_objects(self, request):
        return self.model.objects.all()

    @view(require_POST)
    @view(permission_required('delete'))
    def delete(self, request, pk=None):
        """
        Delete existing model instance with given primary key pk or (if no
        primary key is given in the url) attempt to delete multiple entities
        that are given by ids post argument.
        """
        # determine list of pks
        pks = []
        if pk:
            pks = [pk]
        else:
            pks = request.POST.getlist('pks[]', [])
            if len(pks) == 0:
                pk = request.POST.get('pk')
                if pk:
                    pks = [pk]

        # delete instance(s)...
        if len(pks) == 1:
            instance = self.get_object_or_404(request, pks[0])
            label = instance.__unicode__()
            if not label: label = '<no label>'
            instance.delete()
            message = self._get_success_message(label, 'deleted')
        else:
            instances = self._get_objects(request).filter(pk__in=pks)
            for instance in instances:
                instance.delete()
            message = '%d %s deleted successfully.' % (
                len(instances), self.model._meta.verbose_name_plural)

        # response
        if self._is_json(request):
            return to_json_response({'success': True, 'message': message})
        else:
            messages.add_message(request, messages.SUCCESS, message)
            return self._redirect(request, 'index')

    def change_password(self, request):
        # feature enabled?
        if not settings.SHOP_CHANGE_CUSTOMER_PASSWORD_ENABLED:
            raise Http404('Feature is not enabled.')

        customer_id = request.GET.get('pk')
        try:
            customer = self.model.objects.get(pk=customer_id)
            user = customer.user
        except self.model.DoesNotExist:
            raise Http404('Unknown customer account id %s.' % customer_id)

        if request.method == 'POST':
            form = CustomerChangePasswordForm(request.POST)
        else:
            form = CustomerChangePasswordForm()

        if request.method == 'POST' and form.is_valid():
            user.set_password(form.cleaned_data['password'])
            user.save()
            messages.add_message(
                request, messages.SUCCESS,
                'Password changed for <em>%s</em>.' % customer.email)
            return self._redirect(request, 'index')

        return {'customer': customer, 'form': form}

    @view(csrf_exempt)
    def export(self, request):
        return _export(request)
Пример #20
0
class DeliveryAddressFrom(BaseForm):
    ADDRESS_FIELD_NAMES = [
        'company', 'address1', 'address2', 'address3', 'city', 'country',
        'county', 'postcode'
    ]

    _customer_information = SectionField(label='Customer Information')

    title = forms.ChoiceField(required=True,
                              choices=get_customer_model().TITLE_CHOICES)

    first_name = forms.CharField(label='First Name',
                                 max_length=30,
                                 required=True,
                                 widget=forms.TextInput(attrs={
                                     'size': '40',
                                     'class': 'text'
                                 }))

    last_name = forms.CharField(label='Last Name',
                                max_length=30,
                                required=True,
                                widget=forms.TextInput(attrs={
                                    'size': '40',
                                    'class': 'text'
                                }))

    email = forms.EmailField(max_length=255, required=True, widget=EmailInput)

    telephone = forms.CharField(max_length=40,
                                required=True,
                                widget=PhoneInput)

    postcode_lookup = PostcodeLookupField(label='Find Address',
                                          address1='id_address1',
                                          address2='id_address2',
                                          address3='id_address3',
                                          address4=None,
                                          locality=None,
                                          city='id_city',
                                          county='id_county',
                                          postcode='id_postcode',
                                          custom_css='text')

    _billing_address = SectionField(label='Billing Address')

    company = forms.CharField(label='Company',
                              max_length=255,
                              required=False,
                              widget=forms.TextInput(attrs={
                                  'size': '40',
                                  'class': 'text'
                              }))

    address1 = forms.CharField(label='Address 1',
                               max_length=255,
                               required=True,
                               widget=forms.TextInput(attrs={
                                   'size': '40',
                                   'class': 'text'
                               }))

    address2 = forms.CharField(label='Address 2',
                               max_length=255,
                               required=False,
                               widget=forms.TextInput(attrs={
                                   'size': '40',
                                   'class': 'text'
                               }))

    address3 = forms.CharField(label='Address 3',
                               max_length=255,
                               required=False,
                               widget=forms.TextInput(attrs={
                                   'size': '40',
                                   'class': 'text'
                               }))

    city = forms.CharField(max_length=255,
                           required=True,
                           widget=forms.TextInput(attrs={
                               'size': '40',
                               'class': 'text'
                           }))

    country = forms.ModelChoiceField(required=True,
                                     empty_label=None,
                                     initial='GB',
                                     queryset=Country.objects.all())

    county = forms.CharField(max_length=255,
                             required=True,
                             widget=forms.TextInput(attrs={
                                 'size': '40',
                                 'class': 'text'
                             }))

    postcode = forms.CharField(max_length=10,
                               required=True,
                               widget=forms.TextInput(attrs={
                                   'size': '10',
                                   'class': 'text'
                               }))

    update_profile = forms.BooleanField(
        required=False,
        initial=True,
        help_text=
        'Make this billing address my permanent address to be used for the next checkout.'
    )

    delivery_postcode_lookup = PostcodeLookupField(
        label='Find Address',
        address1='id_delivery_address1',
        address2='id_delivery_address2',
        address3='id_delivery_address3',
        address4=None,
        locality=None,
        city='id_delivery_city',
        county='id_delivery_county',
        postcode='id_delivery_postcode',
        custom_css='text')

    _delivery_address = SectionField(label='Delivery Address')

    FREE_DELIVERY_TO = 'free_delivery_to'
    DELIVERY_BILLING_ADDRESS = 'billing_address'
    DELIVERY_NEW_ADDRESS = 'new_address'
    DELIVERY_COLLECTION = 'click_and_collect'

    DELIVERY_CHOICES = ((DELIVERY_COLLECTION, 'Click and Collect'),
                        (DELIVERY_BILLING_ADDRESS,
                         'Deliver to my billing address'),
                        (DELIVERY_NEW_ADDRESS, 'Enter new delivery address'))
    DELIVERY_CHOICES_RESTRICTED = (
        (DELIVERY_COLLECTION, 'Click and Collect'),
        (DELIVERY_BILLING_ADDRESS, 'Deliver to my billing address'),
    )

    deliver_to = forms.ChoiceField(required=True,
                                   choices=DELIVERY_CHOICES,
                                   widget=forms.RadioSelect())

    delivery_free_name = forms.CharField(label='Name',
                                         max_length='255',
                                         required=False)

    delivery_name = forms.CharField(label='Name',
                                    max_length=255,
                                    required=False,
                                    widget=forms.TextInput(attrs={
                                        'size': '40',
                                        'class': 'text'
                                    }))

    delivery_company = forms.CharField(label='Company',
                                       max_length=255,
                                       required=False,
                                       widget=forms.TextInput(attrs={
                                           'size': '40',
                                           'class': 'text'
                                       }))

    delivery_address1 = forms.CharField(label='Address 1',
                                        max_length=255,
                                        required=False,
                                        widget=forms.TextInput(attrs={
                                            'size': '40',
                                            'class': 'text'
                                        }))

    delivery_address2 = forms.CharField(label='Address 2',
                                        max_length=255,
                                        required=False,
                                        widget=forms.TextInput(attrs={
                                            'size': '40',
                                            'class': 'text'
                                        }))

    delivery_address3 = forms.CharField(label='Address 3',
                                        max_length=255,
                                        required=False,
                                        widget=forms.TextInput(attrs={
                                            'size': '40',
                                            'class': 'text'
                                        }))

    delivery_city = forms.CharField(label='City',
                                    max_length=255,
                                    required=False,
                                    widget=forms.TextInput(attrs={
                                        'size': '40',
                                        'class': 'text'
                                    }))

    delivery_country = forms.ModelChoiceField(label='Country',
                                              required=False,
                                              empty_label=None,
                                              initial='GB',
                                              queryset=Country.objects.all())

    delivery_county = forms.CharField(label='County',
                                      max_length=255,
                                      required=False,
                                      widget=forms.TextInput(attrs={
                                          'size': '40',
                                          'class': 'text'
                                      }))

    delivery_postcode = forms.CharField(label='Postcode',
                                        max_length=10,
                                        required=False,
                                        widget=forms.TextInput(attrs={
                                            'size': '10',
                                            'class': 'text'
                                        }))

    _discount = SectionField(label='Discount')

    signup = forms.BooleanField(
        required=False,
        initial=False,
        help_text='Save this information to make checkout quicker next time.')

    password = forms.CharField(
        label='Password',
        min_length=6,
        max_length=255,
        required=False,
        help_text='Your password must be at least 6 characters in length.',
        widget=forms.PasswordInput(render_value=True))

    password_confirm = forms.CharField(
        label='Password (Confirm)',
        min_length=6,
        max_length=255,
        required=False,
        help_text='Confirm your new password.',
        widget=forms.PasswordInput(render_value=True))

    newsletter = forms.BooleanField(
        label='Newsletter',
        required=False,
        initial=False,
        help_text='Yes, subscribe me to the newsletter.')

    delivery_code = forms.CharField(label='Delivery Code',
                                    required=False,
                                    max_length=32)

    special_req = forms.CharField(
        label='Special Requirements',
        required=False,
        max_length=500,
        widget=forms.Textarea(attrs={
            'cols': '40',
            'rows': '4'
        }),
        help_text='For example: Special Delivery Requirements.')

    survey = forms.ChoiceField(required=False,
                               choices=[],
                               help_text='Where did you hear about us?')

    finance_option = forms.ModelChoiceField(
        label='Finance Option',
        queryset=None,
        required=False,
        help_text='Choose the finance option that best suits your requirements.'
    )

    loan_deposit = forms.IntegerField(label='Deposit',
                                      required=False,
                                      widget=RangeInput(attrs={
                                          'step': '1',
                                          'min': '10',
                                          'max': '50'
                                      }))

    terms = forms.BooleanField(label='Accept Terms',
                               required=True,
                               initial=False)

    def configure(self, request, basket):
        self._request = request
        self._basket = basket

        fields_list = [
            'email', 'signup', 'password', 'password_confirm', 'survey'
        ]

        if request.settings.has_survey:
            self.fields['survey'].choices = [('', '-------')] + [
                (o, o) for o in request.settings.get_survey_options()
            ]
        else:
            del self.fields['survey']

        if not request.settings.mailchimp_enabled:
            del self.fields['newsletter']

        # finance option
        self.fields[
            'finance_option'].queryset = basket.get_finance_options_queryset()

        # terms and condition
        if not request.settings.has_terms:
            del self.fields['terms']
        else:
            self.fields['terms'].help_text = mark_safe(
                'I have read and agree to the <a href="' +
                request.settings.get_terms() +
                '" target="_blank">terms and conditions</a>.')

        # collect additional delivery address options from customer's profile
        # (only available if we are allowed to edit the delivery address)
        if basket.can_edit_delivery_address and not request.user.is_anonymous(
        ):
            addresses = [(x.id, unicode(x))
                         for x in request.user.delivery_addresses.all()]
            self.fields['deliver_to'].choices += addresses

        if not request.user.is_anonymous():
            # authenticated user with a valid profile do not need to fill out
            # all the information but we pre fill out the majority of the
            # fields...
            self.fields['first_name'].initial = request.user.first_name
            self.fields['last_name'].initial = request.user.last_name

            try:
                p = get_customer_model().objects.get(user=request.user)

                self.fields['title'].initial = p.title
                self.fields['address1'].initial = p.address1
                self.fields['address2'].initial = p.address2
                self.fields['address3'].initial = p.address3
                self.fields['city'].initial = p.city
                self.fields['county'].initial = p.county
                self.fields['postcode'].initial = p.postcode
                self.fields['country'].initial = p.country
                self.fields['telephone'].initial = p.telephone

                if p.newsletter:
                    if 'newsletter' in self.fields:
                        del self.fields['newsletter']
                    if '_newsletter' in self.fields:
                        del self.fields['_newsletter']

                for field in fields_list:
                    if field in self.fields:
                        del self.fields[field]
            except get_customer_model().DoesNotExist:
                pass
        else:
            # guests need to fill out the entire form, copy only the email
            self.fields['email'].initial = request.session.get(
                settings.GUEST_USER_SESSION_VAR, '')
            del self.fields['update_profile']

        # billing address changable?
        if not basket.can_edit_billing_address:
            for field in self.ADDRESS_FIELD_NAMES:
                del self.fields[field]

        # delivery address changeable?
        if not basket.can_edit_delivery_address:
            self.fields[
                'deliver_to'].choices = self.DELIVERY_CHOICES_RESTRICTED
            for field in self.ADDRESS_FIELD_NAMES:
                del self.fields['delivery_%s' % field]

        # free delivery to
        if basket.can_have_free_delivery_to():
            self.fields['deliver_to'].choices = [
                (DeliveryAddressFrom.FREE_DELIVERY_TO,
                 'Free delivery to %s' % basket.get_free_delivery_to())
            ] + self.fields['deliver_to'].choices
        else:
            del self.fields['delivery_code']

        # special requirements
        if not request.settings.special_requirements:
            del self.fields['special_req']

    def clean_email(self):
        """
        Make sure that the email is not taken if the user checked signup.
        """
        signup = self.cleaned_data.get('signup', False)
        email = self.cleaned_data.get('email', None)

        if signup == True:
            if get_customer_model().objects.filter(email=email).count() > 0:
                raise forms.ValidationError(
                    'Email address already used. Please provide a different email address for signing up for a new account.'
                )

        return email

    def clean_password(self):
        """
        Password is required if signup is checked
        """
        signup = self.cleaned_data.get('signup', False)
        password = self.cleaned_data.get('password', None)

        if signup == True:
            if not password:
                raise forms.ValidationError(
                    'Password is required in order to signup for a new account.'
                )

        return password

    def clean_password_confirm(self):
        """
        Password confirm is required and must match password if signup is checked.
        """
        signup = self.cleaned_data.get('signup', False)
        password = self.cleaned_data.get('password', None)
        password_confirm = self.cleaned_data.get('password_confirm', None)

        if signup == True:
            if not password_confirm:
                raise forms.ValidationError(
                    'Password confirmation is required in order to signup for a new account.'
                )
            if password != password_confirm:
                raise forms.ValidationError(
                    'Password confirmation is required to match password.')

        return password_confirm

    def clean_deliver_to(self):
        deliver_to = self.cleaned_data.get('deliver_to')

        if deliver_to:
            if self._basket.is_collection_only(
            ) and deliver_to != DeliveryAddressFrom.DELIVERY_COLLECTION:
                raise forms.ValidationError(
                    'At least one product cannot be delivered and must be collected from store. Please select Click and Collect.'
                )

        return deliver_to

    def clean(self):
        d = super(DeliveryAddressFrom, self).clean()

        # deliver to
        deliver_to = d.get('deliver_to')
        if deliver_to:
            if deliver_to == DeliveryAddressFrom.DELIVERY_NEW_ADDRESS:
                fields = [
                    'delivery_name', 'delivery_address1', 'delivery_city',
                    'delivery_county', 'delivery_country', 'delivery_postcode'
                ]
                for field in fields:
                    if not d.get(field):
                        self._errors[field] = self.error_class([
                            'This field is required for the delivery address.'
                        ])

        # finance option is required if we ticked finance option
        loan = d.get('loan')
        finance_option = d.get('finance_option')

        if self._basket.can_have_free_delivery_to():
            delivery_code = d.get('delivery_code')

            if deliver_to == DeliveryAddressFrom.FREE_DELIVERY_TO:
                if delivery_code != self._basket.get_free_delivery_to(
                ).delivery_code:
                    self._errors['delivery_code'] = self.error_class([
                        'Unfortunately we are unable to recognise your free delivery code. Please try again.'
                    ])

                if not d.get('delivery_free_name'):
                    self._errors['delivery_free_name'] = self.error_class(
                        ['This field is required for the free delivery.'])

        if loan and not finance_option:
            self.form_error('finance_option', 'This field is required.')
        if loan and not loan_deposit:
            self.form_error('loan_deposit', 'This field is required.')

        # clean address
        return clean_address(self, d)

    def get_address(self):
        """
        Return the address information as provided from this form.
        """
        d = self.cleaned_data
        return {
            'title':
            d.get('title'),
            'first_name':
            d.get('first_name'),
            'last_name':
            d.get('last_name'),
            'name':
            d.get('delivery_name')
            if d.get('delivery_name') else d.get('delivery_free_name'),
            'address1':
            d.get('address1'),
            'address2':
            d.get('address2'),
            'address3':
            d.get('address3'),
            'city':
            d.get('city'),
            'county':
            d.get('county'),
            'state':
            d.get('county') if d.get('country').iso == 'US' else '',
            'postcode':
            d.get('postcode'),
            'country':
            d.get('country'),
            'country-iso':
            d.get('country').iso
        }