0

I have a one to one relationship between a User and a Subscription model using Stripe for payments, devise for user authentication and Pundit for roles.

When I create my Subscription model from my create action, I get param is missing or the value is empty error because my form isn't passing the @subscription object. Why isn't my @subscription being passed through params?

Here is my code for SubscriptionsContrller:

class SubscriptionsController < ApplicationController
  before_filter :authenticate_user!
  after_action :verify_authorized

 # def index
 #  end
 #
 #  def show
 #  end

  def new
    @subscription = Subscription.new
    authorize @subscription
  end

  def edit
  end

  def create
    # create the customer first if it doesn't exist
    if (current_user.customer_id.blank?)
      customer = Stripe::Customer.create(:email => current_user.email, :card => params[:stripeToken])
      current_user.customer_id = customer.id
      current_user.save!
    end

    @subscription = current_user.create_subscription(secure_params)
    @subscription.save_with_payment
    authorize @subscription
  end

  def secure_params
    params.require(:subscription).permit(:stripeToken, :plan_id)
  end

end

and here is the Subscription Model:

class Subscription < ActiveRecord::Base
  belongs_to :user

  def save_with_payment
    if valid?
      # first get the customer id from the subscriber
      customer = Stripe::Customer.retrieve(user.customer_id)

      if (@subscription_id.blank?)
        stripe_sub = customer.subscriptions.create(:plan => plan_id)
        @subscription_id = stripe_sub.id
      else
        stripe_sub = customer.subscriptions.retrieve(subscription_id)
        stripe_sub.plan = plan_id
        stripe_sub.save
      end

      @plan_id = plan_id
      save
    end
  end

end

Here is the form code in new.html.erb:

<%= form_for @subscription do |f| %>
  <% if @subscription.errors.any? %>
    <div class="error_messages">
      <h2><%= pluralize(@subscription.errors.count, "error") %> prohibited this subscription from being saved:</h2>
      <ul>
      <% @subscription.errors.full_messages.each do |msg| %>
        <li><%= msg %></li>
      <% end %>
      </ul>
    </div>
  <% end %>
  <div class="form-row">
      <%= f.label :plan_id, "Plan " %>
      <%= text_field_tag :plan_id, nil %>
  </div>
  <div class="form-row">
      <%= f.label :card_number, "Credit Card Number " %>
      <%= text_field_tag :card_number, nil, {'data-stripe' => 'number'} %>
  </div>
  <div class="form-row">
      <%= f.label :card_code, "Security Code on Card (CVV)" %>
      <%= text_field_tag :card_code, nil, {'data-stripe' => 'ccv'} %>
  </div>
  <div class="form-row">
    <%= f.label :card_month, "Card Expiration" %>
    <%= select_month nil, {add_month_numbers_true: true}, {name: nil, id: "card_month", 'data-stripe' => 'exp_month'} %>
    <%= select_year nil, {start_year: Date.today.year, end_year: Date.today.year+15}, {name: nil, id: "card_year", 'data-stripe' => 'exp_year'} %>
  </div>
    <div class="payment-errors">
        <noscript>JavaScript is not enabled and is required for this form. First enable it in your web browser settings.</noscript>
      </div>
  <div class="actions"><%= f.submit "Subscribe" %></div>
<% end %>

and finally, here is my request parameters

{"utf8"=>"✓", "authenticity_token"=>"d5tcFSiFw1XIcPou3HTrISSOIObujo0XfUq+MTNihuk=", 
"plan_id"=>"basic_yearly", "card_number"=>"4242 4242 4242 4242", "card_code"=>"123", 
"action"=>"create", "controller"=>"subscriptions"}
Hamed Saadat
  • 429
  • 5
  • 8

1 Answers1

1

Turns out that I was mix and matching form_for helpers and form tags.

To get it working turn this:

<%= text_field_tag :plan_id, nil %>

into

<%= f.text_field :plan_id %>
Hamed Saadat
  • 429
  • 5
  • 8