lolita-paypal 1.0.1 → 1.0.2

Sign up to get free protection for your applications and to get access to all the features.
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA1:
3
- metadata.gz: bb78f556fc597ed2399437d646979f307d8e13fd
4
- data.tar.gz: 1aa48572ad554388d073642fc9b33ee47555762b
3
+ metadata.gz: f72f68aa9c08f40b7d7b96b912d234a52d04ec2b
4
+ data.tar.gz: 39d596dd0d33b3deafd44d1e1ade59636d6f45fc
5
5
  SHA512:
6
- metadata.gz: 1d78cd37db7fee1223cef26cc2c923bd9345ae3970b7dd91d0e6e84950aeefface11a0e42f6d6d666cfec0575cb67849752e330665ed524ce26f74509f3c7893
7
- data.tar.gz: 55542a331afb0af45014145b65debf01db2b5b2ccfe359009ffbaf3323d552f88ad502bc0e6963125be0ab7709ed9b97f7481ba860a4e70e063a675681ea7456
6
+ metadata.gz: 3bc0c193eb33638d9886b1ed27f768e7de57af21c7e91e34f9ace4b54bf9235a0128ba5d61dbd6a7e6c2803358119c588807c3b543017a2fdc9133c03600094d
7
+ data.tar.gz: 3cf02a76d8a93ddf587a17d55424258fe85202ab72f327b6fc04aead833bde50addd688552c71b5fd1e0dd35b7b151900bea8f7e901c61df735a2018272d603f
@@ -43,7 +43,7 @@ module LolitaPaypal
43
43
  def payment_from_ipn
44
44
  if subject = params['custom'] || params['cm']
45
45
  klass, id = subject.split('___')
46
- payment = klass.constantize.find(id)
46
+ payment = klass.camelize.constantize.find(id)
47
47
  end
48
48
  end
49
49
 
@@ -0,0 +1,74 @@
1
+ module LolitaPaypal
2
+ class TransactionsController < LolitaPaypal::ApplicationController
3
+ protect_from_forgery except: :answer
4
+ before_filter :is_ssl_required
5
+ before_filter :set_active_payment, :check_valid_payment, only: :checkout
6
+
7
+ include ActiveMerchant::Billing::Integrations
8
+
9
+ # renders form with encrypted data and redirects to Paypal web interface
10
+ def checkout
11
+ @payment_request = LolitaPaypal::Request.new(@payment)
12
+ render 'lolita_paypal/payment_form'
13
+ ensure
14
+ LolitaPaypal.logger.info("[#{session_id}][#{@payment.id}][checkout]")
15
+ end
16
+
17
+ # process ipn request
18
+ # POST is sent from paypal and will create transaction
19
+ # GET is a redirect from paypal and will redirect back to return_path
20
+ def answer
21
+ if request.post?
22
+ if ipn_notify.acknowledge
23
+ LolitaPaypal::Transaction.create_transaction(ipn_notify, payment_from_ipn, request)
24
+ end
25
+ render nothing: true
26
+ else
27
+ if payment_from_ipn
28
+ redirect_to payment_from_ipn.paypal_return_path
29
+ else
30
+ render text: I18n.t('lolita_paypal.wrong_request'), status: 400
31
+ end
32
+ end
33
+ ensure
34
+ LolitaPaypal.logger.info("[#{session_id}][#{payment_from_ipn && payment_from_ipn.id}][answer] #{params}")
35
+ end
36
+
37
+ private
38
+
39
+ def ipn_notify
40
+ @ipn_notify ||= Paypal::Notification.new(request.raw_post)
41
+ end
42
+
43
+ def payment_from_ipn
44
+ if subject = params['custom'] || params['cm']
45
+ klass, id = subject.split('___')
46
+ payment = klass.constantize.find(id)
47
+ end
48
+ end
49
+
50
+ # returns current payment instance from session
51
+ def set_active_payment
52
+ @payment ||= session[:payment_data][:billing_class].constantize.find(session[:payment_data][:billing_id])
53
+ rescue
54
+ render text: I18n.t('lolita_paypal.wrong_request'), status: 400
55
+ end
56
+
57
+ # payment should not be paid
58
+ def check_valid_payment
59
+ if @payment.paid?
60
+ render text: I18n.t('lolita_paypal.wrong_request'), status: 400
61
+ end
62
+ end
63
+
64
+ # forces SSL in production mode if availab:le
65
+ def is_ssl_required
66
+ ssl_required(:answer, :checkout) if defined?(ssl_required)
67
+ end
68
+
69
+
70
+ def session_id
71
+ request.session_options[:id]
72
+ end
73
+ end
74
+ end
@@ -1,49 +1,49 @@
1
- require "ipaddr"
2
- # Available statuses
3
- # -----------------
4
- # Canceled-Reversal
5
- # Completed
6
- # Denied
7
- # Expired
8
- # Failed
9
- # In-Progress
10
- # Partially-Refunded
11
- # Pending
12
- # Processed
13
- # Refunded
14
- # Reversed
15
- # Voided
16
- module LolitaPaypal
17
- class Transaction < ActiveRecord::Base
18
- self.table_name = "paypal_transactions"
19
- belongs_to :paymentable, polymorphic: true
20
- after_save :touch_paymentable
21
- default_scope -> { order(:id) }
22
- validates_associated :paymentable
23
-
24
- def ip
25
- IPAddr.new(self[:ip].to_i, Socket::AF_INET).to_s
26
- end
27
-
28
- def ip=(x)
29
- self[:ip] = IPAddr.new(x).to_i
30
- end
31
-
32
- # add new transaction after IPN response
33
- def self.create_transaction notify, payment, request
34
- self.create!(
35
- transaction_id: notify.transaction_id,
36
- status: notify.status,
37
- paymentable: payment,
38
- ip: request.remote_ip
39
- )
40
- end
41
-
42
- private
43
-
44
- # trigger "paypal_trx_saved" on our paymentable model
45
- def touch_paymentable
46
- paymentable.paypal_trx_saved(self)
47
- end
48
- end
49
- end
1
+ require "ipaddr"
2
+ # Available statuses
3
+ # -----------------
4
+ # Canceled-Reversal
5
+ # Completed
6
+ # Denied
7
+ # Expired
8
+ # Failed
9
+ # In-Progress
10
+ # Partially-Refunded
11
+ # Pending
12
+ # Processed
13
+ # Refunded
14
+ # Reversed
15
+ # Voided
16
+ module LolitaPaypal
17
+ class Transaction < ActiveRecord::Base
18
+ self.table_name = "paypal_transactions"
19
+ belongs_to :paymentable, polymorphic: true
20
+ after_save :touch_paymentable
21
+ default_scope -> { order(:id) }
22
+ validates_associated :paymentable
23
+
24
+ def ip
25
+ IPAddr.new(self[:ip].to_i, Socket::AF_INET).to_s
26
+ end
27
+
28
+ def ip=(x)
29
+ self[:ip] = IPAddr.new(x).to_i
30
+ end
31
+
32
+ # add new transaction after IPN response
33
+ def self.create_transaction notify, payment, request
34
+ self.create!(
35
+ transaction_id: notify.transaction_id,
36
+ status: notify.status,
37
+ paymentable: payment,
38
+ ip: request.remote_ip
39
+ )
40
+ end
41
+
42
+ private
43
+
44
+ # trigger "paypal_trx_saved" on our paymentable model
45
+ def touch_paymentable
46
+ paymentable.paypal_trx_saved(self)
47
+ end
48
+ end
49
+ end
@@ -1,5 +1,5 @@
1
- Rails.application.routes.draw do
2
- get "/paypal/checkout" => "lolita_paypal/transactions#checkout", as: "checkout_paypal"
3
- get "/paypal/answer" => "lolita_paypal/transactions#answer", as: "answer_paypal"
4
- post "/paypal/answer" => "lolita_paypal/transactions#answer"
5
- end
1
+ Rails.application.routes.draw do
2
+ get "/paypal/checkout" => "lolita_paypal/transactions#checkout", as: "checkout_paypal"
3
+ get "/paypal/answer" => "lolita_paypal/transactions#answer", as: "answer_paypal"
4
+ post "/paypal/answer" => "lolita_paypal/transactions#answer"
5
+ end
@@ -1,4 +1,4 @@
1
- Run
2
- =============
3
-
4
- rails generate lolita_paypal
1
+ Run
2
+ =============
3
+
4
+ rails generate lolita_paypal
@@ -1,12 +1,12 @@
1
- class LolitaPaypalGenerator < Rails::Generator::Base
2
- def initialize(runtime_args, runtime_options = {})
3
- super
4
- usage if @args.first == "help"
5
- end
6
-
7
- def manifest
8
- record do |m|
9
- m.migration_template "paypal_transactions.erb", "db/migrate", :migration_file_name => "create_paypal_transactions"
10
- end
11
- end
12
- end
1
+ class LolitaPaypalGenerator < Rails::Generator::Base
2
+ def initialize(runtime_args, runtime_options = {})
3
+ super
4
+ usage if @args.first == "help"
5
+ end
6
+
7
+ def manifest
8
+ record do |m|
9
+ m.migration_template "paypal_transactions.erb", "db/migrate", :migration_file_name => "create_paypal_transactions"
10
+ end
11
+ end
12
+ end
@@ -1,17 +1,17 @@
1
- class CreatePaypalTransactions < ActiveRecord::Migration
2
- def self.up
3
- create_table :paypal_transactions do |t|
4
- t.string :transaction_id
5
- t.string :status
6
- t.references :paymentable, polymorphic: true
7
- t.string :ip
8
- t.timestamps
9
- end
10
- add_index :paypal_transactions, :status
11
- add_index :paypal_transactions, [:paymentable_type, :paymentable_id]
12
- end
13
-
14
- def self.down
15
- drop_table :paypal_transactions
16
- end
17
- end
1
+ class CreatePaypalTransactions < ActiveRecord::Migration
2
+ def self.up
3
+ create_table :paypal_transactions do |t|
4
+ t.string :transaction_id
5
+ t.string :status
6
+ t.references :paymentable, polymorphic: true
7
+ t.string :ip
8
+ t.timestamps
9
+ end
10
+ add_index :paypal_transactions, :status
11
+ add_index :paypal_transactions, [:paymentable_type, :paymentable_id]
12
+ end
13
+
14
+ def self.down
15
+ drop_table :paypal_transactions
16
+ end
17
+ end
@@ -1,74 +1,74 @@
1
- module LolitaPaypal
2
- module Billing
3
- def self.included(base)
4
- base.has_many :paypal_transactions, as: :paymentable, class_name: 'LolitaPaypal::Transaction', dependent: :destroy
5
- base.class_eval do
6
-
7
- # Payment description
8
- def description
9
- raise 'Redefine this method in your billing model.'
10
- end
11
-
12
- # Price of payment in cents
13
- def price
14
- raise 'Redefine this method in your billing model.'
15
- end
16
-
17
- # Currency as 3 letter code as in ISO 4217
18
- def currency
19
- raise 'Redefine this method in your billing model.'
20
- end
21
-
22
- def paypal_trx_saved trx
23
- raise 'Redefine this method in your billing model.'
24
- end
25
-
26
- # Paypal will redirect to this path after payment
27
- def paypal_return_path
28
- raise 'Redefine this method in your billing model.'
29
- end
30
-
31
- # To pass any extra parameter to paypal, redefine 'paypal_request_variables'
32
- # with any of these keys. Keys business, item_name, amount, currency_code - already are added.
33
- #+---------------+---------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------+
34
- #| business | Email address on your PayPal account |
35
- #| quantity | Number of items. This will multiply the amount if greater than one |
36
- #| item_name | Name of the item (or a name for the shopping cart). Must be alpha-numeric, with a 127character limit |
37
- #| item_number | Optional pass-through variable for you to track payments. Must be alpha-numeric, with a 127 character limit |
38
- #| amount | Price of the item (the total price of all items in the shopping cart) |
39
- #| shipping | The cost of shipping the item |
40
- #| shipping2 | The cost of shipping each additional item |
41
- #| handling | The cost of handling |
42
- #| tax | Transaction-based tax value. If present, the value passed here will override any profile tax settings you may have (regardless of the buyer's location). |
43
- #| no_shipping | Shipping address. If set to "1," your customer will not be asked for a shipping address. This is optional; if omitted or set to "0," your customer will be prompted to include a shipping address |
44
- #| cn | Optional label that will appear above the note field (maximum 40 characters) |
45
- #| no_note | Including a note with payment. If set to "1," your customer will not be prompted to include a note. This is optional; if omitted or set to "0," your customer will be prompted to include a note. |
46
- #| on0 | First option field name. 64 character limit |
47
- #| os0 | First set of option value(s). 200 character limit. "on0" must be defined for "os0" to be recognized. |
48
- #| on1 | Second option field name. 64 character limit |
49
- #| os1 | Second set of option value(s). 200 character limit. "on1" must be defined for "os1" to be recognized. |
50
- #| custom | Optional pass-through variable that will never be presented to your customer. Can be used to track inventory |
51
- #| invoice | Optional pass-through variable that will never be presented to your customer. Can be used to track invoice numbers |
52
- #| notify_url | Only used with IPN. An internet URL where IPN form posts will be sent |
53
- #| return | An internet URL where your customer will be returned after completing payment |
54
- #| cancel_return | An internet URL where your customer will be returned after cancelling payment |
55
- #| image_url | The internet URL of the 150 X 50 pixel image you would like to use as your logo |
56
- #| cs | Sets the background color of your payment pages. If set to "1," the background color will be black. This is optional; if omitted or set to "0," the background color will be white |
57
- #+---------------+---------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------+
58
- # more info at https://www.paypal.com/cgi-bin/webscr?cmd=p/pdn/howto_checkout-outside
59
- def paypal_request_variables
60
- {}
61
- end
62
-
63
- # Add this to your paid? method along with other payment methods
64
- # Example:
65
- # def paid?
66
- # paypal_paid? || first_data_paid?
67
- # end
68
- def paypal_paid?
69
- self.paypal_transactions.where(status: 'Completed').count >= 1
70
- end
71
- end
72
- end
73
- end
74
- end
1
+ module LolitaPaypal
2
+ module Billing
3
+ def self.included(base)
4
+ base.has_many :paypal_transactions, as: :paymentable, class_name: 'LolitaPaypal::Transaction', dependent: :destroy
5
+ base.class_eval do
6
+
7
+ # Payment description
8
+ def description
9
+ raise 'Redefine this method in your billing model.'
10
+ end
11
+
12
+ # Price of payment in cents
13
+ def price
14
+ raise 'Redefine this method in your billing model.'
15
+ end
16
+
17
+ # Currency as 3 letter code as in ISO 4217
18
+ def currency
19
+ raise 'Redefine this method in your billing model.'
20
+ end
21
+
22
+ def paypal_trx_saved trx
23
+ raise 'Redefine this method in your billing model.'
24
+ end
25
+
26
+ # Paypal will redirect to this path after payment
27
+ def paypal_return_path
28
+ raise 'Redefine this method in your billing model.'
29
+ end
30
+
31
+ # To pass any extra parameter to paypal, redefine 'paypal_request_variables'
32
+ # with any of these keys. Keys business, item_name, amount, currency_code - already are added.
33
+ #+---------------+---------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------+
34
+ #| business | Email address on your PayPal account |
35
+ #| quantity | Number of items. This will multiply the amount if greater than one |
36
+ #| item_name | Name of the item (or a name for the shopping cart). Must be alpha-numeric, with a 127character limit |
37
+ #| item_number | Optional pass-through variable for you to track payments. Must be alpha-numeric, with a 127 character limit |
38
+ #| amount | Price of the item (the total price of all items in the shopping cart) |
39
+ #| shipping | The cost of shipping the item |
40
+ #| shipping2 | The cost of shipping each additional item |
41
+ #| handling | The cost of handling |
42
+ #| tax | Transaction-based tax value. If present, the value passed here will override any profile tax settings you may have (regardless of the buyer's location). |
43
+ #| no_shipping | Shipping address. If set to "1," your customer will not be asked for a shipping address. This is optional; if omitted or set to "0," your customer will be prompted to include a shipping address |
44
+ #| cn | Optional label that will appear above the note field (maximum 40 characters) |
45
+ #| no_note | Including a note with payment. If set to "1," your customer will not be prompted to include a note. This is optional; if omitted or set to "0," your customer will be prompted to include a note. |
46
+ #| on0 | First option field name. 64 character limit |
47
+ #| os0 | First set of option value(s). 200 character limit. "on0" must be defined for "os0" to be recognized. |
48
+ #| on1 | Second option field name. 64 character limit |
49
+ #| os1 | Second set of option value(s). 200 character limit. "on1" must be defined for "os1" to be recognized. |
50
+ #| custom | Optional pass-through variable that will never be presented to your customer. Can be used to track inventory |
51
+ #| invoice | Optional pass-through variable that will never be presented to your customer. Can be used to track invoice numbers |
52
+ #| notify_url | Only used with IPN. An internet URL where IPN form posts will be sent |
53
+ #| return | An internet URL where your customer will be returned after completing payment |
54
+ #| cancel_return | An internet URL where your customer will be returned after cancelling payment |
55
+ #| image_url | The internet URL of the 150 X 50 pixel image you would like to use as your logo |
56
+ #| cs | Sets the background color of your payment pages. If set to "1," the background color will be black. This is optional; if omitted or set to "0," the background color will be white |
57
+ #+---------------+---------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------+
58
+ # more info at https://www.paypal.com/cgi-bin/webscr?cmd=p/pdn/howto_checkout-outside
59
+ def paypal_request_variables
60
+ {}
61
+ end
62
+
63
+ # Add this to your paid? method along with other payment methods
64
+ # Example:
65
+ # def paid?
66
+ # paypal_paid? || first_data_paid?
67
+ # end
68
+ def paypal_paid?
69
+ self.paypal_transactions.where(status: 'Completed').count >= 1
70
+ end
71
+ end
72
+ end
73
+ end
74
+ end
@@ -30,7 +30,7 @@ module LolitaPaypal
30
30
  'cmd' => '_xclick',
31
31
  'business' => LolitaPaypal.account_name,
32
32
  'item_name' => payment.description,
33
- 'custom' =>"#{payment.class}___#{payment_id}",
33
+ 'custom' =>"#{payment.class.to_s.underscore}___#{payment_id}",
34
34
  'amount' => amount(payment.price),
35
35
  'currency_code' => payment.currency,
36
36
  'no_note' => '1',
@@ -0,0 +1,42 @@
1
+ module LolitaPaypal
2
+
3
+ class Request
4
+ attr_reader :payment
5
+
6
+ def initialize(payment = nil)
7
+ @payment = payment
8
+ end
9
+
10
+ def self.encrypt_for_paypal(values)
11
+ signed = OpenSSL::PKCS7::sign(OpenSSL::X509::Certificate.new(LolitaPaypal.app_cert_pem), OpenSSL::PKey::RSA.new(LolitaPaypal.app_key_pem, ''), values.map { |k, v| "#{k}=#{v}" }.join("\n"), [], OpenSSL::PKCS7::BINARY)
12
+ OpenSSL::PKCS7::encrypt([OpenSSL::X509::Certificate.new(LolitaPaypal.paypal_cert_pem)], signed.to_der, OpenSSL::Cipher::Cipher::new('DES3'), OpenSSL::PKCS7::BINARY).to_s.gsub("\n", "")
13
+ end
14
+
15
+ def amount(money)
16
+ cents = money.respond_to?(:cents) ? money.cents : money
17
+ if money.nil? || cents.to_i <= 0
18
+ raise ArgumentError, 'money amount must be either a Money object or a positive integer in cents.'
19
+ end
20
+ sprintf("%.2f", cents.to_f / 100)
21
+ end
22
+
23
+ def payment_id
24
+ payment.id
25
+ end
26
+
27
+ def request_variables
28
+ {
29
+ 'cert_id' => LolitaPaypal.cert_id,
30
+ 'cmd' => '_xclick',
31
+ 'business' => LolitaPaypal.account_name,
32
+ 'item_name' => payment.description,
33
+ 'custom' =>"#{payment.class}___#{payment_id}",
34
+ 'amount' => amount(payment.price),
35
+ 'currency_code' => payment.currency,
36
+ 'no_note' => '1',
37
+ 'no_shipping' => '1',
38
+ 'return' => payment.paypal_return_path
39
+ }.merge(payment.paypal_request_variables)
40
+ end
41
+ end
42
+ end
@@ -1,3 +1,3 @@
1
1
  module LolitaPaypal
2
- VERSION = "1.0.1"
2
+ VERSION = "1.0.2"
3
3
  end
@@ -0,0 +1,3 @@
1
+ module LolitaPaypal
2
+ VERSION = "1.0.2"
3
+ end
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: lolita-paypal
3
3
  version: !ruby/object:Gem::Version
4
- version: 1.0.1
4
+ version: 1.0.2
5
5
  platform: ruby
6
6
  authors:
7
7
  - ITHouse
8
8
  autorequire:
9
9
  bindir: bin
10
10
  cert_chain: []
11
- date: 2014-06-03 00:00:00.000000000 Z
11
+ date: 2015-07-14 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: rails
@@ -154,6 +154,7 @@ files:
154
154
  - Rakefile
155
155
  - app/controllers/lolita_paypal/application_controller.rb
156
156
  - app/controllers/lolita_paypal/transactions_controller.rb
157
+ - app/controllers/lolita_paypal/transactions_controller.rb~
157
158
  - app/helpers/lolita_paypal/application_helper.rb
158
159
  - app/models/lolita_paypal/transaction.rb
159
160
  - app/views/lolita_paypal/payment_form.html.erb
@@ -168,7 +169,9 @@ files:
168
169
  - lib/lolita-paypal/custom_logger.rb
169
170
  - lib/lolita-paypal/engine.rb
170
171
  - lib/lolita-paypal/request.rb
172
+ - lib/lolita-paypal/request.rb~
171
173
  - lib/lolita-paypal/version.rb
174
+ - lib/lolita-paypal/version.rb~
172
175
  homepage: http://github.com/ithouse/lolita-paypal
173
176
  licenses: []
174
177
  metadata: {}
@@ -188,7 +191,7 @@ required_rubygems_version: !ruby/object:Gem::Requirement
188
191
  version: '0'
189
192
  requirements: []
190
193
  rubyforge_project:
191
- rubygems_version: 2.2.0
194
+ rubygems_version: 2.2.2
192
195
  signing_key:
193
196
  specification_version: 4
194
197
  summary: Paypal payment plugin for Lolita