diff --git a/app/models/avatar.rb b/app/models/avatar.rb index 486c3fedd..14dfe51d9 100644 --- a/app/models/avatar.rb +++ b/app/models/avatar.rb @@ -22,7 +22,6 @@ add an avatar based on auto detection (email address) # return if we run import mode return if Setting.get('import_mode') - return if !data[:url] return if data[:url].empty? @@ -116,7 +115,13 @@ add a avatar end # fetch image - response = UserAgent.request( data[:url] ) + response = UserAgent.get( + data[:url], + { + :open_timeout => 4, + :read_timeout => 6, + }, + ) if !response.success? #puts "WARNING: Can't fetch '#{self.image_source}' (maybe no avatar available), http code: #{response.code.to_s}" #raise "Can't fetch '#{self.image_source}', http code: #{response.code.to_s}" diff --git a/lib/geo_ip/zammad_geo_ip.rb b/lib/geo_ip/zammad_geo_ip.rb index e878f1c10..3c7cce1ff 100644 --- a/lib/geo_ip/zammad_geo_ip.rb +++ b/lib/geo_ip/zammad_geo_ip.rb @@ -15,10 +15,9 @@ class GeoIp::ZammadGeoIp url = "/lookup?ip=#{CGI::escape address}" data = {} begin - response = UserAgent.request( + response = UserAgent.get( "#{host}#{url}", { - :method => 'get', :open_timeout => 2, :read_timeout => 4, }, diff --git a/lib/geo_location/gmaps.rb b/lib/geo_location/gmaps.rb index 4d09f3f81..2f125c7e9 100644 --- a/lib/geo_location/gmaps.rb +++ b/lib/geo_location/gmaps.rb @@ -4,7 +4,7 @@ class GeoLocation::Gmaps def self.geocode(address) url = "http://maps.googleapis.com/maps/api/geocode/json?address=#{CGI::escape address}&sensor=true" - response = UserAgent.request(url) + response = UserAgent.get(url) return if !response.success? result = JSON.parse( response.body ) @@ -20,7 +20,7 @@ class GeoLocation::Gmaps def self.reverse_geocode(lat,lng) url = "http://maps.googleapis.com/maps/api/geocode/json?latlng=#{lat},#{lng}&sensor=true" - response = UserAgent.request(url) + response = UserAgent.get(url) return if !response.success? result = JSON.parse( response.body ) diff --git a/lib/import/otrs2.rb b/lib/import/otrs2.rb index f88497f8f..e96e632a6 100644 --- a/lib/import/otrs2.rb +++ b/lib/import/otrs2.rb @@ -53,11 +53,13 @@ module Import::OTRS2 def self.request(part) url = Setting.get('import_otrs_endpoint') + part + ';Key=' + Setting.get('import_otrs_endpoint_key') puts 'GET: ' + url - response = UserAgent.request( + response = UserAgent.get( url, { - :user => Setting.get('import_otrs_user'), - :password => Setting.get('import_otrs_password'), + :open_timeout => 6, + :read_timeout => 60, + :user => Setting.get('import_otrs_user'), + :password => Setting.get('import_otrs_password'), }, ) if !response.success? @@ -85,13 +87,14 @@ module Import::OTRS2 end data['Key'] = Setting.get('import_otrs_endpoint_key') puts 'POST: ' + url - response = UserAgent.request( + response = UserAgent.post( url, + data, { - :method => 'post', - :data => data, - :user => Setting.get('import_otrs_user'), - :password => Setting.get('import_otrs_password'), + :open_timeout => 6, + :read_timeout => 60, + :user => Setting.get('import_otrs_user'), + :password => Setting.get('import_otrs_password'), }, ) if !response.success? diff --git a/lib/user_agent.rb b/lib/user_agent.rb index d9598a6cc..13d0c99ad 100644 --- a/lib/user_agent.rb +++ b/lib/user_agent.rb @@ -9,28 +9,13 @@ class UserAgent =begin -http/https/ftp calls +get http/https calls - result = UserAgent.request( 'ftp://host/some_dir/some_file.bin' ) + result = UserAgent.get( 'http://host/some_dir/some_file?param1=123' ) - result = UserAgent.request( 'http://host/some_dir/some_file.bin' ) - - result = UserAgent.request( 'https://host/some_dir/some_file.bin' ) - - # post request - result = UserAgent.request( - 'http://host/some_dir/some_file.bin', - { - :method => 'post', - :data => { :param1 => 123 }, - }, - ) - - # get request - result = UserAgent.request( + result = UserAgent.get( 'http://host/some_dir/some_file?param1=123', { - :method => 'get', :open_timeout => 2, :read_timeout => 4, }, @@ -42,6 +27,190 @@ returns =end + def self.get(url, options = {}, count = 10) + uri = URI.parse(url) + http = get_http(uri, options) + + # prepare request + request = Net::HTTP::Get.new( uri, {'User-Agent' => 'Zammad User Agent'} ) + + # http basic auth (if needed) + request = set_basic_auth(request, options) + + # start http call + begin + response = http.request(request) + return process(response, uri, count, options) + rescue Exception => e + return Result.new( + :error => e.inspect, + :success => false, + :code => 0, + ) + end + end + +=begin + +post http/https calls + + result = UserAgent.post( + 'http://host/some_dir/some_file', + { + :param1 => 1, + :param2 => 2, + }, + { + :open_timeout => 2, + :read_timeout => 4, + }, + ) + +returns + + result # result object + +=end + + def self.post(url, params = {}, options = {}, count = 10) + uri = URI.parse(url) + http = get_http(uri, options) + + # prepare request + request = Net::HTTP::Post.new( uri, {'User-Agent' => 'Zammad User Agent'} ) + + # set params + request.set_form_data( params ) + + # http basic auth (if needed) + request = set_basic_auth(request, options) + + # start http call + begin + response = http.request(request) + return process(response, uri, count, options) + rescue Exception => e + return Result.new( + :error => e.inspect, + :success => false, + :code => 0, + ) + end + end + +=begin + +put http/https calls + + result = UserAgent.put( + 'http://host/some_dir/some_file', + { + :param1 => 1, + :param2 => 2, + }, + { + :open_timeout => 2, + :read_timeout => 4, + }, + ) + +returns + + result # result object + +=end + + def self.put(url, params = {}, options = {}, count = 10) + uri = URI.parse(url) + http = get_http(uri, options) + + # prepare request + request = Net::HTTP::Put.new( uri, {'User-Agent' => 'Zammad User Agent'} ) + + # set params + request.set_form_data( params ) + + # http basic auth (if needed) + request = set_basic_auth(request, options) + + # start http call + begin + response = http.request(request) + return process(response, uri, count, options) + rescue Exception => e + return Result.new( + :error => e.inspect, + :success => false, + :code => 0, + ) + end + end + +=begin + +delete http/https calls + + result = UserAgent.delete( + 'http://host/some_dir/some_file', + { + :open_timeout => 2, + :read_timeout => 4, + }, + ) + +returns + + result # result object + +=end + + def self.delete(url, options = {}, count = 10) + uri = URI.parse(url) + http = get_http(uri, options) + + # prepare request + request = Net::HTTP::Delete.new( uri, {'User-Agent' => 'Zammad User Agent'} ) + + # http basic auth (if needed) + request = set_basic_auth(request, options) + + # start http call + begin + response = http.request(request) + return process(response, uri, count, options) + rescue Exception => e + return Result.new( + :error => e.inspect, + :success => false, + :code => 0, + ) + end + end + +=begin + +perform get http/https/ftp calls + + result = UserAgent.request( 'ftp://host/some_dir/some_file.bin' ) + + result = UserAgent.request( 'http://host/some_dir/some_file.bin' ) + + result = UserAgent.request( 'https://host/some_dir/some_file.bin' ) + + # get request + result = UserAgent.request( + 'http://host/some_dir/some_file?param1=123', + { + :open_timeout => 2, + :read_timeout => 4, + }, + ) + +returns + + result # result object + +=end def self.request(url, options = {}) @@ -50,18 +219,17 @@ returns when /ftp/ ftp(uri, options) when /http|https/ - http(uri, options, 10) + get( url, options ) end end private - def self.http(uri, options, count) - + def self.get_http(uri, options) http = Net::HTTP.new(uri.host, uri.port) - http.open_timeout = options[:open_timeout] || 8 - http.read_timeout = options[:read_timeout] || 8 + http.open_timeout = options[:open_timeout] || 4 + http.read_timeout = options[:read_timeout] || 10 if uri.scheme =~ /https/i http.use_ssl = true @@ -69,45 +237,19 @@ returns http.verify_mode = OpenSSL::SSL::VERIFY_NONE end - if !options[:method] || options[:method] =~ /^get$/i - request = Net::HTTP::Get.new(uri.request_uri) + http + end - # http basic auth (if needed) - if options[:user] && options[:user] != '' && options[:password] && options[:password] != '' - request.basic_auth options[:user], options[:password] - end + def self.set_basic_auth(request, options) - begin - response = http.request(request) - rescue Exception => e - return Result.new( - :error => e.inspect, - :success => false, - :code => 0, - ) - end - elsif options[:method] =~ /^post$/i - request = Net::HTTP::Post.new(uri.request_uri) - - # http basic auth (if needed) - if options[:user] && options[:user] != '' && options[:password] && options[:password] != '' - request.basic_auth options[:user], options[:password] - end - - begin - request.set_form_data( options[:data] ) - response = http.request(request) - rescue Exception => e - return Result.new( - :error => e.inspect, - :success => false, - :code => 0, - ) - end - else - raise "Unknown method '#{options[:method]}'" + # http basic auth (if needed) + if options[:user] && options[:user] != '' && options[:password] && options[:password] != '' + request.basic_auth options[:user], options[:password] end + request + end + def self.process(response, uri, count, options = {}) if !response return Result.new( :error => "Can't connect to #{uri.to_s}, got no response!", @@ -138,9 +280,8 @@ returns ) when Net::HTTPRedirection raise "Too many redirections for the original URL, halting." if count <= 0 - url = response["location"] - uri = URI.parse(url) - return http(uri, options, count - 1) + url = response['location'] + return get(url, options, count - 1) when Net::HTTPOK return Result.new( @@ -178,7 +319,7 @@ returns return Result.new( :error => e.inspect, :success => false, - :code => 550, + :code => '550', ) end end @@ -186,6 +327,7 @@ returns return Result.new( :error => e.inspect, :success => false, + :code => 0, ) end @@ -194,7 +336,7 @@ returns Result.new( :body => contents, :success => true, - :code => 200, + :code => '200', ) end @@ -222,4 +364,4 @@ returns @content_type end end -end +end \ No newline at end of file diff --git a/test/integration/user_agent_test.rb b/test/integration/user_agent_test.rb new file mode 100644 index 000000000..ed50eef2e --- /dev/null +++ b/test/integration/user_agent_test.rb @@ -0,0 +1,407 @@ +# encoding: utf-8 +require 'integration_test_helper' + +class UserAgentTest < ActiveSupport::TestCase + host = 'http://127.0.0.1:3003' + + # check + test 'check some results' do + + # get / 200 + result = UserAgent.get( + "#{host}/test/get/1?submitted=123", + ) + assert(result) + assert_equal(true, result.success?) + assert_equal('200', result.code) + assert_equal(String, result.body.class) + assert(result.body =~ /"get"/) + assert(result.body =~ /"123"/) + + # get / 404 + result = UserAgent.get( + "#{host}/test/not_existing", + ) + assert(result) + assert_equal(false, result.success?) + assert_equal('404', result.code) + assert_equal(NilClass, result.body.class) + + # post / 200 + result = UserAgent.post( + "#{host}/test/post/1", + { + :submitted => 'some value', + } + ) + assert(result) + assert_equal(true, result.success?) + assert_equal('200', result.code) + assert_equal(String, result.body.class) + assert(result.body =~ /"post"/) + assert(result.body =~ /"some value"/) + + # post / 404 + result = UserAgent.post( + "#{host}/test/not_existing", + { + :submitted => 'some value', + } + ) + assert(result) + assert_equal(false, result.success?) + assert_equal('404', result.code) + assert_equal(NilClass, result.body.class) + + # put / 200 + result = UserAgent.put( + "#{host}/test/put/1", + { + :submitted => 'some value', + } + ) + assert(result) + assert_equal(true, result.success?) + assert_equal('200', result.code) + assert_equal(String, result.body.class) + assert(result.body =~ /"put"/) + assert(result.body =~ /"some value"/) + + # put / 404 + result = UserAgent.put( + "#{host}/test/not_existing", + { + :submitted => 'some value', + } + ) + assert(result) + assert_equal(false, result.success?) + assert_equal('404', result.code) + assert_equal(NilClass, result.body.class) + + # delete / 200 + result = UserAgent.delete( + "#{host}/test/delete/1", + ) + assert(result) + assert_equal(true, result.success?) + assert_equal('200', result.code) + assert_equal(String, result.body.class) + assert(result.body =~ /"delete"/) + + # delete / 404 + result = UserAgent.delete( + "#{host}/test/not_existing", + ) + assert(result) + assert_equal(false, result.success?) + assert_equal('404', result.code) + assert_equal(NilClass, result.body.class) + + + + # with http basic auth + + # get / 200 + result = UserAgent.get( + "#{host}/test_basic_auth/get/1?submitted=123", + { + :user => 'basic_auth_user', + :password => 'test123', + } + ) + assert(result) + assert_equal(true, result.success?) + assert_equal('200', result.code) + assert_equal(String, result.body.class) + assert(result.body =~ /"get"/) + assert(result.body =~ /"123"/) + + # get / 401 + result = UserAgent.get( + "#{host}/test_basic_auth/get/1?submitted=123", + { + :user => 'basic_auth_user_not_existing', + :password => 'test<>123', + } + ) + assert(result) + assert_equal(false, result.success?) + assert_equal('401', result.code) + assert_equal(NilClass, result.body.class) + + # post / 200 + result = UserAgent.post( + "#{host}/test_basic_auth/post/1", + { + :submitted => 'some value', + }, + { + :user => 'basic_auth_user', + :password => 'test123', + } + ) + assert(result) + assert_equal(true, result.success?) + assert_equal('200', result.code) + assert_equal(String, result.body.class) + assert(result.body =~ /"post"/) + assert(result.body =~ /"some value"/) + + # post / 401 + result = UserAgent.post( + "#{host}/test_basic_auth/post/1", + { + :submitted => 'some value', + }, + { + :user => 'basic_auth_user_not_existing', + :password => 'test<>123', + } + ) + assert(result) + assert_equal(false, result.success?) + assert_equal('401', result.code) + assert_equal(NilClass, result.body.class) + + # put / 200 + result = UserAgent.put( + "#{host}/test_basic_auth/put/1", + { + :submitted => 'some value', + }, + { + :user => 'basic_auth_user', + :password => 'test123', + } + ) + assert(result) + assert_equal(true, result.success?) + assert_equal('200', result.code) + assert_equal(String, result.body.class) + assert(result.body =~ /"put"/) + assert(result.body =~ /"some value"/) + + # put / 401 + result = UserAgent.put( + "#{host}/test_basic_auth/put/1", + { + :submitted => 'some value', + }, + { + :user => 'basic_auth_user_not_existing', + :password => 'test<>123', + } + ) + assert(result) + assert_equal(false, result.success?) + assert_equal('401', result.code) + assert_equal(NilClass, result.body.class) + + + # delete / 200 + result = UserAgent.delete( + "#{host}/test_basic_auth/delete/1", + { + :user => 'basic_auth_user', + :password => 'test123', + } + ) + assert(result) + assert_equal(true, result.success?) + assert_equal('200', result.code) + assert_equal(String, result.body.class) + assert(result.body =~ /"delete"/) + + # delete / 401 + result = UserAgent.delete( + "#{host}/test_basic_auth/delete/1", + { + :user => 'basic_auth_user_not_existing', + :password => 'test<>123', + } + ) + assert(result) + assert_equal(false, result.success?) + assert_equal('401', result.code) + assert_equal(NilClass, result.body.class) + end + + # check + test 'check redirect' do + + # get / 301 + result = UserAgent.request( + "#{host}/test/redirect", + ) + assert(result) + assert_equal(true, result.success?) + assert_equal('200', result.code) + assert_equal(String, result.body.class) + assert(result.body =~ /"get"/) + assert(result.body =~ /"abc"/) + + + # get / 301 + result = UserAgent.request( + "#{host}/test_basic_auth/redirect", + { + :user => 'basic_auth_user', + :password => 'test123', + } + ) + assert(result) + assert_equal(true, result.success?) + assert_equal('200', result.code) + assert_equal(String, result.body.class) + assert(result.body =~ /"get"/) + assert(result.body =~ /"abc"/) + + + # get / 401 + result = UserAgent.request( + "#{host}/test_basic_auth/redirect", + { + :user => 'basic_auth_user_not_existing', + :password => 'test123', + } + ) + assert(result) + assert_equal(false, result.success?) + assert_equal('401', result.code) + assert_equal(NilClass, result.body.class) + end + + # check + test 'check request' do + + # get / 200 + result = UserAgent.request( + "#{host}/test/get/1?submitted=123", + ) + assert(result) + assert_equal(true, result.success?) + assert_equal('200', result.code) + assert_equal(String, result.body.class) + assert(result.body =~ /"get"/) + assert(result.body =~ /"123"/) + + # ftp / 200 + result = UserAgent.request( + "ftp://ftp.gwdg.de/msgs/banner.msg", + ) + assert(result) + assert_equal(true, result.success?) + assert_equal('200', result.code) + assert_equal(String, result.body.class) + assert(result.body =~ /Gesellschaft/i) + + # ftp / 401 + result = UserAgent.request( + "ftp://ftp.gwdg.de/msgs/not_existing.msg", + ) + assert(result) + assert_equal(false, result.success?) + assert_equal('550', result.code) + assert_equal(NilClass, result.body.class) + + # get / 200 / gzip + result = UserAgent.request( + "https://httpbin.org/gzip", + ) + assert(result) + assert_equal(true, result.success?) + assert_equal('200', result.code) + assert_equal(String, result.body.class) + assert(result.body =~ /"GET"/) + + # get / 200 / gzip + result = UserAgent.request( + "http://httpbin.org/gzip", + ) + assert(result) + assert_equal(true, result.success?) + assert_equal('200', result.code) + assert_equal(String, result.body.class) + assert(result.body =~ /"GET"/) + + # get / 200 / gzip + result = UserAgent.request( + "https://httpbin.org/deflate", + ) + assert(result) + assert_equal(true, result.success?) + assert_equal('200', result.code) + assert_equal(String, result.body.class) + assert(result.body =~ /"GET"/) + + # get / 200 / gzip + result = UserAgent.request( + "http://httpbin.org/deflate", + ) + assert(result) + assert_equal(true, result.success?) + assert_equal('200', result.code) + assert_equal(String, result.body.class) + assert(result.body =~ /"GET"/) + + end + + + # check + test 'check not existing' do + + # get / 0 + result = UserAgent.request( + "http://not.existing.host/test.php", + ) + assert(result) + assert_equal(false, result.success?) + assert_equal(0, result.code) + assert_equal(NilClass, result.body.class) + + # ftp / 0 + result = UserAgent.request( + "ftp://not.existing.host/test.bin", + ) + assert(result) + assert_equal(false, result.success?) + assert_equal(0, result.code) + assert_equal(NilClass, result.body.class) + end + + + # check + test 'check timeout' do + + # get / timeout + result = UserAgent.get( + "#{host}/test/get/3?submitted=123", + { + :open_timeout => 1, + :read_timeout => 1, + } + ) + assert(result) + assert_equal(false, result.success?) + assert_equal(0, result.code) + assert_equal(NilClass, result.body.class) + + # post / timeout + result = UserAgent.post( + "#{host}/test/post/3", + { + :submitted => 'timeout', + }, + { + :open_timeout => 1, + :read_timeout => 1, + } + ) + assert(result) + assert_equal(false, result.success?) + assert_equal(0, result.code) + assert_equal(NilClass, result.body.class) + end + +end \ No newline at end of file diff --git a/test/unit/rest_test.rb b/test/unit/rest_test.rb index 4e4936f51..103c2efba 100644 --- a/test/unit/rest_test.rb +++ b/test/unit/rest_test.rb @@ -1,6 +1,5 @@ # encoding: utf-8 require 'test_helper' -require 'faraday' class RestTest < ActiveSupport::TestCase @@ -235,9 +234,14 @@ class RestTest < ActiveSupport::TestCase end def get(user, pw, url) - conn = Faraday.new( :url => ENV['BROWSER_URL'] ) - conn.basic_auth( user, pw ) - response = conn.get url + + response = UserAgent.get( + :url => ENV['BROWSER_URL'], + { + :user => user, + :password => pw, + } + ) # puts 'URL: ' + url # puts response.body.to_s data = JSON.parse( response.body )