sms_broker 1.0.0 → 1.0.2

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
  SHA1:
3
- metadata.gz: 0b28741c2cf164576894b6b876444ae070f7303f
4
- data.tar.gz: f0549e93ac7bbe3b87fff76d101a6f06152c192a
3
+ metadata.gz: ed1f6bc1988ca3ab9a96cac009892365ddcf39ef
4
+ data.tar.gz: c61521552f75df630c6fd9bea3829cc590bffa6f
5
5
  SHA512:
6
- metadata.gz: fcd96dffdafb77800af5a3798be97beff7ec3a921fcdbc061c0ad1f069f5ea127a976e0dace58624742c5ad510b400fadd866a3d6eba884d22a179d7577ae3c2
7
- data.tar.gz: c6b9c850c13c0c43e2cc324b12fb6bf884bda46a3f0ab709a6ca13a06df0412a82341fd7e4e87d07aa0d47dfd100352906f9a685f6bf9a464c342a1c0cdccf10
6
+ metadata.gz: f4b7658d1d99dfa94ef72292f50f813d17ab9e41640c6b351c65b4b71b1a5c2780422923ca00ffe297c44cef357f5a2bb745df944c349edd6e9d3a2dc12b2653
7
+ data.tar.gz: 8aba81f06d37acbfabb28afd7c4ae3a28b452420c3849b69784573244ee1884c31dfda212c6d583fa3d32a620431f447e48ed57906f68ed870f000dce6bcd4a1
data/.rubocop.yml ADDED
@@ -0,0 +1,16 @@
1
+ Style/MultilineMethodCallIndentation:
2
+ Enabled: false
3
+
4
+ Style/FrozenStringLiteralComment:
5
+ Enabled: false
6
+
7
+ AllCops:
8
+ TargetRubyVersion: 2.3
9
+ DisplayCopNames: true
10
+ Exclude:
11
+ - 'vendor/**/*'
12
+ - 'spec/support/*.rb'
13
+ - '*.gemspec'
14
+
15
+ Documentation:
16
+ Enabled: false
data/.travis.yml ADDED
@@ -0,0 +1,3 @@
1
+ language: ruby
2
+ rvm:
3
+ - 2.3.0
data/Gemfile CHANGED
@@ -6,4 +6,5 @@ group :test do
6
6
  gem 'codeclimate-test-reporter'
7
7
  gem 'simplecov', require: false
8
8
  gem 'rack-test'
9
+ gem 'vcr'
9
10
  end
data/Rakefile CHANGED
@@ -1,5 +1,5 @@
1
1
  require 'bundler/gem_tasks'
2
2
  require 'rspec/core/rake_task'
3
3
 
4
- task :default => :test
4
+ task default: :test
5
5
  RSpec::Core::RakeTask.new(:test)
@@ -1,24 +1,23 @@
1
1
  module SmsBroker
2
2
  module Client
3
-
4
3
  class Base
5
-
6
4
  attr_reader :name,
7
5
  :client,
8
- :options,
9
6
  :sender_id,
10
7
  :phone_number
11
8
 
12
- def initialize(name, client)
9
+ def initialize(name, client, options = {})
13
10
  @name = name
14
11
  @client = client
12
+ @sender_id = options[:sender_id]
13
+ @phone_number = options[:phone_number]
15
14
  end
16
15
 
17
- def serialize_number(number)
18
- "#{number}".delete("+")
19
- end
16
+ def serialize_to_number(number)
17
+ return number if number.start_with?('+')
20
18
 
19
+ "+#{number}"
20
+ end
21
21
  end
22
-
23
22
  end
24
23
  end
@@ -1,27 +1,18 @@
1
1
  module SmsBroker
2
2
  module Client
3
-
4
3
  class Nexmo < Base
5
-
6
4
  def initialize(options)
7
- nexmo_options = options.dup
8
-
9
- auth_options = {
10
- key: nexmo_options.delete(:key),
11
- secret: nexmo_options.delete(:secret)
12
- }
5
+ client = \
6
+ ::Nexmo::Client.new(key: options[:key], secret: options[:secret])
13
7
 
14
- @sender_id = nexmo_options.delete(:sender_id)
15
- @phone_number = nexmo_options.delete(:phone_number)
16
-
17
- super(:nexmo, ::Nexmo::Client.new(auth_options))
8
+ super :nexmo, client, options
18
9
  end
19
10
 
20
11
  def send_message(message)
21
12
  response = client.send_message \
22
13
  text: message[:text],
23
- from: serialize_number(message[:from]),
24
- to: serialize_number(message[:to])
14
+ from: message[:from],
15
+ to: serialize_to_number(message[:to])
25
16
 
26
17
  if success_response?(response)
27
18
  Response::NexmoSuccess.new(response)
@@ -35,10 +26,8 @@ module SmsBroker
35
26
  def success_response?(response)
36
27
  # just looking for the first message,
37
28
  # right now only one message per call
38
- response['messages'].length > 0 && response['messages'][0]['status'] == '0'
29
+ !response['messages'].empty? && response['messages'][0]['status'] == '0'
39
30
  end
40
-
41
31
  end
42
-
43
32
  end
44
33
  end
@@ -1,9 +1,7 @@
1
1
  module SmsBroker
2
2
  module Client
3
3
  module Response
4
-
5
4
  class Error
6
-
7
5
  attr_reader :service,
8
6
  :response,
9
7
  :serialized
@@ -19,11 +17,9 @@ module SmsBroker
19
17
  end
20
18
 
21
19
  def invalid_sender_id?
22
- (@serialized[:errors]['sender_id'] || {}).include?('is invalid')
20
+ (@serialized[:errors]['sender_id'] || []).include?('is invalid')
23
21
  end
24
-
25
22
  end
26
-
27
23
  end
28
24
  end
29
25
  end
@@ -1,10 +1,8 @@
1
1
  module SmsBroker
2
2
  module Client
3
3
  module Response
4
-
5
4
  class NexmoError < Error
6
-
7
- SENDER_ID_NOT_SUPPORTED = '15'
5
+ SENDER_ID_NOT_SUPPORTED = '15'.freeze
8
6
 
9
7
  def initialize(nexmo_response)
10
8
  super :nexmo, nexmo_response, serialize_error_response(nexmo_response)
@@ -27,9 +25,7 @@ module SmsBroker
27
25
 
28
26
  errors
29
27
  end
30
-
31
28
  end
32
-
33
29
  end
34
30
  end
35
31
  end
@@ -1,9 +1,7 @@
1
1
  module SmsBroker
2
2
  module Client
3
3
  module Response
4
-
5
4
  class NexmoSuccess < Success
6
-
7
5
  def initialize(nexmo_response)
8
6
  super :nexmo, nexmo_response, serialize(nexmo_response)
9
7
  end
@@ -17,21 +15,23 @@ module SmsBroker
17
15
  to: single_response['to'],
18
16
  from: single_response['from'],
19
17
  message_id: single_response['message-id'],
20
- raw: {
21
- to: single_response['to'],
22
- from: single_response['from'],
23
- status: single_response['status'],
24
- network: single_response['network'],
25
- message_id: single_response['message-id'],
26
- client_ref: single_response['client-ref'],
27
- remaining_balance: single_response['remaining-balance'],
28
- message_price: single_response['message-price']
29
- }
18
+ raw: response_to_hash(single_response)
30
19
  }
31
20
  end
32
21
 
33
- end
22
+ def response_to_hash(response)
23
+ attributes = %w(
24
+ to from status network message-id client-ref
25
+ remaining-balance message-price
26
+ )
34
27
 
28
+ {}.tap do |hash|
29
+ attributes.each do |attr|
30
+ hash[attr.tr('-', '_').to_sym] = response[attr]
31
+ end
32
+ end
33
+ end
34
+ end
35
35
  end
36
36
  end
37
37
  end
@@ -1,9 +1,7 @@
1
1
  module SmsBroker
2
2
  module Client
3
3
  module Response
4
-
5
4
  class Success
6
-
7
5
  attr_reader :raw,
8
6
  :service,
9
7
  :serialized
@@ -29,9 +27,7 @@ module SmsBroker
29
27
  def message_id
30
28
  serialized[:message_id]
31
29
  end
32
-
33
30
  end
34
-
35
31
  end
36
32
  end
37
33
  end
@@ -1,10 +1,8 @@
1
1
  module SmsBroker
2
2
  module Client
3
3
  module Response
4
-
5
4
  class TwilioError < Error
6
-
7
- SENDER_ID_NOT_SUPPORTED = '21212'
5
+ SENDER_ID_NOT_SUPPORTED = '21212'.freeze
8
6
 
9
7
  def initialize(twilio_response)
10
8
  super :twilio, twilio_response, serialize(twilio_response)
@@ -22,10 +20,10 @@ module SmsBroker
22
20
 
23
21
  def serialize_response_error(response)
24
22
  errors = {
25
- "#{response.error_code}" => [response.error_message]
23
+ response.error_code.to_s => [response.error_message]
26
24
  }
27
25
 
28
- if "#{response.error_code}" == SENDER_ID_NOT_SUPPORTED
26
+ if response.error_code.to_s == SENDER_ID_NOT_SUPPORTED
29
27
  errors['sender_id'] = ['is invalid']
30
28
  end
31
29
 
@@ -34,18 +32,16 @@ module SmsBroker
34
32
 
35
33
  def serialize_exeception_errors(exception)
36
34
  errors = {
37
- "#{exception.code}" => [exception.message]
35
+ exception.code.to_s => [exception.message]
38
36
  }
39
37
 
40
- if "#{exception.code}" == SENDER_ID_NOT_SUPPORTED
38
+ if exception.code.to_s == SENDER_ID_NOT_SUPPORTED
41
39
  errors['sender_id'] = ['is invalid']
42
40
  end
43
41
 
44
42
  errors
45
43
  end
46
-
47
44
  end
48
-
49
45
  end
50
46
  end
51
47
  end
@@ -1,9 +1,7 @@
1
1
  module SmsBroker
2
2
  module Client
3
3
  module Response
4
-
5
4
  class TwilioSuccess < Success
6
-
7
5
  def initialize(twilio_response)
8
6
  super :twilio, twilio_response, serialize(twilio_response)
9
7
  end
@@ -15,27 +13,24 @@ module SmsBroker
15
13
  to: response.to,
16
14
  from: response.from,
17
15
  message_id: response.sid,
18
- raw: {
19
- to: response.to,
20
- sid: response.sid,
21
- uri: response.uri,
22
- from: response.from,
23
- body: response.body,
24
- price: response.price,
25
- status: response.status,
26
- price_unit: response.price_unit,
27
- error_code: response.error_code,
28
- account_sid: response.account_sid,
29
- api_version: response.api_version,
30
- date_created: response.date_created,
31
- error_message: response.error_message,
32
- messaging_service_sid: response.messaging_service_sid
33
- }
16
+ raw: response_to_hash(response)
34
17
  }
35
18
  end
36
19
 
37
- end
20
+ def response_to_hash(response)
21
+ attributes = %i(
22
+ to sid uri from body price status price_unit error_code
23
+ account_sid api_version date_created error_message
24
+ messaging_service_sid
25
+ )
38
26
 
27
+ {}.tap do |hash|
28
+ attributes.each do |attr|
29
+ hash[attr] = response.send(attr)
30
+ end
31
+ end
32
+ end
33
+ end
39
34
  end
40
35
  end
41
36
  end
@@ -1,49 +1,34 @@
1
1
  module SmsBroker
2
2
  module Client
3
-
4
3
  class Twilio < Base
5
-
6
4
  def initialize(options)
7
- twilio_options = options.dup
8
-
9
- auth_options = {
10
- account_sid: twilio_options.delete(:account_sid),
11
- auth_token: twilio_options.delete(:auth_token)
12
- }
5
+ client = ::Twilio::REST::Client.new(
6
+ options[:account_sid],
7
+ options[:auth_token]
8
+ )
13
9
 
14
- @sender_id = twilio_options.delete(:sender_id)
15
- @phone_number = twilio_options.delete(:phone_number)
16
-
17
- super \
18
- :twilio,
19
- ::Twilio::REST::Client.new(auth_options[:account_sid], auth_options[:auth_token])
10
+ super :Twilio, client, options
20
11
  end
21
12
 
22
13
  def send_message(message)
23
- begin
24
- response = client.messages.create \
25
- body: message[:text],
26
- from: serialize_number(message[:from]),
27
- to: serialize_number(message[:to])
14
+ response = client.messages.create \
15
+ body: message[:text],
16
+ from: message[:from],
17
+ to: serialize_to_number(message[:to])
28
18
 
29
- if failed_response?(response)
30
- Response::TwilioError.new(response)
31
- else
32
- Response::TwilioSuccess.new(response)
33
- end
19
+ return Response::TwilioSuccess.new(response) \
20
+ if success_response?(response)
34
21
 
35
- rescue ::Twilio::REST::RequestError => exception
36
- Response::TwilioError.new(exception)
37
- end
22
+ Response::TwilioError.new(response)
23
+ rescue ::Twilio::REST::RequestError => exception
24
+ Response::TwilioError.new(exception)
38
25
  end
39
26
 
40
27
  private
41
28
 
42
- def failed_response?(response)
43
- ['undelivered', 'failed'].include?(response.status)
29
+ def success_response?(response)
30
+ !%w(undelivered failed).include?(response.status)
44
31
  end
45
-
46
32
  end
47
-
48
33
  end
49
34
  end
@@ -2,55 +2,51 @@ require 'sms_broker/setup'
2
2
  require 'sms_broker/exceptions/invalid_setup'
3
3
 
4
4
  module SmsBroker
5
-
6
5
  module Configuration
6
+ extend self
7
7
 
8
- @@configuration = nil
8
+ @configuration = nil
9
9
 
10
10
  def default_service
11
11
  configuration[:default_service]
12
12
  end
13
13
 
14
14
  def clear_setup
15
- @@configuration = nil
15
+ @configuration = nil
16
16
  end
17
17
 
18
18
  def configuration
19
19
  exception = \
20
20
  Exceptions::InvalidSetup.new('setup does not exists')
21
21
 
22
- @@configuration || (raise exception)
22
+ @configuration || (raise exception)
23
23
  end
24
24
 
25
- def setup(&block)
25
+ def setup
26
26
  setup = Setup.new
27
27
  yield setup if block_given?
28
28
 
29
- @@configuration = setup.options
29
+ @configuration = setup.options
30
30
 
31
31
  setup
32
32
  end
33
33
 
34
- def setup!(&block)
34
+ def setup!
35
35
  setup = Setup.new
36
36
  yield setup if block_given?
37
37
 
38
38
  unless setup.valid?
39
39
  exception = \
40
- Exceptions::InvalidSetup.new('setup is invalid, check exception.errors')
40
+ Exceptions::InvalidSetup.new("setup is invalid, #{setup.errors}")
41
41
 
42
42
  exception.errors = setup.errors
43
43
 
44
44
  raise exception
45
45
  end
46
46
 
47
- @@configuration = setup.options
47
+ @configuration = setup.options
48
48
 
49
49
  setup
50
50
  end
51
-
52
- extend self
53
-
54
51
  end
55
-
56
52
  end
@@ -1,9 +1,6 @@
1
1
  module SmsBroker
2
2
  module Exceptions
3
-
4
3
  class InvalidService < StandardError
5
-
6
4
  end
7
-
8
5
  end
9
6
  end
@@ -1,11 +1,7 @@
1
1
  module SmsBroker
2
2
  module Exceptions
3
-
4
3
  class InvalidSetup < StandardError
5
-
6
4
  attr_accessor :errors
7
-
8
5
  end
9
-
10
6
  end
11
7
  end
@@ -1,7 +1,5 @@
1
1
  module SmsBroker
2
-
3
2
  class MessageSender
4
-
5
3
  attr_reader :client,
6
4
  :errors
7
5
 
@@ -28,7 +26,7 @@ module SmsBroker
28
26
 
29
27
  response = client.send_message(build_message)
30
28
 
31
- if should_try_again_with_phone_number?(response)
29
+ if should_try_with_phone_number?(response)
32
30
  return client.send_message(build_message(:phone_number))
33
31
  end
34
32
 
@@ -56,26 +54,27 @@ module SmsBroker
56
54
  private
57
55
 
58
56
  def build_message(from = :sender_id)
59
- sender = \
60
- if client.sender_id && from == :sender_id
61
- client.sender_id
62
- else
63
- client.phone_number
64
- end
65
-
66
57
  {
67
58
  text: @message_text,
68
- from: sender,
59
+ from: get_sender(from),
69
60
  to: @message_to
70
61
  }
71
62
  end
72
63
 
73
- def should_try_again_with_phone_number?(response)
64
+ def get_sender(from)
65
+ if client.sender_id && from == :sender_id
66
+ client.sender_id
67
+ else
68
+ return client.phone_number if client.phone_number.start_with?('+')
69
+
70
+ "+#{client.phone_number}"
71
+ end
72
+ end
73
+
74
+ def should_try_with_phone_number?(response)
74
75
  response.is_a?(Client::Response::Error) &&
75
76
  response.invalid_sender_id? &&
76
- !!client.sender_id
77
+ client.sender_id
77
78
  end
78
-
79
79
  end
80
-
81
80
  end
@@ -1,27 +1,23 @@
1
1
  require 'sms_broker/message_sender'
2
-
3
2
  require 'sms_broker/client/base'
4
3
  require 'sms_broker/client/nexmo'
5
4
  require 'sms_broker/client/twilio'
6
-
7
5
  require 'sms_broker/exceptions/invalid_service'
8
6
 
9
7
  module SmsBroker
10
-
11
8
  CLIENTS = {
12
- nexmo: Client::Nexmo,
9
+ nexmo: Client::Nexmo,
13
10
  twilio: Client::Twilio
14
- }
11
+ }.freeze
15
12
 
16
13
  class Service
17
-
18
14
  def self.get(name)
19
15
  options = service_configuration(name)
20
16
 
21
17
  result = Service.validate(name, options)
22
18
 
23
19
  unless result.valid?
24
- raise Exceptions::InvalidService, { name.to_sym => result.errors }
20
+ raise Exceptions::InvalidService, name.to_sym => result.errors
25
21
  end
26
22
 
27
23
  new CLIENTS[name.to_sym].new(options)
@@ -44,7 +40,5 @@ module SmsBroker
44
40
  def message(message)
45
41
  MessageSender.new(client).message(message)
46
42
  end
47
-
48
43
  end
49
-
50
44
  end
@@ -1,24 +1,22 @@
1
1
  module SmsBroker
2
-
3
2
  class Setup
4
-
5
3
  attr_reader :options,
6
4
  :errors
7
5
 
8
6
  def self.service_validation_schemas
9
7
  {
10
- nexmo: Compel.hash.keys({
8
+ nexmo: Compel.hash.keys(
11
9
  key: Compel.string.required,
12
10
  secret: Compel.string.required,
13
11
  sender_id: Compel.string,
14
12
  phone_number: Compel.string.required
15
- }),
16
- twilio: Compel.hash.keys({
13
+ ),
14
+ twilio: Compel.hash.keys(
17
15
  sender_id: Compel.string,
18
16
  auth_token: Compel.string.required,
19
17
  account_sid: Compel.string.required,
20
18
  phone_number: Compel.string.required
21
- })
19
+ )
22
20
  }
23
21
  end
24
22
 
@@ -48,10 +46,10 @@ module SmsBroker
48
46
  end
49
47
 
50
48
  def compel_validation_schema(services_list = [])
51
- not_all_services_setup = Proc.new do |services_setups|
52
- services_list.all?{ |service|
49
+ not_all_services_setup = proc do |services_setups|
50
+ services_list.all? do |service|
53
51
  services_setups.keys.include?(service.to_sym)
54
- }
52
+ end
55
53
  end
56
54
 
57
55
  services_setups_schema = \
@@ -66,7 +64,7 @@ module SmsBroker
66
64
  end
67
65
 
68
66
  def method_missing(method, args, &block)
69
- service = "#{method}".split('_setup')[0].dup
67
+ service = method.to_s.split('_setup')[0].dup
70
68
 
71
69
  if @options[:services].include?(service)
72
70
  @options[:services_setups][service.to_sym] = args
@@ -76,7 +74,5 @@ module SmsBroker
76
74
  super
77
75
  end
78
76
  end
79
-
80
77
  end
81
-
82
78
  end
@@ -1,5 +1,3 @@
1
1
  module SmsBroker
2
-
3
- VERSION = '1.0.0'
4
-
2
+ VERSION = '1.0.2'.freeze
5
3
  end
data/lib/sms_broker.rb CHANGED
@@ -1,17 +1,16 @@
1
1
  require 'nexmo'
2
2
  require 'compel'
3
3
  require 'twilio-ruby'
4
-
5
4
  require 'sms_broker/client/response/error'
6
5
  require 'sms_broker/client/response/success'
7
-
8
6
  require 'sms_broker/configuration'
9
7
  require 'sms_broker/service'
10
8
 
11
9
  module SmsBroker
12
-
13
10
  extend Configuration
14
11
 
12
+ module_function
13
+
15
14
  def service(name = default_service)
16
15
  Service.get(name)
17
16
  end
@@ -19,7 +18,4 @@ module SmsBroker
19
18
  def message(body)
20
19
  service.message(body)
21
20
  end
22
-
23
- extend self
24
-
25
21
  end