figpay_gateway 1.0.0

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.
checksums.yaml ADDED
@@ -0,0 +1,7 @@
1
+ ---
2
+ SHA256:
3
+ metadata.gz: f0a09ef25c0277c79ba548c7dea0845e8bcbdc85b98ce4b744f68b38cf3f6a7c
4
+ data.tar.gz: 8bc4a5747095180ee934641f4a7519a1770bffa72336b38a5a6c6a5896bb21a1
5
+ SHA512:
6
+ metadata.gz: 586f04f067969ed8ed10712642c0a35a0cae7db3e312f92a2b1fa492ae8ca06e5ebe2e5b08899ef1251cf32954c28cab75e26d8f07305f4ec381e31086990749
7
+ data.tar.gz: dced5d25b7e481f951bb6e29236b5536eb35822c5ba666e1a817b1065f1c8a765bb70cc997e843e1517d654773031319aaa9db982084b1cd007fc9c83508f9f8
data/.env.sample ADDED
@@ -0,0 +1,10 @@
1
+ # Your FigPay/NMI Security Key
2
+ # Get this from: Settings > Security Keys in the merchant control panel
3
+ NMI_SECURITY_KEY=your_security_key_here
4
+
5
+ # For testing, you can use the demo account security key:
6
+ # NMI_SECURITY_KEY=6457Thfj624V5r7WUwc5v6a68Zsd6YEm
7
+
8
+ # Optional: Override default API endpoints
9
+ # NMI_TRANSACTION_URL=https://figpay.transactiongateway.com/api/transact.php
10
+ # NMI_QUERY_URL=https://figpay.transactiongateway.com/api/query.php
@@ -0,0 +1,48 @@
1
+ name: CI
2
+
3
+ on:
4
+ pull_request:
5
+ branches:
6
+ - "**"
7
+ push:
8
+ branches:
9
+ - main
10
+ - master
11
+
12
+ jobs:
13
+ test:
14
+ runs-on: ubuntu-latest
15
+ strategy:
16
+ matrix:
17
+ ruby-version: ['3.0', '3.1', '3.2', '3.3', '3.4']
18
+
19
+ steps:
20
+ - name: Checkout code
21
+ uses: actions/checkout@v4
22
+
23
+ - name: Set up Ruby ${{ matrix.ruby-version }}
24
+ uses: ruby/setup-ruby@v1
25
+ with:
26
+ ruby-version: ${{ matrix.ruby-version }}
27
+ bundler-cache: true
28
+
29
+ - name: Run tests
30
+ run: bundle exec rake test
31
+ env:
32
+ NMI_SECURITY_KEY: ${{ secrets.NMI_SECURITY_KEY || '6457Thfj624V5r7WUwc5v6a68Zsd6YEm' }}
33
+
34
+ lint:
35
+ runs-on: ubuntu-latest
36
+ steps:
37
+ - name: Checkout code
38
+ uses: actions/checkout@v4
39
+
40
+ - name: Set up Ruby
41
+ uses: ruby/setup-ruby@v1
42
+ with:
43
+ ruby-version: .ruby-version
44
+ bundler-cache: true
45
+
46
+ - name: Check for syntax errors
47
+ run: |
48
+ find . -name '*.rb' -not -path './vendor/*' -exec ruby -c {} \;
data/.gitignore ADDED
@@ -0,0 +1,27 @@
1
+ /.bundle/
2
+ /.yardoc
3
+ /Gemfile.lock
4
+ /_yardoc/
5
+ /coverage/
6
+ /doc/
7
+ /pkg/
8
+ /spec/reports/
9
+ /tmp/
10
+ *.bundle
11
+ *.so
12
+ *.o
13
+ *.a
14
+ mkmf.log
15
+ *.sublime-project
16
+ *.sublime-workspace
17
+
18
+ .DS_Store
19
+ .env
20
+ .ruby-version
21
+ .ruby-gemset
22
+
23
+ # Editor tags files
24
+ tags
25
+ TAGS
26
+ .tags
27
+ .tags1
data/.tool-versions ADDED
@@ -0,0 +1,2 @@
1
+ ruby 3.4.5
2
+ nodejs 20.12.0
data/Gemfile ADDED
@@ -0,0 +1,4 @@
1
+ source 'https://rubygems.org'
2
+
3
+ # Specify your gem's dependencies in figpay_gateway.gemspec
4
+ gemspec
data/Guardfile ADDED
@@ -0,0 +1,42 @@
1
+ # A sample Guardfile
2
+ # More info at https://github.com/guard/guard#readme
3
+
4
+ ## Uncomment and set this to only include directories you want to watch
5
+ # directories %w(app lib config test spec features) \
6
+ # .select{|d| Dir.exist?(d) ? d : UI.warning("Directory #{d} does not exist")}
7
+
8
+ ## Note: if you are using the `directories` clause above and you are not
9
+ ## watching the project directory ('.'), then you will want to move
10
+ ## the Guardfile to a watched dir and symlink it back, e.g.
11
+ #
12
+ # $ mkdir config
13
+ # $ mv Guardfile config/
14
+ # $ ln -s config/Guardfile .
15
+ #
16
+ # and, you'll have to watch "config/Guardfile" instead of "Guardfile"
17
+
18
+ guard :minitest do
19
+ # with Minitest::Unit
20
+ watch(%r{^test/(.*)\/?test_(.*)\.rb$})
21
+ watch(%r{^lib/(.*/)?([^/]+)\.rb$}) { |m| "test/#{m[1]}test_#{m[2]}.rb" }
22
+ watch(%r{^test/test_helper\.rb$}) { 'test' }
23
+
24
+ # with Minitest::Spec
25
+ # watch(%r{^spec/(.*)_spec\.rb$})
26
+ # watch(%r{^lib/(.+)\.rb$}) { |m| "spec/#{m[1]}_spec.rb" }
27
+ # watch(%r{^spec/spec_helper\.rb$}) { 'spec' }
28
+
29
+ # Rails 4
30
+ # watch(%r{^app/(.+)\.rb$}) { |m| "test/#{m[1]}_test.rb" }
31
+ # watch(%r{^app/controllers/application_controller\.rb$}) { 'test/controllers' }
32
+ # watch(%r{^app/controllers/(.+)_controller\.rb$}) { |m| "test/integration/#{m[1]}_test.rb" }
33
+ # watch(%r{^app/views/(.+)_mailer/.+}) { |m| "test/mailers/#{m[1]}_mailer_test.rb" }
34
+ # watch(%r{^lib/(.+)\.rb$}) { |m| "test/lib/#{m[1]}_test.rb" }
35
+ # watch(%r{^test/.+_test\.rb$})
36
+ # watch(%r{^test/test_helper\.rb$}) { 'test' }
37
+
38
+ # Rails < 4
39
+ # watch(%r{^app/controllers/(.*)\.rb$}) { |m| "test/functional/#{m[1]}_test.rb" }
40
+ # watch(%r{^app/helpers/(.*)\.rb$}) { |m| "test/helpers/#{m[1]}_test.rb" }
41
+ # watch(%r{^app/models/(.*)\.rb$}) { |m| "test/unit/#{m[1]}_test.rb" }
42
+ end
data/LICENSE.txt ADDED
@@ -0,0 +1,21 @@
1
+ The MIT License (MIT)
2
+
3
+ Copyright (c) 2016 Ben Eggett
4
+
5
+ Permission is hereby granted, free of charge, to any person obtaining a copy
6
+ of this software and associated documentation files (the "Software"), to deal
7
+ in the Software without restriction, including without limitation the rights
8
+ to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
9
+ copies of the Software, and to permit persons to whom the Software is
10
+ furnished to do so, subject to the following conditions:
11
+
12
+ The above copyright notice and this permission notice shall be included in
13
+ all copies or substantial portions of the Software.
14
+
15
+ THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
16
+ IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
17
+ FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
18
+ AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
19
+ LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
20
+ OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
21
+ THE SOFTWARE.
data/README.md ADDED
@@ -0,0 +1,491 @@
1
+ [![Gem Version](https://badge.fury.io/rb/figpay_gateway.svg)](https://badge.fury.io/rb/figpay_gateway)
2
+
3
+ # FigPay Gateway Ruby Library
4
+
5
+ The FigPay Gateway Ruby library provides convenient access to the FigPay payment gateway API from applications written in Ruby. FigPay is a white-label payment gateway powered by NMI, and this library is built with portability in mind for other NMI-based gateways.
6
+
7
+ ## Documentation
8
+
9
+ See the [FigPay API documentation](https://www.figpay.com/) for detailed information about the payment gateway features.
10
+
11
+ ## Requirements
12
+
13
+ - Ruby 3.0.0 or higher
14
+
15
+ ## Installation
16
+
17
+ Install the gem and add to your application's Gemfile:
18
+
19
+ ```bash
20
+ gem install figpay_gateway
21
+ ```
22
+
23
+ Or add this line to your Gemfile:
24
+
25
+ ```ruby
26
+ gem 'figpay_gateway'
27
+ ```
28
+
29
+ And then execute:
30
+
31
+ ```bash
32
+ bundle install
33
+ ```
34
+
35
+ ## Usage
36
+
37
+ The library needs to be configured with your account's security key, which is available in your FigPay merchant control panel under Settings > Security Keys.
38
+
39
+ ### Configuration
40
+
41
+ Set your security key as an environment variable:
42
+
43
+ ```bash
44
+ export NMI_SECURITY_KEY='your_security_key_here'
45
+ ```
46
+
47
+ Or in a `.env` file:
48
+
49
+ ```
50
+ NMI_SECURITY_KEY=your_security_key_here
51
+ ```
52
+
53
+ For testing, you can use the demo account security key:
54
+
55
+ ```
56
+ NMI_SECURITY_KEY=6457Thfj624V5r7WUwc5v6a68Zsd6YEm
57
+ ```
58
+
59
+ ### Quick Start
60
+
61
+ ```ruby
62
+ require 'figpay_gateway'
63
+
64
+ # Process a sale
65
+ result = FigpayGateway::Transaction.new.sale(
66
+ ccnumber: '4111111111111111',
67
+ ccexp: '1225',
68
+ amount: 10.00,
69
+ first_name: 'John',
70
+ last_name: 'Doe',
71
+ email: 'john@example.com'
72
+ )
73
+
74
+ if result.success?
75
+ puts "Transaction approved: #{result.transactionid}"
76
+ else
77
+ puts "Transaction failed: #{result.response_text} #{result.response_message}"
78
+ end
79
+ ```
80
+
81
+ ## API Overview
82
+
83
+ The FigPay Gateway library is organized around three main API sets:
84
+
85
+ ### Transactions
86
+
87
+ Process credit card transactions including sales, authorizations, captures, and refunds.
88
+
89
+ #### Create a Sale
90
+
91
+ Process a direct sale (authorization and capture combined):
92
+
93
+ ```ruby
94
+ transaction = FigpayGateway::Transaction.new
95
+
96
+ result = transaction.sale(
97
+ ccnumber: '4111111111111111',
98
+ ccexp: '1225',
99
+ cvv: '999',
100
+ amount: 25.00,
101
+ first_name: 'John',
102
+ last_name: 'Doe',
103
+ address1: '123 Main St',
104
+ city: 'Beverly Hills',
105
+ state: 'CA',
106
+ zip: '90210',
107
+ country: 'US',
108
+ email: 'john@example.com'
109
+ )
110
+ ```
111
+
112
+ #### Authorize and Capture
113
+
114
+ Authorize a payment for later capture:
115
+
116
+ ```ruby
117
+ # Authorize
118
+ auth = FigpayGateway::Transaction.new.authorize(
119
+ ccnumber: '4111111111111111',
120
+ ccexp: '1225',
121
+ amount: 50.00,
122
+ first_name: 'John',
123
+ last_name: 'Doe'
124
+ )
125
+
126
+ # Capture the authorized amount
127
+ if auth.success?
128
+ capture = FigpayGateway::Transaction.new.capture(
129
+ transactionid: auth.transactionid,
130
+ amount: 50.00
131
+ )
132
+ end
133
+ ```
134
+
135
+ #### Refund a Transaction
136
+
137
+ Issue a refund for a previous transaction:
138
+
139
+ ```ruby
140
+ refund = FigpayGateway::Transaction.new.refund(
141
+ transactionid: '3261844010',
142
+ amount: 10.00
143
+ )
144
+ ```
145
+
146
+ #### Void a Transaction
147
+
148
+ Void a transaction before it settles:
149
+
150
+ ```ruby
151
+ void = FigpayGateway::Transaction.new.void(
152
+ transactionid: '3261830498'
153
+ )
154
+ ```
155
+
156
+ #### Credit (Standalone Credit)
157
+
158
+ Issue a credit without a previous transaction:
159
+
160
+ ```ruby
161
+ credit = FigpayGateway::Transaction.new.credit(
162
+ ccnumber: '4111111111111111',
163
+ ccexp: '1225',
164
+ amount: 15.00,
165
+ first_name: 'John',
166
+ last_name: 'Doe'
167
+ )
168
+ ```
169
+
170
+ #### Validate a Card
171
+
172
+ Validate card details without charging:
173
+
174
+ ```ruby
175
+ validation = FigpayGateway::Transaction.new.validate(
176
+ ccnumber: '4111111111111111',
177
+ ccexp: '1225',
178
+ first_name: 'John',
179
+ last_name: 'Doe'
180
+ )
181
+ ```
182
+
183
+ #### Query a Transaction
184
+
185
+ Retrieve transaction details:
186
+
187
+ ```ruby
188
+ details = FigpayGateway::Transaction.new.find(
189
+ transactionid: '3261844010'
190
+ )
191
+ ```
192
+
193
+ #### Update Transaction Information
194
+
195
+ Update transaction details (e.g., order information):
196
+
197
+ ```ruby
198
+ update = FigpayGateway::Transaction.new.update(
199
+ transactionid: '3261844010',
200
+ orderid: 'ORDER-12345',
201
+ order_description: 'Updated order description'
202
+ )
203
+ ```
204
+
205
+ ### Customer Vault
206
+
207
+ Store customer payment information securely for future transactions.
208
+
209
+ #### Create a Customer
210
+
211
+ Store customer payment details in the vault:
212
+
213
+ ```ruby
214
+ vault = FigpayGateway::CustomerVault.new
215
+
216
+ customer = vault.create(
217
+ ccnumber: '4111111111111111',
218
+ ccexp: '1225',
219
+ cvv: '999',
220
+ first_name: 'Jane',
221
+ last_name: 'Smith',
222
+ address1: '456 Oak Ave',
223
+ city: 'Los Angeles',
224
+ state: 'CA',
225
+ zip: '90001',
226
+ email: 'jane@example.com'
227
+ )
228
+
229
+ if customer.success?
230
+ puts "Customer created: #{customer.customer_vault_id}"
231
+ end
232
+ ```
233
+
234
+ #### Update a Customer
235
+
236
+ Update stored customer information:
237
+
238
+ ```ruby
239
+ update = FigpayGateway::CustomerVault.new.update(
240
+ customer_vault_id: '481397475',
241
+ ccnumber: '4111111111111111',
242
+ ccexp: '0226',
243
+ first_name: 'Jane',
244
+ last_name: 'Doe',
245
+ email: 'jane.doe@example.com'
246
+ )
247
+ ```
248
+
249
+ #### Delete a Customer
250
+
251
+ Remove a customer from the vault:
252
+
253
+ ```ruby
254
+ delete = FigpayGateway::CustomerVault.new.destroy(
255
+ customer_vault_id: '481397475'
256
+ )
257
+ ```
258
+
259
+ #### Retrieve Customer Details
260
+
261
+ Query customer vault information:
262
+
263
+ ```ruby
264
+ customer = FigpayGateway::CustomerVault.new.find(
265
+ customer_vault_id: '481397475'
266
+ )
267
+ ```
268
+
269
+ #### Charge a Vaulted Customer
270
+
271
+ Process a transaction using stored payment information:
272
+
273
+ ```ruby
274
+ sale = FigpayGateway::Transaction.new.sale(
275
+ customer_vault_id: '481397475',
276
+ amount: 99.99,
277
+ orderid: 'ORDER-67890'
278
+ )
279
+ ```
280
+
281
+ ### Recurring Billing
282
+
283
+ Set up and manage recurring subscription payments.
284
+
285
+ #### Create a Billing Plan
286
+
287
+ Define a reusable billing plan:
288
+
289
+ ```ruby
290
+ recurring = FigpayGateway::Recurring.new
291
+
292
+ plan = recurring.create_plan(
293
+ plan_id: 'monthly-premium',
294
+ plan_name: 'Monthly Premium Plan',
295
+ plan_amount: 29.99,
296
+ month_frequency: 1,
297
+ day_of_month: 1
298
+ )
299
+ ```
300
+
301
+ #### Subscribe Customer to a Plan
302
+
303
+ Add a vaulted customer to an existing plan:
304
+
305
+ ```ruby
306
+ subscription = FigpayGateway::Recurring.new.add_subscription_to_plan(
307
+ plan_id: 'monthly-premium',
308
+ customer_vault_id: '664625840'
309
+ )
310
+
311
+ if subscription.success?
312
+ puts "Subscription created: #{subscription.subscription_id}"
313
+ end
314
+ ```
315
+
316
+ #### Create a Custom Subscription
317
+
318
+ Create a one-off subscription without a predefined plan:
319
+
320
+ ```ruby
321
+ custom_sub = FigpayGateway::Recurring.new.add_custom_subscription(
322
+ customer_vault_id: '664625840',
323
+ plan_amount: 49.99,
324
+ month_frequency: 3,
325
+ day_of_month: 15,
326
+ start_date: '20251215'
327
+ )
328
+ ```
329
+
330
+ #### Update a Subscription
331
+
332
+ Modify subscription details:
333
+
334
+ ```ruby
335
+ update = FigpayGateway::Recurring.new.update_subscription(
336
+ subscription_id: '3261766445',
337
+ plan_amount: 39.99
338
+ )
339
+ ```
340
+
341
+ #### Cancel a Subscription
342
+
343
+ Delete an active subscription:
344
+
345
+ ```ruby
346
+ cancel = FigpayGateway::Recurring.new.delete_subscription(
347
+ subscription_id: '3261766445'
348
+ )
349
+ ```
350
+
351
+ ## Advanced Configuration
352
+
353
+ ### Custom API Endpoints
354
+
355
+ Override the default FigPay API endpoints if needed:
356
+
357
+ ```bash
358
+ export NMI_TRANSACTION_URL='https://custom.gateway.com/api/transact.php'
359
+ export NMI_QUERY_URL='https://custom.gateway.com/api/query.php'
360
+ ```
361
+
362
+ ### Per-Request Configuration
363
+
364
+ Pass a custom security key for individual requests:
365
+
366
+ ```ruby
367
+ transaction = FigpayGateway::Transaction.new(security_key: 'custom_key_here')
368
+ result = transaction.sale(amount: 10.00, ...)
369
+ ```
370
+
371
+ ## Response Handling
372
+
373
+ All API methods return response objects with helpful methods:
374
+
375
+ ```ruby
376
+ result = FigpayGateway::Transaction.new.sale(...)
377
+
378
+ # Check transaction status
379
+ if result.success?
380
+ puts "Success!"
381
+ puts "Transaction ID: #{result.transactionid}"
382
+ puts "Auth Code: #{result.authcode}"
383
+ else
384
+ puts "Failed: #{result.response_text} #{result.response_message}"
385
+ puts "Response Code: #{result.response_code}"
386
+ end
387
+
388
+ # Access raw response data
389
+ puts result.response
390
+ ```
391
+
392
+ ## Testing
393
+
394
+ ### Test All Methods Against Your Account
395
+
396
+ The gem includes a comprehensive testing tool that exercises all API methods against a live account. This is useful for:
397
+
398
+ - Verifying your account configuration
399
+ - Testing all available payment gateway features
400
+ - Ensuring your security key has the necessary permissions
401
+ - Learning how different API methods work
402
+
403
+ To run the comprehensive test suite:
404
+
405
+ ```bash
406
+ bin/test_all_methods
407
+ ```
408
+
409
+ By default, it uses the demo security key. To test against your own account, set your security key first:
410
+
411
+ ```bash
412
+ export NMI_SECURITY_KEY='your_security_key_here'
413
+ bin/test_all_methods
414
+ ```
415
+
416
+ The test script will:
417
+
418
+ - Run 18+ different API operations
419
+ - Show detailed results for each test
420
+ - Display a summary with success rate
421
+ - Help identify any configuration issues
422
+
423
+ **Note**: This will create real test transactions on your account (or the demo account if using the demo key).
424
+
425
+ ### Test Credentials
426
+
427
+ Use the demo security key for testing:
428
+
429
+ ```ruby
430
+ # In your test environment
431
+ ENV['NMI_SECURITY_KEY'] = '6457Thfj624V5r7WUwc5v6a68Zsd6YEm'
432
+ ```
433
+
434
+ Test card numbers:
435
+
436
+ - **Visa**: 4111111111111111
437
+ - **Mastercard**: 5555555555554444
438
+ - **Amex**: 378282246310005
439
+ - **Discover**: 6011111111111117
440
+
441
+ ## Development
442
+
443
+ After checking out the repo, run `bin/setup` to install dependencies:
444
+
445
+ ```bash
446
+ bin/setup
447
+ ```
448
+
449
+ Run the test suite:
450
+
451
+ ```bash
452
+ rake test
453
+ ```
454
+
455
+ Start an interactive console for experimentation:
456
+
457
+ ```bash
458
+ bin/console
459
+ ```
460
+
461
+ To install this gem onto your local machine:
462
+
463
+ ```bash
464
+ bundle exec rake install
465
+ ```
466
+
467
+ ## Contributing
468
+
469
+ Bug reports and pull requests are welcome on GitHub at https://github.com/beneggett/figpay_gateway.
470
+
471
+ 1. Fork the repository
472
+ 2. Create your feature branch (`git checkout -b my-new-feature`)
473
+ 3. Commit your changes (`git commit -am 'Add some feature'`)
474
+ 4. Push to the branch (`git push origin my-new-feature`)
475
+ 5. Create a new Pull Request
476
+
477
+ ## Support
478
+
479
+ For issues related to:
480
+
481
+ - **This library**: Open an issue on [GitHub](https://github.com/beneggett/figpay_gateway/issues)
482
+ - **FigPay Gateway API**: Contact FigPay support
483
+ - **NMI Platform**: Refer to NMI documentation at [nmi.com](https://nmi.com)
484
+
485
+ ## License
486
+
487
+ The gem is available as open source under the terms of the [MIT License](http://opensource.org/licenses/MIT).
488
+
489
+ ## About
490
+
491
+ Built with portability in mind for NMI-based payment gateways.
data/Rakefile ADDED
@@ -0,0 +1,10 @@
1
+ require "bundler/gem_tasks"
2
+ require "rake/testtask"
3
+
4
+ Rake::TestTask.new(:test) do |t|
5
+ t.libs << "test"
6
+ t.libs << "lib"
7
+ t.test_files = FileList['test/**/*_test.rb']
8
+ end
9
+
10
+ task :default => :test
data/bin/console ADDED
@@ -0,0 +1,14 @@
1
+ #!/usr/bin/env ruby
2
+ require "dotenv"
3
+ Dotenv.load
4
+ require "bundler/setup"
5
+ require "figpay_gateway"
6
+
7
+ # You can add fixtures and/or initialization code here to make experimenting
8
+ # with your gem easier. You can also use a different console, if you like.
9
+
10
+ # (If you use this, don't forget to add pry to your Gemfile!)
11
+ # require "pry"
12
+ # Pry.start
13
+ require "pry"
14
+ Pry.start
data/bin/setup ADDED
@@ -0,0 +1,8 @@
1
+ #!/usr/bin/env bash
2
+ set -euo pipefail
3
+ IFS=$'\n\t'
4
+ set -vx
5
+
6
+ bundle install
7
+
8
+ # Do any other automated setup that you need to do here