12

I'm having a weird problem with Stripe (on Rails, but the Rails part is probably irrelevant).

When I fill out my sign-up form in production with a syntactically valid but non-working card number (e.g. 4242424242424242), I get this response when I try to create a token:

sjsonp1389885476573({
  "error": {
    "message": "Your card was declined.",
    "type": "card_error",
    "code": "card_declined"
  }
}
, 402)

When in development I use the "always returns card_declined" card number (4000000000000002), Stripe takes it as if it were perfectly good:

sjsonp1389885473743({
  "id": "tok_3JvncLYlEZ5NMF",
  "livemode": false,
  "created": 1389885584,
  "used": false,
  "object": "token",
  "type": "card",
  "card": {
    "id": "card_3Jvnr4MtIxzzd5",
    "object": "card",
    "last4": "0002",
    "type": "Visa",
    "exp_month": 2,
    "exp_year": 2020,
    "fingerprint": "dWQBpXrSXnyqoOxe",
    "customer": null,
    "country": "US",
    "name": null,
    "address_line1": null,
    "address_line2": null,
    "address_city": null,
    "address_state": null,
    "address_zip": null,
    "address_country": null,
    "address_line1_check": null,
    "address_zip_check": null,
    "cvc_check": null
  }
}
, 200)

So it seems that either this part of Stripe's API is not working as advertised or I myself am making some kind of stupid mistake or something.

I'm kind of at a loss. Any thoughts?

Jason Swett
  • 43,526
  • 67
  • 220
  • 351
  • Are you using the testing public/private keys when authenticating, or are you using your live details? (Not just setting the test flag) – Khior Jan 16 '14 at 15:35
  • I'm using the test keys in dev, live keys in prod. – Jason Swett Jan 16 '14 at 15:36
  • Ok; sanity check complete! What other testing have you done? Are other Luhn-invalid card numbers also returning positive? Have you tried the other error card numbers that Stripe provide? – Khior Jan 16 '14 at 15:40
  • Luhn-invalid numbers fail, but it looks like none of the declined-charge numbers work as expected (i.e. they are accepted without an error). – Jason Swett Jan 16 '14 at 15:45
  • 1
    The code you have posted above only concerns the creation of a card token. Have you tried using that token to perform a transaction? – Khior Jan 16 '14 at 15:53
  • No, but I don't really see what that would give me. I need an invalid card to fail on account creation in dev the same way it does it production, or else I can't write code to account for the case of a declined card. Let me know if I'm not getting what you're saying. – Jason Swett Jan 16 '14 at 16:13
  • I agree, it seems inconsistent if the same function works differently in live and dev (and makes it nigh impossible to code for) but it would help to diagnose the issue. If a transaction with the token fails, then it reliably proves that the issue is with Stripe, and not your implementation. – Khior Jan 16 '14 at 16:24
  • I believe I actually figured it out. Answer forthcoming... – Jason Swett Jan 16 '14 at 16:30

1 Answers1

8

I can't attest to the accuracy of the following but it's the best of my understanding. Feel free to set me straight if you know better.

There are two steps that happen when a user creates an account:

  1. Tokenization. This happens via an XHR request.
  2. Account creation. This happens on the server side.

In Stripe test mode, I understand that all numbers that pass the Luhn check will get successfully tokenized, including, significantly, Stripe's special test numbers. Where the (correct) failure will happen is when the server-side account creation happens.

In Stripe live mode, I understand that all numbers that pass the Luhn check will get successfully tokenized EXCEPT Stripe's test numbers. Stripe will reject these numbers precisely because they're Stripe's test numbers.

So the best solution I can think of is to tell the client that Stripe's test numbers will always silently fail in production, and our options are to a) live with that or b) write code that will specifically catch the Stripe test numbers and present an error in production when those numbers are used.

Jason Swett
  • 43,526
  • 67
  • 220
  • 351