ruby net/http openssl security level - ruby

Is it possible to set security level in ruby when calling net::http instead of modifying openssl config?
I found out that OpenSSL has a way how to set security level through
OpenSSL::SSL::SSLContext#security_level
but how can I use it in new Net::Http request?
When I just setup
ctx = OpenSSL::SSL::SSLContext.new
ctx.security_level = 1
it is ignored by http request

Related

Disable basic_auth for Savon WSDL call

Is it possible to disable authentication (basic_auth) when Savon attempts to retrieve the WSDL?
It appears that this changed somewhere around 2.0 or 2.1 and now the authentication headers are always being sent, which the server I am calling throws an error when this happens.
Savon will perform basic auth only if you provide :basic_auth while creating the Savon.client object.

Pre-emptive auth with JMeter and HTTPClient 4 [duplicate]

I am trying to imply the basic authentication process for a web service using JMeter. But everytime it throws out an error 401:Unauthorized. I tried using the HTTP Header manager to add a header Authorization and value to it. Still it does not work. I have also tried using the HTTP Authorization manager. Still no luck. Can someone help.
I've found through debugging requests coming in from JMeter that the HTTP Authorization Manager module doesn't encode the username and password correctly. It puts a newline character after the username.
To run a JMeter test against a Basic Auth protected endpoint, include the HTTP Header Manager and add the Basic Auth header yourself:
Manually Encoding Credentials
From MacOS or Linux:
echo -n "username:password" | base64
From Windows:
Go here and encode your "username:password" string
Adding the Authorization Header
In the HTTP Header Manager, add an entry with the name "Authorization" and the value "Basic [encoded credentials from above]"
Edit 19 august 2017 for JMeter 3.2:
Use answer https://stackoverflow.com/a/12563623/460802
Basically to bypass a Basic Authorization you need to add the Authorization header with the value Basic base64(username:password). The problem is that JMeter has no base64 function embedded.
The solution is :
Step1 Add BeanShell PreProcessor (PreProcessor --> BeanShell Preprocessor)
Step2 Add the following script to the PreProcessor
import org.apache.commons.codec.binary.Base64;
byte[] encodedUsernamePassword = Base64.encodeBase64("neo4j:1234".getBytes());
vars.put("base64HeaderValue",new String(encodedUsernamePassword));
Step3 Add HTTP Header Manager
Step4 Add Authorization header with correct value
header name Authorization
header value Basic ${base64HeaderValue} (base64HeaderValue variable is initialized by the BeanShell Preprocessor)
So in the end when you create a http request Authorization header will be passed to the server with base64 encoded string
Do the following:
1/ Configure HTTP Authorization Manager correctly with all required fields
2/
Option 1 : Using HTTP 4 : (default)
it is possible since JMeter 3.2 without any further configuration using Authorization Manager
Option 2 : Using HTTP 3.1 : (deprecated)
in jmeter.properties , uncomment:
httpclient.parameters.file=httpclient.parameters
in httpclient.parameters, uncomment:
http.authentication.preemptive$Boolean=true
If you're looking to learn JMeter, this book by 3 developers of the project will help you
Make sure to provide a protocol for the base URL, i.e.: "http://localhost" instead of "localhost"
Like Ryan T said, in the HTTP Header Manager, add an entry with the name "Authorization" and the value "Basic [encoded credentials from above]" but without [].
If you get Response code as 401, then add "HTTP Authorization manager" Config Element
I am using Jmeter 3.3
GO to Jmeter on User choose add then HTTP Authorization Manager
Then add ur url , userid,password
If response type is json then add HTTP Header manager
You can easily use JSON Extractor for authentication inside the auth request to store the token in a variable, then you will just need to use it whenever the token is needed, in order to use that you will need an HTTP header manager using that variable you can follow the screenshots for clear instructions.
JSON Extractor configuration:
HTTP header manager configuration:
In reference to the first answer above, the incorrect encoding problem you mention must be now fixed, as Apache 3.1 does appear to encode the username:password correctly in HTTP Auth Manager
Adding a slight variation of #yurko which uses the username & password from User defined variables. (for Jmeter prior to 3.2)
import org.apache.commons.codec.binary.Base64;
String username = vars.get("USERNAME");
String password = vars.get("PASSWORD");
String combineduserpass = username + ":" + password;
byte[] encodedUsernamePassword = Base64.encodeBase64(combineduserpass.getBytes());
vars.put("base64HeaderValue",new String(encodedUsernamePassword));
Updating good findings from your 2013 answers:
The HTTP4 option also works under current Jmeter version 2.13
after adding HTTP Header Manager row containing:
name="Authorization", value="Basic [base64-encoded user/password string]"
Verified on current host amazon linux having reverse proxy from apache 2.4 to tomcat8; tomcat8 recognized the user credentials instead of throwing 401 status.

Example code for SSL client authentication in ruby 1.8.7

Folks,
Can anyone provide a working example of how to do SSL client authentication in ruby 1.8.7? For the record, I am attempting to use a GoDaddy certification to perform an authenticated post request to the Windows Phone push notification service. In this case, my command-line client is using a certificate like an API key or bearer token.
I supply GoDaddy a mydomain.com.key file, and GoDaddy supplies me with a gd_bundle.crt file and a mydomain.com.crt file.
On my Net::HTTP object, I have set these parameters:
my_cert = File.read(File.join(File.dirname(__FILE__), "mydomain.com.crt")) # from godaddy
my_key = File.read(File.join(File.dirname(__FILE__), "mydomain.com.key")) # i made
http.use_ssl = true
http.cert = OpenSSL::X509::Certificate.new(my_cert)
http.key = OpenSSL::PKey::RSA.new(my_key)
http.verify_mode = OpenSSL::SSL::VERIFY_PEER
But the push notification service continues to report a 403 error saying "You do not have permission to view this directory or page using the credentials that you supplied".
Since someone out there is doing push successfully I assume the way I have configured my Net::HTTP object in ruby is incorrect. Does anyone have sample code for how I can use ruby to perform SSL client authentication?

HTTPS Requests in Ruby

Is there a gem or library for HTTPS Requests in Ruby? What is it called and can you provide some example usage?
What I am trying to do is open a page, parse some text from it, and then output it.
SSL Request with Ruby Standard Library
require 'net/http'
require 'uri'
Net::HTTP.get URI('https://encrypted.google.com')
Net::HTTP in Ruby (>= 2.0.0) performs SSL verification by default if you pass a URI object that has a "https" URL to it. See https://github.com/ruby/ruby/blob/778bbac8ac2ae50f0987c4888f7158296ee5bbdd/lib/net/http.rb#L481
You may verify this by performing a get request on a domain with an expired certificate.
uri = URI('https://expired.badssl.com/')
Net::HTTP.get(uri)
# OpenSSL::SSL::SSLError: SSL_connect returned=1 errno=0 state=error: certificate verify failed
SSL Request with Ruby HTTP gems
If you wish to use an alternative, you may use the following gems that also performs SSL verification by default:
Excon
Excon is a pure Ruby HTTP implementation.
require 'excon'
Excon.get 'https://encrypted.google.com'
Curb
Curb is a HTTP client that uses libcurl under the hood.
require 'curl'
Curl.get 'https://encrypted.google.com'
http.rb
HTTP or http.rb is a pure Ruby HTTP implementation but uses http_parser.rb to parse HTTP requests and responses. Since http_parser.rb uses native extensions, it claims to be one of the fastest HTTP client library. But as always, take benchmarks with a grain of salt.
require 'http'
HTTP.get 'https://encrypted.google.com'
HTTPClient
HTTPClient is another pure Ruby implementation.
require 'httpclient'
HTTPClient.get 'https://encrypted.google.com'
What's listed here are HTTP libraries and not HTTP wrappers. Wrapper gems like HTTParty and Faraday either wrap around a particular HTTP implementation or use adapters to provide a unified HTTP interface. You may check out this Comparison matrix of Ruby HTTP client features. It compares the features of every single HTTP client library out there. But do note that the information isn't updated since 2012.
There is an integrated library in the language called Net::HTTP
An example usage of it would be:
uri = URI('https://example.com/some_path?query=string')
response = Net::HTTP.start(uri.host, uri.port) do |http|
request = Net::HTTP::Get.new uri.request_uri
http.request request # Net::HTTPResponse object
end
puts response.body
UPDATE:
You need to include that library like this:
require 'net/https'

specify proxy authentication with savonrb

I'm using savon to communicate with a soap web service.
It all works well, and I now need to get the ruby code into production where we have to go through a proxy server.
This proxy server requires authentication.
So my question is, how can I go ahead to specify proxy server authentication details with savon?
Some further info:
I've figured out that you can specify a proxy server as such:
client = Savon::Client.new do
...
http.proxy = "http://proxy.example.com"
end
Looking through the code for savon, I found that the http variable in the client block refers to the following:
def http
#http ||= HTTPI::Request.new
end
Unfortunately, going through the code for HTTPI::Request, I couldn't see a way to specify authentication for the proxy itself. Here's the code for the httpi request: https://github.com/rubiii/httpi/blob/master/lib/httpi/request.rb
Just to be clear: I'm not trying to do HTTP authentication, I'm attempting to perform proxy authentication.
When specifying the proxy server, I get the following error, because I can't find a way to specify the proxy authentication credentials:
407 "Proxy Authentication Required"
Thanks in advance for any help.
Try this:
http.proxy = "http://username:password#host:port"
Managed to resolve it with the following code:
#proxy_path = '<insert your proxy url here>'
#wsdl_path = '<insert your wsdl url here>'
#client = Savon.client do |variable|
variable.proxy #proxy_path
variable.wsdl #wsdl_path
end
#client.operations #to list operations

Resources