EGP_Rates 0.2.0 → 0.3.0

Sign up to get free protection for your applications and to get access to all the features.
Files changed (40) hide show
  1. checksums.yaml +4 -4
  2. data/lib/egp_rates.rb +9 -0
  3. data/lib/egp_rates/aaib.rb +5 -6
  4. data/lib/egp_rates/al_ahli_bank_of_kuwait.rb +61 -0
  5. data/lib/egp_rates/al_baraka_bank.rb +84 -0
  6. data/lib/egp_rates/bank.rb +36 -0
  7. data/lib/egp_rates/banque_du_caire.rb +66 -0
  8. data/lib/egp_rates/banque_misr.rb +69 -0
  9. data/lib/egp_rates/cae.rb +62 -0
  10. data/lib/egp_rates/cbe.rb +1 -20
  11. data/lib/egp_rates/cib.rb +2 -1
  12. data/lib/egp_rates/midb.rb +60 -0
  13. data/lib/egp_rates/nbe.rb +1 -2
  14. data/lib/egp_rates/saib.rb +62 -0
  15. data/lib/egp_rates/suez_canal_bank.rb +80 -0
  16. data/lib/egp_rates/ube.rb +59 -0
  17. data/spec/cassettes/AlAhliBankOfKuwait.yml +1379 -0
  18. data/spec/cassettes/AlBarakaBank.yml +308 -0
  19. data/spec/cassettes/BanqueDuCaire.yml +1475 -0
  20. data/spec/cassettes/BanqueMisr.yml +1327 -0
  21. data/spec/cassettes/CAE.yml +6098 -0
  22. data/spec/cassettes/MIDB.yml +507 -0
  23. data/spec/cassettes/SAIB.yml +567 -0
  24. data/spec/cassettes/SuezCanalBank.yml +1399 -0
  25. data/spec/cassettes/UBE.yml +69 -0
  26. data/spec/egp_rates/aaib_spec.rb +4 -4
  27. data/spec/egp_rates/al_ahli_bank_of_kuwait_spec.rb +76 -0
  28. data/spec/egp_rates/al_baraka_bank_spec.rb +89 -0
  29. data/spec/egp_rates/banque_du_caire_spec.rb +111 -0
  30. data/spec/egp_rates/banque_misr_spec.rb +119 -0
  31. data/spec/egp_rates/cae_spec.rb +93 -0
  32. data/spec/egp_rates/cbe_spec.rb +4 -4
  33. data/spec/egp_rates/cib_spec.rb +3 -3
  34. data/spec/egp_rates/midb_spec.rb +73 -0
  35. data/spec/egp_rates/nbe_spec.rb +3 -3
  36. data/spec/egp_rates/saib_spec.rb +77 -0
  37. data/spec/egp_rates/suez_canal_bank_spec.rb +102 -0
  38. data/spec/egp_rates/ube_spec.rb +71 -0
  39. data/spec/egp_rates_spec.rb +2 -0
  40. metadata +30 -3
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA1:
3
- metadata.gz: 179ed0bbc6e04914fdf9fec1e526270aaefe14ff
4
- data.tar.gz: 43296feb1231e90af389eb3372f07135211ef3e6
3
+ metadata.gz: 67e2ffa9c086a7c6a6ae0a7c23603d48d0fd8126
4
+ data.tar.gz: cef9ab2c432e9dda519a6bb7a910a547efe71aab
5
5
  SHA512:
6
- metadata.gz: 88e624e998f66d0c356e9ce7142a6dc9b45c31d4376e2ccfd0c1a443e77e2d85abfa94f70aed37c7f2eb5be25e1c13028a019c1d1b0b2f9860cd54e1785cf9a8
7
- data.tar.gz: a8dac0a7afb3b9f422edbca668a7d7d8e7c744ce70081fca02fbdb06a4d5a72922b45f74e89bd614586a7f08f0738440cbc05ea9c300ee592fe79ce7c74bcfe4
6
+ metadata.gz: 05722005a91509a13adea01a5ff0686633af1662f84042a7262cc6ebcd3f432fe4b2abfa75f1a2e8dc37e91c1dbb798ded05b3dcaba2ac6e1a14ed541bbb0c42
7
+ data.tar.gz: a29e3075482b9d81fd76768dc4077909f38036c53f0a0c8f70152371bf5ad7dcb004b2299dac9307a8eceaf36348aff635ab25496142edd76aece62e06366bb0
@@ -7,6 +7,15 @@ require 'egp_rates/cbe'
7
7
  require 'egp_rates/nbe'
8
8
  require 'egp_rates/cib'
9
9
  require 'egp_rates/aaib'
10
+ require 'egp_rates/banque_misr'
11
+ require 'egp_rates/banque_du_caire'
12
+ require 'egp_rates/suez_canal_bank'
13
+ require 'egp_rates/al_baraka_bank'
14
+ require 'egp_rates/al_ahli_bank_of_kuwait'
15
+ require 'egp_rates/saib'
16
+ require 'egp_rates/midb'
17
+ require 'egp_rates/ube'
18
+ require 'egp_rates/cae'
10
19
 
11
20
  # Base Module
12
21
  module EGPRates
@@ -41,11 +41,9 @@ module EGPRates
41
41
  # ...
42
42
  # ]
43
43
  def raw_exchange_rates
44
- response = Net::HTTP.get_response(@uri)
45
- fail ResponseError, response.code unless response.is_a? Net::HTTPSuccess
46
- response = response.body&.gsub("\u0000", '')
44
+ raw = response.body&.gsub("\u0000", '')
47
45
  # AAIB provide 7 currencies only
48
- table_rows = Oga.parse_html(response).css('#rates-table tr')
46
+ table_rows = Oga.parse_html(raw).css('#rates-table tr')
49
47
  fail ResponseError, 'Unknown HTML' unless table_rows&.size == 7
50
48
  table_rows.lazy.map(&:children).map { |cell| cell.map(&:text) }
51
49
  end
@@ -56,12 +54,12 @@ module EGPRates
56
54
  # rubocop:disable Metrics/CyclomaticComplexity
57
55
  def currency_symbol(currency)
58
56
  case currency
59
- when /US/ then :USD
57
+ when /US DOLLAR/ then :USD
60
58
  when /EURO/ then :EUR
61
59
  when /STERLING/ then :GBP
62
60
  when /SWISS/ then :CHF
63
61
  when /SAUDI/ then :SAR
64
- when /KUWAIT/ then :KWD
62
+ when /KUWAITI/ then :KWD
65
63
  when /DIRHAM/ then :AED
66
64
  else fail ResponseError, "Unknown currency #{currency}"
67
65
  end
@@ -69,6 +67,7 @@ module EGPRates
69
67
  # rubocop:enable Metrics/CyclomaticComplexity
70
68
 
71
69
  # Parse the #raw_exchange_rates returned in response
70
+ # @param [Array] of the raw_data scraped
72
71
  # @return [Hash] of exchange rates for selling and buying
73
72
  # {
74
73
  # { sell: { SYM: rate }, { SYM: rate }, ... },
@@ -0,0 +1,61 @@
1
+ # frozen_string_literal: true
2
+ module EGPRates
3
+ # Central Bank of Egypt
4
+ class AlAhliBankOfKuwait < EGPRates::Bank
5
+ def initialize
6
+ @sym = :AlAhliBankOfKuwait
7
+ @uri = URI.parse('http://www.piraeusbank.com.eg/rates_abk.aspx')
8
+ end
9
+
10
+ # @return [Hash] of exchange rates for selling and buying
11
+ # {
12
+ # { sell: { SYM: rate }, { SYM: rate }, ... },
13
+ # { buy: { SYM: rate }, { SYM: rate }, ... }
14
+ # }
15
+ def exchange_rates
16
+ @exchange_rates ||= parse(raw_exchange_rates)
17
+ end
18
+
19
+ private
20
+
21
+ # Send the request to the URL and retrun raw data of the response
22
+ # @return [Enumerator::Lazy] with the table row in HTML that evaluates to
23
+ # [
24
+ # [
25
+ # "", "EUR", "", "17.094800", "", "17.528100", "", ...
26
+ # ], [
27
+ # "", "CHF", "", "15.983800", "", "16.395900", "", ...
28
+ # ]
29
+ # ...
30
+ # ]
31
+ #
32
+ def raw_exchange_rates
33
+ response = Net::HTTP.get_response(@uri)
34
+ fail ResponseError, response.code unless response.is_a? Net::HTTPSuccess
35
+ table_rows = Oga.parse_html(response.body).css('.ORANGE_TEXT, .BLUE_TEXT')
36
+ # AlAhliBankOfKuwait porvide 8 currencies on the home page
37
+ fail ResponseError, 'Unknown HTML' unless table_rows&.size == 8
38
+ table_rows.lazy.map(&:children).map do |cell|
39
+ cell.map(&:text).map(&:strip)
40
+ end
41
+ end
42
+
43
+ # Parse the #raw_exchange_rates returned in response
44
+ # @param [Array] of the raw_data scraped
45
+ # @return [Hash] of exchange rates for selling and buying
46
+ # {
47
+ # { sell: { SYM: rate }, { SYM: rate }, ... },
48
+ # { buy: { SYM: rate }, { SYM: rate }, ... }
49
+ # }
50
+ def parse(raw_data)
51
+ raw_data.each_with_object(sell: {}, buy: {}) do |row, result|
52
+ sell_rate = row[9].to_f
53
+ buy_rate = row[7].to_f
54
+ currency = row[1].to_sym
55
+
56
+ result[:sell][currency] = sell_rate
57
+ result[:buy][currency] = buy_rate
58
+ end
59
+ end
60
+ end
61
+ end
@@ -0,0 +1,84 @@
1
+ # frozen_string_literal: true
2
+ module EGPRates
3
+ # Central Bank of Egypt
4
+ class AlBarakaBank < EGPRates::Bank
5
+ def initialize
6
+ @sym = :AlBarakaBank
7
+ @uri = URI.parse('http://www.albaraka-bank.com.eg/banking-services/exchange-rates.aspx')
8
+ end
9
+
10
+ # @return [Hash] of exchange rates for selling and buying
11
+ # {
12
+ # { sell: { SYM: rate }, { SYM: rate }, ... },
13
+ # { buy: { SYM: rate }, { SYM: rate }, ... }
14
+ # }
15
+ def exchange_rates
16
+ @exchange_rates ||= parse(raw_exchange_rates)
17
+ end
18
+
19
+ private
20
+
21
+ # Send the request to the URL and retrun raw data of the response
22
+ # @return [Enumerator::Lazy] with the table row in HTML that evaluates to
23
+ # [
24
+ # [
25
+ # "USD", "1596.00", "1650.00", ...
26
+ # ], [
27
+ # "GBP", "1953.06", "2079.83", ...
28
+ # ], [
29
+ # "EURO", "1672.32", "1787.11", ...
30
+ # ]
31
+ # ...
32
+ # ]
33
+ #
34
+ def raw_exchange_rates
35
+ table_rows = Oga.parse_html(response.body).css('table').first&.children
36
+ # AlBarakaBank porvide 7 currencies on the home page
37
+ fail ResponseError, 'Unknown HTML' unless table_rows&.size == 8
38
+ table_rows.lazy.drop(1).map(&:children).map { |cell| cell.map(&:text) }
39
+ end
40
+
41
+ # Convert currency string to ISO symbol
42
+ # @param currency [String] "US Dollar"
43
+ # @return [Symbol] :USD ISO currency name
44
+ # rubocop:disable Metrics/CyclomaticComplexity
45
+ def currency_symbol(currency)
46
+ case currency
47
+ when /USD/ then :USD
48
+ when /EURO/ then :EUR
49
+ when /GBP/ then :GBP
50
+ when /CHF/ then :CHF
51
+ when /JPY/ then :JPY
52
+ when /SAR/ then :SAR
53
+ when /BHD/ then :BHD
54
+ else fail ResponseError, "Unknown currency #{currency}"
55
+ end
56
+ end
57
+ # rubocop:enable Metrics/CyclomaticComplexity
58
+
59
+ # Parse the #raw_exchange_rates returned in response
60
+ # @param [Array] of the raw_data scraped
61
+ # [
62
+ # [ 'Currency_1', 'BuyRate', 'SellRate', ... ],
63
+ # [ 'Currency_2', 'BuyRate', 'SellRate', ... ],
64
+ # [ 'Currency_3', 'BuyRate', 'SellRate', ... ],
65
+ # ...
66
+ # ]
67
+ #
68
+ # @return [Hash] of exchange rates for selling and buying
69
+ # {
70
+ # { sell: { SYM: rate }, { SYM: rate }, ... },
71
+ # { buy: { SYM: rate }, { SYM: rate }, ... }
72
+ # }
73
+ def parse(raw_data)
74
+ raw_data.each_with_object(sell: {}, buy: {}) do |row, result|
75
+ sell_rate = (row[2].to_f / 100).round(4)
76
+ buy_rate = (row[1].to_f / 100).round(4)
77
+ currency = currency_symbol(row[0])
78
+
79
+ result[:sell][currency] = sell_rate
80
+ result[:buy][currency] = buy_rate
81
+ end
82
+ end
83
+ end
84
+ end
@@ -11,5 +11,41 @@ module EGPRates
11
11
  def exchange_rates
12
12
  raise NotImplementedError
13
13
  end
14
+
15
+ private
16
+
17
+ # Make a call to the @uri to get the raw_response
18
+ # @return [Net::HTTPSuccess] of the raw response
19
+ # @raises [ResponseError] if response is not 200 OK
20
+ def response
21
+ response = Net::HTTP.get_response(@uri)
22
+ fail ResponseError, response.code unless response.is_a? Net::HTTPSuccess
23
+ response
24
+ end
25
+
26
+ # Parse the #raw_exchange_rates returned in response
27
+ # @param [Array] of the raw_data scraped
28
+ # [
29
+ # [ 'Currency_1', 'BuyRate', 'SellRate', ... ],
30
+ # [ 'Currency_2', 'BuyRate', 'SellRate', ... ],
31
+ # [ 'Currency_3', 'BuyRate', 'SellRate', ... ],
32
+ # ...
33
+ # ]
34
+ #
35
+ # @return [Hash] of exchange rates for selling and buying
36
+ # {
37
+ # { sell: { SYM: rate }, { SYM: rate }, ... },
38
+ # { buy: { SYM: rate }, { SYM: rate }, ... }
39
+ # }
40
+ def parse(raw_data)
41
+ raw_data.each_with_object(sell: {}, buy: {}) do |row, result|
42
+ sell_rate = row[2].to_f
43
+ buy_rate = row[1].to_f
44
+ currency = currency_symbol(row[0])
45
+
46
+ result[:sell][currency] = sell_rate
47
+ result[:buy][currency] = buy_rate
48
+ end
49
+ end
14
50
  end
15
51
  end
@@ -0,0 +1,66 @@
1
+
2
+ # frozen_string_literal: true
3
+ module EGPRates
4
+ # Banque Du Caire
5
+ class BanqueDuCaire < EGPRates::Bank
6
+ def initialize
7
+ @sym = :BanqueDuCaire
8
+ @uri = URI.parse('http://www.banqueducaire.com/English/MarketUpdates/Pages/CurrencyExchange.aspx')
9
+ end
10
+
11
+ # @return [Hash] of exchange rates for selling and buying
12
+ # {
13
+ # { sell: { SYM: rate }, { SYM: rate }, ... },
14
+ # { buy: { SYM: rate }, { SYM: rate }, ... }
15
+ # }
16
+ def exchange_rates
17
+ @exchange_rates ||= parse(raw_exchange_rates)
18
+ end
19
+
20
+ private
21
+
22
+ # Send the request to the URL and retrun raw data of the response
23
+ # @return [Enumerator::Lazy] with the table row in HTML that evaluates to
24
+ # [
25
+ # ["US DOLLAR", "15.35", "16.25"],
26
+ # ["EURO", "16.6194", "17.7499"],
27
+ # ...
28
+ # ]
29
+ #
30
+ def raw_exchange_rates
31
+ # Banque Du Caire provide 17 currencies only
32
+ table_rows = Oga.parse_html(response.body).css('table.curTbl tr')
33
+ # But they have 1 empty <tr> and 1 header <tr> elements
34
+ fail ResponseError, 'Unknown HTML' unless table_rows&.size == 19
35
+ table_rows.lazy.drop(2).map(&:children).map { |cell| cell.map(&:text) }
36
+ end
37
+
38
+ # Convert currency string to ISO symbol
39
+ # @param currency [String] "US Dollar"
40
+ # @return [Symbol] :USD ISO currency name
41
+ # rubocop:disable Metrics/CyclomaticComplexity
42
+ def currency_symbol(currency)
43
+ case currency
44
+ when /EMIRATES/ then :AED
45
+ when /AUSTRALIAN/ then :AUD
46
+ when /BAHRAIN/ then :BHD
47
+ when /CANADIAN/ then :CAD
48
+ when /SWISS/ then :CHF
49
+ when /DANISH/ then :DKK
50
+ when /EURO/ then :EUR
51
+ when /BRITISH/ then :GBP
52
+ when /JORDANIAN/ then :JOD
53
+ when /JAPANESE/ then :JPY
54
+ when /KUWAITI/ then :KWD
55
+ when /NORWEGIAN/ then :NOK
56
+ when /OMANI/ then :OMR
57
+ when /QATAR/ then :QAR
58
+ when /SAUDI/ then :SAR
59
+ when /SWEDISH/ then :SEK
60
+ when /US DOLLAR/ then :USD
61
+ else fail ResponseError, "Unknown currency #{currency}"
62
+ end
63
+ end
64
+ # rubocop:enable Metrics/CyclomaticComplexity
65
+ end
66
+ end
@@ -0,0 +1,69 @@
1
+ # frozen_string_literal: true
2
+ module EGPRates
3
+ # Banque Misr
4
+ class BanqueMisr < EGPRates::Bank
5
+ def initialize
6
+ @sym = :BanqueMisr
7
+ @uri = URI.parse('http://www.banquemisr.com/en/exchangerates')
8
+ end
9
+
10
+ # @return [Hash] of exchange rates for selling and buying
11
+ # {
12
+ # { sell: { SYM: rate }, { SYM: rate }, ... },
13
+ # { buy: { SYM: rate }, { SYM: rate }, ... }
14
+ # }
15
+ def exchange_rates
16
+ @exchange_rates ||= parse(raw_exchange_rates)
17
+ end
18
+
19
+ private
20
+
21
+ # Send the request to the URL and retrun raw data of the response
22
+ # @return [Enumerator::Lazy] with the table row in HTML that evaluates to
23
+ # [
24
+ # ["US DOLLAR", "15.35", "15.91", "15.35", "15.91"],
25
+ # ["EURO", "16.6256", "17.3698", "16.633898", "17.378493"]
26
+ # ...
27
+ # ]
28
+ #
29
+ def raw_exchange_rates
30
+ # BanqueMisr provide 18 currencies (17 Used and CYPRUS POUND)
31
+ # But they have 2 <tr> for headers
32
+ table_rows = Oga.parse_html(response.body).css('.exchangeRates tbody tr')
33
+ fail ResponseError, 'Unknown HTML' unless table_rows&.size == 20
34
+ # remove the first 2 headers of the array and the last element
35
+ # which is CYPRUS POUND which is not used anymore
36
+ table_rows.lazy.drop(2).take(17).map(&:children).map do |cell|
37
+ cell.map(&:text)
38
+ end
39
+ end
40
+
41
+ # Convert currency string to ISO symbol
42
+ # @param currency [String] "US Dollar"
43
+ # @return [Symbol] :USD ISO currency name
44
+ # rubocop:disable Metrics/CyclomaticComplexity
45
+ def currency_symbol(currency)
46
+ case currency
47
+ when /UAE DIRHAM/ then :AED
48
+ when /AUSTRALIA/ then :AUD
49
+ when /BAHRAIN/ then :BHD
50
+ when /CANADA/ then :CAD
51
+ when /SWEDISH/ then :CHF
52
+ when /DENMARK/ then :DKK
53
+ when /EURO/ then :EUR
54
+ when /GB POUND/ then :GBP
55
+ when /JORDANIAN/ then :JOD
56
+ when /JAPAN/ then :JPY
57
+ when /KUWAIT/ then :KWD
58
+ when /NORWAY/ then :NOK
59
+ when /OMAN/ then :OMR
60
+ when /QATARI/ then :QAR
61
+ when /SAUDI/ then :SAR
62
+ when /SWISS/ then :SEK
63
+ when /US DOLLAR/ then :USD
64
+ else fail ResponseError, "Unknown currency #{currency}"
65
+ end
66
+ end
67
+ # rubocop:enable Metrics/CyclomaticComplexity
68
+ end
69
+ end
@@ -0,0 +1,62 @@
1
+ # frozen_string_literal: true
2
+ module EGPRates
3
+ # Crédit Agricole Egypt (CAE)
4
+ class CAE < EGPRates::Bank
5
+ def initialize
6
+ @sym = :CAE
7
+ @uri = URI.parse('https://www.ca-egypt.com/en/personal-banking/')
8
+ end
9
+
10
+ # @return [Hash] of exchange rates for selling and buying
11
+ # {
12
+ # { sell: { SYM: rate }, { SYM: rate }, ... },
13
+ # { buy: { SYM: rate }, { SYM: rate }, ... }
14
+ # }
15
+ def exchange_rates
16
+ @exchange_rates ||= parse(raw_exchange_rates)
17
+ end
18
+
19
+ private
20
+
21
+ # Send the request to the URL and retrun raw data of the response
22
+ # @return [Enumerator::Lazy] with the table row in HTML that evaluates to
23
+ # [
24
+ # ["QAR", "4.7367", "4.9294"],
25
+ # ["USD", "17.25", "17.95"]
26
+ # ...
27
+ # ]
28
+ def raw_exchange_rates
29
+ response = Net::HTTP.get_response(@uri)
30
+ fail ResponseError, response.code unless response.is_a? Net::HTTPSuccess
31
+ table_rows = Oga.parse_html(response.body).css('#f_box option')
32
+ # CAE porvide 17 currencies on the home page but with header
33
+ # and an empty row in the end
34
+ fail ResponseError, 'Unknown HTML' unless table_rows&.size == 17
35
+ table_rows.lazy.map do |row|
36
+ [
37
+ row.text,
38
+ row.attribute('data-buy').value,
39
+ row.attribute('data-sell').value
40
+ ]
41
+ end
42
+ end
43
+
44
+ # Parse the #raw_exchange_rates returned in response
45
+ # @param [Array] of the raw_data scraped
46
+ # @return [Hash] of exchange rates for selling and buying
47
+ # {
48
+ # { sell: { SYM: rate }, { SYM: rate }, ... },
49
+ # { buy: { SYM: rate }, { SYM: rate }, ... }
50
+ # }
51
+ def parse(raw_data)
52
+ raw_data.each_with_object(sell: {}, buy: {}) do |row, result|
53
+ sell_rate = row[2].to_f
54
+ buy_rate = row[1].to_f
55
+ currency = row[0].to_sym
56
+
57
+ result[:sell][currency] = sell_rate
58
+ result[:buy][currency] = buy_rate
59
+ end
60
+ end
61
+ end
62
+ end