deliveries 0.1.0

Sign up to get free protection for your applications and to get access to all the features.
Files changed (81) hide show
  1. checksums.yaml +7 -0
  2. data/.github/workflows/main.yml +19 -0
  3. data/.gitignore +12 -0
  4. data/.rspec +3 -0
  5. data/.rubocop.yml +34 -0
  6. data/CHANGELOG.md +13 -0
  7. data/Gemfile +12 -0
  8. data/Gemfile.lock +127 -0
  9. data/LICENSE.txt +21 -0
  10. data/README.md +207 -0
  11. data/Rakefile +12 -0
  12. data/bin/console +15 -0
  13. data/bin/setup +8 -0
  14. data/deliveries.gemspec +36 -0
  15. data/lib/deliveries/address.rb +71 -0
  16. data/lib/deliveries/checkpoint.rb +12 -0
  17. data/lib/deliveries/collection_point.rb +45 -0
  18. data/lib/deliveries/courier.rb +69 -0
  19. data/lib/deliveries/couriers/correos_express/address.rb +31 -0
  20. data/lib/deliveries/couriers/correos_express/collection_points/search/format_response.rb +82 -0
  21. data/lib/deliveries/couriers/correos_express/collection_points/search.rb +56 -0
  22. data/lib/deliveries/couriers/correos_express/labels/generate.rb +68 -0
  23. data/lib/deliveries/couriers/correos_express/pickups/create/defaults.rb +60 -0
  24. data/lib/deliveries/couriers/correos_express/pickups/create/format_params.rb +95 -0
  25. data/lib/deliveries/couriers/correos_express/pickups/create.rb +66 -0
  26. data/lib/deliveries/couriers/correos_express/pickups/cutoff_time/format_params.rb +40 -0
  27. data/lib/deliveries/couriers/correos_express/pickups/cutoff_time.rb +61 -0
  28. data/lib/deliveries/couriers/correos_express/pickups/trace/correos.test.wsdl +163 -0
  29. data/lib/deliveries/couriers/correos_express/pickups/trace/correos.wsdl +163 -0
  30. data/lib/deliveries/couriers/correos_express/pickups/trace/format_response.rb +71 -0
  31. data/lib/deliveries/couriers/correos_express/pickups/trace.rb +49 -0
  32. data/lib/deliveries/couriers/correos_express/shipments/create/defaults.rb +80 -0
  33. data/lib/deliveries/couriers/correos_express/shipments/create/format_params.rb +99 -0
  34. data/lib/deliveries/couriers/correos_express/shipments/create.rb +101 -0
  35. data/lib/deliveries/couriers/correos_express/shipments/trace/format_response.rb +67 -0
  36. data/lib/deliveries/couriers/correos_express/shipments/trace.rb +65 -0
  37. data/lib/deliveries/couriers/correos_express.rb +162 -0
  38. data/lib/deliveries/couriers/dummy.rb +106 -0
  39. data/lib/deliveries/couriers/mondial_relay/address.rb +31 -0
  40. data/lib/deliveries/couriers/mondial_relay/collection_points/search/format_response.rb +103 -0
  41. data/lib/deliveries/couriers/mondial_relay/labels/generate.rb +40 -0
  42. data/lib/deliveries/couriers/mondial_relay/pickups/create/format_params.rb +57 -0
  43. data/lib/deliveries/couriers/mondial_relay/shipments/create/defaults.rb +96 -0
  44. data/lib/deliveries/couriers/mondial_relay/shipments/create/format_params.rb +68 -0
  45. data/lib/deliveries/couriers/mondial_relay/shipments/create.rb +36 -0
  46. data/lib/deliveries/couriers/mondial_relay/shipments/trace/format_response.rb +94 -0
  47. data/lib/deliveries/couriers/mondial_relay/shipments/trace.rb +47 -0
  48. data/lib/deliveries/couriers/mondial_relay/status_codes.rb +105 -0
  49. data/lib/deliveries/couriers/mondial_relay.rb +189 -0
  50. data/lib/deliveries/couriers/mondial_relay_dual/address.rb +31 -0
  51. data/lib/deliveries/couriers/mondial_relay_dual/pickups/create/format_params.rb +39 -0
  52. data/lib/deliveries/couriers/mondial_relay_dual/shipments/create/format_params.rb +101 -0
  53. data/lib/deliveries/couriers/mondial_relay_dual/shipments/create.rb +133 -0
  54. data/lib/deliveries/couriers/mondial_relay_dual.rb +105 -0
  55. data/lib/deliveries/couriers/spring/address.rb +23 -0
  56. data/lib/deliveries/couriers/spring/labels/generate.rb +33 -0
  57. data/lib/deliveries/couriers/spring/request.rb +43 -0
  58. data/lib/deliveries/couriers/spring/shipments/create/defaults.rb +73 -0
  59. data/lib/deliveries/couriers/spring/shipments/create/format_params.rb +77 -0
  60. data/lib/deliveries/couriers/spring/shipments/create.rb +45 -0
  61. data/lib/deliveries/couriers/spring/shipments/trace/format_response.rb +79 -0
  62. data/lib/deliveries/couriers/spring/shipments/trace.rb +29 -0
  63. data/lib/deliveries/couriers/spring.rb +84 -0
  64. data/lib/deliveries/couriers/ups/collection_points/search.rb +142 -0
  65. data/lib/deliveries/couriers/ups/json_request.rb +40 -0
  66. data/lib/deliveries/couriers/ups/labels/generate.rb +72 -0
  67. data/lib/deliveries/couriers/ups/shipments/create.rb +210 -0
  68. data/lib/deliveries/couriers/ups/shipments/trace.rb +79 -0
  69. data/lib/deliveries/couriers/ups.rb +122 -0
  70. data/lib/deliveries/couriers.rb +14 -0
  71. data/lib/deliveries/delivery.rb +20 -0
  72. data/lib/deliveries/errors.rb +22 -0
  73. data/lib/deliveries/label.rb +20 -0
  74. data/lib/deliveries/label_utils.rb +67 -0
  75. data/lib/deliveries/labels.rb +40 -0
  76. data/lib/deliveries/pickup.rb +15 -0
  77. data/lib/deliveries/shipment.rb +15 -0
  78. data/lib/deliveries/tracking_info.rb +29 -0
  79. data/lib/deliveries/version.rb +5 -0
  80. data/lib/deliveries.rb +63 -0
  81. metadata +240 -0
@@ -0,0 +1,69 @@
1
+ require 'ostruct'
2
+
3
+ module Deliveries
4
+ module Courier
5
+ @config = nil
6
+
7
+ def configure
8
+ @config ||= ancestors.first::Config.new
9
+ yield @config
10
+ end
11
+
12
+ def configured?
13
+ @config.present?
14
+ end
15
+
16
+ # Get configuration value by key.
17
+ #
18
+ # @param key [String, Symbol[]] Dot notation string or array of symbols.
19
+ # @param default [Mixed]
20
+ #
21
+ # @return [Mixed]
22
+ def config(key, default: nil)
23
+ raise 'Courier not configured' unless configured?
24
+
25
+ key = key.split('.').map(&:to_sym) if key.is_a? String
26
+ @config.dig(*key) || default
27
+ end
28
+
29
+ def test?
30
+ Deliveries.test?
31
+ end
32
+
33
+ def live?
34
+ Deliveries.live?
35
+ end
36
+
37
+ def get_collection_point(global_point_id:)
38
+ raise NotImplementedError
39
+ end
40
+
41
+ def get_collection_points(country:, postcode:)
42
+ raise NotImplementedError
43
+ end
44
+
45
+ def create_shipment(sender:, receiver:, collection_point:, parcels:, reference_code:, shipment_date: nil, remarks: nil, language: nil)
46
+ raise NotImplementedError
47
+ end
48
+
49
+ def create_pickup(sender:, receiver:, parcels:, reference_code:, pickup_date: nil, remarks: nil, language: nil)
50
+ raise NotImplementedError
51
+ end
52
+
53
+ def get_label(tracking_code:, language: nil)
54
+ raise NotImplementedError
55
+ end
56
+
57
+ def get_labels(tracking_codes:, language: nil)
58
+ raise NotImplementedError
59
+ end
60
+
61
+ def shipment_info(tracking_code:, language: nil)
62
+ raise NotImplementedError
63
+ end
64
+
65
+ def pickup_info(tracking_code:, language: nil)
66
+ raise NotImplementedError
67
+ end
68
+ end
69
+ end
@@ -0,0 +1,31 @@
1
+ module Deliveries
2
+ module Couriers
3
+ module CorreosExpress
4
+ class Address < Deliveries::Address
5
+ def name
6
+ @name.to_s[0, 40]
7
+ end
8
+
9
+ def street
10
+ @street.to_s[0, 300]
11
+ end
12
+
13
+ def city
14
+ @city.to_s[0, 40]
15
+ end
16
+
17
+ def phone
18
+ @phone.to_s[0, 15]
19
+ end
20
+
21
+ def email
22
+ @email.gsub(/\+.+@/, '@').to_s[0, 75]
23
+ end
24
+
25
+ def country
26
+ @country.to_s.upcase
27
+ end
28
+ end
29
+ end
30
+ end
31
+ end
@@ -0,0 +1,82 @@
1
+ # "codigoOficina"=>"4894006",
2
+ # "nombreOficina"=>"OF.CORREOS: LAMIAKO - 4894006",
3
+ # "direccionOficina"=>"LANGILERIA 88",
4
+ # "codigoPostalOficina"=>"48940",
5
+ # "poblacionOficina"=>"LAMIAKO",
6
+ # "horarioOficina"=>"L-V:DE 08:30 A 14:30/S:DE 09:30 A 13:00/Festivos:SIN SERVICIO",
7
+ # "horarioOficinaVerano"=>"L-V:08:30-14:30/S:09:30-13:00/Festivos:SIN SERVICIO",
8
+ # "geoposicionOficina"=>"43.32142,-3.00031"
9
+
10
+ module Deliveries
11
+ module Couriers
12
+ module CorreosExpress
13
+ module CollectionPoints
14
+ class Search
15
+ class FormatResponse
16
+ SATURDAY_HOUR_KEY = 'S:'.freeze
17
+ WORKDAY_HOUR_KEY = 'L-V:'.freeze
18
+ HOLIDAY_HOUR_KEY = 'Festivos:'.freeze
19
+
20
+ attr_accessor :response
21
+
22
+ def initialize(response:)
23
+ self.response = response
24
+ end
25
+
26
+ def execute
27
+ collection_point = {}
28
+ collection_point[:courier_id] = 'correos_express'
29
+ collection_point[:name] = response['nombreOficina']
30
+ collection_point[:point_id] = response['codigoOficina']
31
+ collection_point[:street] = response['direccionOficina']
32
+ collection_point[:city] = response['poblacionOficina']
33
+ collection_point[:postcode] = response['codigoPostalOficina']
34
+ latitude, longitude = response['geoposicionOficina'].split(',')
35
+ collection_point[:latitude] = latitude.to_f
36
+ collection_point[:longitude] = longitude.to_f
37
+ collection_point[:timetable] = formatted_timetable(response['horarioOficina'])
38
+
39
+ collection_point
40
+ end
41
+
42
+ private
43
+
44
+ def formatted_timetable(params)
45
+ workday_hour, saturday_hour, holiday_hour = get_week_hours_from_result(params)
46
+
47
+ timetable = {}
48
+
49
+ if workday_hour.present?
50
+ 1.upto(5) do |weekday|
51
+ timetable[weekday] = [formatted_slot(workday_hour, WORKDAY_HOUR_KEY)]
52
+ end
53
+ end
54
+
55
+ timetable[6] = [formatted_slot(saturday_hour, SATURDAY_HOUR_KEY)] if saturday_hour.present?
56
+
57
+ timetable[0] = nil if holiday_hour.present?
58
+
59
+ timetable
60
+ end
61
+
62
+ def get_week_hours_from_result(params)
63
+ week_hours = params.split('/')
64
+
65
+ workday_hour = week_hours.select { |o| o.start_with?(WORKDAY_HOUR_KEY) }.first
66
+ saturday_hour = week_hours.select { |o| o.start_with?(SATURDAY_HOUR_KEY) }.first
67
+ holiday_hour = week_hours.select { |o| o.start_with?(HOLIDAY_HOUR_KEY) }.first
68
+
69
+ [workday_hour, saturday_hour, holiday_hour]
70
+ end
71
+
72
+ def formatted_slot(hour, key)
73
+ open, close = hour.sub(key, '').sub('DE ', '').split(' A ')
74
+
75
+ OpenStruct.new(open: open, close: close)
76
+ end
77
+ end
78
+ end
79
+ end
80
+ end
81
+ end
82
+ end
@@ -0,0 +1,56 @@
1
+ require 'httparty'
2
+
3
+ module Deliveries
4
+ module Couriers
5
+ module CorreosExpress
6
+ module CollectionPoints
7
+ class Search
8
+ include HTTParty
9
+
10
+ attr_accessor :postcode
11
+
12
+ def initialize(postcode:)
13
+ self.postcode = postcode
14
+ end
15
+
16
+ def execute
17
+ auth = {
18
+ username: CorreosExpress.config(:username),
19
+ password: CorreosExpress.config(:password)
20
+ }
21
+
22
+ headers = { 'Content-Type' => 'application/json;charset=UTF-8', 'Accept' => 'application/json' }
23
+
24
+ response = self.class.post(
25
+ api_endpoint,
26
+ basic_auth: auth,
27
+ body: { cod_postal: postcode }.to_json,
28
+ headers: headers,
29
+ debug_output: Deliveries.debug ? Deliveries.logger : nil
30
+ )
31
+ parsed_response = JSON.parse(response.body)
32
+
33
+ if parsed_response['tipoRespuesta'] == 'KO'
34
+ raise Deliveries::APIError.new(
35
+ parsed_response['listaErrores'].first['descError'],
36
+ parsed_response['listaErrores'].first['codError']
37
+ )
38
+ end
39
+
40
+ parsed_response['oficinas']
41
+ end
42
+
43
+ private
44
+
45
+ def api_endpoint
46
+ if CorreosExpress.live?
47
+ CorreosExpress::COLLECTION_POINTS_ENDPOINT_LIVE
48
+ else
49
+ CorreosExpress::COLLECTION_POINTS_ENDPOINT_TEST
50
+ end
51
+ end
52
+ end
53
+ end
54
+ end
55
+ end
56
+ end
@@ -0,0 +1,68 @@
1
+ require 'httparty'
2
+
3
+ module Deliveries
4
+ module Couriers
5
+ module CorreosExpress
6
+ module Labels
7
+ class Generate
8
+ include HTTParty
9
+
10
+ attr_accessor :tracking_codes
11
+
12
+ def initialize(tracking_codes:)
13
+ self.tracking_codes = tracking_codes.respond_to?(:each) ? tracking_codes : [tracking_codes]
14
+ end
15
+
16
+ def execute
17
+ auth = {
18
+ username: CorreosExpress.config(:username),
19
+ password: CorreosExpress.config(:password)
20
+ }
21
+ decoded_labels = []
22
+ tracking_codes.each do |tracking_code|
23
+ params = {
24
+ keyCli: CorreosExpress.config(:shipment_sender_code),
25
+ nenvio: tracking_code,
26
+ tipo: '1' # "1" - pdf, "2" - zpl image
27
+ }.to_json
28
+
29
+ headers = { 'Content-Type' => 'application/json' }
30
+ response = self.class.post(
31
+ api_endpoint,
32
+ basic_auth: auth,
33
+ body: params,
34
+ headers: headers,
35
+ debug_output: Deliveries.debug ? Deliveries.logger : nil
36
+ )
37
+ parsed_response = JSON.parse(response.body)
38
+ if (parsed_response['codErr']).zero?
39
+ if parsed_response['listaEtiquetas'].any?
40
+ parsed_response['listaEtiquetas'].each do |encoded_label|
41
+ decoded_labels << Base64.decode64(encoded_label).force_encoding('binary')
42
+ end
43
+ end
44
+ else
45
+ raise Deliveries::APIError.new(
46
+ parsed_response['desErr'],
47
+ parsed_response['codErr']
48
+ )
49
+ end
50
+ end
51
+
52
+ decoded_labels
53
+ end
54
+
55
+ private
56
+
57
+ def api_endpoint
58
+ if CorreosExpress.live?
59
+ CorreosExpress::LABELS_ENDPOINT_LIVE
60
+ else
61
+ CorreosExpress::LABELS_ENDPOINT_TEST
62
+ end
63
+ end
64
+ end
65
+ end
66
+ end
67
+ end
68
+ end
@@ -0,0 +1,60 @@
1
+ module Deliveries
2
+ module Couriers
3
+ module CorreosExpress
4
+ module Pickups
5
+ class Create
6
+ module Defaults
7
+ PARAMS = {
8
+ solicitante: '',
9
+ password: '',
10
+ canalEntrada: '',
11
+ refRecogida: '',
12
+ fechaRecogida: '', # ddmmyyyy
13
+ horaDesde1: '09:00',
14
+ horaDesde2: '',
15
+ horaHasta1: '17:00',
16
+ horaHasta2: '',
17
+ clienteRecogida: '',
18
+ codRemit: '',
19
+ nomRemit: '',
20
+ nifRemit: '',
21
+ dirRecog: '',
22
+ poblRecog: '',
23
+ cpRecog: '',
24
+ contRecog: '',
25
+ tlfnoRecog: '',
26
+ oTlfnRecog: '',
27
+ emailRecog: '',
28
+ observ: '',
29
+ tipoServ: '',
30
+ codDest: '',
31
+ nomDest: '',
32
+ nifDest: '',
33
+ dirDest: '',
34
+ pobDest: '',
35
+ cpDest: '',
36
+ paisDest: '',
37
+ cpiDest: '',
38
+ contactoDest: '',
39
+ tlfnoDest: '',
40
+ emailDest: '',
41
+ nEnvio: '',
42
+ refEnvio: '',
43
+ producto: '63',
44
+ kilos: '',
45
+ bultos: '',
46
+ volumen: '',
47
+ tipoPortes: '',
48
+ importReembol: '',
49
+ valDeclMerc: '',
50
+ infTec: '',
51
+ nSerie: '',
52
+ modelo: '',
53
+ latente: '0'
54
+ }.freeze
55
+ end
56
+ end
57
+ end
58
+ end
59
+ end
60
+ end
@@ -0,0 +1,95 @@
1
+ module Deliveries
2
+ module Couriers
3
+ module CorreosExpress
4
+ module Pickups
5
+ class Create
6
+ class FormatParams
7
+ attr_accessor :sender, :receiver, :parcels, :reference_code,
8
+ :pickup_date, :remarks, :time_interval
9
+
10
+ def initialize(sender:, receiver:, parcels:, reference_code:,
11
+ pickup_date:, remarks:, time_interval: nil)
12
+ self.sender = sender
13
+ self.receiver = receiver
14
+ self.parcels = parcels
15
+ self.reference_code = reference_code
16
+ self.pickup_date = pickup_date
17
+ self.remarks = remarks
18
+ self.time_interval = time_interval
19
+ end
20
+
21
+ def execute
22
+ postcode = format_postcode(sender.postcode, sender.country)
23
+ params = {
24
+ solicitante: CorreosExpress.config(:client_code),
25
+ refRecogida: reference_code,
26
+ fechaRecogida: pickup_date&.strftime('%d%m%Y') || '',
27
+ clienteRecogida: CorreosExpress.config(:pickup_receiver_code),
28
+ codRemit: '',
29
+ nomRemit: sender.name,
30
+ nifRemit: '',
31
+ dirRecog: sender.street,
32
+ poblRecog: sender.city,
33
+ cpRecog: postcode,
34
+ contRecog: sender.name,
35
+ tlfnoRecog: sender.phone,
36
+ emailRecog: sender.email,
37
+ codDest: CorreosExpress.config(:pickup_receiver_code),
38
+ nomDest: receiver.name,
39
+ dirDest: receiver.street,
40
+ pobDest: receiver.city,
41
+ cpDest: receiver.postcode,
42
+ paisDest: receiver.country,
43
+ contactoDest: receiver.name,
44
+ tlfnoDest: receiver.phone,
45
+ emailDest: receiver.email,
46
+ bultos: parcels.to_s
47
+ }
48
+
49
+ unless CorreosExpress.test?
50
+ custom_product = CorreosExpress.config("countries.#{sender.country.to_s.downcase}.product")
51
+ params[:producto] = custom_product if custom_product
52
+ end
53
+
54
+ defaults = Defaults::PARAMS
55
+
56
+ defaults = defaults.merge(params)
57
+
58
+ if time_interval
59
+ defaults[:horaDesde1] = format '%02d:00', time_interval.first
60
+ defaults[:horaHasta1] = format '%02d:00', time_interval.last
61
+ else
62
+ # Try to set cutoff time for the sender postal code.
63
+ begin
64
+ cutoff_time = CutoffTime.new(country: sender.country, postcode: postcode).execute
65
+ # Set only when cuttoff time is less than 19:00 (the default cutoff time in correos express)
66
+ if cutoff_time.to_i < 19
67
+ defaults[:horaHasta1] = cutoff_time
68
+
69
+ # Update start hour if the period if smaller than 2 hours
70
+ min_start_hour = cutoff_time.to_i - 2
71
+ defaults[:horaDesde1] = format('%02d:00', min_start_hour) if defaults[:horaDesde1].to_i > min_start_hour
72
+ end
73
+ rescue Deliveries::Error => e
74
+ Deliveries.logger&.error "Cannot obtain cutoff time: #{e.message}"
75
+ end
76
+ end
77
+
78
+ defaults.to_json
79
+ end
80
+
81
+ private
82
+
83
+ def format_postcode(postcode, country)
84
+ if country.to_sym.downcase == :pt
85
+ postcode&.split('-')&.first
86
+ else
87
+ postcode
88
+ end
89
+ end
90
+ end
91
+ end
92
+ end
93
+ end
94
+ end
95
+ end
@@ -0,0 +1,66 @@
1
+ require 'httparty'
2
+
3
+ module Deliveries
4
+ module Couriers
5
+ module CorreosExpress
6
+ module Pickups
7
+ class Create
8
+ include HTTParty
9
+
10
+ attr_accessor :params
11
+
12
+ def initialize(params:)
13
+ self.params = params
14
+ end
15
+
16
+ def execute
17
+ auth = {
18
+ username: CorreosExpress.config(:username),
19
+ password: CorreosExpress.config(:password)
20
+ }
21
+
22
+ response = self.class.post(
23
+ api_endpoint,
24
+ basic_auth: auth,
25
+ body: params,
26
+ headers: headers,
27
+ debug_output: Deliveries.debug ? Deliveries.logger : nil
28
+ )
29
+ raise ClientError, "Failed with status code #{response.code}" unless response.success?
30
+
31
+ parsed_response = JSON.parse(response.body, symbolize_names: true)
32
+ if parsed_response[:codigoRetorno]&.zero? && parsed_response[:numRecogida].present?
33
+ parsed_response[:numRecogida]
34
+ else
35
+ exception_class =
36
+ case parsed_response[:codigoRetorno]
37
+ when 105 then InvalidDateError
38
+ when 154 then InvalidTimeIntervalError
39
+ else APIError
40
+ end
41
+
42
+ raise exception_class.new(
43
+ parsed_response[:mensajeRetorno],
44
+ parsed_response[:codigoRetorno]
45
+ )
46
+ end
47
+ end
48
+
49
+ private
50
+
51
+ def api_endpoint
52
+ if CorreosExpress.live?
53
+ CorreosExpress::PICKUPS_ENDPOINT_LIVE
54
+ else
55
+ CorreosExpress::PICKUPS_ENDPOINT_TEST
56
+ end
57
+ end
58
+
59
+ def headers
60
+ { 'Content-Type' => 'application/json' }
61
+ end
62
+ end
63
+ end
64
+ end
65
+ end
66
+ end
@@ -0,0 +1,40 @@
1
+ module Deliveries
2
+ module Couriers
3
+ module CorreosExpress
4
+ module Pickups
5
+ class CutoffTime
6
+ class FormatParams
7
+ attr_accessor :country, :postcode
8
+
9
+ def initialize(country:, postcode:)
10
+ self.country = country
11
+ self.postcode = postcode
12
+ end
13
+
14
+ def execute
15
+ params = {
16
+ strCP: postcode,
17
+ strPais: country_code_to_id(country)
18
+ }
19
+
20
+ params.to_json
21
+ end
22
+
23
+ private
24
+
25
+ def country_code_to_id(country_code)
26
+ case country_code.to_sym.downcase
27
+ when :es
28
+ '34'
29
+ when :pt
30
+ '35'
31
+ else
32
+ raise Deliveries::Error, "Invalid country #{country_code}"
33
+ end
34
+ end
35
+ end
36
+ end
37
+ end
38
+ end
39
+ end
40
+ end
@@ -0,0 +1,61 @@
1
+ require 'httparty'
2
+
3
+ module Deliveries
4
+ module Couriers
5
+ module CorreosExpress
6
+ module Pickups
7
+ class CutoffTime
8
+ include HTTParty
9
+
10
+ attr_accessor :country, :postcode
11
+
12
+ def initialize(country:, postcode:)
13
+ self.country = country
14
+ self.postcode = postcode
15
+ end
16
+
17
+ def execute
18
+ auth = {
19
+ username: CorreosExpress.config(:username),
20
+ password: CorreosExpress.config(:password)
21
+ }
22
+
23
+ params = FormatParams.new(
24
+ country: country,
25
+ postcode: postcode
26
+ ).execute
27
+
28
+ response = self.class.post(
29
+ api_endpoint,
30
+ basic_auth: auth,
31
+ body: params,
32
+ headers: headers,
33
+ debug_output: Deliveries.debug ? Deliveries.logger : nil
34
+ )
35
+ raise Deliveries::Error unless response.success?
36
+
37
+ parsed_response = JSON.parse(response.body, symbolize_names: true)
38
+ if (parsed_response[:codError]).zero? && parsed_response[:horaCorte].present?
39
+ parsed_response[:horaCorte]
40
+ else
41
+ raise Deliveries::APIError.new(
42
+ parsed_response[:mensError],
43
+ parsed_response[:codError]
44
+ )
45
+ end
46
+ end
47
+
48
+ private
49
+
50
+ def api_endpoint
51
+ CorreosExpress::CUTOFF_TIME_ENDPOINT_LIVE
52
+ end
53
+
54
+ def headers
55
+ { 'Content-Type' => 'application/json' }
56
+ end
57
+ end
58
+ end
59
+ end
60
+ end
61
+ end