class Mfms::SMS

Attributes

account[RW]
cert[RW]
errors[R]
id[R]
login[RW]
message[RW]
password[RW]
phone[RW]
port[RW]
server[RW]
ssl[RW]
ssl_port[RW]
status[R]
subject[RW]

Public Class Methods

default_account() click to toggle source
# File lib/mfms/sms.rb, line 59
def self.default_account
  default_account = nil
  Array.wrap(class_variables).each do |account|
    if class_variable_get(account.to_s).has_key?(:default)
      default_account = account
      break
    end
  end
  default_account || raise(ArgumentError, 'One of the accounts should be specified by default')
end
new(data) click to toggle source
# File lib/mfms/sms.rb, line 13
def initialize(data)
  @phone = data.fetch(:phone, nil)
  @subject = data.fetch(:subject, nil)
  @message = data.fetch(:message, nil)
  @status = 'not-sent'
  account_name = data[:account]
  account_variable = if account_name.present?
                       var_name = "@@#{account_name}".to_sym
                       if self.class.class_variables.include?(var_name)
                         var_name
                       else
                         raise ArgumentError, "Account with name '#{account_name}' is not defined"
                       end
                     else
                       self.class.default_account
                     end
  account_settings = self.class.class_variable_get(account_variable)
  @login = account_settings[:login]
  @connector = account_settings[:connector]
  @password = account_settings[:password]
  @ssl = account_settings[:ssl]
  @ssl_port = account_settings[:ssl_port]
  @port = account_settings[:port]
  @cert = account_settings[:cert]
  @server = account_settings[:server]
  @translit = data.fetch(:translit, account_settings[:translit])
  @priority = data.fetch(:priority, account_settings[:priority])
  @errors = []
  validate!
end
settings=(settings=[]) click to toggle source
# File lib/mfms/sms.rb, line 44
def self.settings=(settings=[])
  settings.each do |setting|
    account = setting.keys.first
    account_settings = setting[account]
    account_settings[:cert] = init_cert_store(account_settings[:cert])
    account_settings[:ssl] = account_settings.fetch(:ssl, true)
    account_settings[:translit] = account_settings.fetch(:translit, false)
    account_settings[:additional_args] = account_settings.fetch(:additional_args, nil)
    account_settings[:priority] = account_settings.fetch(:priority, nil)
    if settings_valid?(account_settings)
      self.class_variable_set("@@#{account}", account_settings)
    end
  end
end
status(id) click to toggle source

> SMS status check response codes:

"ok"                           "Запрос успешно обработан"
"error-system"                 "Произошла системная ошибка"
"error-provider-id-unknown"    "Сообщение с таким идентификатором не найдено"
# File lib/mfms/sms.rb, line 109
def self.status(id)
  establish_connection.start do |http|
    request = Net::HTTP::Get.new(status_url id)
    response = http.request(request)
    body = response.body.split(';')
    return body[0], body[2] # code, status
  end
end

Private Class Methods

init_cert_store(cert) click to toggle source
# File lib/mfms/sms.rb, line 148
def self.init_cert_store(cert)
  raise ArgumentError, "Path to certificate should be defined for #{self}." if cert.nil?
  raise ArgumentError, "Certificate file '#{File.expand_path(cert)}' does not exist." unless File.exist?(cert)
  cert_store = OpenSSL::X509::Store.new
  cert_store.add_cert OpenSSL::X509::Certificate.new File.read(cert)
  cert_store
end
settings_valid?(settings) click to toggle source
# File lib/mfms/sms.rb, line 156
def self.settings_valid?(settings)
  [:login, :password, :server, :port, :ssl_port].each do |attr|
    if settings[attr].nil?
      raise ArgumentError, "#{attr.to_s.gsub(/_/,' ').capitalize} should be defined for #{self}."
    end
  end
  [:port, :ssl_port].each do |attr|
    unless settings[attr].instance_of?(Fixnum)
      raise ArgumentError,
            "#{attr.to_s.gsub(/_/,' ').capitalize} should contain only numbers. #{settings[attr].inspect} is given."
    end
  end
  true
end

Public Instance Methods

send() click to toggle source

> SMS send status codes:

"ok"                     "Сообщения приняты на отправку"
"error-system"           "При обработке данного сообщения произошла системная ошибка"
"error-address-format"   "Ошибка формата адреса"
"error-address-unknown"  "Отправка по данному направлению не разрешена"
"error-subject-format"   "Ошибка формата отправителя"
"error-subject-unknown"  "Данный отправителть не разрешен на нашей платформе"
# File lib/mfms/sms.rb, line 78
def send
  #return stubbed_send if (defined?(Rails) && !Rails.env.production?)
  establish_connection.start do |http|
    request = Net::HTTP::Get.new(send_url)
    response = http.request(request)
    body = response.body.split(';')
    if body[0] == 'ok'
      @status = 'sent'
      @id = body[2]
      true
    else
      @errors << body[0]
      false
    end
  end
end
update_status() click to toggle source
# File lib/mfms/sms.rb, line 118
def update_status
  return @status if @id.nil?
  code, status = self.class.status(@id)
  return code unless code == 'ok'
  @status = status
end
validate!() click to toggle source
# File lib/mfms/sms.rb, line 125
def validate!
  raise ArgumentError, "Phone should be assigned to #{self.class}." if @phone.nil?
  unless @phone =~ /^[0-9]{10,}$/
    raise ArgumentError, 'Phone number should contain only numbers. Minimum'+
                         "length is 10. #{@phone.inspect} is given."
  end
  raise ArgumentError, "Subject should be assigned to #{self.class}." if @subject.nil?
  raise ArgumentError, "Message should be assigned to #{self.class}." if @message.nil?
  if @priority && !%w(low normal high realtime).include?(@priority)
    raise ArgumentError, 'Priority is not valid.'
  end
end

Private Instance Methods

establish_connection() click to toggle source
# File lib/mfms/sms.rb, line 140
def establish_connection
  port = @ssl ? @ssl_port : @port
  http = Net::HTTP.new(@server, port)
  http.use_ssl = @ssl
  http.cert_store = @cert
  http
end
send_url() click to toggle source
# File lib/mfms/sms.rb, line 171
def send_url
  message = @translit ? Russian.translit(@message) : @message
  url = "/revoup/#{@connector}/send?login=#{@login}&password=#{@password}&" +
      "subject[0]=#{@subject}&address[0]=#{@phone}&text[0]=#{URI.encode(message)}"
  url += "&priority=#{@priority}" if @priority
  url
end
status_url(msg_id) click to toggle source
# File lib/mfms/sms.rb, line 179
def status_url(msg_id)
  "/revoup/#{@connector}/status?login=#{@login}&password=#{@password}&providerId[0]=#{msg_id}"
end