investec_open_api 1.1.0 → 2.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 CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: 77c64b266bba27ab306dea5d458ad2d712bad628a7969e633ba2443267c9e893
4
- data.tar.gz: a74ccee5e67cfc5d0255eb2a9acd4d80e7f62d6c3615b4f20aaca4480c2fbda6
3
+ metadata.gz: d63aea6ee443ea35ef173be3a2de9f21c36ccf03bf9545249700a443d274360e
4
+ data.tar.gz: 176d7edd574dcdc1be3a54a7cce109c861d3bdeba7b32f6c3a769e40fdffea93
5
5
  SHA512:
6
- metadata.gz: ac96b83766d92429bac7f6976566ea73e83b5c057ac1c9426ce511d630f7924c33690a6379bbb352bcaecaf264beeafc0395e57178a3018604be183a656add2a
7
- data.tar.gz: 4bbe8c37fc10868da9dd940c9fc3570069a07f25d8f5238da9d0767ed35eb21da7604a32945b0a7a26bbae16616368dccf2748e29da55706586766d601413451
6
+ metadata.gz: 071f395d389f11333db5b5a36048ad9f0b66ff688fbfb35bccb83296b49491279a1b83f458507dd4e83426ffa39fd96d720ef000d0753595cc849e9901749d53
7
+ data.tar.gz: 54d8986eccc4461d9b59c4f16b894e0274d660be311b6862cb1734010be7a7e386e496a36a7eb0f07621ab2cbf1785374fed3328a4fecfb210c52e40ec85437c
@@ -0,0 +1,30 @@
1
+ name: CI
2
+ on:
3
+ push:
4
+ branches:
5
+ - master
6
+
7
+ pull_request:
8
+ branches:
9
+ - master
10
+
11
+ jobs:
12
+ build:
13
+ runs-on: ubuntu-latest
14
+ name: Run Specs
15
+
16
+ steps:
17
+ - uses: actions/checkout@v2
18
+ - uses: ruby/setup-ruby@v1
19
+ with:
20
+ ruby-version: 3.1.1
21
+
22
+ - name: Run bundle install
23
+ run: |
24
+ gem install bundler
25
+ bundle install --jobs 4 --retry 3
26
+
27
+ - name: Build and test with rspec
28
+ env:
29
+ RAILS_ENV: test
30
+ run: bundle exec rspec spec
data/.gitignore CHANGED
@@ -6,6 +6,8 @@
6
6
  /pkg/
7
7
  /spec/reports/
8
8
  /tmp/
9
+ /.idea/
9
10
 
10
11
  # rspec failure tracking
11
12
  .rspec_status
13
+ .env
data/CODE_OF_CONDUCT.md CHANGED
@@ -55,7 +55,7 @@ further defined and clarified by project maintainers.
55
55
  ## Enforcement
56
56
 
57
57
  Instances of abusive, harassing, or otherwise unacceptable behavior may be
58
- reported by contacting the project team at mkk0856@gmail.com. All
58
+ reported by contacting the project team at community@make.dev. All
59
59
  complaints will be reviewed and investigated and will result in a response that
60
60
  is deemed necessary and appropriate to the circumstances. The project team is
61
61
  obligated to maintain confidentiality with regard to the reporter of an incident.
data/Gemfile CHANGED
@@ -2,3 +2,7 @@ source "https://rubygems.org"
2
2
 
3
3
  # Specify your gem's dependencies in investec_open_api.gemspec
4
4
  gemspec
5
+
6
+ gem 'pry'
7
+
8
+ gem "faker", "~> 3.4"
data/Gemfile.lock CHANGED
@@ -1,125 +1,68 @@
1
1
  PATH
2
2
  remote: .
3
3
  specs:
4
- investec_open_api (1.1.0)
5
- active_attr
4
+ investec_open_api (2.0.0)
6
5
  faraday
7
- faraday_middleware
8
6
  money
9
7
 
10
8
  GEM
11
9
  remote: https://rubygems.org/
12
10
  specs:
13
- actionpack (7.0.4.3)
14
- actionview (= 7.0.4.3)
15
- activesupport (= 7.0.4.3)
16
- rack (~> 2.0, >= 2.2.0)
17
- rack-test (>= 0.6.3)
18
- rails-dom-testing (~> 2.0)
19
- rails-html-sanitizer (~> 1.0, >= 1.2.0)
20
- actionview (7.0.4.3)
21
- activesupport (= 7.0.4.3)
22
- builder (~> 3.1)
23
- erubi (~> 1.4)
24
- rails-dom-testing (~> 2.0)
25
- rails-html-sanitizer (~> 1.1, >= 1.2.0)
26
- active_attr (0.15.4)
27
- actionpack (>= 3.0.2, < 7.1)
28
- activemodel (>= 3.0.2, < 7.1)
29
- activesupport (>= 3.0.2, < 7.1)
30
- activemodel (7.0.4.3)
31
- activesupport (= 7.0.4.3)
32
- activesupport (7.0.4.3)
33
- concurrent-ruby (~> 1.0, >= 1.0.2)
34
- i18n (>= 1.6, < 2)
35
- minitest (>= 5.1)
36
- tzinfo (~> 2.0)
37
- addressable (2.8.4)
11
+ addressable (2.8.6)
38
12
  public_suffix (>= 2.0.2, < 6.0)
39
- builder (3.2.4)
40
- concurrent-ruby (1.2.2)
41
- crack (0.4.5)
13
+ bigdecimal (3.1.7)
14
+ coderay (1.1.3)
15
+ concurrent-ruby (1.2.3)
16
+ crack (1.0.0)
17
+ bigdecimal
42
18
  rexml
43
- crass (1.0.6)
44
- diff-lcs (1.4.4)
45
- erubi (1.12.0)
46
- faraday (1.10.3)
47
- faraday-em_http (~> 1.0)
48
- faraday-em_synchrony (~> 1.0)
49
- faraday-excon (~> 1.1)
50
- faraday-httpclient (~> 1.0)
51
- faraday-multipart (~> 1.0)
52
- faraday-net_http (~> 1.0)
53
- faraday-net_http_persistent (~> 1.0)
54
- faraday-patron (~> 1.0)
55
- faraday-rack (~> 1.0)
56
- faraday-retry (~> 1.0)
57
- ruby2_keywords (>= 0.0.4)
58
- faraday-em_http (1.0.0)
59
- faraday-em_synchrony (1.0.0)
60
- faraday-excon (1.1.0)
61
- faraday-httpclient (1.0.1)
62
- faraday-multipart (1.0.4)
63
- multipart-post (~> 2)
64
- faraday-net_http (1.0.1)
65
- faraday-net_http_persistent (1.2.0)
66
- faraday-patron (1.0.0)
67
- faraday-rack (1.0.0)
68
- faraday-retry (1.0.3)
69
- faraday_middleware (1.2.0)
70
- faraday (~> 1.0)
71
- hashdiff (1.0.1)
72
- i18n (1.13.0)
19
+ diff-lcs (1.5.1)
20
+ faker (3.4.2)
21
+ i18n (>= 1.8.11, < 2)
22
+ faraday (2.9.0)
23
+ faraday-net_http (>= 2.0, < 3.2)
24
+ faraday-net_http (3.1.0)
25
+ net-http
26
+ hashdiff (1.1.0)
27
+ i18n (1.14.4)
73
28
  concurrent-ruby (~> 1.0)
74
- loofah (2.20.0)
75
- crass (~> 1.0.2)
76
- nokogiri (>= 1.5.9)
77
- mini_portile2 (2.8.2)
78
- minitest (5.18.0)
79
- money (6.16.0)
29
+ method_source (1.0.0)
30
+ money (6.19.0)
80
31
  i18n (>= 0.6.4, <= 2)
81
- multipart-post (2.3.0)
82
- nokogiri (1.14.3)
83
- mini_portile2 (~> 2.8.0)
84
- racc (~> 1.4)
85
- public_suffix (5.0.1)
86
- racc (1.6.2)
87
- rack (2.2.7)
88
- rack-test (2.1.0)
89
- rack (>= 1.3)
90
- rails-dom-testing (2.0.3)
91
- activesupport (>= 4.2.0)
92
- nokogiri (>= 1.6)
93
- rails-html-sanitizer (1.5.0)
94
- loofah (~> 2.19, >= 2.19.1)
95
- rake (12.3.3)
96
- rexml (3.2.5)
97
- rspec (3.9.0)
98
- rspec-core (~> 3.9.0)
99
- rspec-expectations (~> 3.9.0)
100
- rspec-mocks (~> 3.9.0)
101
- rspec-core (3.9.2)
102
- rspec-support (~> 3.9.3)
103
- rspec-expectations (3.9.2)
32
+ net-http (0.4.1)
33
+ uri
34
+ pry (0.14.2)
35
+ coderay (~> 1.1)
36
+ method_source (~> 1.0)
37
+ public_suffix (5.0.5)
38
+ rake (13.2.1)
39
+ rexml (3.2.6)
40
+ rspec (3.13.0)
41
+ rspec-core (~> 3.13.0)
42
+ rspec-expectations (~> 3.13.0)
43
+ rspec-mocks (~> 3.13.0)
44
+ rspec-core (3.13.0)
45
+ rspec-support (~> 3.13.0)
46
+ rspec-expectations (3.13.0)
104
47
  diff-lcs (>= 1.2.0, < 2.0)
105
- rspec-support (~> 3.9.0)
106
- rspec-mocks (3.9.1)
48
+ rspec-support (~> 3.13.0)
49
+ rspec-mocks (3.13.0)
107
50
  diff-lcs (>= 1.2.0, < 2.0)
108
- rspec-support (~> 3.9.0)
109
- rspec-support (3.9.3)
110
- ruby2_keywords (0.0.5)
111
- tzinfo (2.0.6)
112
- concurrent-ruby (~> 1.0)
113
- webmock (3.18.1)
51
+ rspec-support (~> 3.13.0)
52
+ rspec-support (3.13.1)
53
+ uri (0.13.0)
54
+ webmock (3.23.0)
114
55
  addressable (>= 2.8.0)
115
56
  crack (>= 0.3.2)
116
57
  hashdiff (>= 0.4.0, < 2.0.0)
117
58
 
118
59
  PLATFORMS
119
- ruby
60
+ arm64-darwin-23
120
61
 
121
62
  DEPENDENCIES
63
+ faker (~> 3.4)
122
64
  investec_open_api!
65
+ pry
123
66
  rake
124
67
  rspec
125
68
  webmock
data/README.md CHANGED
@@ -1,3 +1,7 @@
1
+ ## 🌟 Community-Powered Repository 🌟
2
+
3
+ This repository is crafted with ❤️ by our talented community members. It's a space for everyone to use, contribute to, and share. While it aligns with the spirit of our community, please note that this repo is not directly endorsed or supported by Investec. Always exercise caution and discretion when using or contributing to community-driven projects.
4
+
1
5
  # InvestecOpenApi Client
2
6
 
3
7
  [![Gem Version](https://badge.fury.io/rb/investec_open_api.svg)](https://badge.fury.io/rb/investec_open_api)
@@ -9,6 +13,8 @@ A simple client wrapper for the [Investec Open API](https://developer.investec.c
9
13
  - Authorize access via OAuth
10
14
  - Retrieve accounts
11
15
  - Retrieve transactions per account
16
+ - Retrieve balances per account
17
+ - Transfer between accounts
12
18
 
13
19
  ## Installation
14
20
 
@@ -30,26 +36,32 @@ Or install it yourself as:
30
36
  $ gem install investec_open_api
31
37
  ```
32
38
 
33
- Create a new initializer called `investec_open_api.rb` in `config/initializers`:
39
+ ## Configuration
40
+
41
+ To configure the client, create a new file in the root of your directory called `.env` and place the following:
42
+
43
+ ```dotenv
44
+ API_KEY='YOUR API KEY'
45
+ CLIENT_ID='YOUR CLIENT ID'
46
+ CLIENT_SECRET='YOUR CLIENT SECRET'
47
+ ```
48
+
49
+ > **Note:** you will need to register to get the above credentials.
50
+ > Follow the steps in [Enrolment in the documentation](https://developer.investec.com/programmable-banking/#enrolment).
51
+ > You can also test in sandbox mode (see [Running in Sandbox Mode](#running-in-sandbox-mode)).
52
+
53
+ Once you have set this up, configure the client using:
34
54
 
35
55
  ```ruby
36
56
  InvestecOpenApi.configuration do |config|
37
57
  config.api_key = ENV['API_KEY']
38
58
  config.client_id = ENV['CLIENT_ID']
39
59
  config.client_secret = ENV['CLIENT_SECRET']
60
+ config.base_url = ENV['BASE_URL'] # optional
40
61
  end
41
62
  ```
42
63
 
43
- Create a new file in the root of your directory called `.env` and place the following:
44
-
45
- ```
46
- API_KEY='YOUR API KEY'
47
- CLIENT_ID='YOUR CLIENT ID'
48
- CLIENT_SECRET='YOUR CLIENT SECRET'
49
- ```
50
-
51
- You will need to register to get the following credentials. Follow the steps in [Enrolment in the documentation](https://developer.investec.com/programmable-banking/#enrolment).
52
-
64
+ For Rails apps, create a new initializer called `investec_open_api.rb` in `config/initializers`:
53
65
 
54
66
  ## Usage
55
67
 
@@ -60,19 +72,64 @@ client = InvestecOpenApi::Client.new
60
72
  client.authenticate!
61
73
  ```
62
74
 
63
- Once authenticated you can retrieve your accounts:
75
+ ### Accounts
76
+
77
+ Calling `accounts` returns all of the associated accounts:
64
78
 
65
79
  ```ruby
66
80
  accounts = client.accounts
67
81
  my_account = accounts.first
68
82
  ```
69
83
 
70
- Use the ID of one of your accounts to retrieve transactions:
84
+ ### List transactions for an account
85
+
86
+ You can list your transactions by passing the account id into the `transactions` method:
71
87
 
72
88
  ```ruby
73
89
  client.transactions(my_account.id)
74
90
  ```
75
91
 
92
+ ### Get Balance for an account
93
+
94
+ Pass the `account_id` into the `balance` method to get the latest account balances:
95
+
96
+ ```ruby
97
+ client.balance(my_account.id)
98
+ ```
99
+
100
+ ### Inter-account transfers
101
+
102
+ To transfer between accounts, create a `InvestecOpenApi::Models::Transfer` object and pass it into the `transfer_multiple` method:
103
+
104
+ ```ruby
105
+ transfer = InvestecOpenApi::Models::Transfer.new(
106
+ beneficiary_account_id,
107
+ 1000.00, # amount as a Float
108
+ "My reference - of the account transferring from",
109
+ "Their reference - of the account transferring to"
110
+ )
111
+ client.transfer_multiple(
112
+ my_account.id,
113
+ [ transfer ],
114
+ profile_id # optional
115
+ )
116
+ ```
117
+
118
+ ## Running in Sandbox mode
119
+
120
+ To run in sandbox mode, use the following configuration:
121
+
122
+ ```ruby
123
+ InvestecOpenApi.configuration do |config|
124
+ config.api_key = "eUF4elFSRlg5N3ZPY3lRQXdsdUVVNkg2ZVB4TUE1ZVk6YVc1MlpYTjBaV010ZW1FdGNHSXRZV05qYjNWdWRITXRjMkZ1WkdKdmVBPT0="
125
+ config.client_id = "yAxzQRFX97vOcyQAwluEU6H6ePxMA5eY"
126
+ config.client_secret = "4dY0PjEYqoBrZ99r"
127
+ config.base_url = "https://openapisandbox.investec.com/"
128
+ end
129
+ ```
130
+
131
+ You can now test the API without affecting your actual account.
132
+
76
133
  ## License
77
134
 
78
135
  The gem is available as open source under the terms of the [MIT License](https://opensource.org/licenses/MIT).
data/bin/console CHANGED
@@ -7,8 +7,8 @@ require "investec_open_api"
7
7
  # with your gem easier. You can also use a different console, if you like.
8
8
 
9
9
  # (If you use this, don't forget to add pry to your Gemfile!)
10
- # require "pry"
11
- # Pry.start
10
+ require "pry"
11
+ Pry.start
12
12
 
13
- require "irb"
14
- IRB.start(__FILE__)
13
+ # require "irb"
14
+ # IRB.start(__FILE__)
data/bin/sandbox ADDED
@@ -0,0 +1,21 @@
1
+ #!/usr/bin/env ruby
2
+
3
+ require "bundler/setup"
4
+ require "investec_open_api"
5
+
6
+ # You can add fixtures and/or initialization code here to make experimenting
7
+ # with your gem easier. You can also use a different console, if you like.
8
+
9
+ InvestecOpenApi.configuration do |config|
10
+ config.api_key = "eUF4elFSRlg5N3ZPY3lRQXdsdUVVNkg2ZVB4TUE1ZVk6YVc1MlpYTjBaV010ZW1FdGNHSXRZV05qYjNWdWRITXRjMkZ1WkdKdmVBPT0="
11
+ config.client_id = "yAxzQRFX97vOcyQAwluEU6H6ePxMA5eY"
12
+ config.client_secret = "4dY0PjEYqoBrZ99r"
13
+ config.base_url = "https://openapisandbox.investec.com/"
14
+ end
15
+
16
+ # (If you use this, don't forget to add pry to your Gemfile!)
17
+ require "pry"
18
+ Pry.start
19
+
20
+ # require "irb"
21
+ # IRB.start(__FILE__)
@@ -28,13 +28,12 @@ Gem::Specification.new do |spec|
28
28
  spec.require_paths = ["lib"]
29
29
 
30
30
  # add runtime dependencies
31
- spec.add_runtime_dependency 'active_attr'
32
31
  spec.add_runtime_dependency 'faraday'
33
- spec.add_runtime_dependency 'faraday_middleware'
34
32
  spec.add_runtime_dependency 'money'
35
33
 
36
34
  # add development dependencies
37
35
  spec.add_development_dependency 'rake'
38
36
  spec.add_development_dependency 'rspec'
39
37
  spec.add_development_dependency 'webmock'
38
+ spec.add_development_dependency 'faker'
40
39
  end
@@ -0,0 +1,12 @@
1
+ module InvestecOpenApi
2
+ module CamelCaseRefinement
3
+ refine Hash do
4
+ def camelize
5
+ transform_keys do |key|
6
+ words = key.to_s.split('_')
7
+ words.drop(1).collect(&:capitalize).unshift(words.first).join
8
+ end
9
+ end
10
+ end
11
+ end
12
+ end
@@ -1,10 +1,13 @@
1
1
  require "faraday"
2
- require "faraday_middleware"
3
2
  require "investec_open_api/models/account"
4
3
  require "investec_open_api/models/transaction"
4
+ require "investec_open_api/models/balance"
5
+ require "investec_open_api/models/transfer"
6
+ require "investec_open_api/camel_case_refinement"
7
+ require 'base64'
5
8
 
6
9
  class InvestecOpenApi::Client
7
- INVESTEC_API_URL="https://openapi.investec.com/"
10
+ using InvestecOpenApi::CamelCaseRefinement
8
11
 
9
12
  def authenticate!
10
13
  @token = get_oauth_token["access_token"]
@@ -17,23 +20,56 @@ class InvestecOpenApi::Client
17
20
  end
18
21
  end
19
22
 
20
- def transactions(account_id)
21
- response = connection.get("za/pb/v1/accounts/#{account_id}/transactions")
23
+ def transactions(account_id, options = {})
24
+ endpoint_url = "za/pb/v1/accounts/#{account_id}/transactions"
25
+
26
+ unless options.empty?
27
+ query_string = URI.encode_www_form(options.camelize)
28
+ endpoint_url += "?#{query_string}"
29
+ end
30
+
31
+ response = connection.get(endpoint_url)
22
32
  response.body["data"]["transactions"].map do |transaction_raw|
23
33
  InvestecOpenApi::Models::Transaction.from_api(transaction_raw)
24
34
  end
25
35
  end
26
36
 
37
+ def balance(account_id)
38
+ endpoint_url = "za/pb/v1/accounts/#{account_id}/balance"
39
+ response = connection.get(endpoint_url)
40
+ raise "Error fetching balance" if response.body["data"].nil?
41
+ InvestecOpenApi::Models::Balance.from_api(response.body["data"])
42
+ end
43
+
44
+ # @param [String] account_id
45
+ # @param [Array<InvestecOpenApi::Models::Transfer>] transfers
46
+ def transfer_multiple(
47
+ account_id,
48
+ transfers,
49
+ profile_id = nil
50
+ )
51
+ endpoint_url = "za/pb/v1/accounts/#{account_id}/transfermultiple"
52
+ data = {
53
+ transferList: transfers.map(&:to_h),
54
+ }
55
+ data[:profileId] = profile_id if profile_id
56
+ response = connection.post(
57
+ endpoint_url,
58
+ JSON.generate(data)
59
+ )
60
+ response.body
61
+ end
62
+
27
63
  private
28
64
 
29
65
  def get_oauth_token
30
- auth_token = Base64.strict_encode64("#{InvestecOpenApi.client_id}:#{InvestecOpenApi.client_secret}")
66
+ auth_token = ::Base64.strict_encode64("#{InvestecOpenApi.config.client_id}:#{InvestecOpenApi.config.client_secret}")
31
67
 
32
68
  response = Faraday.post(
33
- "#{INVESTEC_API_URL}identity/v2/oauth2/token",
69
+ "#{InvestecOpenApi.config.base_url}identity/v2/oauth2/token",
34
70
  { grant_type: "client_credentials" },
35
71
  {
36
- 'x-api-key' => InvestecOpenApi.api_key,
72
+ 'x-api-key' => InvestecOpenApi.config.api_key,
37
73
  'Authorization' => "Basic #{auth_token}"
38
74
  }
39
75
  )
@@ -42,7 +78,7 @@ class InvestecOpenApi::Client
42
78
  end
43
79
 
44
80
  def connection
45
- @_connection ||= Faraday.new(url: INVESTEC_API_URL) do |builder|
81
+ @_connection ||= Faraday.new(url: InvestecOpenApi.config.base_url) do |builder|
46
82
  if @token
47
83
  builder.headers["Authorization"] = "Bearer #{@token}"
48
84
  end
@@ -1,25 +1,19 @@
1
1
  module InvestecOpenApi::Models
2
2
  class Account < Base
3
- attribute :id
4
- attribute :number
5
- attribute :name
6
- attribute :reference_name
7
- attribute :product_name
3
+ attr_reader :id,
4
+ :number,
5
+ :name,
6
+ :reference_name,
7
+ :product_name,
8
+ :kyc_compliant,
9
+ :profile_id,
10
+ :profile_name
8
11
 
9
12
  def self.from_api(params = {})
10
- if params['accountId'].present?
11
- params['id'] = params['accountId']
12
- end
13
-
14
- if params['accountNumber'].present?
15
- params['number'] = params['accountNumber']
16
- end
17
-
18
- if params['accountName'].present?
19
- params['name'] = params['accountName']
20
- end
21
-
22
- super
13
+ rewrite_param_key(params, "accountId", "id")
14
+ rewrite_param_key(params, "accountNumber", "number")
15
+ rewrite_param_key(params, "accountName", "name")
16
+ new params
23
17
  end
24
18
  end
25
19
  end
@@ -0,0 +1,25 @@
1
+ # frozen_string_literal: true
2
+
3
+ module InvestecOpenApi::Models
4
+ class Balance < Base
5
+ attr_reader :id,
6
+ :current_balance,
7
+ :available_balance,
8
+ :budget_balance,
9
+ :straight_balance,
10
+ :cash_balance,
11
+ :currency
12
+
13
+ def self.from_api(params = {})
14
+ rewrite_param_key(params, "accountId", "id")
15
+
16
+ convert_param_value_to_money(params, "currentBalance")
17
+ convert_param_value_to_money(params, "availableBalance")
18
+ convert_param_value_to_money(params, "budgetBalance")
19
+ convert_param_value_to_money(params, "straightBalance")
20
+ convert_param_value_to_money(params, "cashBalance")
21
+
22
+ new params
23
+ end
24
+ end
25
+ end
@@ -1,15 +1,37 @@
1
- require "active_attr"
1
+ require_relative "../string_utilities"
2
2
 
3
3
  module InvestecOpenApi::Models
4
+ using InvestecOpenApi::StringUtilities
5
+
4
6
  class Base
5
- include ActiveAttr::Model
7
+ def initialize(params)
8
+ params
9
+ .transform_keys(&:underscore)
10
+ .each { |key, value| instance_variable_set("@#{key}", value) }
11
+ end
6
12
 
7
- def self.from_api(params = {})
8
- underscored_params = params.deep_transform_keys do |key|
9
- key.underscore.to_sym
13
+ def self.rewrite_param_key(params, key, rewritten_key)
14
+ params[rewritten_key] = params[key] unless params[key].nil?
15
+ end
16
+
17
+ def self.convert_param_value_to_money(
18
+ params,
19
+ key,
20
+ currency_key = "currency",
21
+ should_make_negative = false
22
+ )
23
+ if params[key].nil?
24
+ return
10
25
  end
26
+ value_in_cents = params[key] * 100
27
+ value_in_cents = -value_in_cents if should_make_negative
28
+ params[key] = Money.from_cents(
29
+ value_in_cents,
30
+ params[currency_key])
31
+ end
11
32
 
12
- new(underscored_params)
33
+ def self.convert_param_value_to_date(params, key)
34
+ params[key] = Date.parse(params[key]) unless params[key].nil?
13
35
  end
14
36
  end
15
37
  end
@@ -2,39 +2,47 @@ require "money"
2
2
 
3
3
  module InvestecOpenApi::Models
4
4
  class Transaction < Base
5
- attribute :account_id
6
- attribute :type
7
- attribute :status
8
- attribute :card_number
9
- attribute :amount
10
- attribute :description
11
- attribute :date, type: Date
12
- attribute :posting_date, type: Date
13
- attribute :value_date, type: Date
14
- attribute :action_date, type: Date
5
+ attr_reader :id,
6
+ :account_id,
7
+ :posted_order,
8
+ :type,
9
+ :transaction_type,
10
+ :status,
11
+ :card_number,
12
+ :amount,
13
+ :description,
14
+ :running_balance,
15
+ :date,
16
+ :posting_date,
17
+ :value_date,
18
+ :action_date
19
+
20
+ def initialize(params)
21
+ super
22
+ set_id
23
+ end
15
24
 
16
25
  # At this point, there is no unique identifier being returned from Investec's API.
17
26
  # This method serves to create a stable unique identifier based on the transaction details.
18
- def id
19
- [
27
+ def set_id
28
+ @id = [
20
29
  amount.to_i,
21
30
  description,
22
31
  date.to_s
23
32
  ].map(&:to_s).join('-')
24
33
  end
25
34
 
26
- def self.from_api(params)
27
- if params['amount'].present?
28
- adjusted_amount = params['amount'] * 100
29
- adjusted_amount = -adjusted_amount if params['type'] == 'DEBIT'
30
- params['amount'] = Money.new(adjusted_amount, "ZAR")
31
- end
32
-
33
- if params['transactionDate']
34
- params['date'] = params['transactionDate']
35
- end
36
-
37
- super
35
+ def self.from_api(params, currency = "ZAR")
36
+ params["currency"] = currency
37
+ should_make_amount_negative = params['type'] == 'DEBIT'
38
+ convert_param_value_to_money(params, "amount", "currency", should_make_amount_negative)
39
+ convert_param_value_to_money(params, "runningBalance")
40
+ rewrite_param_key(params, "transactionDate", "date")
41
+ convert_param_value_to_date(params, "date")
42
+ convert_param_value_to_date(params, "postingDate")
43
+ convert_param_value_to_date(params, "valueDate")
44
+ convert_param_value_to_date(params, "actionDate")
45
+ new params
38
46
  end
39
47
  end
40
48
  end
@@ -0,0 +1,32 @@
1
+ # frozen_string_literal: true
2
+
3
+ module InvestecOpenApi::Models
4
+ class Transfer
5
+ attr_reader :beneficiary_account_id, :amount, :my_reference, :their_reference
6
+
7
+ # @param [String] beneficiary_account_id
8
+ # @param [Float] amount
9
+ # @param [String] my_reference
10
+ # @param [String] their_reference
11
+ def initialize(
12
+ beneficiary_account_id,
13
+ amount,
14
+ my_reference,
15
+ their_reference
16
+ )
17
+ @beneficiary_account_id = beneficiary_account_id
18
+ @amount = amount.to_s
19
+ @my_reference = my_reference
20
+ @their_reference = their_reference
21
+ end
22
+
23
+ def to_h
24
+ {
25
+ beneficiaryAccountId: @beneficiary_account_id,
26
+ amount: @amount,
27
+ myReference: @my_reference,
28
+ theirReference: @their_reference
29
+ }
30
+ end
31
+ end
32
+ end
@@ -0,0 +1,13 @@
1
+ module InvestecOpenApi
2
+ module StringUtilities
3
+ refine String do
4
+ def underscore
5
+ self.gsub(/::/, "/")
6
+ .gsub(/([A-Z]+)([A-Z][a-z])/, '\1_\2')
7
+ .gsub(/([a-z\d])([A-Z])/, '\1_\2')
8
+ .tr("-", "_")
9
+ .downcase
10
+ end
11
+ end
12
+ end
13
+ end
@@ -1,3 +1,3 @@
1
1
  module InvestecOpenApi
2
- VERSION = "1.1.0"
2
+ VERSION = "2.0.0"
3
3
  end
@@ -1,13 +1,34 @@
1
1
  require "investec_open_api/version"
2
2
  require "investec_open_api/models/base"
3
+ require "investec_open_api/camel_case_refinement"
3
4
  require "investec_open_api/client"
4
5
 
5
6
  module InvestecOpenApi
6
7
  class Error < StandardError; end
7
8
 
8
- mattr_accessor :api_key, :client_id, :client_secret, :scope
9
+ class Configuration
10
+ DEFAULT_BASE_URL = "https://openapi.investec.com/"
9
11
 
10
- def self.configuration(&block)
11
- yield self
12
+ attr_accessor :api_key,
13
+ :client_id,
14
+ :client_secret,
15
+ :scope,
16
+ :base_url
17
+
18
+ def initialize
19
+ @base_url = DEFAULT_BASE_URL
20
+
21
+ Money.locale_backend = :i18n
22
+ end
23
+ end
24
+
25
+ class << self
26
+ def config
27
+ @config ||= Configuration.new
28
+ end
29
+
30
+ def configuration
31
+ yield config
32
+ end
12
33
  end
13
34
  end
metadata CHANGED
@@ -1,29 +1,15 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: investec_open_api
3
3
  version: !ruby/object:Gem::Version
4
- version: 1.1.0
4
+ version: 2.0.0
5
5
  platform: ruby
6
6
  authors:
7
7
  - Community Core Team
8
8
  autorequire:
9
9
  bindir: exe
10
10
  cert_chain: []
11
- date: 2023-05-10 00:00:00.000000000 Z
11
+ date: 2024-09-12 00:00:00.000000000 Z
12
12
  dependencies:
13
- - !ruby/object:Gem::Dependency
14
- name: active_attr
15
- requirement: !ruby/object:Gem::Requirement
16
- requirements:
17
- - - ">="
18
- - !ruby/object:Gem::Version
19
- version: '0'
20
- type: :runtime
21
- prerelease: false
22
- version_requirements: !ruby/object:Gem::Requirement
23
- requirements:
24
- - - ">="
25
- - !ruby/object:Gem::Version
26
- version: '0'
27
13
  - !ruby/object:Gem::Dependency
28
14
  name: faraday
29
15
  requirement: !ruby/object:Gem::Requirement
@@ -39,7 +25,7 @@ dependencies:
39
25
  - !ruby/object:Gem::Version
40
26
  version: '0'
41
27
  - !ruby/object:Gem::Dependency
42
- name: faraday_middleware
28
+ name: money
43
29
  requirement: !ruby/object:Gem::Requirement
44
30
  requirements:
45
31
  - - ">="
@@ -53,13 +39,13 @@ dependencies:
53
39
  - !ruby/object:Gem::Version
54
40
  version: '0'
55
41
  - !ruby/object:Gem::Dependency
56
- name: money
42
+ name: rake
57
43
  requirement: !ruby/object:Gem::Requirement
58
44
  requirements:
59
45
  - - ">="
60
46
  - !ruby/object:Gem::Version
61
47
  version: '0'
62
- type: :runtime
48
+ type: :development
63
49
  prerelease: false
64
50
  version_requirements: !ruby/object:Gem::Requirement
65
51
  requirements:
@@ -67,7 +53,7 @@ dependencies:
67
53
  - !ruby/object:Gem::Version
68
54
  version: '0'
69
55
  - !ruby/object:Gem::Dependency
70
- name: rake
56
+ name: rspec
71
57
  requirement: !ruby/object:Gem::Requirement
72
58
  requirements:
73
59
  - - ">="
@@ -81,7 +67,7 @@ dependencies:
81
67
  - !ruby/object:Gem::Version
82
68
  version: '0'
83
69
  - !ruby/object:Gem::Dependency
84
- name: rspec
70
+ name: webmock
85
71
  requirement: !ruby/object:Gem::Requirement
86
72
  requirements:
87
73
  - - ">="
@@ -95,7 +81,7 @@ dependencies:
95
81
  - !ruby/object:Gem::Version
96
82
  version: '0'
97
83
  - !ruby/object:Gem::Dependency
98
- name: webmock
84
+ name: faker
99
85
  requirement: !ruby/object:Gem::Requirement
100
86
  requirements:
101
87
  - - ">="
@@ -115,9 +101,9 @@ executables: []
115
101
  extensions: []
116
102
  extra_rdoc_files: []
117
103
  files:
104
+ - ".github/workflows/main.yml"
118
105
  - ".gitignore"
119
106
  - ".rspec"
120
- - ".ruby-version"
121
107
  - ".travis.yml"
122
108
  - CODE_OF_CONDUCT.md
123
109
  - Gemfile
@@ -126,13 +112,18 @@ files:
126
112
  - README.md
127
113
  - Rakefile
128
114
  - bin/console
115
+ - bin/sandbox
129
116
  - bin/setup
130
117
  - investec_open_api.gemspec
131
118
  - lib/investec_open_api.rb
119
+ - lib/investec_open_api/camel_case_refinement.rb
132
120
  - lib/investec_open_api/client.rb
133
121
  - lib/investec_open_api/models/account.rb
122
+ - lib/investec_open_api/models/balance.rb
134
123
  - lib/investec_open_api/models/base.rb
135
124
  - lib/investec_open_api/models/transaction.rb
125
+ - lib/investec_open_api/models/transfer.rb
126
+ - lib/investec_open_api/string_utilities.rb
136
127
  - lib/investec_open_api/version.rb
137
128
  homepage: https://github.com/programmable-banking-community/investec_open_api
138
129
  licenses:
@@ -157,7 +148,7 @@ required_rubygems_version: !ruby/object:Gem::Requirement
157
148
  - !ruby/object:Gem::Version
158
149
  version: '0'
159
150
  requirements: []
160
- rubygems_version: 3.4.1
151
+ rubygems_version: 3.5.16
161
152
  signing_key:
162
153
  specification_version: 4
163
154
  summary: Investec Open API Wrapper
data/.ruby-version DELETED
@@ -1 +0,0 @@
1
- 3.2.0