ideal-mollie 0.0.1
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- data/.gitignore +7 -0
- data/.rspec +2 -0
- data/.yardopts +3 -0
- data/CHANGELOG.md +4 -0
- data/Gemfile +4 -0
- data/LICENSE.md +20 -0
- data/README.md +52 -0
- data/Rakefile +8 -0
- data/ideal-mollie.gemspec +32 -0
- data/lib/ideal-mollie.rb +172 -0
- data/lib/ideal-mollie/config.rb +32 -0
- data/lib/ideal-mollie/engine.rb +15 -0
- data/lib/ideal-mollie/ideal_exception.rb +17 -0
- data/lib/ideal-mollie/version.rb +4 -0
- data/spec/config_spec.rb +35 -0
- data/spec/ideal_exception_spec.rb +38 -0
- data/spec/ideal_mollie_spec.rb +66 -0
- data/spec/spec_helper.rb +15 -0
- data/spec/vcr_cassettes/banks.yml +33 -0
- data/spec/vcr_cassettes/check_payment.yml +82 -0
- data/spec/vcr_cassettes/new_payment.yml +54 -0
- data/spec/vcr_cassettes/request_payment.yml +32 -0
- metadata +196 -0
data/.gitignore
ADDED
data/.rspec
ADDED
data/.yardopts
ADDED
data/CHANGELOG.md
ADDED
data/Gemfile
ADDED
data/LICENSE.md
ADDED
@@ -0,0 +1,20 @@
|
|
1
|
+
Copyright (c) 2012 Manuel van Rijn, http://manuel.manuelles.nl/
|
2
|
+
|
3
|
+
Permission is hereby granted, free of charge, to any person obtaining
|
4
|
+
a copy of this software and associated documentation files (the
|
5
|
+
"Software"), to deal in the Software without restriction, including
|
6
|
+
without limitation the rights to use, copy, modify, merge, publish,
|
7
|
+
distribute, sublicense, and/or sell copies of the Software, and to
|
8
|
+
permit persons to whom the Software is furnished to do so, subject to
|
9
|
+
the following conditions:
|
10
|
+
|
11
|
+
The above copyright notice and this permission notice shall be
|
12
|
+
included in all copies or substantial portions of the Software.
|
13
|
+
|
14
|
+
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
|
15
|
+
EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
|
16
|
+
MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
|
17
|
+
NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
|
18
|
+
LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
|
19
|
+
OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
|
20
|
+
WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
|
data/README.md
ADDED
@@ -0,0 +1,52 @@
|
|
1
|
+
|
2
|
+
# Ideal Mollie (ideal-mollie)
|
3
|
+
|
4
|
+
A simple Ruby implementation for handling iDeal transactions with the [Mollie API](https://www.mollie.nl/support/documentatie/betaaldiensten/ideal/).
|
5
|
+
|
6
|
+
Here you can find the [Documentation](http://rubydoc.info/github/manuelvanrijn/ideal-mollie/master/frames)
|
7
|
+
|
8
|
+
## Getting started
|
9
|
+
|
10
|
+
### Install
|
11
|
+
|
12
|
+
To install the gem you could execute
|
13
|
+
|
14
|
+
```
|
15
|
+
sudo gem install ideal-mollie
|
16
|
+
```
|
17
|
+
|
18
|
+
Or you could add the gem into your `Gemfile`.
|
19
|
+
|
20
|
+
```
|
21
|
+
gem 'ideal-mollie'
|
22
|
+
```
|
23
|
+
|
24
|
+
Finally, if you don’t dig any of that gemming that’s so popular nowadays, you can install it as a plugin;
|
25
|
+
|
26
|
+
```
|
27
|
+
cd vendor/plugins
|
28
|
+
git clone --depth 1 git://github.com/manuelvanrijn/ideal-mollie.git ideal-mollie
|
29
|
+
```
|
30
|
+
|
31
|
+
### Configuration
|
32
|
+
|
33
|
+
Add the following config parameters to your environment config file
|
34
|
+
|
35
|
+
```
|
36
|
+
config.ideal_mollie.partner_id = 123456
|
37
|
+
config.ideal_mollie.report_url = "http://example.org/report"
|
38
|
+
config.ideal_mollie.return_url = "http://example.org/return"
|
39
|
+
config.ideal_mollie.test_mode = false
|
40
|
+
```
|
41
|
+
|
42
|
+
### Example Controller
|
43
|
+
|
44
|
+
TODO
|
45
|
+
|
46
|
+
## Changelog
|
47
|
+
|
48
|
+
A details overview could be found in the [CHANGELOG](https://github.com/manuelvanrijn/ideal-mollie/blob/master/CHANGELOG.md).
|
49
|
+
|
50
|
+
## Copyright
|
51
|
+
|
52
|
+
Copyright © 2012 Manuel van Rijn. See [LICENSE](https://github.com/manuelvanrijn/ideal-mollie/blob/master/LICENSE.md) for further details.
|
data/Rakefile
ADDED
@@ -0,0 +1,32 @@
|
|
1
|
+
# -*- encoding: utf-8 -*-
|
2
|
+
$:.push File.expand_path("../lib", __FILE__)
|
3
|
+
require "ideal-mollie/version"
|
4
|
+
|
5
|
+
Gem::Specification.new do |s|
|
6
|
+
s.name = "ideal-mollie"
|
7
|
+
s.version = IdealMollie::VERSION
|
8
|
+
s.authors = ["Manuel van Rijn"]
|
9
|
+
s.email = ["manuel@manuelles.nl"]
|
10
|
+
s.homepage = "https://github.com/manuelvanrijn/ideal-mollie"
|
11
|
+
s.summary = %q{Make iDeal Mollie payments without the pain}
|
12
|
+
s.description = %q{A simple Ruby implementation for handeling iDeal transactions with the Mollie API}
|
13
|
+
|
14
|
+
s.rubyforge_project = "ideal-mollie"
|
15
|
+
|
16
|
+
s.files = `git ls-files`.split("\n")
|
17
|
+
s.test_files = `git ls-files -- {test,spec,features}/*`.split("\n")
|
18
|
+
s.require_paths = ["lib"]
|
19
|
+
|
20
|
+
s.add_development_dependency "rspec"
|
21
|
+
s.add_development_dependency "vcr"
|
22
|
+
s.add_development_dependency "fakeweb"
|
23
|
+
s.add_development_dependency "yard"
|
24
|
+
s.add_development_dependency "redcarpet"
|
25
|
+
s.add_development_dependency "simplecov"
|
26
|
+
|
27
|
+
s.add_dependency "rake", "~> 0.9.0"
|
28
|
+
s.add_dependency "faraday", "~> 0.5.7"
|
29
|
+
s.add_dependency "faraday_middleware", "~> 0.3.2"
|
30
|
+
s.add_dependency "multi_xml", "~> 0.2.2"
|
31
|
+
s.add_dependency "nokogiri", "~> 1.4.1"
|
32
|
+
end
|
data/lib/ideal-mollie.rb
ADDED
@@ -0,0 +1,172 @@
|
|
1
|
+
# Gems
|
2
|
+
require "faraday"
|
3
|
+
require "faraday_middleware"
|
4
|
+
require "multi_xml"
|
5
|
+
|
6
|
+
# Files
|
7
|
+
require "ideal-mollie/config"
|
8
|
+
require "ideal-mollie/ideal_exception"
|
9
|
+
require "ideal-mollie/engine" if defined?(Rails) && Rails::VERSION::MAJOR == 3
|
10
|
+
|
11
|
+
#
|
12
|
+
# IdealMollie Module
|
13
|
+
#
|
14
|
+
module IdealMollie
|
15
|
+
#
|
16
|
+
# List of supported banks.
|
17
|
+
#
|
18
|
+
# @visibility public
|
19
|
+
#
|
20
|
+
# @example
|
21
|
+
# IdealMollie.banks
|
22
|
+
# # => [{:id=>"9999", :name=>"TBM Bank"}, ...]
|
23
|
+
#
|
24
|
+
# @return [Array] list of supported banks.
|
25
|
+
def self.banks
|
26
|
+
response = IdealMollie.request("banklist")
|
27
|
+
|
28
|
+
banks = response["bank"]
|
29
|
+
banks = [banks] unless banks.is_a?Array # to array if it isn't already
|
30
|
+
|
31
|
+
banks.map do |bank|
|
32
|
+
{:id => bank["bank_id"], :name => bank["bank_name"]}
|
33
|
+
end
|
34
|
+
end
|
35
|
+
|
36
|
+
#
|
37
|
+
# Create a new payment
|
38
|
+
#
|
39
|
+
# @visibility public
|
40
|
+
#
|
41
|
+
# @param [int] amount The amount of money to transfer (defined in cents).
|
42
|
+
# @param [String] description The description of the payment on the bank transfer.
|
43
|
+
# @param [String] bank_id The id of the bank selected from one of the supported banks.
|
44
|
+
#
|
45
|
+
# @example
|
46
|
+
#
|
47
|
+
# IdealMollie.new_payment(1000, "Ordernumber #123: new gadget", "0031")
|
48
|
+
# # => {
|
49
|
+
# # :transaction_id=>"72457c865d4b800eb8b0f3ba928ff495",
|
50
|
+
# # :amount=>1000,
|
51
|
+
# # :currency=>"EUR",
|
52
|
+
# # :URL=>"http://www.mollie.nl/partners/ideal-test-bank?order_nr=M738907M05885973&transaction_id=72457c865d4b800eb8b0f3ba928ff495&trxid=0073890705885973",
|
53
|
+
# # :message=>"Your iDEAL-payment has successfully been setup. Your customer should visit the given URL to make the payment"
|
54
|
+
# # }
|
55
|
+
#
|
56
|
+
# @return [Hash] the transaction object
|
57
|
+
def self.new_payment(amount, description, bank_id)
|
58
|
+
response = IdealMollie.request("fetch", {
|
59
|
+
:partnerid => Config.partner_id,
|
60
|
+
:reporturl => Config.report_url,
|
61
|
+
:returnurl => Config.return_url,
|
62
|
+
:description => description,
|
63
|
+
:amount => amount,
|
64
|
+
:bank_id => bank_id
|
65
|
+
})
|
66
|
+
order = response["order"]
|
67
|
+
|
68
|
+
result = {
|
69
|
+
:transaction_id => order["transaction_id"],
|
70
|
+
:amount => order["amount"].to_i,
|
71
|
+
:currency => order["currency"],
|
72
|
+
:url => order["URL"],
|
73
|
+
:message => order["message"]
|
74
|
+
}
|
75
|
+
result
|
76
|
+
end
|
77
|
+
|
78
|
+
#
|
79
|
+
# Check the status of a transaction.
|
80
|
+
#
|
81
|
+
# @visibility public
|
82
|
+
#
|
83
|
+
# @param [String] transaction_id the transaction to verify.
|
84
|
+
#
|
85
|
+
# @example
|
86
|
+
# IdealMollie.check_payment("4b99662febb42ce6f889d9c57f5cf3fa")
|
87
|
+
# # => {
|
88
|
+
# # :transaction_id => '4b99662febb42ce6f889d9c57f5cf3fa',
|
89
|
+
# # :amount => 1465,
|
90
|
+
# # :currency => "EUR",
|
91
|
+
# # :payed => true,
|
92
|
+
# # :consumer => {
|
93
|
+
# # :name => "Hr J Janssen",
|
94
|
+
# # :account => "P001234567",
|
95
|
+
# # :city => "Amsterdam"
|
96
|
+
# # },
|
97
|
+
# # :message => "This iDEAL-order has successfuly been payed for,
|
98
|
+
# # and this is the first time you check it.",
|
99
|
+
# # :status => "Expired"
|
100
|
+
# # }
|
101
|
+
#
|
102
|
+
# @note Once a transaction is payed, only the next time you verify the
|
103
|
+
# transaction will the value of 'payed' be 'true'.
|
104
|
+
# Else it will be 'false'.
|
105
|
+
#
|
106
|
+
# @return [Hash] the status of the transaction.
|
107
|
+
def self.check_payment(transaction_id)
|
108
|
+
response = IdealMollie.request("check", {
|
109
|
+
:partnerid => Config.partner_id,
|
110
|
+
:transaction_id => transaction_id
|
111
|
+
})
|
112
|
+
order = response["order"]
|
113
|
+
|
114
|
+
result = {
|
115
|
+
:transaction_id => order["transaction_id"],
|
116
|
+
:amount => order["amount"].to_i,
|
117
|
+
:currency => order["currency"],
|
118
|
+
:payed => order["payed"] == "true" ? true : false,
|
119
|
+
:message => order["message"],
|
120
|
+
:status => order["status"]
|
121
|
+
}
|
122
|
+
if order.has_key?("consumer")
|
123
|
+
consumer = order["consumer"]
|
124
|
+
result.merge!(:consumer => {
|
125
|
+
:name => consumer["consumerName"],
|
126
|
+
:account => consumer["consumerAccount"],
|
127
|
+
:city => consumer["consumerCity"]
|
128
|
+
})
|
129
|
+
end
|
130
|
+
result
|
131
|
+
end
|
132
|
+
|
133
|
+
class << self
|
134
|
+
MultiXml.parser = :nokogiri
|
135
|
+
|
136
|
+
#
|
137
|
+
# Perform a request to the https xlm server of mollie and return the responded xml
|
138
|
+
# which is converted to an hash
|
139
|
+
#
|
140
|
+
# @param [String] action The action to perform.
|
141
|
+
# @param [Hash] params Additional parameters to send like partner_id
|
142
|
+
#
|
143
|
+
# @raise [IdealMollie::IdealException] When a error is returned by Mollie
|
144
|
+
#
|
145
|
+
# @return [Hash] the returned XML as a Hash
|
146
|
+
def request(action, params={})
|
147
|
+
params.merge!(:a => action)
|
148
|
+
params.merge!(:testmode => Config.test_mode)
|
149
|
+
request = connection.post do |req|
|
150
|
+
req.url("", params)
|
151
|
+
end
|
152
|
+
response = request.body["response"]
|
153
|
+
|
154
|
+
if response.has_key?("item")
|
155
|
+
error = response["item"]
|
156
|
+
raise IdealMollie::IdealException.new(error["errorcode"], error["message"], error["type"])
|
157
|
+
end
|
158
|
+
response
|
159
|
+
end
|
160
|
+
|
161
|
+
private
|
162
|
+
|
163
|
+
def connection
|
164
|
+
@connection ||= Faraday::Connection.new(:url => "https://secure.mollie.nl/xml/ideal",
|
165
|
+
:headers => {:user_agent => "Ruby-IdealMollie"},
|
166
|
+
:ssl => {:verify => false}) do |builder|
|
167
|
+
builder.adapter Faraday.default_adapter
|
168
|
+
builder.use Faraday::Response::ParseXml
|
169
|
+
end
|
170
|
+
end
|
171
|
+
end
|
172
|
+
end
|
@@ -0,0 +1,32 @@
|
|
1
|
+
#
|
2
|
+
# Configuration object for storing some parameters required for making transactions
|
3
|
+
#
|
4
|
+
module IdealMollie::Config
|
5
|
+
class << self
|
6
|
+
attr_accessor :partner_id, :report_url, :return_url, :test_mode
|
7
|
+
|
8
|
+
# Set's the default value's to nil and false
|
9
|
+
def init!
|
10
|
+
@defaults = {
|
11
|
+
:@partner_id => nil,
|
12
|
+
:@report_url => nil,
|
13
|
+
:@return_url => nil,
|
14
|
+
:@test_mode => false
|
15
|
+
}
|
16
|
+
end
|
17
|
+
|
18
|
+
# Resets the value's to there previous value (instance_variable)
|
19
|
+
def reset!
|
20
|
+
@defaults.each { |key, value| instance_variable_set(key, value) }
|
21
|
+
end
|
22
|
+
|
23
|
+
# Set's the new value's as instance variables
|
24
|
+
def update!
|
25
|
+
@defaults.each do |key, value|
|
26
|
+
instance_variable_set(key, value) unless instance_variable_defined?(key)
|
27
|
+
end
|
28
|
+
end
|
29
|
+
end
|
30
|
+
init!
|
31
|
+
reset!
|
32
|
+
end
|
@@ -0,0 +1,15 @@
|
|
1
|
+
module IdealMollie
|
2
|
+
#
|
3
|
+
# Simpel extend on the Rails::Engine to add support for a new config section within the environment configs
|
4
|
+
#
|
5
|
+
# @example
|
6
|
+
# # /config/environments/development.rb
|
7
|
+
# config.ideal_mollie.partner_id = 123456
|
8
|
+
# config.ideal_mollie.report_url = "http://example.org/report"
|
9
|
+
# config.ideal_mollie.return_url = "http://example.org/return"
|
10
|
+
# config.ideal_mollie.test_mode = false
|
11
|
+
#
|
12
|
+
class Engine < Rails::Engine
|
13
|
+
config.ideal_mollie = IdealMollie::Config
|
14
|
+
end
|
15
|
+
end
|
@@ -0,0 +1,17 @@
|
|
1
|
+
module IdealMollie
|
2
|
+
#
|
3
|
+
# Exception class specific for the IdealMollie error that might occur
|
4
|
+
#
|
5
|
+
class IdealException < Exception
|
6
|
+
attr_accessor :errorcode, :message, :type
|
7
|
+
|
8
|
+
# @param [String] errorcode The errorcode
|
9
|
+
# @param [String] message The error description
|
10
|
+
# @param [String] type The error type
|
11
|
+
def initialize(errorcode, message, type)
|
12
|
+
self.errorcode = errorcode
|
13
|
+
self.message = message
|
14
|
+
self.type = type
|
15
|
+
end
|
16
|
+
end
|
17
|
+
end
|
data/spec/config_spec.rb
ADDED
@@ -0,0 +1,35 @@
|
|
1
|
+
require 'spec_helper'
|
2
|
+
|
3
|
+
describe IdealMollie::Config do
|
4
|
+
before(:each) do
|
5
|
+
@config = IdealMollie::Config
|
6
|
+
@config.test_mode = true
|
7
|
+
@config.partner_id = 123456
|
8
|
+
@config.report_url = "http://example.org/report"
|
9
|
+
@config.return_url = "http://example.org/return"
|
10
|
+
end
|
11
|
+
describe "#reset!" do
|
12
|
+
it "should reset the values" do
|
13
|
+
@config.reset!
|
14
|
+
@config.test_mode.should be_false
|
15
|
+
@config.partner_id.should be_nil
|
16
|
+
@config.report_url.should be_nil
|
17
|
+
@config.return_url.should be_nil
|
18
|
+
end
|
19
|
+
end
|
20
|
+
describe "#update!" do
|
21
|
+
it "should update" do
|
22
|
+
@config.test_mode = false
|
23
|
+
@config.partner_id = 987654
|
24
|
+
@config.report_url = "report"
|
25
|
+
@config.return_url = "return"
|
26
|
+
@config.update!
|
27
|
+
|
28
|
+
config = IdealMollie::Config
|
29
|
+
config.test_mode.should be_false
|
30
|
+
config.partner_id.should eq 987654
|
31
|
+
config.report_url.should eq "report"
|
32
|
+
config.return_url.should eq "return"
|
33
|
+
end
|
34
|
+
end
|
35
|
+
end
|
@@ -0,0 +1,38 @@
|
|
1
|
+
require 'spec_helper'
|
2
|
+
|
3
|
+
describe IdealMollie::IdealException do
|
4
|
+
context "#new_payment" do
|
5
|
+
it "should throw exception when no config is set" do
|
6
|
+
VCR.use_cassette("new_payment") do
|
7
|
+
expect { IdealMollie.new_payment(1234, "exception test", "0031") }.
|
8
|
+
to raise_error(IdealMollie::IdealException, /This account does not exist or is suspended./)
|
9
|
+
end
|
10
|
+
end
|
11
|
+
it "should throw an exception when a unknown account is specified" do
|
12
|
+
config = IdealMollie::Config
|
13
|
+
config.test_mode = false
|
14
|
+
config.partner_id = 123456
|
15
|
+
config.report_url = "http://example.org/report"
|
16
|
+
config.return_url = "http://example.org/return"
|
17
|
+
|
18
|
+
VCR.use_cassette("new_payment") do
|
19
|
+
expect { IdealMollie.new_payment(1234, "exception test", "0031") }.
|
20
|
+
to raise_error(IdealMollie::IdealException, /This account does not exist or is suspended./)
|
21
|
+
end
|
22
|
+
end
|
23
|
+
end
|
24
|
+
context "#check_payment" do
|
25
|
+
it "should raise an exception when a invalid transaction_id is asked" do
|
26
|
+
config = IdealMollie::Config
|
27
|
+
config.test_mode = false
|
28
|
+
config.partner_id = 738907
|
29
|
+
config.report_url = "http://example.org/report"
|
30
|
+
config.return_url = "http://example.org/return"
|
31
|
+
|
32
|
+
VCR.use_cassette("check_payment") do
|
33
|
+
expect { IdealMollie.check_payment("482d599bbcc7795727650330ad65fe9b") }.
|
34
|
+
to raise_error(IdealMollie::IdealException, /This is an unknown order./)
|
35
|
+
end
|
36
|
+
end
|
37
|
+
end
|
38
|
+
end
|
@@ -0,0 +1,66 @@
|
|
1
|
+
require 'spec_helper'
|
2
|
+
|
3
|
+
describe IdealMollie do
|
4
|
+
before(:each) do
|
5
|
+
config = IdealMollie::Config
|
6
|
+
config.test_mode = false
|
7
|
+
config.partner_id = 123456
|
8
|
+
config.report_url = "http://example.org/report"
|
9
|
+
config.return_url = "http://example.org/return"
|
10
|
+
end
|
11
|
+
|
12
|
+
context "#banks" do
|
13
|
+
it "returns an array with banks" do
|
14
|
+
VCR.use_cassette("banks") do
|
15
|
+
banks = IdealMollie.banks
|
16
|
+
banks.class.is_a?Array.should be_true
|
17
|
+
banks.count > 0
|
18
|
+
|
19
|
+
bank = banks.first
|
20
|
+
bank[:id].should eq "0031"
|
21
|
+
bank[:name].should eq "ABN AMRO"
|
22
|
+
end
|
23
|
+
end
|
24
|
+
end
|
25
|
+
|
26
|
+
context "#new_payment" do
|
27
|
+
it "should return a transaction hash with the correct values" do
|
28
|
+
VCR.use_cassette("new_payment") do
|
29
|
+
payment = IdealMollie.new_payment(1000, "test", "0031")
|
30
|
+
payment[:transaction_id].should eq "c9f93e5c2bd6c1e7c5bee5c5580c6f83"
|
31
|
+
payment[:amount].should eq 1000
|
32
|
+
payment[:currency].should eq "EUR"
|
33
|
+
payment[:url].should eq "https://www.abnamro.nl/nl/ideal/identification.do?randomizedstring=8433910909&trxid=30000217841224"
|
34
|
+
payment[:message].should eq "Your iDEAL-payment has successfully been setup. Your customer should visit the given URL to make the payment"
|
35
|
+
end
|
36
|
+
end
|
37
|
+
end
|
38
|
+
|
39
|
+
context "#check_payment" do
|
40
|
+
it "should return a payment response with the correct values" do
|
41
|
+
VCR.use_cassette("check_payment") do
|
42
|
+
payment = IdealMollie.check_payment("c9f93e5c2bd6c1e7c5bee5c5580c6f83")
|
43
|
+
payment[:transaction_id].should eq "c9f93e5c2bd6c1e7c5bee5c5580c6f83"
|
44
|
+
payment[:amount].should eq 1000
|
45
|
+
payment[:currency].should eq "EUR"
|
46
|
+
payment[:payed].should eq false
|
47
|
+
payment[:message].should eq "This iDEAL-order wasn't payed for, or was already checked by you. (We give payed=true only once, for your protection)"
|
48
|
+
payment[:status].should eq "CheckedBefore"
|
49
|
+
end
|
50
|
+
end
|
51
|
+
it "should mark the transaction as payed and contain the consumer information when called by mollie" do
|
52
|
+
VCR.use_cassette("check_payment") do
|
53
|
+
payment = IdealMollie.check_payment("482d599bbcc7795727650330ad65fe9b")
|
54
|
+
payment[:transaction_id].should eq "482d599bbcc7795727650330ad65fe9b"
|
55
|
+
payment[:amount].should eq 1000
|
56
|
+
payment[:currency].should eq "EUR"
|
57
|
+
payment[:payed].should eq true
|
58
|
+
payment[:message].should eq "This iDEAL-order has successfuly been payed for, and this is the first time you check it."
|
59
|
+
consumer = payment[:consumer]
|
60
|
+
consumer[:name].should eq "Hr J Janssen"
|
61
|
+
consumer[:account].should eq "P001234567"
|
62
|
+
consumer[:city].should eq "Amsterdam"
|
63
|
+
end
|
64
|
+
end
|
65
|
+
end
|
66
|
+
end
|
data/spec/spec_helper.rb
ADDED
@@ -0,0 +1,15 @@
|
|
1
|
+
require 'simplecov'
|
2
|
+
SimpleCov.start
|
3
|
+
|
4
|
+
require 'rubygems'
|
5
|
+
require 'bundler/setup'
|
6
|
+
require 'vcr'
|
7
|
+
require 'ideal-mollie'
|
8
|
+
|
9
|
+
VCR.config do |c|
|
10
|
+
c.cassette_library_dir = 'spec/vcr_cassettes'
|
11
|
+
c.stub_with :fakeweb
|
12
|
+
end
|
13
|
+
|
14
|
+
RSpec.configure do |config|
|
15
|
+
end
|
@@ -0,0 +1,33 @@
|
|
1
|
+
---
|
2
|
+
- !ruby/struct:VCR::HTTPInteraction
|
3
|
+
request: !ruby/struct:VCR::Request
|
4
|
+
method: :post
|
5
|
+
uri: https://secure.mollie.nl:443/xml/ideal/?a=banklist&testmode=false
|
6
|
+
body:
|
7
|
+
headers:
|
8
|
+
user-agent:
|
9
|
+
- Ruby-IdealMollie
|
10
|
+
response: !ruby/struct:VCR::Response
|
11
|
+
status: !ruby/struct:VCR::ResponseStatus
|
12
|
+
code: 200
|
13
|
+
message: OK
|
14
|
+
headers:
|
15
|
+
server:
|
16
|
+
- nginx/0.7.67
|
17
|
+
date:
|
18
|
+
- Tue, 24 Jan 2012 12:44:39 GMT
|
19
|
+
content-type:
|
20
|
+
- text/xml
|
21
|
+
x-powered-by:
|
22
|
+
- PHP/5.2.6-1+lenny13
|
23
|
+
content-length:
|
24
|
+
- '854'
|
25
|
+
body: ! "<?xml version=\"1.0\" ?>\n<response>\n\t<bank>\n\t\t<bank_id>0031</bank_id>\n\t\t<bank_name>ABN
|
26
|
+
AMRO</bank_name>\n\t</bank>\n\t<bank>\n\t\t<bank_id>0761</bank_id>\n\t\t<bank_name>ASN
|
27
|
+
Bank</bank_name>\n\t</bank>\n\t<bank>\n\t\t<bank_id>0091</bank_id>\n\t\t<bank_name>Friesland
|
28
|
+
Bank</bank_name>\n\t</bank>\n\t<bank>\n\t\t<bank_id>0721</bank_id>\n\t\t<bank_name>ING</bank_name>\n\t</bank>\n\t<bank>\n\t\t<bank_id>0021</bank_id>\n\t\t<bank_name>Rabobank</bank_name>\n\t</bank>\n\t<bank>\n\t\t<bank_id>0771</bank_id>\n\t\t<bank_name>RegioBank</bank_name>\n\t</bank>\n\t<bank>\n\t\t<bank_id>0751</bank_id>\n\t\t<bank_name>SNS
|
29
|
+
Bank</bank_name>\n\t</bank>\n\t<bank>\n\t\t<bank_id>0511</bank_id>\n\t\t<bank_name>Triodos
|
30
|
+
Bank</bank_name>\n\t</bank>\n\t<bank>\n\t\t<bank_id>0161</bank_id>\n\t\t<bank_name>van
|
31
|
+
Lanschot</bank_name>\n\t</bank>\n<message>This is the current list of banks
|
32
|
+
and their ID's that currently support iDEAL-payments</message>\n</response>"
|
33
|
+
http_version: '1.1'
|
@@ -0,0 +1,82 @@
|
|
1
|
+
---
|
2
|
+
- !ruby/struct:VCR::HTTPInteraction
|
3
|
+
request: !ruby/struct:VCR::Request
|
4
|
+
method: :post
|
5
|
+
uri: https://secure.mollie.nl:443/xml/ideal/?partnerid=123456&transaction_id=c9f93e5c2bd6c1e7c5bee5c5580c6f83&a=check&testmode=false
|
6
|
+
body:
|
7
|
+
headers:
|
8
|
+
user-agent:
|
9
|
+
- Ruby-IdealMollie
|
10
|
+
response: !ruby/struct:VCR::Response
|
11
|
+
status: !ruby/struct:VCR::ResponseStatus
|
12
|
+
code: 200
|
13
|
+
message: OK
|
14
|
+
headers:
|
15
|
+
server:
|
16
|
+
- nginx/0.7.67
|
17
|
+
date:
|
18
|
+
- Tue, 24 Jan 2012 13:02:18 GMT
|
19
|
+
content-type:
|
20
|
+
- text/xml
|
21
|
+
x-powered-by:
|
22
|
+
- PHP/5.2.6-1+lenny13
|
23
|
+
content-length:
|
24
|
+
- '151'
|
25
|
+
body: ! "<?xml version=\"1.0\" ?>\n<response>\n\t<order>\n\t\t<transaction_id>c9f93e5c2bd6c1e7c5bee5c5580c6f83</transaction_id>\n\t\t<amount>1000</amount>\n\t\t<currency>EUR</currency>\n\t\t<payed>false</payed>\n\t\t<message>This
|
26
|
+
iDEAL-order wasn't payed for, or was already checked by you. (We give payed=true
|
27
|
+
only once, for your protection)</message>\n\t\t<status>CheckedBefore</status>\n\t</order>\n\n</response>"
|
28
|
+
http_version: '1.1'
|
29
|
+
- !ruby/struct:VCR::HTTPInteraction
|
30
|
+
request: !ruby/struct:VCR::Request
|
31
|
+
method: :post
|
32
|
+
uri: https://secure.mollie.nl:443/xml/ideal/?partnerid=123456&transaction_id=482d599bbcc7795727650330ad65fe9b&a=check&testmode=false
|
33
|
+
body:
|
34
|
+
headers:
|
35
|
+
user-agent:
|
36
|
+
- Ruby-IdealMollie
|
37
|
+
response: !ruby/struct:VCR::Response
|
38
|
+
status: !ruby/struct:VCR::ResponseStatus
|
39
|
+
code: 200
|
40
|
+
message: OK
|
41
|
+
headers:
|
42
|
+
server:
|
43
|
+
- nginx/0.7.67
|
44
|
+
date:
|
45
|
+
- Tue, 24 Jan 2012 13:02:18 GMT
|
46
|
+
content-type:
|
47
|
+
- text/xml
|
48
|
+
x-powered-by:
|
49
|
+
- PHP/5.2.6-1+lenny13
|
50
|
+
content-length:
|
51
|
+
- '151'
|
52
|
+
body: ! "<?xml version=\"1.0\" ?>\n<response>\n\t<order>\n\t\t<transaction_id>482d599bbcc7795727650330ad65fe9b</transaction_id>\n\t\t<amount>1000</amount>\n\t\t<currency>EUR</currency>\n\t\t<payed>true</payed>\n\t\t<consumer>\n\t\t\t<consumerName>Hr
|
53
|
+
J Janssen</consumerName>\n\t\t\t<consumerAccount>P001234567</consumerAccount>\n\t\t\t<consumerCity>Amsterdam</consumerCity>\n\t\t</consumer>\n\t\t<message>This
|
54
|
+
iDEAL-order has successfuly been payed for, and this is the first time you check
|
55
|
+
it.</message>\n\t</order>\n\n</response>"
|
56
|
+
http_version: '1.1'
|
57
|
+
- !ruby/struct:VCR::HTTPInteraction
|
58
|
+
request: !ruby/struct:VCR::Request
|
59
|
+
method: :post
|
60
|
+
uri: https://secure.mollie.nl:443/xml/ideal/?partnerid=738907&transaction_id=482d599bbcc7795727650330ad65fe9b&a=check&testmode=false
|
61
|
+
body:
|
62
|
+
headers:
|
63
|
+
user-agent:
|
64
|
+
- Ruby-IdealMollie
|
65
|
+
response: !ruby/struct:VCR::Response
|
66
|
+
status: !ruby/struct:VCR::ResponseStatus
|
67
|
+
code: 200
|
68
|
+
message: OK
|
69
|
+
headers:
|
70
|
+
server:
|
71
|
+
- nginx/0.7.67
|
72
|
+
date:
|
73
|
+
- Tue, 24 Jan 2012 13:26:15 GMT
|
74
|
+
content-type:
|
75
|
+
- text/xml
|
76
|
+
x-powered-by:
|
77
|
+
- PHP/5.2.6-1+lenny13
|
78
|
+
content-length:
|
79
|
+
- '151'
|
80
|
+
body: ! "<?xml version=\"1.0\" ?>\n<response>\n\t<item type=\"error\">\n\t\t<errorcode>-10</errorcode>\n\t\t<message>This
|
81
|
+
is an unknown order.</message>\n\t</item>\n</response>"
|
82
|
+
http_version: '1.1'
|
@@ -0,0 +1,54 @@
|
|
1
|
+
---
|
2
|
+
- !ruby/struct:VCR::HTTPInteraction
|
3
|
+
request: !ruby/struct:VCR::Request
|
4
|
+
method: :post
|
5
|
+
uri: https://secure.mollie.nl:443/xml/ideal/?partnerid=123456&reporturl=http%3A%2F%2Fexample.org%2Freport&returnurl=http%3A%2F%2Fexample.org%2Freturn&description=test&amount=1000&bank_id=0031&a=fetch&testmode=false
|
6
|
+
body:
|
7
|
+
headers:
|
8
|
+
user-agent:
|
9
|
+
- Ruby-IdealMollie
|
10
|
+
response: !ruby/struct:VCR::Response
|
11
|
+
status: !ruby/struct:VCR::ResponseStatus
|
12
|
+
code: 200
|
13
|
+
message: OK
|
14
|
+
headers:
|
15
|
+
server:
|
16
|
+
- nginx/0.7.67
|
17
|
+
date:
|
18
|
+
- Tue, 24 Jan 2012 12:52:31 GMT
|
19
|
+
content-type:
|
20
|
+
- text/xml
|
21
|
+
x-powered-by:
|
22
|
+
- PHP/5.2.6-1+lenny13
|
23
|
+
content-length:
|
24
|
+
- '212'
|
25
|
+
body: ! "<?xml version=\"1.0\" ?>\n<response>\n\t<order>\n\t\t<transaction_id>c9f93e5c2bd6c1e7c5bee5c5580c6f83</transaction_id>\n\t\t<amount>1000</amount>\n\t\t<currency>EUR</currency>\n\t\t<URL>https://www.abnamro.nl/nl/ideal/identification.do?randomizedstring=8433910909&trxid=30000217841224</URL>\n\t\t<message>Your
|
26
|
+
iDEAL-payment has successfully been setup. Your customer should visit the given
|
27
|
+
URL to make the payment</message>\n\t</order>\n</response>"
|
28
|
+
http_version: '1.1'
|
29
|
+
- !ruby/struct:VCR::HTTPInteraction
|
30
|
+
request: !ruby/struct:VCR::Request
|
31
|
+
method: :post
|
32
|
+
uri: https://secure.mollie.nl:443/xml/ideal/?partnerid=123456&reporturl=http%3A%2F%2Fexample.org%2Freport&returnurl=http%3A%2F%2Fexample.org%2Freturn&description=exception%20test&amount=1234&bank_id=0031&a=fetch&testmode=false
|
33
|
+
body:
|
34
|
+
headers:
|
35
|
+
user-agent:
|
36
|
+
- Ruby-IdealMollie
|
37
|
+
response: !ruby/struct:VCR::Response
|
38
|
+
status: !ruby/struct:VCR::ResponseStatus
|
39
|
+
code: 200
|
40
|
+
message: OK
|
41
|
+
headers:
|
42
|
+
server:
|
43
|
+
- nginx/0.7.67
|
44
|
+
date:
|
45
|
+
- Tue, 24 Jan 2012 13:18:45 GMT
|
46
|
+
content-type:
|
47
|
+
- text/xml
|
48
|
+
x-powered-by:
|
49
|
+
- PHP/5.2.6-1+lenny13
|
50
|
+
content-length:
|
51
|
+
- '169'
|
52
|
+
body: ! "<?xml version=\"1.0\" ?>\n<response>\n\t<item type=\"error\">\n\t\t<errorcode>-2</errorcode>\n\t\t<message>This
|
53
|
+
account does not exist or is suspended.</message>\n\t</item>\n</response>"
|
54
|
+
http_version: '1.1'
|
@@ -0,0 +1,32 @@
|
|
1
|
+
---
|
2
|
+
- !ruby/struct:VCR::HTTPInteraction
|
3
|
+
request: !ruby/struct:VCR::Request
|
4
|
+
method: :get
|
5
|
+
uri: https://secure.mollie.nl:443/xml/ideal?a=fetch&partnerid=123456&description=description&reporturl=http%3A%2F%2Fexample.org%2Ftransactions%2Freport_payment&returnurl=http%3A%2F%2Fexample.org%2Ftransactions%2Ffinish&amount=1000&bank_id=0031&testmode=false
|
6
|
+
body:
|
7
|
+
headers:
|
8
|
+
response: !ruby/struct:VCR::Response
|
9
|
+
status: !ruby/struct:VCR::ResponseStatus
|
10
|
+
code: 200
|
11
|
+
message: OK
|
12
|
+
headers:
|
13
|
+
server:
|
14
|
+
- nginx/0.7.67
|
15
|
+
date:
|
16
|
+
- Fri, 20 Jan 2012 13:39:15 GMT
|
17
|
+
content-type:
|
18
|
+
- text/xml
|
19
|
+
content-location:
|
20
|
+
- ideal.php
|
21
|
+
vary:
|
22
|
+
- negotiate
|
23
|
+
tcn:
|
24
|
+
- choice
|
25
|
+
x-powered-by:
|
26
|
+
- PHP/5.2.6-1+lenny13
|
27
|
+
content-length:
|
28
|
+
- '429'
|
29
|
+
body: ! "<?xml version=\"1.0\" ?>\n<response>\n\t<order>\n\t\t<transaction_id>c9f93e5c2bd6c1e7c5bee5c5580c6f83</transaction_id>\n\t\t<amount>1000</amount>\n\t\t<currency>EUR</currency>\n\t\t<URL>https://www.abnamro.nl/nl/ideal/identification.do?randomizedstring=8433910909&trxid=30000217841224</URL>\n\t\t<message>Your
|
30
|
+
iDEAL-payment has successfully been setup. Your customer should visit the given
|
31
|
+
URL to make the payment</message>\n\t</order>\n</response>"
|
32
|
+
http_version: '1.1'
|
metadata
ADDED
@@ -0,0 +1,196 @@
|
|
1
|
+
--- !ruby/object:Gem::Specification
|
2
|
+
name: ideal-mollie
|
3
|
+
version: !ruby/object:Gem::Version
|
4
|
+
version: 0.0.1
|
5
|
+
prerelease:
|
6
|
+
platform: ruby
|
7
|
+
authors:
|
8
|
+
- Manuel van Rijn
|
9
|
+
autorequire:
|
10
|
+
bindir: bin
|
11
|
+
cert_chain: []
|
12
|
+
date: 2012-01-25 00:00:00.000000000 Z
|
13
|
+
dependencies:
|
14
|
+
- !ruby/object:Gem::Dependency
|
15
|
+
name: rspec
|
16
|
+
requirement: &16337200 !ruby/object:Gem::Requirement
|
17
|
+
none: false
|
18
|
+
requirements:
|
19
|
+
- - ! '>='
|
20
|
+
- !ruby/object:Gem::Version
|
21
|
+
version: '0'
|
22
|
+
type: :development
|
23
|
+
prerelease: false
|
24
|
+
version_requirements: *16337200
|
25
|
+
- !ruby/object:Gem::Dependency
|
26
|
+
name: vcr
|
27
|
+
requirement: &16336640 !ruby/object:Gem::Requirement
|
28
|
+
none: false
|
29
|
+
requirements:
|
30
|
+
- - ! '>='
|
31
|
+
- !ruby/object:Gem::Version
|
32
|
+
version: '0'
|
33
|
+
type: :development
|
34
|
+
prerelease: false
|
35
|
+
version_requirements: *16336640
|
36
|
+
- !ruby/object:Gem::Dependency
|
37
|
+
name: fakeweb
|
38
|
+
requirement: &16335860 !ruby/object:Gem::Requirement
|
39
|
+
none: false
|
40
|
+
requirements:
|
41
|
+
- - ! '>='
|
42
|
+
- !ruby/object:Gem::Version
|
43
|
+
version: '0'
|
44
|
+
type: :development
|
45
|
+
prerelease: false
|
46
|
+
version_requirements: *16335860
|
47
|
+
- !ruby/object:Gem::Dependency
|
48
|
+
name: yard
|
49
|
+
requirement: &16335260 !ruby/object:Gem::Requirement
|
50
|
+
none: false
|
51
|
+
requirements:
|
52
|
+
- - ! '>='
|
53
|
+
- !ruby/object:Gem::Version
|
54
|
+
version: '0'
|
55
|
+
type: :development
|
56
|
+
prerelease: false
|
57
|
+
version_requirements: *16335260
|
58
|
+
- !ruby/object:Gem::Dependency
|
59
|
+
name: redcarpet
|
60
|
+
requirement: &16334340 !ruby/object:Gem::Requirement
|
61
|
+
none: false
|
62
|
+
requirements:
|
63
|
+
- - ! '>='
|
64
|
+
- !ruby/object:Gem::Version
|
65
|
+
version: '0'
|
66
|
+
type: :development
|
67
|
+
prerelease: false
|
68
|
+
version_requirements: *16334340
|
69
|
+
- !ruby/object:Gem::Dependency
|
70
|
+
name: simplecov
|
71
|
+
requirement: &16333000 !ruby/object:Gem::Requirement
|
72
|
+
none: false
|
73
|
+
requirements:
|
74
|
+
- - ! '>='
|
75
|
+
- !ruby/object:Gem::Version
|
76
|
+
version: '0'
|
77
|
+
type: :development
|
78
|
+
prerelease: false
|
79
|
+
version_requirements: *16333000
|
80
|
+
- !ruby/object:Gem::Dependency
|
81
|
+
name: rake
|
82
|
+
requirement: &16332260 !ruby/object:Gem::Requirement
|
83
|
+
none: false
|
84
|
+
requirements:
|
85
|
+
- - ~>
|
86
|
+
- !ruby/object:Gem::Version
|
87
|
+
version: 0.9.0
|
88
|
+
type: :runtime
|
89
|
+
prerelease: false
|
90
|
+
version_requirements: *16332260
|
91
|
+
- !ruby/object:Gem::Dependency
|
92
|
+
name: faraday
|
93
|
+
requirement: &16346260 !ruby/object:Gem::Requirement
|
94
|
+
none: false
|
95
|
+
requirements:
|
96
|
+
- - ~>
|
97
|
+
- !ruby/object:Gem::Version
|
98
|
+
version: 0.5.7
|
99
|
+
type: :runtime
|
100
|
+
prerelease: false
|
101
|
+
version_requirements: *16346260
|
102
|
+
- !ruby/object:Gem::Dependency
|
103
|
+
name: faraday_middleware
|
104
|
+
requirement: &16344600 !ruby/object:Gem::Requirement
|
105
|
+
none: false
|
106
|
+
requirements:
|
107
|
+
- - ~>
|
108
|
+
- !ruby/object:Gem::Version
|
109
|
+
version: 0.3.2
|
110
|
+
type: :runtime
|
111
|
+
prerelease: false
|
112
|
+
version_requirements: *16344600
|
113
|
+
- !ruby/object:Gem::Dependency
|
114
|
+
name: multi_xml
|
115
|
+
requirement: &16343320 !ruby/object:Gem::Requirement
|
116
|
+
none: false
|
117
|
+
requirements:
|
118
|
+
- - ~>
|
119
|
+
- !ruby/object:Gem::Version
|
120
|
+
version: 0.2.2
|
121
|
+
type: :runtime
|
122
|
+
prerelease: false
|
123
|
+
version_requirements: *16343320
|
124
|
+
- !ruby/object:Gem::Dependency
|
125
|
+
name: nokogiri
|
126
|
+
requirement: &16342380 !ruby/object:Gem::Requirement
|
127
|
+
none: false
|
128
|
+
requirements:
|
129
|
+
- - ~>
|
130
|
+
- !ruby/object:Gem::Version
|
131
|
+
version: 1.4.1
|
132
|
+
type: :runtime
|
133
|
+
prerelease: false
|
134
|
+
version_requirements: *16342380
|
135
|
+
description: A simple Ruby implementation for handeling iDeal transactions with the
|
136
|
+
Mollie API
|
137
|
+
email:
|
138
|
+
- manuel@manuelles.nl
|
139
|
+
executables: []
|
140
|
+
extensions: []
|
141
|
+
extra_rdoc_files: []
|
142
|
+
files:
|
143
|
+
- .gitignore
|
144
|
+
- .rspec
|
145
|
+
- .yardopts
|
146
|
+
- CHANGELOG.md
|
147
|
+
- Gemfile
|
148
|
+
- LICENSE.md
|
149
|
+
- README.md
|
150
|
+
- Rakefile
|
151
|
+
- ideal-mollie.gemspec
|
152
|
+
- lib/ideal-mollie.rb
|
153
|
+
- lib/ideal-mollie/config.rb
|
154
|
+
- lib/ideal-mollie/engine.rb
|
155
|
+
- lib/ideal-mollie/ideal_exception.rb
|
156
|
+
- lib/ideal-mollie/version.rb
|
157
|
+
- spec/config_spec.rb
|
158
|
+
- spec/ideal_exception_spec.rb
|
159
|
+
- spec/ideal_mollie_spec.rb
|
160
|
+
- spec/spec_helper.rb
|
161
|
+
- spec/vcr_cassettes/banks.yml
|
162
|
+
- spec/vcr_cassettes/check_payment.yml
|
163
|
+
- spec/vcr_cassettes/new_payment.yml
|
164
|
+
- spec/vcr_cassettes/request_payment.yml
|
165
|
+
homepage: https://github.com/manuelvanrijn/ideal-mollie
|
166
|
+
licenses: []
|
167
|
+
post_install_message:
|
168
|
+
rdoc_options: []
|
169
|
+
require_paths:
|
170
|
+
- lib
|
171
|
+
required_ruby_version: !ruby/object:Gem::Requirement
|
172
|
+
none: false
|
173
|
+
requirements:
|
174
|
+
- - ! '>='
|
175
|
+
- !ruby/object:Gem::Version
|
176
|
+
version: '0'
|
177
|
+
segments:
|
178
|
+
- 0
|
179
|
+
hash: 3389092229287419673
|
180
|
+
required_rubygems_version: !ruby/object:Gem::Requirement
|
181
|
+
none: false
|
182
|
+
requirements:
|
183
|
+
- - ! '>='
|
184
|
+
- !ruby/object:Gem::Version
|
185
|
+
version: '0'
|
186
|
+
segments:
|
187
|
+
- 0
|
188
|
+
hash: 3389092229287419673
|
189
|
+
requirements: []
|
190
|
+
rubyforge_project: ideal-mollie
|
191
|
+
rubygems_version: 1.8.11
|
192
|
+
signing_key:
|
193
|
+
specification_version: 3
|
194
|
+
summary: Make iDeal Mollie payments without the pain
|
195
|
+
test_files: []
|
196
|
+
has_rdoc:
|