require 'oauth2' require 'blabla_client/version' require 'blabla_client/trip' module BlablaClient # Note : token expiration is ignored for now (current token expires on 15/04/2015) # PREVIOUS_TOKEN = 'eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJleHAiOjE0MjY0MjY5NTUsImNsaWVudCI6ImE3NzM3ODdhNmI2YjM0NzlhMjk5NTg0MDUwMmUwNDZkNGE0NDNjYmE2MDFjMDk2Y2U1NGI4OTcyYjRkZTdjNzkiLCJzY29wZSI6IiIsInVzZXIiOm51bGx9.dOZF0wbZtW6_Vfa5dU6_X831yGCJlsSZE7gkdp2lldg' CURRENT_TOKEN = 'eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJleHAiOjE0MjkxMzIwMDUsImNsaWVudCI6ImE3NzM3ODdhNmI2YjM0NzlhMjk5NTg0MDUwMmUwNDZkNGE0NDNjYmE2MDFjMDk2Y2U1NGI4OTcyYjRkZTdjNzkiLCJzY29wZSI6IiIsInVzZXIiOm51bGx9.HKdhHE8XilgrK9cfK6GYUWFbaaQDg_fOWdc0Ze06qIA' # token "eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJleHAiOjE0MjY0MjY5NTUsImNsaWVudCI6ImE3NzM3ODdhNmI2YjM0NzlhMjk5NTg0MDUwMmUwNDZkNGE0NDNjYmE2MDFjMDk2Y2U1NGI4OTcyYjRkZTdjNzkiLCJzY29wZSI6IiIsInVzZXIiOm51bGx9.dOZF0wbZtW6_Vfa5dU6_X831yGCJlsSZE7gkdp2lldg" # expires_at : 1426426958 # expires_in : 2419200 # Configuration defaults (as of API v3) @config = { :auth_site => 'https://www.blablacar.fr', :token_path => '/oauth/v2/access_token', :client_id => '', :client_secret => '', :api_url => 'https://api.blablacar.fr/api/v2/trips' } @valid_config_keys = @config.keys @logger = Logger.new(STDOUT) # Configure through hash def self.configure(opts = {}) opts.each {|k,v| @config[k.to_sym] = v if @valid_config_keys.include? k.to_sym} end def self.config @config end def self.available_trips(departure, arrival, date_range_start, date_range_end, page = 1) trips = [] range_start = normalize_date(date_range_start) range_end = normalize_date(date_range_end) begin response = get_response(departure, arrival, range_start, range_end, page) trips = Trip.parse_response(response.body) @logger.info("Retrieved #{trips[:trips].length} trips for page #{page} of request #{departure}-#{arrival} from #{range_start} to #{range_end}") rescue OAuth2::Error => e http_code = e.response.status @logger.error("An error occurred while calling the API on #{@config[:api_url]}") @logger.error("Response : #{e.response}") @logger.error("Code : #{e.code}") @logger.error("HTTP status code : #{http_code}") @logger.error("Description : #{e.description}") if http_code == 403 @logger.info('Token seems to have expired - Retrying with a new one') trips = renew_and_get_trips(departure, arrival, range_start, range_end, page) end end trips end def self.normalize_date(date) if date.is_a?(Date) || date.is_a?(DateTime) || date.is_a?(Time) date_as_object = date else date_as_object = Date.parse(date) end date_as_object.strftime('%d-%m-%Y') end private def self.renew_and_get_trips(departure, arrival, date_range_start, date_range_end, page) trips = [] begin response = get_response(departure, arrival, date_range_start, date_range_end, page, true) trips = Trip.parse_response(response.body) @logger.info("Retrieved #{trips[:trips].length} trips for page #{page} of request #{departure}-#{arrival} from #{date_range_start} to #{date_range_start}") rescue OAuth2::Error => e http_code = e.response.status @logger.error("An error occurred while calling the API on #{@config[:api_url]} after attempting to renew the token") @logger.error("Response : #{e.response}") @logger.error("Code : #{e.code}") @logger.error("HTTP status code : #{http_code}") @logger.error("Description : #{e.description}") end trips end def self.get_response(departure, arrival, date_range_start, date_range_end, page, renew_token = false) client = OAuth2::Client.new(@config[:client_id], @config[:client_secret], :site => @config[:auth_site], :token_url => @config[:token_path]) token = renew_token ? client.client_credentials.get_token : OAuth2::AccessToken.new(client, CURRENT_TOKEN, :mode => :query) token.get(@config[:api_url], :params => { :_format => 'json', :fn => departure, :tn => arrival, :db => date_range_start, :de => date_range_end, :seats => '1', :page => page } ) end end