我正确设置了Stripe集成,因为它确实返回了一个错误This customer has no attached payment source
,这是一个条带错误,表明该表单没有返回足够的付款信息。
这是我的subscriptions.js.coffee
:
stripeResponseHandler = (status, response) ->
$form = $('#payment-form')
if response.error
#Show the errors on the form
$form.find('.payment-errors').text response.error.message
$form.find('button').prop 'disabled', false
else
# response contains id and card, which contains additional card details
token = response.id
#Insert the token into the form so it gets submitted to the server
$form.append $('<input type="hidden" name="stripeToken" />').val(token)
# and submit
$form.get(0).submit()
return
jQuery ($) ->
$('payment-form').submit (event) ->
$form = $(this)
$form.find('button').attr 'disabled', true
Stripe.card.createToken $form, stripeResponseHandler
false
return
这是new.html.erb
的表格:
<% unless @subscription.errors.blank? %>
<%= @subscription.errors.full_messages.to_sentence %>
<% end %>
<h2>Subcribing to <%= @plan.name %></h2>
<%= form_for @subscription, html: {id: 'payment-form'} do |f| %>
<input type="hidden" name="plan_id", value="<%= @plan.id %>" />
<span class="payment-errors"></span>
<div class="form-row">
<label>
<span>Email Address</span>
<input type="email" size="20" name="email_address" />
</label>
</div>
<div class="form-row">
<label>
<span>Card Number</span>
<input type="text" size="20" data-stripe="number" />
</label>
</div>
<div class="form-row">
<label>
<span>CVC</span>
<input type="text" size="4" data-stripe="cvc" />
</label>
</div>
<div class="form-row">
<label>
<span>Expiration (MM/YYYY)</span>
<input type="text" size="2" data-stripe="exp-month" />
</label>
<span> / </span>
<input type="text" size="4" data-stripe="exp-year" />
</div>
<button type="submit">Pay Now</button>
<% end %>
这是SubscriptionsController#Create
:
def create
@plan = Plan.find(params[:plan_id])
@subscription = CreateSubscription.call(
@plan,
params[:email_address],
params[:stripeToken]
)
if @subscription.errors.blank?
flash[:notice] = "Thank you for your purchase! Please click the link in the email we just sent you to get started."
redirect_to authenticated_root_path
else
render :new
end
end
以上称之为app/services/create_subscription.rb
:
class CreateSubscription
def self.call(plan, email_address, token)
user, raw_token = CreateUser.call(email_address)
subscription = Subscription.new(
plan: plan,
user: user
)
begin
stripe_sub = nil
if user.stripe_customer_id.blank?
binding.pry
customer = Stripe::Customer.create(
source: token,
email: user.email,
plan: plan.stripe_id
)
user.stripe_customer_id = customer.id
user.save!
stripe_sub = customer.subscriptions.first
else
customer = Stripe::Customer.retrieve(user.stripe_customer_id)
stripe_sub = customer.subscriptions.create(
plan: plan.stripe_id
)
end
subscription.stripe_id = stripe_sub.id
subscription.save!
rescue Stripe::StripeError => e
subscription.errors[:base] << e.message
end
subscription
end
end
我知道表单未收到stripeToken
的原因是因为当我在binding.pry
中使用create
并执行此操作时:
00:52:31 web.1 | 14: def create
00:52:31 web.1 | 15: @plan = Plan.find(params[:plan_id])
00:52:31 web.1 | => 16: binding.pry
00:52:31 web.1 | 17: @subscription = CreateSubscription.call(
00:52:31 web.1 | 18: @plan,
00:52:31 web.1 | 19: params[:email_address],
00:52:31 web.1 | 20: params[:stripeToken]
00:52:31 web.1 | 21: )
00:52:31 web.1 | 22: if @subscription.errors.blank?
00:52:31 web.1 | 23: flash[:notice] = "Thank you for your purchase! Please click the link in the email we just sent you to get started."
00:52:31 web.1 | 24: redirect_to authenticated_root_path
00:52:31 web.1 | 25: else
00:52:31 web.1 | 26: render :new
00:52:31 web.1 | 27: end
00:52:31 web.1 | 28: end
00:52:31 web.1 |
[1] pry(#<SubscriptionsController>)> params
00:52:37 web.1 | => {"utf8"=>"✓", "plan_id"=>"1", "email_address"=>"someuser@test.com", "action"=>"create", "controller"=>"subscriptions"}
请注意,没有params[:stripeToken]
。
此外,当我在binding.pry
服务中尝试create_subscription.rb
时,这就是我得到的:
00:52:41 web.1 | 10: begin
00:52:41 web.1 | 11: stripe_sub = nil
00:52:41 web.1 | 12: if user.stripe_customer_id.blank?
00:52:41 web.1 | => 13: binding.pry
00:52:41 web.1 | 14: customer = Stripe::Customer.create(
00:52:41 web.1 | 15: source: token,
00:52:41 web.1 | 16: email: user.email,
00:52:41 web.1 | 17: plan: plan.stripe_id
00:52:41 web.1 | 18: )
00:52:41 web.1 |
[1] pry(CreateSubscription)> token
00:52:44 web.1 | => nil
可能导致此问题的原因以及如何解决?
答案 0 :(得分:0)
事实证明,我的问题是一个愚蠢的错误。
请注意我的CoffeeScript中有这个:
<!DOCTYPE html> //specifying the html version
<html> //a html file will show on to the remote browser
<head>// head element of an html
<meta charset="ISO-8859-1">
<title>Insert title here</title>
<script>
function addMoreInputType() //custom function when a button is clicked
{ // opening of a function
var ip=document.getElementById("p1"); // id of a <p>tag
var cele=document.createElement("embed");//creating a new html element
cele.setAttribute("src","1.pdf"); //setting an attribute named src and 1.pdf is the pdf file on the server which i wanted to show on the client browser
cele.setAttribute("width","600px"); //setting an attribute named width to diplay
cele.setAttribute("height","500px");//setting an attribute named height
cele.setAttribute("alt","pdf");
cele.setAttribute("pluginspace","http://www.adobe.com/products/acrobat/readstep2 .html");// that is the plugin
cele.setAttribute("internalinstanceid","14");// that is setting the attribute for the new html element
ip.appendChild(cele);// finally appending it to p tag child
} //closing of a function
</script> // ending of the script tag
</head> //end of the head tag
<body> // the content to be displayed on the client browser
<input type="button" value=" clickme " onclick="addMoreInputType()">Button click// a button which on clicking will invoke the addM....() so that they will request to server to give the pdf file and show onto browser's webpage area
<p id="p1"></p> // p tag having id p1
</body>//end of body of html
</html>//end of html file
问题出在表单选择器中。我没有将jQuery ($) ->
$('payment-form').submit (event) ->
$form = $(this)
$form.find('button').attr 'disabled', true
Stripe.card.createToken $form, stripeResponseHandler
false
return
添加到表单的ID中。
所以一旦改变了这一行:
#
对此:
$('payment-form').submit (event) ->
它就像一个魅力。
DOH! Faceslap