Module: Magpie::Utils

Included in:
Alipay, Chinabank, Snake, Tenpay
Defined in:
lib/magpie/utils.rb

Instance Method Summary collapse

Instance Method Details

#build_xml(h = { }) ⇒ Object



29
30
31
32
33
34
# File 'lib/magpie/utils.rb', line 29

def build_xml(h = { })
  "<?xml version=\"1.0\" encoding=\"UTF-8\"?>" +
    "<result>" +
    hash_to_xml(h) +
    "</result>"
end

#dig(env) ⇒ Object



11
12
13
14
15
16
17
18
19
# File 'lib/magpie/utils.rb', line 11

def dig(env)
  status, header, body = @app.call env
  req = Rack::Request.new env
  doc = send_req_to @pay_gateway, req
  red_text = (doc/@red_xpath).inner_text
  red_text = (doc/@error_xpath).inner_text if red_text.blank? and @error_xpath
  red_text = Iconv.iconv("UTF-8//IGNORE","GBK//IGNORE", red_text).to_s
  return status, header, body, req, red_text
end

#get_notify_res(am) ⇒ Object



63
64
65
66
67
68
69
70
71
72
73
74
# File 'lib/magpie/utils.rb', line 63

def get_notify_res(am)
  case am
  when AlipayModel, ChinabankModel
    notify_res = send_notify("POST", am.notify_url, am.notify).gsub(/<[^>]*>|<\/[^>]*> |\s/m, '')
    method = "POST"
  when TenpayModel
    notify_res = send_notify("GET", am.notify_url, am.notify_string).gsub(/<[^>]*>|<\/[^>]*>|\s/m, '')
    method = "GET"
  end
  log_notify(method, am.notify_url, am.notify, notify_res)
  notify_res
end

#get_query(url, q_string) ⇒ Object



93
94
95
96
97
# File 'lib/magpie/utils.rb', line 93

def get_query(url, q_string)
  url = URI.parse(url + "?" + q_string)
  req = Net::HTTP::Get.new("#{url.path}?#{url.query}")
  res = start_http(url, req)
end

#get_xml_body(env, am, red_text) ⇒ Object



51
52
53
54
55
56
57
58
59
60
61
# File 'lib/magpie/utils.rb', line 51

def get_xml_body(env, am, red_text)
  if red_text.blank?
    notify_res = get_notify_res(am)
    xml_body = build_xml(:payment_success => "Yes",  :business => notify_res )
  else
    am.valid?
    xml_body = build_xml(:payment_success => "No", :errors => am.errors.merge(:final => red_text))
    log_errors(am.errors.merge(:final => red_text))
  end
  xml_body
end

#hash_to_xml(h = { }) ⇒ Object



36
37
38
39
40
41
42
43
44
45
46
47
48
49
# File 'lib/magpie/utils.rb', line 36

def hash_to_xml(h = { })
  h.inject(""){ |xml, (k, v)|
    case v
    when Hash, String
      xml << "<#{k}>"
      xml << (Hash === v ? hash_to_xml(v) : v)
      xml << "</#{k}>"
    when Array
      v.each{ |vv| xml << hash_to_xml(k => vv)}
      xml
    end

  }
end

#log_errors(errors = { }) ⇒ Object



80
81
82
# File 'lib/magpie/utils.rb', line 80

def log_errors(errors = { })
  Magpie.logger.info(errors.map{ |kv| "%s: %s" % kv }.join("\n"))
end

#log_notify(method, notify_url, notify_params, notify_res) ⇒ Object



76
77
78
# File 'lib/magpie/utils.rb', line 76

def log_notify(method, notify_url, notify_params, notify_res)
  Magpie.logger.info(FORMAT_NOTIFY % [method, notify_url, Time.now.strftime("%d/%b/%Y %H:%M:%S"), notify_params.inspect, notify_res])
end

#post_query(url, params) ⇒ Object



99
100
101
102
103
104
# File 'lib/magpie/utils.rb', line 99

def post_query(url, params)
  url = URI.parse url
  req = Net::HTTP::Post.new(url.path)
  req.set_form_data params
  res = start_http(url, req)
end

#send_notify(method, url, notify) ⇒ String

向商户系统发送通知

Parameters:

  • url是商户系统用来接收通知的url, (String, String, Hash)

    notify是支付平台发过来的参数

Returns:

  • (String)

    如果有异常需要你确认url是否有效



109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
# File 'lib/magpie/utils.rb', line 109

def send_notify(method, url, notify)
  times = [4, 6, 2]
  Rubber.try(3){|i|
    timeout(times[3-i]) do
      res = case method.to_s.upcase
            when "GET"; get_query(url, notify)
            when "POST"; post_query(url, notify)
            end
      case res
      when Net::HTTPSuccess, Net::HTTPRedirection; res.body
      else
        raise "#{res.class}@#{res.code}"
      end
    end
  }
rescue Exception => e
  "发送通知时出现异常#{e}, 请确认#{url}在你的商户系统中可用, 比如#{url}是否可以#{method.upcase}方式接收其他应用的请求"
end

#send_req_to(gw, req) ⇒ Object



21
22
23
24
25
26
27
# File 'lib/magpie/utils.rb', line 21

def send_req_to(gw, req)
  text = case req.request_method
         when "GET"; get_query(gw, req.query_string).body
         when "POST"; post_query(gw, req.params).body
         end
  doc = Hpricot text
end

#start_http(url, req) ⇒ Object



84
85
86
87
88
89
90
91
# File 'lib/magpie/utils.rb', line 84

def start_http(url, req)
  http = Net::HTTP.new(url.host, url.port)
  if url.scheme == "https"
    http.use_ssl = true
    http.verify_mode = OpenSSL::SSL::VERIFY_NONE
  end
  http.start{ |hp| hp.request req }
end