zai_payment 2.0.2 → 2.1.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.
@@ -0,0 +1,75 @@
1
+ # frozen_string_literal: true
2
+
3
+ module ZaiPayment
4
+ module Resources
5
+ # TokenAuth resource for generating tokens for bank or card accounts
6
+ #
7
+ # @see https://developer.hellozai.com/reference/generatetoken
8
+ class TokenAuth
9
+ attr_reader :client
10
+
11
+ # Token types
12
+ TOKEN_TYPE_BANK = 'bank'
13
+ TOKEN_TYPE_CARD = 'card'
14
+
15
+ # Valid token types
16
+ VALID_TOKEN_TYPES = [TOKEN_TYPE_BANK, TOKEN_TYPE_CARD].freeze
17
+
18
+ def initialize(client: nil)
19
+ @client = client || Client.new(base_endpoint: :core_base)
20
+ end
21
+
22
+ # Generate a token for bank or card account
23
+ #
24
+ # Create a token, either for a bank or a card account, that can be used with the
25
+ # PromisePay.js package to securely send Assembly credit card details.
26
+ #
27
+ # @param user_id [String] (Required) Buyer or Seller ID (already created)
28
+ # @param token_type [String] Token type ID, use 'bank' or 'card' (default: 'bank')
29
+ # @return [Response] the API response containing generated token
30
+ #
31
+ # @example Generate a bank token
32
+ # token_auth = ZaiPayment::Resources::TokenAuth.new
33
+ # response = token_auth.generate(
34
+ # user_id: "seller-68611249",
35
+ # token_type: "bank"
36
+ # )
37
+ # response.data # => {"token_auth" => {"token" => "...", "user_id" => "...", ...}}
38
+ #
39
+ # @example Generate a card token
40
+ # token_auth = ZaiPayment::Resources::TokenAuth.new
41
+ # response = token_auth.generate(
42
+ # user_id: "buyer-12345",
43
+ # token_type: "card"
44
+ # )
45
+ #
46
+ # @see https://developer.hellozai.com/reference/generatetoken
47
+ def generate(user_id:, token_type: TOKEN_TYPE_BANK)
48
+ validate_user_id!(user_id)
49
+ validate_token_type!(token_type)
50
+
51
+ body = {
52
+ token_type: token_type,
53
+ user_id: user_id
54
+ }
55
+
56
+ client.post('/token_auths', body: body)
57
+ end
58
+
59
+ private
60
+
61
+ def validate_user_id!(user_id)
62
+ return unless user_id.nil? || user_id.to_s.strip.empty?
63
+
64
+ raise Errors::ValidationError, 'user_id is required and cannot be blank'
65
+ end
66
+
67
+ def validate_token_type!(token_type)
68
+ return if VALID_TOKEN_TYPES.include?(token_type.to_s.downcase)
69
+
70
+ raise Errors::ValidationError,
71
+ "token_type must be one of: #{VALID_TOKEN_TYPES.join(', ')}"
72
+ end
73
+ end
74
+ end
75
+ end
@@ -1,5 +1,5 @@
1
1
  # frozen_string_literal: true
2
2
 
3
3
  module ZaiPayment
4
- VERSION = '2.0.2'
4
+ VERSION = '2.1.0'
5
5
  end
data/lib/zai_payment.rb CHANGED
@@ -13,6 +13,7 @@ require_relative 'zai_payment/response'
13
13
  require_relative 'zai_payment/resources/webhook'
14
14
  require_relative 'zai_payment/resources/user'
15
15
  require_relative 'zai_payment/resources/item'
16
+ require_relative 'zai_payment/resources/token_auth'
16
17
 
17
18
  module ZaiPayment
18
19
  class << self
@@ -51,5 +52,10 @@ module ZaiPayment
51
52
  def items
52
53
  @items ||= Resources::Item.new(client: Client.new(base_endpoint: :core_base))
53
54
  end
55
+
56
+ # @return [ZaiPayment::Resources::TokenAuth] token_auth resource instance
57
+ def token_auths
58
+ @token_auths ||= Resources::TokenAuth.new(client: Client.new(base_endpoint: :core_base))
59
+ end
54
60
  end
55
61
  end
data/readme.md CHANGED
@@ -21,6 +21,7 @@ A lightweight and extensible Ruby client for the **Zai (AssemblyPay)** API — s
21
21
  - 🧠 **Smart Token Caching** - Auto-refresh before expiration, thread-safe storage
22
22
  - 👥 **User Management** - Create and manage payin (buyers) & payout (sellers) users
23
23
  - 📦 **Item Management** - Full CRUD for transactions/payments between buyers and sellers
24
+ - 🎫 **Token Auth** - Generate secure tokens for bank and card account data collection
24
25
  - 🪝 **Webhooks** - Full CRUD + secure signature verification (HMAC SHA256)
25
26
  - ⚙️ **Environment-Aware** - Seamless Pre-live / Production switching
26
27
  - 🧱 **Modular & Extensible** - Clean resource-based architecture
@@ -183,6 +184,34 @@ response = ZaiPayment.items.list_transactions('item_id')
183
184
  - 💡 [Item Examples](examples/items.md) - Real-world usage patterns and complete workflows
184
185
  - 🔗 [Zai: Items API Reference](https://developer.hellozai.com/reference/listitems)
185
186
 
187
+ ### Token Auth
188
+
189
+ Generate secure tokens for collecting bank and card account information:
190
+
191
+ ```ruby
192
+ # Generate a bank token (for collecting bank account details)
193
+ response = ZaiPayment.token_auths.generate(
194
+ user_id: "seller-68611249",
195
+ token_type: "bank"
196
+ )
197
+
198
+ token = response.data['token_auth']['token']
199
+ # Use this token with PromisePay.js on the frontend
200
+
201
+ # Generate a card token (for collecting credit card details)
202
+ response = ZaiPayment.token_auths.generate(
203
+ user_id: "buyer-12345",
204
+ token_type: "card"
205
+ )
206
+
207
+ token = response.data['token_auth']['token']
208
+ # Use this token with PromisePay.js on the frontend
209
+ ```
210
+
211
+ **📚 Documentation:**
212
+ - 💡 [Token Auth Examples](examples/token_auths.md) - Complete integration guide with PromisePay.js
213
+ - 🔗 [Zai: Generate Token API Reference](https://developer.hellozai.com/reference/generatetoken)
214
+
186
215
  ### Webhooks
187
216
 
188
217
  Manage webhook endpoints:
@@ -243,6 +272,7 @@ end
243
272
  | ✅ Webhooks | CRUD for webhook endpoints | Done |
244
273
  | ✅ Users | Manage PayIn / PayOut users | Done |
245
274
  | ✅ Items | Transactions/payments (CRUD) | Done |
275
+ | ✅ Token Auth | Generate bank/card tokens | Done |
246
276
  | 💳 Payments | Single and recurring payments | 🚧 In progress |
247
277
  | 🏦 Virtual Accounts (VA / PIPU) | Manage virtual accounts & PayTo | ⏳ Planned |
248
278
  | 💼 Wallets | Create and manage wallet accounts | ⏳ Planned |
@@ -307,6 +337,7 @@ Everyone interacting in the ZaiPayment project's codebases, issue trackers, chat
307
337
  ### Examples & Patterns
308
338
  - [User Examples](examples/users.md) - Real-world user management patterns
309
339
  - [Item Examples](examples/items.md) - Transaction and payment workflows
340
+ - [Token Auth Examples](examples/token_auths.md) - Secure token generation and integration
310
341
  - [Webhook Examples](examples/webhooks.md) - Webhook integration patterns
311
342
 
312
343
  ### Technical Guides
@@ -0,0 +1,249 @@
1
+ # Token Auth API Implementation Summary
2
+
3
+ ## Overview
4
+
5
+ Successfully implemented the **Generate Token** endpoint from the Zai API (https://developer.hellozai.com/reference/generatetoken) to enable secure bank and card account data collection.
6
+
7
+ ## What Was Implemented
8
+
9
+ ### 1. Core Resource Implementation
10
+
11
+ **File:** `lib/zai_payment/resources/token_auth.rb`
12
+
13
+ - Created `TokenAuth` resource class following the project's resource pattern
14
+ - Implemented `generate(user_id:, token_type:)` method
15
+ - Added token type validation (bank or card)
16
+ - Added user ID validation
17
+ - Support for case-insensitive token types
18
+ - Default token type: 'bank'
19
+
20
+ **Key Features:**
21
+ ```ruby
22
+ # Generate a bank token (default)
23
+ ZaiPayment.token_auths.generate(user_id: "seller-123")
24
+
25
+ # Generate a card token
26
+ ZaiPayment.token_auths.generate(user_id: "buyer-123", token_type: "card")
27
+ ```
28
+
29
+ ### 2. Module Integration
30
+
31
+ **File:** `lib/zai_payment.rb`
32
+
33
+ - Added `require_relative` for token_auth resource
34
+ - Added `token_auths` accessor method
35
+ - Configured to use `core_base` endpoint (https://test.api.promisepay.com)
36
+
37
+ ### 3. Test Suite
38
+
39
+ **File:** `spec/zai_payment/resources/token_auth_spec.rb`
40
+
41
+ - 15 comprehensive test cases covering:
42
+ - Bank token generation
43
+ - Card token generation
44
+ - Default token type behavior
45
+ - Validation errors (nil, empty, whitespace, invalid types)
46
+ - Case-insensitive token types
47
+ - Client initialization
48
+ - Constants verification
49
+ - All tests passing with 95.22% line coverage
50
+ - Follows project's testing pattern using Faraday test stubs
51
+ - RuboCop compliant
52
+
53
+ ### 4. Documentation
54
+
55
+ **File:** `examples/token_auths.md` (600+ lines)
56
+
57
+ Comprehensive examples including:
58
+ - Basic usage patterns
59
+ - Bank token collection workflows
60
+ - Card token collection workflows
61
+ - Rails controller integration
62
+ - Service object pattern
63
+ - Frontend integration with PromisePay.js
64
+ - Complete payment flow examples
65
+ - Error handling strategies
66
+ - Retry logic with exponential backoff
67
+ - Security best practices:
68
+ - Token expiry management
69
+ - Audit logging
70
+ - Rate limiting protection
71
+
72
+ **File:** `docs/token_auths.md` (500+ lines)
73
+
74
+ Complete technical guide covering:
75
+ - When to use Token Auth
76
+ - How it works (flow diagram)
77
+ - API methods reference
78
+ - Token types (bank vs card) with use cases
79
+ - Security considerations (PCI compliance, token lifecycle)
80
+ - Integration guide (backend + frontend)
81
+ - Error handling patterns
82
+ - Best practices with code examples
83
+ - Related resources and API references
84
+
85
+ ### 5. Version Updates
86
+
87
+ **File:** `lib/zai_payment/version.rb`
88
+
89
+ - Updated version from `2.0.2` to `2.1.0`
90
+ - Follows semantic versioning (minor version bump for new feature)
91
+
92
+ ### 6. Changelog
93
+
94
+ **File:** `changelog.md`
95
+
96
+ Added comprehensive release notes for version 2.1.0:
97
+ - Feature description
98
+ - API methods
99
+ - Documentation additions
100
+ - Testing coverage
101
+ - Link to full changelog
102
+
103
+ ### 7. README Updates
104
+
105
+ **File:** `readme.md`
106
+
107
+ - Added Token Auth to features list (🎫 emoji)
108
+ - Added Token Auth section with quick examples
109
+ - Updated roadmap (marked Token Auth as Done ✅)
110
+ - Added documentation links in Examples & Patterns section
111
+
112
+ ### 8. Documentation Index
113
+
114
+ **File:** `docs/readme.md`
115
+
116
+ - Added token_auths.md to Architecture & Design section
117
+ - Added Token Auth Examples to Examples section
118
+ - Added Token Auth to Quick Links with guide, examples, and API reference
119
+ - Updated documentation structure tree
120
+ - Added tips for collecting payment data
121
+
122
+ ## API Endpoint
123
+
124
+ **POST** `https://test.api.promisepay.com/token_auths`
125
+
126
+ **Request Body:**
127
+ ```json
128
+ {
129
+ "token_type": "bank", // or "card"
130
+ "user_id": "seller-68611249"
131
+ }
132
+ ```
133
+
134
+ **Response:**
135
+ ```json
136
+ {
137
+ "token_auth": {
138
+ "token": "tok_bank_abc123...",
139
+ "user_id": "seller-68611249",
140
+ "token_type": "bank",
141
+ "created_at": "2025-10-24T12:00:00Z",
142
+ "expires_at": "2025-10-24T13:00:00Z"
143
+ }
144
+ }
145
+ ```
146
+
147
+ ## Usage Example
148
+
149
+ ```ruby
150
+ # Configure the gem
151
+ ZaiPayment.configure do |c|
152
+ c.environment = :prelive
153
+ c.client_id = ENV['ZAI_CLIENT_ID']
154
+ c.client_secret = ENV['ZAI_CLIENT_SECRET']
155
+ c.scope = ENV['ZAI_OAUTH_SCOPE']
156
+ end
157
+
158
+ # Generate a card token for buyer
159
+ response = ZaiPayment.token_auths.generate(
160
+ user_id: "buyer-12345",
161
+ token_type: "card"
162
+ )
163
+
164
+ token = response.data['token_auth']['token']
165
+ # Send token to frontend for use with PromisePay.js
166
+ ```
167
+
168
+ ## Integration with PromisePay.js
169
+
170
+ ```javascript
171
+ // Frontend (JavaScript)
172
+ PromisePay.setToken(token_from_backend);
173
+
174
+ PromisePay.createCardAccount({
175
+ card_number: '4111111111111111',
176
+ expiry_month: '12',
177
+ expiry_year: '2025',
178
+ cvv: '123'
179
+ }, function(response) {
180
+ if (response.error) {
181
+ console.error('Error:', response.error);
182
+ } else {
183
+ const cardAccountId = response.card_accounts.id;
184
+ // Send cardAccountId back to backend
185
+ }
186
+ });
187
+ ```
188
+
189
+ ## Test Results
190
+
191
+ - **Total Tests:** 272 examples
192
+ - **Failures:** 0
193
+ - **Line Coverage:** 95.22% (518 / 544)
194
+ - **Branch Coverage:** 80.79% (143 / 177)
195
+ - **RuboCop:** No offenses detected
196
+
197
+ ## Files Created
198
+
199
+ 1. `lib/zai_payment/resources/token_auth.rb` - Core resource implementation
200
+ 2. `spec/zai_payment/resources/token_auth_spec.rb` - Test suite
201
+ 3. `examples/token_auths.md` - Comprehensive usage examples
202
+ 4. `docs/token_auths.md` - Technical documentation
203
+
204
+ ## Files Modified
205
+
206
+ 1. `lib/zai_payment.rb` - Added token_auths accessor
207
+ 2. `lib/zai_payment/version.rb` - Version bump to 2.1.0
208
+ 3. `changelog.md` - Added 2.1.0 release notes
209
+ 4. `readme.md` - Added Token Auth documentation
210
+ 5. `docs/readme.md` - Updated documentation index
211
+
212
+ ## Security Considerations
213
+
214
+ - **PCI Compliance:** Tokens enable PCI-compliant card data collection without sensitive data touching your server
215
+ - **Token Expiration:** Tokens have limited lifespan (typically 1 hour)
216
+ - **Single-use:** Tokens should be generated fresh for each session
217
+ - **User-specific:** Each token is tied to a specific user ID
218
+ - **Type-specific:** Bank tokens only for bank accounts, card tokens only for cards
219
+ - **HTTPS Required:** All communication over secure HTTPS
220
+
221
+ ## Next Steps
222
+
223
+ The Token Auth implementation is complete and ready for use. Developers can now:
224
+
225
+ 1. Generate tokens for buyers to collect credit card information
226
+ 2. Generate tokens for sellers to collect bank account details
227
+ 3. Integrate with PromisePay.js for secure frontend data collection
228
+ 4. Process payments without handling sensitive payment data directly
229
+
230
+ ## Related APIs
231
+
232
+ This implementation complements existing resources:
233
+ - **Users API** - Create users before generating tokens
234
+ - **Items API** - Use payment accounts to create transactions
235
+ - **Webhooks API** - Receive notifications about payment events
236
+
237
+ ## Documentation Links
238
+
239
+ - **API Reference:** https://developer.hellozai.com/reference/generatetoken
240
+ - **Examples:** [examples/token_auths.md](examples/token_auths.md)
241
+ - **Guide:** [docs/token_auths.md](docs/token_auths.md)
242
+ - **PromisePay.js:** https://developer.hellozai.com/docs/promisepay-js
243
+
244
+ ---
245
+
246
+ **Implementation Date:** October 24, 2025
247
+ **Version:** 2.1.0
248
+ **Status:** ✅ Complete and tested
249
+
metadata CHANGED
@@ -1,7 +1,7 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: zai_payment
3
3
  version: !ruby/object:Gem::Version
4
- version: 2.0.2
4
+ version: 2.1.0
5
5
  platform: ruby
6
6
  authors:
7
7
  - Eddy Jaga
@@ -70,6 +70,7 @@ files:
70
70
  - docs/authentication.md
71
71
  - docs/items.md
72
72
  - docs/readme.md
73
+ - docs/token_auths.md
73
74
  - docs/user_id_field.md
74
75
  - docs/user_quick_reference.md
75
76
  - docs/users.md
@@ -77,6 +78,7 @@ files:
77
78
  - docs/webhook_signature.md
78
79
  - docs/webhooks.md
79
80
  - examples/items.md
81
+ - examples/token_auths.md
80
82
  - examples/users.md
81
83
  - examples/webhooks.md
82
84
  - implementation.md
@@ -89,12 +91,14 @@ files:
89
91
  - lib/zai_payment/config.rb
90
92
  - lib/zai_payment/errors.rb
91
93
  - lib/zai_payment/resources/item.rb
94
+ - lib/zai_payment/resources/token_auth.rb
92
95
  - lib/zai_payment/resources/user.rb
93
96
  - lib/zai_payment/resources/webhook.rb
94
97
  - lib/zai_payment/response.rb
95
98
  - lib/zai_payment/version.rb
96
99
  - readme.md
97
100
  - sig/zai_payment.rbs
101
+ - token_auth_implementation_summary.md
98
102
  homepage: https://github.com/Sentia/zai-payment
99
103
  licenses:
100
104
  - MIT