diff options
Diffstat (limited to 'billing/app/controllers')
-rw-r--r-- | billing/app/controllers/billing_base_controller.rb | 22 | ||||
-rw-r--r-- | billing/app/controllers/credit_card_info_controller.rb | 35 | ||||
-rw-r--r-- | billing/app/controllers/customer_controller.rb | 64 | ||||
-rw-r--r-- | billing/app/controllers/payments_controller.rb | 47 | ||||
-rw-r--r-- | billing/app/controllers/subscriptions_controller.rb | 51 |
5 files changed, 219 insertions, 0 deletions
diff --git a/billing/app/controllers/billing_base_controller.rb b/billing/app/controllers/billing_base_controller.rb new file mode 100644 index 0000000..06820a6 --- /dev/null +++ b/billing/app/controllers/billing_base_controller.rb @@ -0,0 +1,22 @@ +class BillingBaseController < ApplicationController + before_filter :assign_user + + helper 'billing' + + # required for navigation to work. + def assign_user + if params[:user_id] + @user = User.find_by_param(params[:user_id]) + elsif params[:action] == "confirm" or params[:action] == "destroy" # confirms and subscription deletes will come back with different ID set, so check for this first + # This is only for cases where an admin cannot apply action for customer, but should be all confirms + @user = current_user + elsif params[:id] + @user = User.find_by_param(params[:id]) + else + # TODO + # hacky, what are cases where @user hasn't yet been set? certainly some cases with subscriptions and payments + @user = current_user + end + end + +end diff --git a/billing/app/controllers/credit_card_info_controller.rb b/billing/app/controllers/credit_card_info_controller.rb new file mode 100644 index 0000000..717fa18 --- /dev/null +++ b/billing/app/controllers/credit_card_info_controller.rb @@ -0,0 +1,35 @@ +class CreditCardInfoController < ApplicationController + before_filter :authorize, :set_user + + def edit + @credit_card = Braintree::CreditCard.find(params[:id]) + customer = Customer.find_by_user_id(@user.id) + if customer and customer.braintree_customer_id == @credit_card.customer_id + @tr_data = Braintree::TransparentRedirect. + update_credit_card_data(:redirect_url => confirm_credit_card_info_url, + :payment_method_token => @credit_card.token) + else + access_denied + end + + end + + def confirm + @result = Braintree::TransparentRedirect.confirm(request.query_string) + if @result.success? + render :action => "confirm" + else + @credit_card = Braintree::CreditCard.find(@result.params[:payment_method_token]) + render :action => "edit" + end + end + + + private + + def set_user + # this assumes anybody, even an admin, will not access for another user. + @user = current_user + end + +end diff --git a/billing/app/controllers/customer_controller.rb b/billing/app/controllers/customer_controller.rb new file mode 100644 index 0000000..901cb34 --- /dev/null +++ b/billing/app/controllers/customer_controller.rb @@ -0,0 +1,64 @@ +class CustomerController < BillingBaseController + before_filter :authorize, :fetch_customer + + def show + if @customer + @customer.with_braintree_data! + @default_cc = @customer.default_credit_card + @active_subscription = @customer.subscriptions + @transactions = @customer.braintree_customer.transactions + end + end + + def new + if @customer.has_payment_info? + redirect_to edit_customer_path(@user), :notice => 'Here is your saved customer data' + else + fetch_new_transparent_redirect_data + end + end + + def edit + fetch_edit_transparent_redirect_data + end + + def confirm + @result = Braintree::TransparentRedirect.confirm(request.query_string) + if @result.success? + @customer.braintree_customer = @result.customer + @customer.save + render :action => "confirm" + elsif @customer.has_payment_info? + fetch_edit_transparent_redirect_data + render :action => "edit" + else + fetch_new_transparent_redirect_data + render :action => "new" + end + end + + protected + + def fetch_new_transparent_redirect_data + access_denied unless @user == current_user # admins cannot do this for others + @tr_data = Braintree::TransparentRedirect. + create_customer_data(:redirect_url => confirm_customer_url) + end + + def fetch_edit_transparent_redirect_data + access_denied unless @user == current_user # admins cannot do this for others + @customer.with_braintree_data! + @default_cc = @customer.default_credit_card + @tr_data = Braintree::TransparentRedirect. + update_customer_data(:redirect_url => confirm_customer_url, + :customer_id => @customer.braintree_customer_id) ##?? + end + + def fetch_customer + @customer = Customer.find_by_user_id(@user.id) + if @user == current_user + @customer ||= Customer.new(user: @user) + end + access_denied unless (@customer and (@customer.user == current_user)) or admin? + end +end diff --git a/billing/app/controllers/payments_controller.rb b/billing/app/controllers/payments_controller.rb new file mode 100644 index 0000000..17ac0f3 --- /dev/null +++ b/billing/app/controllers/payments_controller.rb @@ -0,0 +1,47 @@ +class PaymentsController < BillingBaseController + before_filter :authorize, :only => [:index] + + def new + fetch_transparent_redirect + end + + def confirm + @result = Braintree::TransparentRedirect.confirm(request.query_string) + if @result.success? + render :action => "confirm" + else + fetch_transparent_redirect + render :action => "new" + end + end + + def index + access_denied unless admin? or (@user == current_user) + customer = Customer.find_by_user_id(@user.id) + braintree_data = Braintree::Customer.find(customer.braintree_customer_id) + # these will be ordered by created_at descending, per http://stackoverflow.com/questions/16425475/ + @transactions = braintree_data.transactions + end + + protected + + + def fetch_transparent_redirect + if logged_in? + if @customer = Customer.find_by_user_id(@user.id) + @customer.with_braintree_data! + braintree_customer_id = @customer.braintree_customer_id + @default_cc = @customer.default_credit_card + else + # TODO: this requires user to add self to vault before making payment. Is that desired functionality? + redirect_to new_customer_path, :notice => 'Before making payment, please add your customer data' + end + end + + # TODO: What is this supposed to do if braintree_customer_id was not set yet? + # Response: it can be used to make a payment that is not attributed to any customer (ie, a donation) + @tr_data = Braintree::TransparentRedirect.transaction_data redirect_url: confirm_payment_url, + transaction: { type: "sale", customer_id: braintree_customer_id, options: {submit_for_settlement: true } } + end + +end diff --git a/billing/app/controllers/subscriptions_controller.rb b/billing/app/controllers/subscriptions_controller.rb new file mode 100644 index 0000000..4047847 --- /dev/null +++ b/billing/app/controllers/subscriptions_controller.rb @@ -0,0 +1,51 @@ +class SubscriptionsController < BillingBaseController + before_filter :authorize + before_filter :fetch_subscription, :only => [:show, :destroy] + before_filter :confirm_no_active_subscription, :only => [:new, :create] + # for now, admins cannot create or destroy subscriptions for others: + before_filter :confirm_self, :only => [:destroy, :new, :create] + + def new + # don't show link to subscribe if they are already subscribed? + credit_card = @customer.default_credit_card #safe to assume default? + @payment_method_token = credit_card.token + @plans = Braintree::Plan.all + end + + # show has no content, so not needed at this point. + + def create + @result = Braintree::Subscription.create( :payment_method_token => params[:payment_method_token], :plan_id => params[:plan_id] ) + end + + def destroy + @result = Braintree::Subscription.cancel params[:id] + end + + def index + customer = Customer.find_by_user_id(@user.id) + @subscriptions = customer.subscriptions(nil, false) + end + + private + + def fetch_subscription + @subscription = Braintree::Subscription.find params[:id] + @subscription_customer_id = @subscription.transactions.first.customer_details.id #all of subscriptions transactions should have same customer + current_user_customer = Customer.find_by_user_id(current_user.id) + access_denied unless admin? or (current_user_customer and current_user_customer.braintree_customer_id == @subscription_customer_id) + + end + + def confirm_no_active_subscription + @customer = Customer.find_by_user_id(@user.id) + if subscription = @customer.subscriptions # will return active subscription, if it exists + redirect_to subscription_path(subscription.id), :notice => 'You already have an active subscription' + end + end + + def confirm_self + @user == current_user + end + +end |