Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

400 Unable to verify data submission #310

Open
harry2909 opened this issue Aug 28, 2024 · 3 comments
Open

400 Unable to verify data submission #310

harry2909 opened this issue Aug 28, 2024 · 3 comments

Comments

@harry2909
Copy link

harry2909 commented Aug 28, 2024

Description

Whenever I navigate to the payment page, the stripe form just renders a 400 error.

We're using blitz caching alongside a static caching solution, but this page should be omitted from the cache.

I can see in the request, the craft CSRF token is not added to the automatic post to the endpoint.

action: commerce/payments/pay
redirect: 80aabe5f62fc4cd38802a416a9aba3031d17816ea7134bea6897057175ab9ecchttps://drivedevilbiss.co.uk.ddev.site/store/customer/order?number=713e1c44d318b384db4c0c8127c6abdd&success=true
cancelUrl: abac018efdd9185f35742418abf2c89f6c4afd9048fec9d42589212d3ec6c146https://drivedevilbiss.co.uk.ddev.site/store/checkout/payment
orderEmail: [email protected]
gatewayId: 3

Payment form code:

 <form
                id="paymentForm"
                method="post"
                class="max-w-listing mx-auto {{ autoSubmitForm ? 'js-auto-submit' : '' }}"
            >
                <div class="flex flex-col lg:flex-row justify-between">
                    <div class="{{ cart.gatewayId == 1 ? 'mx-auto' : 'mr-[20px]' }} max-w-[700px] w-full p-8 lg:p-10 bg-white rounded-xl border border-ddh-grey-border self-start mb-[20px]">

                        {% if cart.gatewayId == 1 %}
                                <div class="text-center">
                                    {% if autoSubmitForm %}
                                        <p class="text-2xl font-heading font-medium pb-2">Loading...</p>
                                        <p class="text-sm">
                                            The browser should automatically continue, click the button to manually continue.
                                        </p>
                                        <div class="py-3">
                                            {% include '_partials/spinner' %}
                                        </div>
                                        {% include "_partials/button" with {
                                            element: 'button',
                                            type: 'submit',
                                            text: 'Continue',
                                            style: 1,
                                        } %}
                                    {% else %}
                                        <p class="text-2xl font-heading font-medium pb-2">There was a problem.</p>
                                        <p class="text-sm">{{ flashMessages.checkoutInvoicePaymentMethodFailedMessage }}</p>
                                        {% for key, errors in cart.getErrors() %}
                                            {% for error in errors %}
                                                {% if loop.first %}<ul>{% endif %}
                                                <li class="text-red-600"><strong>{{ key }}</strong> {{ error }}</li>
                                                {% if loop.last %}</ul>{% endif %}
                                            {% endfor %}
                                        {% endfor %}
                                        {% include "_partials/button" with {
                                            element: 'a',
                                            href: '/store/checkout/payment-method',
                                            text: 'Go back',
                                            style: 3,
                                            extraClasses: 'mt-4',
                                        } %}
                                    {% endif %}
                                </div>
                        {% endif %}

                        {% if cart.gatewayId %}

                            {% if paymentForm is defined %}
                                {% for key, errors in paymentForm.getErrors() %}
                                    {% for error in errors %}
                                        {% if loop.first %}<ul>{% endif %}
                                        <li class="text-red-600"><strong>{{ key }}</strong> {{ error }}</li>
                                        {% if loop.last %}</ul>{% endif %}
                                    {% endfor %}
                                {% endfor %}
                            {% endif %}

                            {{ actionInput('commerce/payments/pay') }}
                            {{ redirectInput(siteUrl('/store/customer/order', { number: cart.number, success: 'true' })) }}
                            {{ hiddenInput('cancelUrl', siteUrl('/store/checkout/payment')|hash) }}
                            {{ hiddenInput('orderEmail', cart.email) }}
                            {{ csrfInput() }}


                            {{ hiddenInput('gatewayId', cart.gatewayId) }}
                            {% set params = {
                                submitButtonClasses: 'mt-4 inline-flex border-2 border-transparent transition-colors relative rounded-4xl text-white font-heading font-bold leading-tight py-5 pr-14 pl-8 bg-ddh-yellow-dark items-center leading-normal text-center justify-center pr-8 w-full mt-8 hover:bg-white hover:border-ddh-yellow-dark hover:text-ddh-yellow-dark',
                                submitButtonText: 'Pay',
                            } %}

                            {% namespace cart.gateway.handle|commercePaymentFormNamespace %}
                                {{ cart.gateway.getPaymentFormHtml(params)|raw }}
                            {% endnamespace %}

                        {% endif %}
                    </div>

                    {% if cart.gatewayId != 1 %}
                        <div class="flex flex-wrap content-start justify-end lg:justify-between items-baseline xl:ml-4">
                            {{ include('store/checkout/_includes/order-summary', { showShippingAddress: true, showShippingMethod: true, }) }}
                        </div>
                    {% endif %}
                </div>
            </form>

image

It is worth noting that this worked absolutely fine until I set enableCsrfProtection to true in the general config, which does make sense. We needed this true so that asyncCsrfInputs would work.

I've tested and setting asyncCsrfInputs to false does make it work, so it could be to do with this.

Please let me know if you need any more information.

Steps to reproduce

Additional info

  • Craft CMS version: 4.11.3
  • Stripe for Craft Commerce version: 4.1.5
  • PHP version: 8.3.9
  • Database driver & version: MySQL 28.1
  • Plugins & versions:
Copy link

linear bot commented Aug 28, 2024

@jonnykates
Copy link

Also experiencing this with Commerce 4.6.11 and Stripe for Craft Commerce 4.1.5.

I've got a form on my payment page like;

<form method="post" id="payment-form" action="">
        {{ csrfInput() }}
        {{ actionInput('commerce/payments/pay') }}
        {{ redirectInput(siteUrl('/shop/checkout/order?number=' ~ cart.number) )}}
        {{ hiddenInput('cancelUrl', siteUrl('/shop/checkout/payment')|hash) }}
        {{ hiddenInput('orderEmail', cart.email) }}

        {{ cart.gateway.getPaymentFormHtml({})|raw }}
</form>

And with asyncCsrfInputs set to true in general config, the Stripe element doesn't render but shows 'Unable to verify your data submission'.

@lukeholder
Copy link
Member

@jonnykates

Does using {{ csrfInput({ async: false }) }} in the payment form fix this issue?

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Projects
None yet
Development

No branches or pull requests

3 participants