finconnect 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.
- package/LICENSE +21 -0
- package/README.md +328 -0
- package/dist/index.d.ts +21 -0
- package/dist/index.d.ts.map +1 -0
- package/dist/index.js +81 -0
- package/dist/index.js.map +1 -0
- package/dist/providers/AzampayProvider.d.ts +18 -0
- package/dist/providers/AzampayProvider.d.ts.map +1 -0
- package/dist/providers/AzampayProvider.js +134 -0
- package/dist/providers/AzampayProvider.js.map +1 -0
- package/dist/providers/BaseProvider.d.ts +14 -0
- package/dist/providers/BaseProvider.d.ts.map +1 -0
- package/dist/providers/BaseProvider.js +15 -0
- package/dist/providers/BaseProvider.js.map +1 -0
- package/dist/providers/ClickpesaProvider.d.ts +10 -0
- package/dist/providers/ClickpesaProvider.d.ts.map +1 -0
- package/dist/providers/ClickpesaProvider.js +99 -0
- package/dist/providers/ClickpesaProvider.js.map +1 -0
- package/dist/providers/PesapalProvider.d.ts +14 -0
- package/dist/providers/PesapalProvider.d.ts.map +1 -0
- package/dist/providers/PesapalProvider.js +88 -0
- package/dist/providers/PesapalProvider.js.map +1 -0
- package/package.json +73 -0
package/LICENSE
ADDED
|
@@ -0,0 +1,21 @@
|
|
|
1
|
+
MIT License
|
|
2
|
+
|
|
3
|
+
Copyright (c) 2026 Elisha Gerson
|
|
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 all
|
|
13
|
+
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 THE
|
|
21
|
+
SOFTWARE.
|
package/README.md
ADDED
|
@@ -0,0 +1,328 @@
|
|
|
1
|
+
# FinConnect
|
|
2
|
+
|
|
3
|
+
<div align="center">
|
|
4
|
+
|
|
5
|
+
[](https://opensource.org/licenses/MIT)
|
|
6
|
+
[](https://www.typescriptlang.org/)
|
|
7
|
+
[](https://nodejs.org/)
|
|
8
|
+
|
|
9
|
+
**A unified wrapper for East African fintech payment providers**
|
|
10
|
+
|
|
11
|
+
[Features](#features) • [Quick Start](#quick-start) • [Supported Providers](#supported-providers) • [Documentation](#documentation) • [Contributing](#contributing)
|
|
12
|
+
|
|
13
|
+
</div>
|
|
14
|
+
|
|
15
|
+
---
|
|
16
|
+
|
|
17
|
+
## Overview
|
|
18
|
+
|
|
19
|
+
FinConnect is a lightweight, provider-agnostic integration wrapper that simplifies payment processing across multiple East African fintech platforms. Instead of managing different authentication flows, payload structures, and error handling for each provider, FinConnect provides a **single, unified API** for PesaPal, AzamPay, ClickPesa, and more.
|
|
20
|
+
|
|
21
|
+
### The Problem We Solve
|
|
22
|
+
|
|
23
|
+
Integrating multiple payment providers typically requires:
|
|
24
|
+
- Learning different authentication flows (OAuth2 vs. JWT)
|
|
25
|
+
- Managing different payload structures per provider
|
|
26
|
+
- Implementing custom error handling for each API
|
|
27
|
+
- Maintaining complex provider-specific logic
|
|
28
|
+
|
|
29
|
+
FinConnect eliminates this complexity with a consistent, developer-friendly interface.
|
|
30
|
+
|
|
31
|
+
---
|
|
32
|
+
|
|
33
|
+
## ✨ Features
|
|
34
|
+
|
|
35
|
+
- 🔌 **Provider-Agnostic API** - Single interface for multiple payment providers
|
|
36
|
+
- 🔐 **Multi-Auth Support** - OAuth2, JWT, Bearer tokens handled transparently
|
|
37
|
+
- ⚡ **Type-Safe** - Full TypeScript support with complete type definitions
|
|
38
|
+
- 🌍 **Regional Coverage** - PesaPal (East Africa), AzamPay (Tanzania), ClickPesa (East Africa)
|
|
39
|
+
- 🛡️ **Error Handling** - Consistent error messages and status tracking
|
|
40
|
+
- 🔄 **Async/Await Ready** - Modern async patterns throughout
|
|
41
|
+
- 📝 **Well-Documented** - Comprehensive examples and API documentation
|
|
42
|
+
|
|
43
|
+
---
|
|
44
|
+
|
|
45
|
+
## 🚀 Quick Start
|
|
46
|
+
|
|
47
|
+
### Prerequisites
|
|
48
|
+
|
|
49
|
+
- Node.js 16.x or later
|
|
50
|
+
- npm 7.x or later
|
|
51
|
+
|
|
52
|
+
### Installation
|
|
53
|
+
|
|
54
|
+
```bash
|
|
55
|
+
npm install finconnect
|
|
56
|
+
```
|
|
57
|
+
|
|
58
|
+
Or from the repository source:
|
|
59
|
+
|
|
60
|
+
```bash
|
|
61
|
+
# Clone the repository
|
|
62
|
+
git clone https://github.com/somebody1011/finconnect.git
|
|
63
|
+
|
|
64
|
+
# Navigate to project directory
|
|
65
|
+
cd finconnect
|
|
66
|
+
|
|
67
|
+
# Install dependencies
|
|
68
|
+
npm install
|
|
69
|
+
```
|
|
70
|
+
|
|
71
|
+
### Configuration
|
|
72
|
+
|
|
73
|
+
Create a `.env` file in your root directory with your provider credentials:
|
|
74
|
+
|
|
75
|
+
```env
|
|
76
|
+
# PesaPal Configuration
|
|
77
|
+
PESAPAL_APP_KEY=your_key
|
|
78
|
+
PESAPAL_APP_SECRET=your_secret
|
|
79
|
+
|
|
80
|
+
|
|
81
|
+
# AzamPay Configuration
|
|
82
|
+
AZAMPAY_SECRET=your_secret
|
|
83
|
+
|
|
84
|
+
# ClickPesa Configuration
|
|
85
|
+
CLICKPESA_CLIENT_ID=your_id
|
|
86
|
+
CLICKPESA_API_KEY=your_api_key
|
|
87
|
+
```
|
|
88
|
+
|
|
89
|
+
### Basic Usage
|
|
90
|
+
|
|
91
|
+
```typescript
|
|
92
|
+
import { FintechGateway } from './src/index';
|
|
93
|
+
|
|
94
|
+
// Initialize gateway for pesapal
|
|
95
|
+
const gateway = new FintechGateway('pesapal', {
|
|
96
|
+
apiKey: process.env.PESAPAL_CONSUMER_KEY,
|
|
97
|
+
apiSecret: process.env.PESAPAL_CONSUMER_SECRET,
|
|
98
|
+
shortCode: '174379',
|
|
99
|
+
environment: 'sandbox'
|
|
100
|
+
});
|
|
101
|
+
|
|
102
|
+
// Process a payment
|
|
103
|
+
async function processPayment() {
|
|
104
|
+
try {
|
|
105
|
+
const response = await gateway.processPayment({
|
|
106
|
+
amount: 1000,
|
|
107
|
+
phoneNumber: '255700000000',
|
|
108
|
+
reference: 'REF-99'
|
|
109
|
+
});
|
|
110
|
+
|
|
111
|
+
if (response.success) {
|
|
112
|
+
console.log(`✅ Payment successful! Transaction ID: ${response.transactionId}`);
|
|
113
|
+
} else {
|
|
114
|
+
console.error(`❌ Payment failed: ${response.message}`);
|
|
115
|
+
}
|
|
116
|
+
} catch (error) {
|
|
117
|
+
console.error('Error processing payment:', error);
|
|
118
|
+
}
|
|
119
|
+
}
|
|
120
|
+
|
|
121
|
+
processPayment();
|
|
122
|
+
```
|
|
123
|
+
|
|
124
|
+
---
|
|
125
|
+
|
|
126
|
+
## 🏗️ Supported Providers
|
|
127
|
+
|
|
128
|
+
| Provider | Status | Auth Method | Region(s) |
|
|
129
|
+
|----------|--------|-------------|-----------|
|
|
130
|
+
| **ClickPesa** |🚧🛠️ Onprogress | JWT | East Africa |
|
|
131
|
+
| **PesaPal** | 🚧🛠️ Onprogress| OAuth2 | East Africa |
|
|
132
|
+
| **AzamPay** | 📋 Planned | Bearer/Secret | Tanzania |
|
|
133
|
+
|
|
134
|
+
|
|
135
|
+
---
|
|
136
|
+
|
|
137
|
+
## 📚 API Reference
|
|
138
|
+
|
|
139
|
+
### FintechGateway
|
|
140
|
+
|
|
141
|
+
#### Constructor
|
|
142
|
+
|
|
143
|
+
```typescript
|
|
144
|
+
new FintechGateway(provider: string, config: ProviderConfig)
|
|
145
|
+
```
|
|
146
|
+
|
|
147
|
+
**Parameters:**
|
|
148
|
+
- `provider` - The payment provider identifier ('pesapal', 'azampay', 'clickpesa')
|
|
149
|
+
- `config` - Provider-specific configuration object
|
|
150
|
+
|
|
151
|
+
#### Methods
|
|
152
|
+
|
|
153
|
+
##### `processPayment()`
|
|
154
|
+
|
|
155
|
+
```typescript
|
|
156
|
+
processPayment(params: PaymentParams): Promise<PaymentResponse>
|
|
157
|
+
```
|
|
158
|
+
|
|
159
|
+
**Parameters:**
|
|
160
|
+
```typescript
|
|
161
|
+
interface PaymentParams {
|
|
162
|
+
amount: number;
|
|
163
|
+
phoneNumber: string;
|
|
164
|
+
reference: string;
|
|
165
|
+
description?: string;
|
|
166
|
+
}
|
|
167
|
+
```
|
|
168
|
+
|
|
169
|
+
**Returns:**
|
|
170
|
+
```typescript
|
|
171
|
+
interface PaymentResponse {
|
|
172
|
+
success: boolean;
|
|
173
|
+
transactionId?: string;
|
|
174
|
+
message: string;
|
|
175
|
+
status: 'pending' | 'completed' | 'failed';
|
|
176
|
+
timestamp: Date;
|
|
177
|
+
}
|
|
178
|
+
```
|
|
179
|
+
|
|
180
|
+
**Example:**
|
|
181
|
+
```typescript
|
|
182
|
+
const result = await gateway.processPayment({
|
|
183
|
+
amount: 5000,
|
|
184
|
+
phoneNumber: '254712345678',
|
|
185
|
+
reference: 'ORD-2024-001',
|
|
186
|
+
description: 'Payment for order #123'
|
|
187
|
+
});
|
|
188
|
+
```
|
|
189
|
+
|
|
190
|
+
---
|
|
191
|
+
|
|
192
|
+
## 📁 Project Structure
|
|
193
|
+
|
|
194
|
+
```
|
|
195
|
+
finconnect/
|
|
196
|
+
├── src/
|
|
197
|
+
│ ├── FintechGateway.ts # Main gateway class
|
|
198
|
+
│ ├── providers/
|
|
199
|
+
│ │ ├── BaseProvider.ts # Abstract base class
|
|
200
|
+
│ │ ├── MpesaProvider.ts # M-Pesa implementation
|
|
201
|
+
│ │ ├── AzampayProvider.ts # AzamPay implementation
|
|
202
|
+
│ │ └── ClickpesaProvider.ts # ClickPesa implementation
|
|
203
|
+
│ ├── types/
|
|
204
|
+
│ │ └── index.ts # TypeScript type definitions
|
|
205
|
+
│ └── utils/
|
|
206
|
+
│ └── errorHandler.ts # Error handling utilities
|
|
207
|
+
├── tests/
|
|
208
|
+
│ ├── unit/
|
|
209
|
+
│ └── integration/
|
|
210
|
+
├── .env.example
|
|
211
|
+
├── package.json
|
|
212
|
+
├── tsconfig.json
|
|
213
|
+
├── jest.config.js
|
|
214
|
+
└── README.md
|
|
215
|
+
```
|
|
216
|
+
|
|
217
|
+
---
|
|
218
|
+
|
|
219
|
+
## 🔒 Security Best Practices
|
|
220
|
+
|
|
221
|
+
1. **Never commit credentials** - Use `.env` files and add them to `.gitignore`
|
|
222
|
+
2. **Use environment variables** - Store sensitive keys outside version control
|
|
223
|
+
3. **Validate inputs** - Always validate payment amounts and phone numbers
|
|
224
|
+
4. **HTTPS only** - All API calls are made over HTTPS
|
|
225
|
+
5. **Error messages** - Avoid exposing sensitive details in error responses
|
|
226
|
+
|
|
227
|
+
**Example:**
|
|
228
|
+
```typescript
|
|
229
|
+
// ❌ DO NOT DO THIS
|
|
230
|
+
const gateway = new FintechGateway('mpesa', {
|
|
231
|
+
apiKey: 'your_actual_key_here'
|
|
232
|
+
});
|
|
233
|
+
|
|
234
|
+
// ✅ DO THIS
|
|
235
|
+
const gateway = new FintechGateway('pesapal', {
|
|
236
|
+
apiKey: process.env.PESAPAL_CONSUMER_KEY,
|
|
237
|
+
apiSecret: process.env.PESAPAL_CONSUMER_SECRET
|
|
238
|
+
});
|
|
239
|
+
```
|
|
240
|
+
|
|
241
|
+
---
|
|
242
|
+
|
|
243
|
+
## 🗺️ Roadmap
|
|
244
|
+
|
|
245
|
+
- [x] ClickPesa integration
|
|
246
|
+
- [x] PesaPal integration
|
|
247
|
+
- [ ] AzamPay integration
|
|
248
|
+
- [ ] Add B2C (Business to Customer) support
|
|
249
|
+
- [ ] Implement automatic retry logic for failed API calls
|
|
250
|
+
- [ ] Add comprehensive unit tests using Jest
|
|
251
|
+
- [ ] Add rate limiting and throttling
|
|
252
|
+
- [ ] Support for transaction status polling
|
|
253
|
+
- [ ] Webhook integration for payment notifications
|
|
254
|
+
- [ ] SDK for React Native
|
|
255
|
+
|
|
256
|
+
---
|
|
257
|
+
|
|
258
|
+
## 🤝 Contributing
|
|
259
|
+
|
|
260
|
+
We welcome contributions! Here's how to get started:
|
|
261
|
+
|
|
262
|
+
1. **Fork the repository** on GitHub
|
|
263
|
+
2. **Create a feature branch** for your changes:
|
|
264
|
+
```bash
|
|
265
|
+
git checkout -b feature/add-new-provider
|
|
266
|
+
```
|
|
267
|
+
3. **Add a new provider** (if applicable):
|
|
268
|
+
- Create a new file in `src/providers/` (e.g., `NewProviderName.ts`)
|
|
269
|
+
- Extend the `BaseProvider` class
|
|
270
|
+
- Implement required methods: `authenticate()`, `processPayment()`, `getTransactionStatus()`
|
|
271
|
+
4. **Add tests** for your changes:
|
|
272
|
+
```bash
|
|
273
|
+
npm test
|
|
274
|
+
```
|
|
275
|
+
5. **Commit your changes** with clear messages:
|
|
276
|
+
```bash
|
|
277
|
+
git commit -m "Add support for XYZ provider"
|
|
278
|
+
```
|
|
279
|
+
6. **Push to your fork** and submit a Pull Request
|
|
280
|
+
|
|
281
|
+
### Development Setup
|
|
282
|
+
|
|
283
|
+
```bash
|
|
284
|
+
# Install dev dependencies
|
|
285
|
+
npm install --save-dev
|
|
286
|
+
|
|
287
|
+
# Run tests
|
|
288
|
+
npm test
|
|
289
|
+
|
|
290
|
+
# Build the project
|
|
291
|
+
npm run build
|
|
292
|
+
|
|
293
|
+
# Lint the code
|
|
294
|
+
npm run lint
|
|
295
|
+
```
|
|
296
|
+
|
|
297
|
+
---
|
|
298
|
+
|
|
299
|
+
## 📝 License
|
|
300
|
+
|
|
301
|
+
This project is licensed under the **MIT License** - see the [LICENSE](LICENSE) file for details.
|
|
302
|
+
|
|
303
|
+
---
|
|
304
|
+
|
|
305
|
+
## 📞 Support & Contact
|
|
306
|
+
|
|
307
|
+
- **Issues** - Report bugs or request features via [GitHub Issues](https://github.com/somebody1011/finconnect/issues)
|
|
308
|
+
- **Discussions** - Join our community discussions [here](https://github.com/somebody1011/finconnect/discussions)
|
|
309
|
+
- **Author** - [@somebody1011](https://github.com/somebody1011)
|
|
310
|
+
|
|
311
|
+
---
|
|
312
|
+
|
|
313
|
+
## 🙏 Acknowledgments
|
|
314
|
+
|
|
315
|
+
- Built with ❤️ for the East African fintech community
|
|
316
|
+
- Inspired by Stripe's elegant API design
|
|
317
|
+
- Special thanks to all contributors and early users
|
|
318
|
+
- Thanks to the open-source community for amazing tools and libraries
|
|
319
|
+
|
|
320
|
+
---
|
|
321
|
+
|
|
322
|
+
<div align="center">
|
|
323
|
+
|
|
324
|
+
Made with ❤️ by [somebody1011](https://github.com/somebody1011)
|
|
325
|
+
|
|
326
|
+
⭐ Star us on GitHub! [somebody1011/finconnect](https://github.com/somebody1011/finconnect)
|
|
327
|
+
|
|
328
|
+
</div>
|
package/dist/index.d.ts
ADDED
|
@@ -0,0 +1,21 @@
|
|
|
1
|
+
export declare const ProviderType: {
|
|
2
|
+
readonly clickpesa: "clickpesa";
|
|
3
|
+
readonly pesapal: "pesapal";
|
|
4
|
+
readonly azampay: "azampay";
|
|
5
|
+
};
|
|
6
|
+
export type ProviderType = typeof ProviderType[keyof typeof ProviderType];
|
|
7
|
+
export declare class FintechSDK {
|
|
8
|
+
private gateway;
|
|
9
|
+
constructor(options: {
|
|
10
|
+
provider: ProviderType | string;
|
|
11
|
+
config: any;
|
|
12
|
+
});
|
|
13
|
+
registerIpn(ipnUrl: string, ipnNotificationType?: "GET" | "POST"): Promise<any>;
|
|
14
|
+
pay(data: any, ipnId?: string): Promise<any>;
|
|
15
|
+
checkPaymentStatus(transactionId: string): Promise<any>;
|
|
16
|
+
handleCallback(callbackData: any): Promise<{
|
|
17
|
+
isValid: boolean;
|
|
18
|
+
data: any;
|
|
19
|
+
}>;
|
|
20
|
+
}
|
|
21
|
+
//# sourceMappingURL=index.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAKA,eAAO,MAAM,YAAY;;;;CAIf,CAAC;AAEX,MAAM,MAAM,YAAY,GAAG,OAAO,YAAY,CAAC,MAAM,OAAO,YAAY,CAAC,CAAC;AAuC1E,qBAAa,UAAU;IACrB,OAAO,CAAC,OAAO,CAAe;gBAElB,OAAO,EAAE;QAAE,QAAQ,EAAE,YAAY,GAAG,MAAM,CAAC;QAAC,MAAM,EAAE,GAAG,CAAA;KAAE;IAK/D,WAAW,CAAC,MAAM,EAAE,MAAM,EAAE,mBAAmB,GAAE,KAAK,GAAG,MAAc;IAKvE,GAAG,CAAC,IAAI,EAAE,GAAG,EAAE,KAAK,CAAC,EAAE,MAAM;IAc7B,kBAAkB,CAAC,aAAa,EAAE,MAAM;IAIxC,cAAc,CAAC,YAAY,EAAE,GAAG;;;;CAMvC"}
|
package/dist/index.js
ADDED
|
@@ -0,0 +1,81 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
+
exports.FintechSDK = exports.ProviderType = void 0;
|
|
4
|
+
const ClickpesaProvider_js_1 = require("./providers/ClickpesaProvider.js");
|
|
5
|
+
const PesapalProvider_js_1 = require("./providers/PesapalProvider.js");
|
|
6
|
+
const AzampayProvider_js_1 = require("./providers/AzampayProvider.js");
|
|
7
|
+
exports.ProviderType = {
|
|
8
|
+
clickpesa: 'clickpesa',
|
|
9
|
+
pesapal: 'pesapal',
|
|
10
|
+
azampay: 'azampay',
|
|
11
|
+
};
|
|
12
|
+
class ProviderFactory {
|
|
13
|
+
/**
|
|
14
|
+
* Factory method to create a specific provider instance.
|
|
15
|
+
*
|
|
16
|
+
* Security Considerations:
|
|
17
|
+
* 1. Validates the provider type against an allowed list via a switch statement,
|
|
18
|
+
* preventing prototype pollution or instantiation of arbitrary objects.
|
|
19
|
+
* 2. Throws an explicit error for unsupported providers, avoiding silent failures.
|
|
20
|
+
* 3. Validates that essential configuration parameters are present before instantiating.
|
|
21
|
+
*/
|
|
22
|
+
static createProvider(provider, config) {
|
|
23
|
+
switch (String(provider).toLowerCase()) {
|
|
24
|
+
case exports.ProviderType.clickpesa:
|
|
25
|
+
if (!config || !config.baseUrl || !config.CLICKPESA_CLIENT_ID || !config.CLICKPESA_API_KEY) {
|
|
26
|
+
throw new Error("Invalid configuration: Missing required fields for Clickpesa.");
|
|
27
|
+
}
|
|
28
|
+
return new ClickpesaProvider_js_1.ClickpesaProvider(config);
|
|
29
|
+
case exports.ProviderType.pesapal:
|
|
30
|
+
if (!config || !config.baseUrl || !config.PESAPAL_CONSUMER_KEY || !config.PESAPAL_CONSUMER_SECRET) {
|
|
31
|
+
throw new Error("Invalid configuration: Missing required fields for Pesapal.");
|
|
32
|
+
}
|
|
33
|
+
return new PesapalProvider_js_1.PesapalProvider(config);
|
|
34
|
+
case exports.ProviderType.azampay:
|
|
35
|
+
if (!config || !config.baseUrl || !config.AZAMPAY_APP_NAME || !config.AZAMPAY_CONSUMER_KEY || !config.AZAMPAY_CONSUMER_SECRET) {
|
|
36
|
+
throw new Error("Invalid configuration: Missing required fields for Azampay.");
|
|
37
|
+
}
|
|
38
|
+
return new AzampayProvider_js_1.AzampayProvider(config);
|
|
39
|
+
default:
|
|
40
|
+
// Security: Fail securely if an unknown provider is requested.
|
|
41
|
+
throw new Error(`Unsupported provider type: ${String(provider)}`);
|
|
42
|
+
}
|
|
43
|
+
}
|
|
44
|
+
}
|
|
45
|
+
class FintechSDK {
|
|
46
|
+
gateway;
|
|
47
|
+
constructor(options) {
|
|
48
|
+
// Utilize the secure ProviderFactory to instantiate the gateway
|
|
49
|
+
this.gateway = ProviderFactory.createProvider(options.provider, options.config);
|
|
50
|
+
}
|
|
51
|
+
async registerIpn(ipnUrl, ipnNotificationType = "GET") {
|
|
52
|
+
// Allows the user to register an IPN and retrieve an ipnId
|
|
53
|
+
return this.gateway.registerIpn(ipnUrl, ipnNotificationType);
|
|
54
|
+
}
|
|
55
|
+
async pay(data, ipnId) {
|
|
56
|
+
// Normalizes the data structure depending on what the underlying provider expects.
|
|
57
|
+
if (this.gateway instanceof PesapalProvider_js_1.PesapalProvider) {
|
|
58
|
+
// Pesapal expects an object with payload and ipnId
|
|
59
|
+
return this.gateway.initiateUssdPushRequest({ payload: data, ipnId });
|
|
60
|
+
}
|
|
61
|
+
else if (this.gateway instanceof AzampayProvider_js_1.AzampayProvider) {
|
|
62
|
+
// Azampay expects an object with payload
|
|
63
|
+
return this.gateway.initiateUssdPushRequest({ payload: data });
|
|
64
|
+
}
|
|
65
|
+
else {
|
|
66
|
+
// Clickpesa and others expect the raw payload directly
|
|
67
|
+
return this.gateway.initiateUssdPushRequest(data);
|
|
68
|
+
}
|
|
69
|
+
}
|
|
70
|
+
async checkPaymentStatus(transactionId) {
|
|
71
|
+
return this.gateway.checkPaymentStatus({ transactionId });
|
|
72
|
+
}
|
|
73
|
+
async handleCallback(callbackData) {
|
|
74
|
+
if (this.gateway instanceof AzampayProvider_js_1.AzampayProvider) {
|
|
75
|
+
return this.gateway.handleCallback(callbackData);
|
|
76
|
+
}
|
|
77
|
+
throw new Error(`Callback handling is not supported for provider ${this.gateway.constructor.name}`);
|
|
78
|
+
}
|
|
79
|
+
}
|
|
80
|
+
exports.FintechSDK = FintechSDK;
|
|
81
|
+
//# sourceMappingURL=index.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"index.js","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,18 @@
|
|
|
1
|
+
import { baseProvider } from "./BaseProvider.js";
|
|
2
|
+
export declare class AzampayProvider extends baseProvider {
|
|
3
|
+
constructor(config: any);
|
|
4
|
+
authenticate(): Promise<string>;
|
|
5
|
+
initiateUssdPushRequest({ payload }: {
|
|
6
|
+
payload: any;
|
|
7
|
+
}): Promise<any>;
|
|
8
|
+
checkPaymentStatus(params: {
|
|
9
|
+
transactionId: string;
|
|
10
|
+
}): Promise<any>;
|
|
11
|
+
getPublicKey(): Promise<string>;
|
|
12
|
+
verifyCallbackSignature(utilityRef: string, externalReference: string, transactionStatus: string, operatorName: string, signatureBase64: string, publicKeyPem: string): boolean;
|
|
13
|
+
handleCallback(callbackData: any): Promise<{
|
|
14
|
+
isValid: boolean;
|
|
15
|
+
data: any;
|
|
16
|
+
}>;
|
|
17
|
+
}
|
|
18
|
+
//# sourceMappingURL=AzampayProvider.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"AzampayProvider.d.ts","sourceRoot":"","sources":["../../src/providers/AzampayProvider.ts"],"names":[],"mappings":"AAAA,OAAO,EAAC,YAAY,EAAC,MAAM,mBAAmB,CAAC;AAM/C,qBAAa,eAAgB,SAAQ,YAAY;gBACjC,MAAM,EAAE,GAAG;IAIjB,YAAY,IAAI,OAAO,CAAC,MAAM,CAAC;IA2B/B,uBAAuB,CAAC,EAAE,OAAO,EAAE,EAAE;QAAE,OAAO,EAAE,GAAG,CAAA;KAAE,GAAG,OAAO,CAAC,GAAG,CAAC;IA4BpE,kBAAkB,CAAC,MAAM,EAAE;QAAE,aAAa,EAAE,MAAM,CAAA;KAAE,GAAG,OAAO,CAAC,GAAG,CAAC;IAKnE,YAAY,IAAI,OAAO,CAAC,MAAM,CAAC;IAcrC,uBAAuB,CACnB,UAAU,EAAE,MAAM,EAClB,iBAAiB,EAAE,MAAM,EACzB,iBAAiB,EAAE,MAAM,EACzB,YAAY,EAAE,MAAM,EACpB,eAAe,EAAE,MAAM,EACvB,YAAY,EAAE,MAAM,GACrB,OAAO;IAQJ,cAAc,CAAC,YAAY,EAAE,GAAG,GAAG,OAAO,CAAC;QAAC,OAAO,EAAE,OAAO,CAAC;QAAC,IAAI,EAAE,GAAG,CAAA;KAAC,CAAC;CAkBlF"}
|
|
@@ -0,0 +1,134 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
var __createBinding = (this && this.__createBinding) || (Object.create ? (function(o, m, k, k2) {
|
|
3
|
+
if (k2 === undefined) k2 = k;
|
|
4
|
+
var desc = Object.getOwnPropertyDescriptor(m, k);
|
|
5
|
+
if (!desc || ("get" in desc ? !m.__esModule : desc.writable || desc.configurable)) {
|
|
6
|
+
desc = { enumerable: true, get: function() { return m[k]; } };
|
|
7
|
+
}
|
|
8
|
+
Object.defineProperty(o, k2, desc);
|
|
9
|
+
}) : (function(o, m, k, k2) {
|
|
10
|
+
if (k2 === undefined) k2 = k;
|
|
11
|
+
o[k2] = m[k];
|
|
12
|
+
}));
|
|
13
|
+
var __setModuleDefault = (this && this.__setModuleDefault) || (Object.create ? (function(o, v) {
|
|
14
|
+
Object.defineProperty(o, "default", { enumerable: true, value: v });
|
|
15
|
+
}) : function(o, v) {
|
|
16
|
+
o["default"] = v;
|
|
17
|
+
});
|
|
18
|
+
var __importStar = (this && this.__importStar) || (function () {
|
|
19
|
+
var ownKeys = function(o) {
|
|
20
|
+
ownKeys = Object.getOwnPropertyNames || function (o) {
|
|
21
|
+
var ar = [];
|
|
22
|
+
for (var k in o) if (Object.prototype.hasOwnProperty.call(o, k)) ar[ar.length] = k;
|
|
23
|
+
return ar;
|
|
24
|
+
};
|
|
25
|
+
return ownKeys(o);
|
|
26
|
+
};
|
|
27
|
+
return function (mod) {
|
|
28
|
+
if (mod && mod.__esModule) return mod;
|
|
29
|
+
var result = {};
|
|
30
|
+
if (mod != null) for (var k = ownKeys(mod), i = 0; i < k.length; i++) if (k[i] !== "default") __createBinding(result, mod, k[i]);
|
|
31
|
+
__setModuleDefault(result, mod);
|
|
32
|
+
return result;
|
|
33
|
+
};
|
|
34
|
+
})();
|
|
35
|
+
var __importDefault = (this && this.__importDefault) || function (mod) {
|
|
36
|
+
return (mod && mod.__esModule) ? mod : { "default": mod };
|
|
37
|
+
};
|
|
38
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
39
|
+
exports.AzampayProvider = void 0;
|
|
40
|
+
const BaseProvider_js_1 = require("./BaseProvider.js");
|
|
41
|
+
const dotenv = __importStar(require("dotenv"));
|
|
42
|
+
dotenv.config();
|
|
43
|
+
const axios_1 = __importDefault(require("axios"));
|
|
44
|
+
const crypto = __importStar(require("crypto"));
|
|
45
|
+
class AzampayProvider extends BaseProvider_js_1.baseProvider {
|
|
46
|
+
constructor(config) {
|
|
47
|
+
super(config);
|
|
48
|
+
}
|
|
49
|
+
async authenticate() {
|
|
50
|
+
try {
|
|
51
|
+
const response = await axios_1.default.post(` https://authenticator-sandbox.azampay.co.tz/AppRegistration/GenerateToken`, {
|
|
52
|
+
'appName': this.config.AZAMPAY_APP_NAME,
|
|
53
|
+
'clientId': this.config.AZAMPAY_CONSUMER_KEY,
|
|
54
|
+
'clientSecret': this.config.AZAMPAY_CONSUMER_SECRET,
|
|
55
|
+
}, {
|
|
56
|
+
headers: {
|
|
57
|
+
'Content-Type': 'application/json',
|
|
58
|
+
}
|
|
59
|
+
});
|
|
60
|
+
return response.data.data.accessToken;
|
|
61
|
+
}
|
|
62
|
+
catch (error) {
|
|
63
|
+
if (error.response) {
|
|
64
|
+
console.error('Authentication Error Response:', error.response.data);
|
|
65
|
+
throw new Error(`Authentication failed: ${error.response.data.message || error.message}`);
|
|
66
|
+
}
|
|
67
|
+
throw new Error(`Authentication failed: ${error}`);
|
|
68
|
+
}
|
|
69
|
+
}
|
|
70
|
+
async initiateUssdPushRequest({ payload }) {
|
|
71
|
+
try {
|
|
72
|
+
const token = await this.authenticate();
|
|
73
|
+
// console.log('Obtained Auth Token:', token); // Debug log for token
|
|
74
|
+
const response = await axios_1.default.post(`${this.config.baseUrl}/azampay/mno/checkout`, payload, {
|
|
75
|
+
headers: {
|
|
76
|
+
'Content-Type': 'application/json',
|
|
77
|
+
'Authorization': `Bearer ${token}`,
|
|
78
|
+
}
|
|
79
|
+
});
|
|
80
|
+
return response.data.transactionId;
|
|
81
|
+
}
|
|
82
|
+
catch (error) {
|
|
83
|
+
if (error.response) {
|
|
84
|
+
console.error('USSD Push Request Error Response:', error.response.data);
|
|
85
|
+
throw new Error(`Payment request failed: ${error.response.data.message || error.message}`);
|
|
86
|
+
}
|
|
87
|
+
throw new Error(`Payment request failed: ${error.message || error}`);
|
|
88
|
+
}
|
|
89
|
+
}
|
|
90
|
+
// Check Transaction Status (Unsupported in Tanzania Sandbox)
|
|
91
|
+
async checkPaymentStatus(params) {
|
|
92
|
+
throw new Error("AzamPay Tanzania does not support polling for payment status. Please use the Webhook Callback (handleCallback) strategy instead.");
|
|
93
|
+
}
|
|
94
|
+
// Handle Payment Callback with Signature Verification
|
|
95
|
+
async getPublicKey() {
|
|
96
|
+
try {
|
|
97
|
+
const token = await this.authenticate();
|
|
98
|
+
const response = await axios_1.default.get(`${this.config.baseUrl}/azampay/v1/public-key?format=Pem`, {
|
|
99
|
+
headers: {
|
|
100
|
+
'Authorization': `Bearer ${token}`
|
|
101
|
+
}
|
|
102
|
+
});
|
|
103
|
+
return response.data.publicKey;
|
|
104
|
+
}
|
|
105
|
+
catch (error) {
|
|
106
|
+
throw new Error(`Failed to fetch public key: ${error.message}`);
|
|
107
|
+
}
|
|
108
|
+
}
|
|
109
|
+
verifyCallbackSignature(utilityRef, externalReference, transactionStatus, operatorName, signatureBase64, publicKeyPem) {
|
|
110
|
+
const dataToVerify = `${utilityRef}${externalReference}${transactionStatus}${operatorName}`;
|
|
111
|
+
const verifier = crypto.createVerify('SHA256');
|
|
112
|
+
verifier.update(dataToVerify, 'utf8');
|
|
113
|
+
verifier.end();
|
|
114
|
+
return verifier.verify(publicKeyPem, signatureBase64, 'base64');
|
|
115
|
+
}
|
|
116
|
+
async handleCallback(callbackData) {
|
|
117
|
+
try {
|
|
118
|
+
const publicKeyPem = await this.getPublicKey();
|
|
119
|
+
const isValid = this.verifyCallbackSignature(callbackData.utilityref || '', callbackData.externalreference || '', callbackData.transactionstatus || '', callbackData.operator || '', callbackData.signature || '', publicKeyPem);
|
|
120
|
+
return { isValid, data: callbackData };
|
|
121
|
+
}
|
|
122
|
+
catch (error) {
|
|
123
|
+
throw new Error(`Callback handling failed: ${error.message}`);
|
|
124
|
+
}
|
|
125
|
+
}
|
|
126
|
+
}
|
|
127
|
+
exports.AzampayProvider = AzampayProvider;
|
|
128
|
+
// async function testAzampay() {
|
|
129
|
+
// const azampay = new AzampayProvider({baseUrl:process.env.AZAMPAY_BASE_URL,AZAMPAY_APP_NAME:process.env.AZAMPAY_APP_NAME, AZAMPAY_CONSUMER_KEY:process.env.AZAMPAY_CLIENT_ID, AZAMPAY_CONSUMER_SECRET:process.env.AZAMPAY_API_KEY});
|
|
130
|
+
// const auth = await azampay.authenticate();
|
|
131
|
+
// console.log('Auth token:', auth);
|
|
132
|
+
// }
|
|
133
|
+
// testAzampay()
|
|
134
|
+
//# sourceMappingURL=AzampayProvider.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"AzampayProvider.js","sourceRoot":"","sources":["../../src/providers/AzampayProvider.ts"],"names":[],"mappings":";;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;AAAA,uDAA+C;AAC/C,+CAAiC;AACjC,MAAM,CAAC,MAAM,EAAE,CAAC;AAChB,kDAA0B;AAC1B,+CAAiC;AAEjC,MAAa,eAAgB,SAAQ,8BAAY;IAC7C,YAAY,MAAW;QACnB,KAAK,CAAC,MAAM,CAAC,CAAC;IAClB,CAAC;IAED,KAAK,CAAC,YAAY;QACd,IAAI,CAAC;YACD,MAAM,QAAQ,GAAG,MAAM,eAAK,CAAC,IAAI,CAC7B,4EAA4E,EAC5E;gBACI,SAAS,EAAE,IAAI,CAAC,MAAM,CAAC,gBAAgB;gBACvC,UAAU,EAAE,IAAI,CAAC,MAAM,CAAC,oBAAoB;gBAC5C,cAAc,EAAE,IAAI,CAAC,MAAM,CAAC,uBAAuB;aACtD,EACD;gBACI,OAAO,EAAE;oBAEL,cAAc,EAAE,kBAAkB;iBACrC;aACJ,CACJ,CAAC;YAEF,OAAO,QAAQ,CAAC,IAAI,CAAC,IAAI,CAAC,WAAW,CAAC;QAC1C,CAAC;QAAC,OAAO,KAAS,EAAE,CAAC;YACjB,IAAI,KAAK,CAAC,QAAQ,EAAE,CAAC;gBACjB,OAAO,CAAC,KAAK,CAAC,gCAAgC,EAAE,KAAK,CAAC,QAAQ,CAAC,IAAI,CAAC,CAAC;gBACrE,MAAM,IAAI,KAAK,CAAC,0BAA0B,KAAK,CAAC,QAAQ,CAAC,IAAI,CAAC,OAAO,IAAI,KAAK,CAAC,OAAO,EAAE,CAAC,CAAC;YAC9F,CAAC;YACD,MAAM,IAAI,KAAK,CAAC,0BAA0B,KAAK,EAAE,CAAC,CAAC;QACvD,CAAC;IACL,CAAC;IAED,KAAK,CAAC,uBAAuB,CAAC,EAAE,OAAO,EAAoB;QACvD,IAAI,CAAC;YACD,MAAM,KAAK,GAAG,MAAM,IAAI,CAAC,YAAY,EAAE,CAAC;YACxC,uEAAuE;YACvE,MAAM,QAAQ,GAAG,MAAM,eAAK,CAAC,IAAI,CAC7B,GAAG,IAAI,CAAC,MAAM,CAAC,OAAO,uBAAuB,EAC7C,OAAO,EACP;gBACI,OAAO,EAAE;oBAEL,cAAc,EAAE,kBAAkB;oBAClC,eAAe,EAAE,UAAU,KAAK,EAAE;iBACrC;aACJ,CACJ,CAAC;YAGF,OAAO,QAAQ,CAAC,IAAI,CAAC,aAAa,CAAC;QACvC,CAAC;QAAC,OAAO,KAAU,EAAE,CAAC;YAClB,IAAI,KAAK,CAAC,QAAQ,EAAE,CAAC;gBACjB,OAAO,CAAC,KAAK,CAAC,mCAAmC,EAAE,KAAK,CAAC,QAAQ,CAAC,IAAI,CAAC,CAAC;gBACxE,MAAM,IAAI,KAAK,CAAC,2BAA2B,KAAK,CAAC,QAAQ,CAAC,IAAI,CAAC,OAAO,IAAI,KAAK,CAAC,OAAO,EAAE,CAAC,CAAC;YAC/F,CAAC;YACD,MAAM,IAAI,KAAK,CAAC,2BAA2B,KAAK,CAAC,OAAO,IAAI,KAAK,EAAE,CAAC,CAAC;QACzE,CAAC;IACL,CAAC;IAED,8DAA8D;IAC9D,KAAK,CAAC,kBAAkB,CAAC,MAAiC;QACtD,MAAM,IAAI,KAAK,CAAC,kIAAkI,CAAC,CAAC;IACxJ,CAAC;IAED,uDAAuD;IACvD,KAAK,CAAC,YAAY;QACd,IAAI,CAAC;YACD,MAAM,KAAK,GAAG,MAAM,IAAI,CAAC,YAAY,EAAE,CAAC;YACxC,MAAM,QAAQ,GAAG,MAAM,eAAK,CAAC,GAAG,CAAC,GAAG,IAAI,CAAC,MAAM,CAAC,OAAO,mCAAmC,EAAE;gBACxF,OAAO,EAAE;oBACL,eAAe,EAAE,UAAU,KAAK,EAAE;iBACrC;aACJ,CAAC,CAAC;YACH,OAAO,QAAQ,CAAC,IAAI,CAAC,SAAS,CAAC;QACnC,CAAC;QAAC,OAAO,KAAU,EAAE,CAAC;YAClB,MAAM,IAAI,KAAK,CAAC,+BAA+B,KAAK,CAAC,OAAO,EAAE,CAAC,CAAC;QACpE,CAAC;IACL,CAAC;IAED,uBAAuB,CACnB,UAAkB,EAClB,iBAAyB,EACzB,iBAAyB,EACzB,YAAoB,EACpB,eAAuB,EACvB,YAAoB;QAEpB,MAAM,YAAY,GAAG,GAAG,UAAU,GAAG,iBAAiB,GAAG,iBAAiB,GAAG,YAAY,EAAE,CAAC;QAC5F,MAAM,QAAQ,GAAG,MAAM,CAAC,YAAY,CAAC,QAAQ,CAAC,CAAC;QAC/C,QAAQ,CAAC,MAAM,CAAC,YAAY,EAAE,MAAM,CAAC,CAAC;QACtC,QAAQ,CAAC,GAAG,EAAE,CAAC;QACf,OAAO,QAAQ,CAAC,MAAM,CAAC,YAAY,EAAE,eAAe,EAAE,QAAQ,CAAC,CAAC;IACpE,CAAC;IAED,KAAK,CAAC,cAAc,CAAC,YAAiB;QAClC,IAAI,CAAC;YACD,MAAM,YAAY,GAAG,MAAM,IAAI,CAAC,YAAY,EAAE,CAAC;YAE/C,MAAM,OAAO,GAAG,IAAI,CAAC,uBAAuB,CACxC,YAAY,CAAC,UAAU,IAAI,EAAE,EAC7B,YAAY,CAAC,iBAAiB,IAAI,EAAE,EACpC,YAAY,CAAC,iBAAiB,IAAI,EAAE,EACpC,YAAY,CAAC,QAAQ,IAAI,EAAE,EAC3B,YAAY,CAAC,SAAS,IAAI,EAAE,EAC5B,YAAY,CACf,CAAC;YAEF,OAAO,EAAE,OAAO,EAAE,IAAI,EAAE,YAAY,EAAE,CAAC;QAC3C,CAAC;QAAC,OAAO,KAAU,EAAE,CAAC;YAClB,MAAM,IAAI,KAAK,CAAC,6BAA6B,KAAK,CAAC,OAAO,EAAE,CAAC,CAAC;QAClE,CAAC;IACL,CAAC;CACJ;AAhHD,0CAgHC;AAID,iCAAiC;AACjC,0OAA0O;AAC1O,iDAAiD;AACjD,wCAAwC;AAExC,IAAI;AAEJ,gBAAgB"}
|
|
@@ -0,0 +1,14 @@
|
|
|
1
|
+
export declare abstract class baseProvider {
|
|
2
|
+
protected config: any;
|
|
3
|
+
constructor(config: any);
|
|
4
|
+
abstract authenticate(): Promise<string>;
|
|
5
|
+
abstract initiateUssdPushRequest(params: {
|
|
6
|
+
payload: any;
|
|
7
|
+
ipnId?: string;
|
|
8
|
+
}): Promise<any>;
|
|
9
|
+
abstract checkPaymentStatus(params: {
|
|
10
|
+
transactionId: string;
|
|
11
|
+
}): Promise<any>;
|
|
12
|
+
registerIpn(_ipnUrl: string, _ipnNotificationType: "GET" | "POST"): Promise<any>;
|
|
13
|
+
}
|
|
14
|
+
//# sourceMappingURL=BaseProvider.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"BaseProvider.d.ts","sourceRoot":"","sources":["../../src/providers/BaseProvider.ts"],"names":[],"mappings":"AACA,8BAAsB,YAAY;IAChC,SAAS,CAAC,MAAM,EAAE,GAAG,CAAC;gBACV,MAAM,EAAE,GAAG;IAGvB,QAAQ,CAAC,YAAY,IAAI,OAAO,CAAC,MAAM,CAAC;IACxC,QAAQ,CAAC,uBAAuB,CAAC,MAAM,EAAE;QAAE,OAAO,EAAE,GAAG,CAAC;QAAC,KAAK,CAAC,EAAE,MAAM,CAAA;KAAE,GAAG,OAAO,CAAC,GAAG,CAAC;IACxF,QAAQ,CAAC,kBAAkB,CAAC,MAAM,EAAC;QAAC,aAAa,EAAC,MAAM,CAAA;KAAC,GAAG,OAAO,CAAC,GAAG,CAAC;IAClE,WAAW,CAAC,OAAO,EAAE,MAAM,EAAE,oBAAoB,EAAE,KAAK,GAAG,MAAM,GAAG,OAAO,CAAC,GAAG,CAAC;CAGvF"}
|
|
@@ -0,0 +1,15 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
+
exports.baseProvider = void 0;
|
|
4
|
+
// Add 'export' right here
|
|
5
|
+
class baseProvider {
|
|
6
|
+
config;
|
|
7
|
+
constructor(config) {
|
|
8
|
+
this.config = config;
|
|
9
|
+
}
|
|
10
|
+
async registerIpn(_ipnUrl, _ipnNotificationType) {
|
|
11
|
+
throw new Error("IPN registration not supported by this provider");
|
|
12
|
+
}
|
|
13
|
+
}
|
|
14
|
+
exports.baseProvider = baseProvider;
|
|
15
|
+
//# sourceMappingURL=BaseProvider.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"BaseProvider.js","sourceRoot":"","sources":["../../src/providers/BaseProvider.ts"],"names":[],"mappings":";;;AAAA,0BAA0B;AAC1B,MAAsB,YAAY;IACtB,MAAM,CAAM;IACtB,YAAY,MAAW;QACrB,IAAI,CAAC,MAAM,GAAG,MAAM,CAAC;IACvB,CAAC;IAID,KAAK,CAAC,WAAW,CAAC,OAAe,EAAE,oBAAoC;QACrE,MAAM,IAAI,KAAK,CAAC,iDAAiD,CAAC,CAAC;IACrE,CAAC;CACF;AAXD,oCAWC"}
|
|
@@ -0,0 +1,10 @@
|
|
|
1
|
+
import { baseProvider } from "./BaseProvider.js";
|
|
2
|
+
export declare class ClickpesaProvider extends baseProvider {
|
|
3
|
+
constructor(config: any);
|
|
4
|
+
authenticate(): Promise<string>;
|
|
5
|
+
initiateUssdPushRequest(payload: any): Promise<any>;
|
|
6
|
+
checkPaymentStatus(params: {
|
|
7
|
+
transactionId: string;
|
|
8
|
+
}): Promise<any>;
|
|
9
|
+
}
|
|
10
|
+
//# sourceMappingURL=ClickpesaProvider.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"ClickpesaProvider.d.ts","sourceRoot":"","sources":["../../src/providers/ClickpesaProvider.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,YAAY,EAAE,MAAM,mBAAmB,CAAC;AAMjD,qBAAa,iBAAkB,SAAQ,YAAY;gBACrC,MAAM,EAAE,GAAG;IAIjB,YAAY,IAAI,OAAO,CAAC,MAAM,CAAC;IAkB/B,uBAAuB,CAAC,OAAO,EAAE,GAAG,GAAG,OAAO,CAAC,GAAG,CAAC;IAoBnD,kBAAkB,CAAC,MAAM,EAAE;QAAE,aAAa,EAAE,MAAM,CAAA;KAAE,GAAG,OAAO,CAAC,GAAG,CAAC;CAkB1E"}
|
|
@@ -0,0 +1,99 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
var __createBinding = (this && this.__createBinding) || (Object.create ? (function(o, m, k, k2) {
|
|
3
|
+
if (k2 === undefined) k2 = k;
|
|
4
|
+
var desc = Object.getOwnPropertyDescriptor(m, k);
|
|
5
|
+
if (!desc || ("get" in desc ? !m.__esModule : desc.writable || desc.configurable)) {
|
|
6
|
+
desc = { enumerable: true, get: function() { return m[k]; } };
|
|
7
|
+
}
|
|
8
|
+
Object.defineProperty(o, k2, desc);
|
|
9
|
+
}) : (function(o, m, k, k2) {
|
|
10
|
+
if (k2 === undefined) k2 = k;
|
|
11
|
+
o[k2] = m[k];
|
|
12
|
+
}));
|
|
13
|
+
var __setModuleDefault = (this && this.__setModuleDefault) || (Object.create ? (function(o, v) {
|
|
14
|
+
Object.defineProperty(o, "default", { enumerable: true, value: v });
|
|
15
|
+
}) : function(o, v) {
|
|
16
|
+
o["default"] = v;
|
|
17
|
+
});
|
|
18
|
+
var __importStar = (this && this.__importStar) || (function () {
|
|
19
|
+
var ownKeys = function(o) {
|
|
20
|
+
ownKeys = Object.getOwnPropertyNames || function (o) {
|
|
21
|
+
var ar = [];
|
|
22
|
+
for (var k in o) if (Object.prototype.hasOwnProperty.call(o, k)) ar[ar.length] = k;
|
|
23
|
+
return ar;
|
|
24
|
+
};
|
|
25
|
+
return ownKeys(o);
|
|
26
|
+
};
|
|
27
|
+
return function (mod) {
|
|
28
|
+
if (mod && mod.__esModule) return mod;
|
|
29
|
+
var result = {};
|
|
30
|
+
if (mod != null) for (var k = ownKeys(mod), i = 0; i < k.length; i++) if (k[i] !== "default") __createBinding(result, mod, k[i]);
|
|
31
|
+
__setModuleDefault(result, mod);
|
|
32
|
+
return result;
|
|
33
|
+
};
|
|
34
|
+
})();
|
|
35
|
+
var __importDefault = (this && this.__importDefault) || function (mod) {
|
|
36
|
+
return (mod && mod.__esModule) ? mod : { "default": mod };
|
|
37
|
+
};
|
|
38
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
39
|
+
exports.ClickpesaProvider = void 0;
|
|
40
|
+
const BaseProvider_js_1 = require("./BaseProvider.js");
|
|
41
|
+
const axios_1 = __importDefault(require("axios"));
|
|
42
|
+
const dotenv = __importStar(require("dotenv"));
|
|
43
|
+
dotenv.config();
|
|
44
|
+
class ClickpesaProvider extends BaseProvider_js_1.baseProvider {
|
|
45
|
+
constructor(config) {
|
|
46
|
+
super(config);
|
|
47
|
+
}
|
|
48
|
+
async authenticate() {
|
|
49
|
+
try {
|
|
50
|
+
const response = await axios_1.default.post(`${this.config.baseUrl}/third-parties/generate-token`, {
|
|
51
|
+
headers: {
|
|
52
|
+
'client-id': this.config.CLICKPESA_CLIENT_ID,
|
|
53
|
+
'api-key': this.config.CLICKPESA_API_KEY,
|
|
54
|
+
"Content-Type": "application/json",
|
|
55
|
+
},
|
|
56
|
+
});
|
|
57
|
+
return response.data?.token || response.data;
|
|
58
|
+
}
|
|
59
|
+
catch (error) {
|
|
60
|
+
throw new Error(`Authentication failed: ${error}`);
|
|
61
|
+
}
|
|
62
|
+
}
|
|
63
|
+
async initiateUssdPushRequest(payload) {
|
|
64
|
+
try {
|
|
65
|
+
const token = await this.authenticate();
|
|
66
|
+
const response = await axios_1.default.post(`${this.config.baseUrl}/third-parties/payments/initiate-ussd-push-request`, // Added /third-parties/
|
|
67
|
+
payload, {
|
|
68
|
+
headers: {
|
|
69
|
+
"Content-Type": "application/json",
|
|
70
|
+
"Authorization": token,
|
|
71
|
+
},
|
|
72
|
+
});
|
|
73
|
+
return response.data;
|
|
74
|
+
}
|
|
75
|
+
catch (error) {
|
|
76
|
+
console.error('USSD Push Error:', error.response?.data || error.message);
|
|
77
|
+
throw new Error(`Payment request failed: ${error.response?.data?.message || error.message}`);
|
|
78
|
+
}
|
|
79
|
+
}
|
|
80
|
+
async checkPaymentStatus(params) {
|
|
81
|
+
try {
|
|
82
|
+
const token = await this.authenticate();
|
|
83
|
+
const response = await axios_1.default.get(`${this.config.baseUrl}/third-parties/payments/${params.transactionId}`, // Added /third-parties/
|
|
84
|
+
{
|
|
85
|
+
headers: {
|
|
86
|
+
'Accept': 'application/json',
|
|
87
|
+
'Content-Type': 'application/json',
|
|
88
|
+
'Authorization': token,
|
|
89
|
+
}
|
|
90
|
+
});
|
|
91
|
+
return response.data;
|
|
92
|
+
}
|
|
93
|
+
catch (error) {
|
|
94
|
+
throw new Error(`Payment status check failed: ${error}`);
|
|
95
|
+
}
|
|
96
|
+
}
|
|
97
|
+
}
|
|
98
|
+
exports.ClickpesaProvider = ClickpesaProvider;
|
|
99
|
+
//# sourceMappingURL=ClickpesaProvider.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"ClickpesaProvider.js","sourceRoot":"","sources":["../../src/providers/ClickpesaProvider.ts"],"names":[],"mappings":";;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;AAAA,uDAAiD;AACjD,kDAA0B;AAC1B,+CAAiC;AAEjC,MAAM,CAAC,MAAM,EAAE,CAAC;AAEhB,MAAa,iBAAkB,SAAQ,8BAAY;IACjD,YAAY,MAAW;QACrB,KAAK,CAAC,MAAM,CAAC,CAAC;IAChB,CAAC;IAED,KAAK,CAAC,YAAY;QAChB,IAAI,CAAC;YACH,MAAM,QAAQ,GAAG,MAAM,eAAK,CAAC,IAAI,CAC/B,GAAG,IAAI,CAAC,MAAM,CAAC,OAAO,+BAA+B,EACrD;gBACE,OAAO,EAAE;oBACP,WAAW,EAAE,IAAI,CAAC,MAAM,CAAC,mBAAmB;oBAC5C,SAAS,EAAE,IAAI,CAAC,MAAM,CAAC,iBAAiB;oBACxC,cAAc,EAAE,kBAAkB;iBACnC;aACF,CACF,CAAC;YACF,OAAO,QAAQ,CAAC,IAAI,EAAE,KAAK,IAAI,QAAQ,CAAC,IAAI,CAAC;QAC/C,CAAC;QAAC,OAAO,KAAK,EAAE,CAAC;YACf,MAAM,IAAI,KAAK,CAAC,0BAA0B,KAAK,EAAE,CAAC,CAAC;QACrD,CAAC;IACH,CAAC;IAED,KAAK,CAAC,uBAAuB,CAAC,OAAY;QACxC,IAAI,CAAC;YACH,MAAM,KAAK,GAAG,MAAM,IAAI,CAAC,YAAY,EAAE,CAAC;YACxC,MAAM,QAAQ,GAAG,MAAM,eAAK,CAAC,IAAI,CAC/B,GAAG,IAAI,CAAC,MAAM,CAAC,OAAO,oDAAoD,EAAE,wBAAwB;YACpG,OAAO,EACP;gBACE,OAAO,EAAE;oBACP,cAAc,EAAE,kBAAkB;oBAClC,eAAe,EAAE,KAAK;iBACvB;aACF,CACF,CAAC;YACF,OAAO,QAAQ,CAAC,IAAI,CAAC;QACvB,CAAC;QAAC,OAAO,KAAU,EAAE,CAAC;YACpB,OAAO,CAAC,KAAK,CAAC,kBAAkB,EAAE,KAAK,CAAC,QAAQ,EAAE,IAAI,IAAI,KAAK,CAAC,OAAO,CAAC,CAAC;YACzE,MAAM,IAAI,KAAK,CAAC,2BAA2B,KAAK,CAAC,QAAQ,EAAE,IAAI,EAAE,OAAO,IAAI,KAAK,CAAC,OAAO,EAAE,CAAC,CAAC;QAC/F,CAAC;IACH,CAAC;IAED,KAAK,CAAC,kBAAkB,CAAC,MAAiC;QACxD,IAAI,CAAC;YACH,MAAM,KAAK,GAAG,MAAM,IAAI,CAAC,YAAY,EAAE,CAAC;YACxC,MAAM,QAAQ,GAAG,MAAM,eAAK,CAAC,GAAG,CAC9B,GAAG,IAAI,CAAC,MAAM,CAAC,OAAO,2BAA2B,MAAM,CAAC,aAAa,EAAE,EAAE,wBAAwB;YACjG;gBACE,OAAO,EAAE;oBACP,QAAQ,EAAE,kBAAkB;oBAC5B,cAAc,EAAE,kBAAkB;oBAClC,eAAe,EAAE,KAAK;iBACvB;aACF,CACF,CAAC;YACF,OAAO,QAAQ,CAAC,IAAI,CAAC;QACvB,CAAC;QAAC,OAAO,KAAK,EAAE,CAAC;YACf,MAAM,IAAI,KAAK,CAAC,gCAAgC,KAAK,EAAE,CAAC,CAAC;QAC3D,CAAC;IACH,CAAC;CACF;AA7DD,8CA6DC"}
|
|
@@ -0,0 +1,14 @@
|
|
|
1
|
+
import { baseProvider } from './BaseProvider.js';
|
|
2
|
+
export declare class PesapalProvider extends baseProvider {
|
|
3
|
+
constructor(config: any);
|
|
4
|
+
authenticate(): Promise<string>;
|
|
5
|
+
registerIpn(ipnUrl: string, ipnNotificationType: "GET" | "POST"): Promise<any>;
|
|
6
|
+
initiateUssdPushRequest({ payload, ipnId }: {
|
|
7
|
+
payload: any;
|
|
8
|
+
ipnId?: string;
|
|
9
|
+
}): Promise<any>;
|
|
10
|
+
checkPaymentStatus(params: {
|
|
11
|
+
transactionId: string;
|
|
12
|
+
}): Promise<any>;
|
|
13
|
+
}
|
|
14
|
+
//# sourceMappingURL=PesapalProvider.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"PesapalProvider.d.ts","sourceRoot":"","sources":["../../src/providers/PesapalProvider.ts"],"names":[],"mappings":"AAAA,OAAO,EAAC,YAAY,EAAC,MAAM,mBAAmB,CAAC;AAG/C,qBAAa,eAAgB,SAAQ,YAAY;gBACjC,MAAM,EAAE,GAAG;IAIjB,YAAY,IAAI,OAAO,CAAC,MAAM,CAAC;IAqBnC,WAAW,CAAC,MAAM,EAAE,MAAM,EAAE,mBAAmB,EAAE,KAAK,GAAG,MAAM,GAAG,OAAO,CAAC,GAAG,CAAC;IAwB1E,uBAAuB,CAAC,EAAE,OAAO,EAAE,KAAK,EAAE,EAAE;QAAE,OAAO,EAAE,GAAG,CAAC;QAAC,KAAK,CAAC,EAAE,MAAM,CAAA;KAAE,GAAG,OAAO,CAAC,GAAG,CAAC;IAwB3F,kBAAkB,CAAC,MAAM,EAAC;QAAC,aAAa,EAAC,MAAM,CAAA;KAAC,GAAG,OAAO,CAAC,GAAG,CAAC;CAmBxE"}
|
|
@@ -0,0 +1,88 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
var __importDefault = (this && this.__importDefault) || function (mod) {
|
|
3
|
+
return (mod && mod.__esModule) ? mod : { "default": mod };
|
|
4
|
+
};
|
|
5
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
6
|
+
exports.PesapalProvider = void 0;
|
|
7
|
+
const BaseProvider_js_1 = require("./BaseProvider.js");
|
|
8
|
+
const axios_1 = __importDefault(require("axios"));
|
|
9
|
+
class PesapalProvider extends BaseProvider_js_1.baseProvider {
|
|
10
|
+
constructor(config) {
|
|
11
|
+
super(config);
|
|
12
|
+
}
|
|
13
|
+
async authenticate() {
|
|
14
|
+
try {
|
|
15
|
+
const response = await axios_1.default.post(`${this.config.baseUrl}/api/Auth/RequestToken`, {
|
|
16
|
+
consumer_key: this.config.PESAPAL_CONSUMER_KEY,
|
|
17
|
+
consumer_secret: this.config.PESAPAL_CONSUMER_SECRET,
|
|
18
|
+
}, {
|
|
19
|
+
headers: {
|
|
20
|
+
'Accept': 'application/json',
|
|
21
|
+
'Content-Type': 'application/json',
|
|
22
|
+
}
|
|
23
|
+
});
|
|
24
|
+
return response.data.token;
|
|
25
|
+
}
|
|
26
|
+
catch (error) {
|
|
27
|
+
throw new Error(`Authentication failed: ${error}`);
|
|
28
|
+
}
|
|
29
|
+
}
|
|
30
|
+
async registerIpn(ipnUrl, ipnNotificationType) {
|
|
31
|
+
try {
|
|
32
|
+
const token = await this.authenticate();
|
|
33
|
+
const response = await axios_1.default.post(`${this.config.baseUrl}/api/URLSetup/RegisterIPN`, // sandbox path
|
|
34
|
+
{
|
|
35
|
+
url: ipnUrl,
|
|
36
|
+
ipn_notification_type: ipnNotificationType
|
|
37
|
+
}, {
|
|
38
|
+
headers: {
|
|
39
|
+
'Accept': 'application/json',
|
|
40
|
+
'Content-Type': 'application/json',
|
|
41
|
+
'Authorization': `Bearer ${token}`,
|
|
42
|
+
}
|
|
43
|
+
});
|
|
44
|
+
return response.data.ipn_id;
|
|
45
|
+
}
|
|
46
|
+
catch (error) {
|
|
47
|
+
throw new Error(`IPN registration failed: ${error}`);
|
|
48
|
+
}
|
|
49
|
+
}
|
|
50
|
+
async initiateUssdPushRequest({ payload, ipnId }) {
|
|
51
|
+
try {
|
|
52
|
+
const token = await this.authenticate();
|
|
53
|
+
const finalPayload = {
|
|
54
|
+
...payload,
|
|
55
|
+
notification_id: ipnId
|
|
56
|
+
};
|
|
57
|
+
const response = await axios_1.default.post(`${this.config.baseUrl}/api/Transactions/SubmitOrderRequest`, finalPayload, {
|
|
58
|
+
headers: {
|
|
59
|
+
'Accept': 'application/json',
|
|
60
|
+
'Content-Type': 'application/json',
|
|
61
|
+
'Authorization': `Bearer ${token}`,
|
|
62
|
+
}
|
|
63
|
+
});
|
|
64
|
+
return response.data;
|
|
65
|
+
}
|
|
66
|
+
catch (error) {
|
|
67
|
+
throw new Error(`Payment request failed: ${error}`);
|
|
68
|
+
}
|
|
69
|
+
}
|
|
70
|
+
async checkPaymentStatus(params) {
|
|
71
|
+
try {
|
|
72
|
+
const token = await this.authenticate();
|
|
73
|
+
const response = await axios_1.default.get(`${this.config.baseUrl}/api/Transactions/GetTransactionStatus?orderTrackingId=${params.transactionId}`, {
|
|
74
|
+
headers: {
|
|
75
|
+
'Accept': 'application/json',
|
|
76
|
+
'Content-Type': 'application/json',
|
|
77
|
+
'Authorization': `Bearer ${token}`,
|
|
78
|
+
}
|
|
79
|
+
});
|
|
80
|
+
return response.data;
|
|
81
|
+
}
|
|
82
|
+
catch (error) {
|
|
83
|
+
throw new Error(`Payment status check failed: ${error}`);
|
|
84
|
+
}
|
|
85
|
+
}
|
|
86
|
+
}
|
|
87
|
+
exports.PesapalProvider = PesapalProvider;
|
|
88
|
+
//# sourceMappingURL=PesapalProvider.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"PesapalProvider.js","sourceRoot":"","sources":["../../src/providers/PesapalProvider.ts"],"names":[],"mappings":"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"}
|
package/package.json
ADDED
|
@@ -0,0 +1,73 @@
|
|
|
1
|
+
{
|
|
2
|
+
"name": "finconnect",
|
|
3
|
+
"version": "1.0.0",
|
|
4
|
+
"description": "A lightweight, provider-agnostic integration wrapper for East African Fintech APIs.",
|
|
5
|
+
"homepage": "https://github.com/somebody1011/finconnect#readme",
|
|
6
|
+
"bugs": {
|
|
7
|
+
"url": "https://github.com/somebody1011/finconnect/issues"
|
|
8
|
+
},
|
|
9
|
+
"repository": {
|
|
10
|
+
"type": "git",
|
|
11
|
+
"url": "git+https://github.com/somebody1011/finconnect.git"
|
|
12
|
+
},
|
|
13
|
+
"license": "MIT",
|
|
14
|
+
"author": "elisha gerson",
|
|
15
|
+
"type": "commonjs",
|
|
16
|
+
"main": "dist/index.js",
|
|
17
|
+
"types": "dist/index.d.ts",
|
|
18
|
+
"exports": {
|
|
19
|
+
".": {
|
|
20
|
+
"types": "./dist/index.d.ts",
|
|
21
|
+
"require": "./dist/index.js",
|
|
22
|
+
"default": "./dist/index.js"
|
|
23
|
+
}
|
|
24
|
+
},
|
|
25
|
+
"files": [
|
|
26
|
+
"dist",
|
|
27
|
+
"README.md",
|
|
28
|
+
"LICENSE"
|
|
29
|
+
],
|
|
30
|
+
"directories": {
|
|
31
|
+
"example": "examples",
|
|
32
|
+
"test": "test"
|
|
33
|
+
},
|
|
34
|
+
"keywords": [
|
|
35
|
+
"fintech",
|
|
36
|
+
"payments",
|
|
37
|
+
"azampay",
|
|
38
|
+
"pesapal",
|
|
39
|
+
"clickpesa",
|
|
40
|
+
"typescript",
|
|
41
|
+
"node"
|
|
42
|
+
],
|
|
43
|
+
"engines": {
|
|
44
|
+
"node": ">=16"
|
|
45
|
+
},
|
|
46
|
+
"scripts": {
|
|
47
|
+
"build": "tsc",
|
|
48
|
+
"test": "jest --runInBand",
|
|
49
|
+
"dev": "ts-node scripts/server.ts",
|
|
50
|
+
"dev-tool": "tsx scripts/dev-tool.ts",
|
|
51
|
+
"provider-test": "tsx src/providers/ClickpesaProvider.ts",
|
|
52
|
+
"prepublishOnly": "npm run build && npm test"
|
|
53
|
+
},
|
|
54
|
+
"dependencies": {
|
|
55
|
+
"axios": "^1.15.2",
|
|
56
|
+
"dotenv": "^17.4.2",
|
|
57
|
+
"express": "^5.2.1"
|
|
58
|
+
},
|
|
59
|
+
"devDependencies": {
|
|
60
|
+
"@types/express": "^5.0.6",
|
|
61
|
+
"@types/jest": "^30.0.0",
|
|
62
|
+
"@types/node": "^25.6.0",
|
|
63
|
+
"axios-mock-adapter": "^2.1.0",
|
|
64
|
+
"jest": "^30.3.0",
|
|
65
|
+
"ts-jest": "^29.4.9",
|
|
66
|
+
"ts-node": "^10.9.2",
|
|
67
|
+
"tsx": "^4.21.0",
|
|
68
|
+
"typescript": "^6.0.3"
|
|
69
|
+
},
|
|
70
|
+
"publishConfig": {
|
|
71
|
+
"access": "public"
|
|
72
|
+
}
|
|
73
|
+
}
|