HTTPS Requests in Ruby - 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'

Related

ruby net/http openssl security level

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

Get Instagram Access Token using Restful Ruby

I am trying to use the Instagram API to create a rails background worker to query hashtags. I don't need to log in any other user but myself furthermore I don't want to have to use any browsers, just RESTful calls.
I'm trying to automate getting my access token in a Ruby script using the gem "rest-client" (https://github.com/rest-client/rest-client)
I can successfully navigate to the following url in a browser and get the access token from the response url
I have used both this URL:
https://www.instagram.com/oauth/authorize/?client_id=xxx&redirect_uri=xxx&response_type=token
BUT When I use the RESTful gem response = RestClient.get(url) the
response.headers['location'] is nil
I have also tried using the Instagram API URL but no luck: https://api.instagram.com/oauth/authorize/?client_id=xxx&redirect_uri=xxx&response_type=code
Anyone know how to get the access token completely programmatically in Ruby?
I think I'm missing the step to log in the user (which will be me). Not sure how to do this programatically.
Can I use the instagram API with a code or access token that never changes?
rest-client automatically request to get to redirect host.
https://github.com/rest-client/rest-client/blob/master/lib/restclient/abstract_response.rb
I have never used the instagram API yet, but the code to get "Location" on 302 is shown below.
# client
require 'net/http'
require 'uri'
url = URI.parse('http://localhost:2000')
res = Net::HTTP.start(url.host, url.port) do |http|
http.get('/')
end
puts "#{res.header['Location']} is https://google.com"
# test server
require 'socket'
server = TCPServer.new 2000
loop do
socket = server.accept
while header = socket.gets
break if header.chomp.empty?
puts header.chomp
end
socket.puts "HTTP/1.0 302"
socket.puts "Location: https://google.com"
socket.close
end
I hope that this information is helpful to you.

Basic authentication in Github api with http request in Ruby?

I'm trying to use basic authentication in Github api. I wrote something like this:
require 'httpclient'
request = HTTPClient.new
request.set_basic_auth("http://api.github.com/authorizations", "my_username", "my_password")
request.get "http://api.github.com/user/repos"
and expect it returns the repos of a user. However, it keeps throwing an error:
Connection refused - connect(2) for "api.github.com" port 80 (Errno::ECONNREFUSED)
I know there are a whole bunch of gems like github, octokit that do the stuff for users. I want to try it myself. Does anyone know how do I authenticate with a simple http request in Ruby?
You need to make an HTTPS request instead of HTTP. Authentication always needs to use SSL.
You are also using the wrong URL's. As per their docs (https://developer.github.com/v3/auth/#basic-authentication) you need to set your basic authentication to the following path:
https://api.github.com/user
And make your repo request at:
"https://api.github.com/users/<USERNAME>/repos"
So your request would look something like
request = HTTPClient.new
request.set_basic_auth("https://api.github.com/user", "my_username", "my_password")
request.get "https://api.github.com/users/<USERNAME>/repos"
I suggest taking a look at the documentation that I linked to above, and make your first attempt by using curl requests, as they offer more information to help you debug.

How do I pass debug and logging options through Faraday to Net::HTTP or Net::HTTPS

I'm using Faraday and Net::HTTP, Net::HTTPS to connect to a site using SSL. However I get the following error:
'SSL_connect returned=1 errno=0 state=SSLv3 read finished A: sslv3 alert handshake failure'
How do I make Faraday turn on debugging and logging in the underlying client?
Where you initialize the Faraday connection, you can pass things through to the underlying adapter. For example, I use this behavior in one of my clients, albeit with Excon instead of Net::HTTP, but you should be able to adapt:
excon_options = {}
excon_options.merge!(instrumentor: instrumentor) if instrumentor
#connection = Faraday::Connection.new(url: url) do |builder|
builder.adapter :excon, excon_options
end
The excon_options hash in this case is the format of a hash that I would pass to the Excon connection object if I weren't using Faraday. You should be able to do something similar with Net::HTTP

How to set cookie in faraday

I'm using Faraday as an HTTP client to test my HTTP service (based on Sinatra). It's very powerful for me, but I have a problem.
We track sessions on the Sinatra service, but I cannot set the cookie value with the Faraday client. This is the sample code:
# `response` is from the Sinatra service
cookie = response.headers['set-cookie']
# now, for the follow up request...
response = client.get '/api/profile' do |req|
req.headers['Cookie'] = cookie
end
The server cannot find the session. Why?
The Set-Cookie and Cookie headers are not the same, read the RFC to know how to interpret them. In short the Set-Cookie header also contains instructions for the client how to handle the data (domain, path, expiry, etc.) and gives an update to the existing cookie store. The Cookie header on the other hand provides the contents of the cookie store, but not the meta data.
You would need to obtain or implement some kind of cookie handler to insert into your Faraday middle-ware stack.

Resources