diff --git a/lib/predictionio/client.rb b/lib/predictionio/client.rb
deleted file mode 100644
index e2b405b..0000000
--- a/lib/predictionio/client.rb
+++ /dev/null
@@ -1,703 +0,0 @@
-# Ruby SDK for convenient access of PredictionIO Output API.
-#
-# Author::    TappingStone (help@tappingstone.com)
-# Copyright:: Copyright (c) 2013 TappingStone
-# License::   Apache License, Version 2.0
-
-require 'date'
-require 'json'
-require 'net/http'
-require 'predictionio/async_request'
-require 'predictionio/async_response'
-require 'predictionio/connection'
-
-module PredictionIO
-  # This class contains methods that access PredictionIO via REST requests.
-  #
-  # Many REST request methods support optional arguments.
-  # They can be supplied to these methods as Hash'es.
-  # For a complete reference, please visit http://prediction.io.
-  #
-  # == High-performance Asynchronous Backend
-  #
-  # All REST request methods come in both synchronous and asynchronous flavors.
-  # Both flavors accept the same set of arguments.
-  # In addition, all synchronous request methods can instead accept a PredictionIO::AsyncResponse object generated from asynchronous request methods as its first argument.
-  # In this case, the method will block until a response is received from it.
-  #
-  # Any network reconnection and request retry is automatically handled in the background.
-  # Exceptions will be thrown after a request times out to avoid infinite blocking.
-  #
-  # == Special Handling of Some Optional Arguments
-  # Some optional arguments have additional special handling:
-  # - For all requests that accept "itypes" as input, the value can be supplied as either an Array of String's, or a comma-delimited String.
-  # - For all requests that accept "pio_latlng" as input, they will also accept "pio_latitude" and "pio_longitude".
-  #   When these are supplied, they will override any existing "pio_latlng" value.
-  # - All time arguments (e.g. t, pio_startT, pio_endT, etc) can be supplied as either a Time or Float object.
-  #   When supplied as a Float, the SDK will interpret it as a UNIX UTC timestamp in seconds.
-  #   The SDK will automatically round to the nearest millisecond, e.g. 3.14159 => 3.142.
-  #
-  # == Installation
-  # The easiest way is to use RubyGems:
-  #     gem install predictionio
-  #
-  # == Synopsis
-  # The recommended usage of the SDK is to fire asynchronous requests as early as you can in your code,
-  # and check results later when you need them.
-  #
-  # === Instantiate PredictionIO Client
-  #     # Include the PredictionIO SDK
-  #     require "predictionio"
-  #
-  #     client = PredictionIO::Client.new(<appkey>)
-  #
-  # === Import a User Record from Your App (with asynchronous/non-blocking requests)
-  #
-  #     #
-  #     # (your user registration logic)
-  #     #
-  #
-  #     uid = get_user_from_your_db()
-  #
-  #     # PredictionIO call to create user
-  #     response = client.acreate_user(uid)
-  #
-  #     #
-  #     # (other work to do for the rest of the page)
-  #     #
-  #
-  #     begin
-  #       # PredictionIO call to retrieve results from an asynchronous response
-  #       result = client.create_user(response)
-  #     rescue UserNotCreatedError => e
-  #       log_and_email_error(...)
-  #     end
-  #
-  # === Import a User Action (Rate) from Your App (with synchronous/blocking requests)
-  #     # PredictionIO call to record the view action
-  #     begin
-  #       client.identify("foouser")
-  #       result = client.record_action_on_item("rate", "baritem", "pio_rate" => 4)
-  #     rescue U2IActionNotCreatedError => e
-  #       ...
-  #     end
-  #
-  # === Retrieving Top N Recommendations for a User
-  #     # PredictionIO call to get recommendations
-  #     client.identify("foouser")
-  #     response = client.aget_itemrec_top_n("barengine", 10)
-  #
-  #     #
-  #     # work you need to do for the page (rendering, db queries, etc)
-  #     #
-  #
-  #     begin
-  #       result = client.get_itemrec_top_n(response)
-  #       # display results, store results, or your other work...
-  #     rescue ItemRecNotFoundError => e
-  #       # graceful error handling
-  #     end
-  #
-  # === Retrieving Top N Similar Items for an Item
-  #     # PredictionIO call to get similar items
-  #     response = client.aget_itemsim_top_n("barengine", "fooitem", 10)
-  #
-  #     #
-  #     # work you need to do for the page (rendering, db queries, etc)
-  #     #
-  #
-  #     begin
-  #       result = client.get_itemsim_top_n(response)
-  #       # display results, store results, or your other work...
-  #     rescue ItemSimNotFoundError => e
-  #       # graceful error handling
-  #     end
-
-  class Client
-
-    # Appkey can be changed on-the-fly after creation of the client.
-    attr_accessor :appkey
-
-    # Only JSON is currently supported as API response format.
-    attr_accessor :apiformat
-
-    # The UID used for recording user-to-item actions and retrieving recommendations.
-    attr_accessor :apiuid
-
-    # Raised when a user is not created after a synchronous API call.
-    class UserNotCreatedError < StandardError; end
-
-    # Raised when a user is not found after a synchronous API call.
-    class UserNotFoundError < StandardError; end
-
-    # Raised when a user is not deleted after a synchronous API call.
-    class UserNotDeletedError < StandardError; end
-
-    # Raised when an item is not created after a synchronous API call.
-    class ItemNotCreatedError < StandardError; end
-
-    # Raised when an item is not found after a synchronous API call.
-    class ItemNotFoundError < StandardError; end
-
-    # Raised when an item is not deleted after a synchronous API call.
-    class ItemNotDeletedError < StandardError; end
-
-    # Raised when ItemRec results cannot be found for a user after a synchronous API call.
-    class ItemRecNotFoundError < StandardError; end
-
-    # Raised when ItemRank results cannot be found for a user after a synchronous API call.
-    class ItemRankNotFoundError < StandardError; end
-
-    # Raised when ItemSim results cannot be found for an item after a synchronous API call.
-    class ItemSimNotFoundError < StandardError; end
-
-    # Raised when an user-to-item action is not created after a synchronous API call.
-    class U2IActionNotCreatedError < StandardError; end
-
-    # Create a new PredictionIO client with default:
-    # - 10 concurrent HTTP(S) connections (threads)
-    # - API entry point at http://localhost:8000 (apiurl)
-    # - a 60-second timeout for each HTTP(S) connection (thread_timeout)
-    def initialize(appkey, threads = 10, apiurl = "http://localhost:8000", thread_timeout = 60)
-      @appkey = appkey
-      @apiformat = "json"
-      @http = PredictionIO::Connection.new(URI(apiurl), threads, thread_timeout)
-    end
-
-    # Returns the number of pending requests within the current client.
-    def pending_requests
-      @http.packages.size
-    end
-
-    # Returns PredictionIO's status in string.
-    def get_status
-      status = @http.aget(PredictionIO::AsyncRequest.new("/")).get()
-      begin
-        status.body
-      rescue Exception
-        status
-      end
-    end
-
-    # :category: Asynchronous Methods
-    # Asynchronously request to create a user and return a PredictionIO::AsyncResponse object immediately.
-    #
-    # Corresponding REST API method: POST /users
-    #
-    # See also #create_user.
-    def acreate_user(uid, params = {})
-      rparams = params
-      rparams["pio_appkey"] = @appkey
-      rparams["pio_uid"] = uid
-      if params["pio_latitude"] && params["pio_longitude"]
-        rparams["pio_latlng"] = "#{params["pio_latitude"]},#{params["pio_longitude"]}"
-      end
-
-      @http.apost(PredictionIO::AsyncRequest.new("/users.#{@apiformat}", rparams))
-    end
-
-    # :category: Synchronous Methods
-    # Synchronously request to create a user and block until a response is received.
-    #
-    # See also #acreate_user.
-    #
-    # call-seq:
-    # create_user(uid, params = {})
-    # create_user(async_response)
-    def create_user(*args)
-      uid_or_res = args[0]
-      if uid_or_res.is_a?(PredictionIO::AsyncResponse)
-        response = uid_or_res.get
-      else
-        uid = uid_or_res
-        response = acreate_user(*args).get
-      end
-      unless response.is_a?(Net::HTTPCreated)
-        begin
-          msg = response.body
-        rescue Exception
-          raise UserNotCreatedError, response
-        end
-        raise UserNotCreatedError, msg
-      end
-    end
-
-    # :category: Asynchronous Methods
-    # Asynchronously request to get a user and return a PredictionIO::AsyncResponse object immediately.
-    #
-    # Creation time of the user will be returned as a Time object.
-    #
-    # If the result contains a latlng key, both latitude and longitude will also be available as separate keys.
-    #
-    # Corresponding REST API method: GET /users/:uid
-    #
-    # See also #get_user.
-    def aget_user(uid)
-      @http.aget(PredictionIO::AsyncRequest.new("/users/#{uid}.#{@apiformat}",
-                                                "pio_appkey" => @appkey,
-                                                "pio_uid" => uid))
-    end
-
-    # :category: Synchronous Methods
-    # Synchronously request to get a user and block until a response is received.
-    #
-    # Creation time of the user will be returned as a Time object.
-    #
-    # If the result contains a latlng key, both latitude and longitude will also be available as separate keys.
-    #
-    # See also #aget_user.
-    #
-    # call-seq:
-    # get_user(uid)
-    # get_user(async_response)
-    def get_user(uid_or_res)
-      if uid_or_res.is_a?(PredictionIO::AsyncResponse)
-        response = uid_or_res.get
-      else
-        response = aget_user(uid_or_res).get
-      end
-      if response.is_a?(Net::HTTPOK)
-        res = JSON.parse(response.body)
-        if res["pio_latlng"]
-          latlng = res["pio_latlng"]
-          res["pio_latitude"] = latlng[0]
-          res["pio_longitude"] = latlng[1]
-        end
-        res
-      else
-        begin
-          msg = response.body
-        rescue Exception
-          raise UserNotFoundError, response
-        end
-        raise UserNotFoundError, msg
-      end
-    end
-
-    # :category: Asynchronous Methods
-    # Asynchronously request to delete a user and return a PredictionIO::AsyncResponse object immediately.
-    #
-    # Corresponding REST API method: DELETE /users/:uid
-    #
-    # See also #delete_user.
-    def adelete_user(uid)
-      @http.adelete(PredictionIO::AsyncRequest.new("/users/#{uid}.#{@apiformat}",
-                                                   "pio_appkey" => @appkey,
-                                                   "pio_uid" => uid))
-    end
-
-    # :category: Synchronous Methods
-    # Synchronously request to delete a user and block until a response is received.
-    #
-    # See also #adelete_user.
-    #
-    # call-seq:
-    # delete_user(uid)
-    # delete_user(async_response)
-    def delete_user(uid_or_res)
-      if uid_or_res.is_a?(PredictionIO::AsyncResponse)
-        response = uid_or_res.get
-      else
-        response = adelete_user(uid_or_res).get
-      end
-      unless response.is_a?(Net::HTTPOK)
-        begin
-          msg = response.body
-        rescue Exception
-          raise UserNotDeletedError, response
-        end
-        raise msg
-      end
-    end
-
-    # :category: Asynchronous Methods
-    # Asynchronously request to create an item and return a PredictionIO::AsyncResponse object immediately.
-    #
-    # Corresponding REST API method: POST /items
-    #
-    # See also #create_item.
-    def acreate_item(iid, itypes, params = {})
-      rparams = params
-      rparams["pio_appkey"] = @appkey
-      rparams["pio_iid"] = iid
-      begin
-        rparams["pio_itypes"] = itypes.join(",")
-      rescue Exception
-        rparams["pio_itypes"] = itypes
-      end
-      if params["pio_latitude"] && params["pio_longitude"]
-        rparams["pio_latlng"] = "#{params["pio_latitude"]},#{params["pio_longitude"]}"
-      end
-      rparams["pio_startT"] = ((params["pio_startT"].to_r) * 1000).round(0).to_s if params["pio_startT"]
-      rparams["pio_endT"]   = ((params["pio_endT"].to_r) * 1000).round(0).to_s if params["pio_endT"]
-
-      @http.apost(PredictionIO::AsyncRequest.new("/items.#{@apiformat}", rparams))
-    end
-
-    # :category: Synchronous Methods
-    # Synchronously request to create an item and block until a response is received.
-    #
-    # See #acreate_item for a description of other accepted arguments.
-    #
-    # call-seq:
-    # create_item(iid, itypes, params = {})
-    # create_item(async_response)
-    def create_item(*args)
-      iid_or_res = args[0]
-      if iid_or_res.is_a?(PredictionIO::AsyncResponse)
-        response = iid_or_res.get
-      else
-        response = acreate_item(*args).get
-      end
-      unless response.is_a?(Net::HTTPCreated)
-        begin
-          msg = response.body
-        rescue Exception
-          raise ItemNotCreatedError, response
-        end
-        raise ItemNotCreatedError, msg
-      end
-    end
-
-    # :category: Asynchronous Methods
-    # Asynchronously request to get an item and return a PredictionIO::AsyncResponse object immediately.
-    #
-    # Creation time of the user will be returned as a Time object.
-    #
-    # If the result contains a latlng key, both latitude and longitude will also be available as separate keys.
-    #
-    # Corresponding REST API method: GET /items/:iid
-    #
-    # See also #get_item.
-    def aget_item(iid)
-      @http.aget(PredictionIO::AsyncRequest.new("/items/#{iid}.#{@apiformat}",
-                                                "pio_appkey" => @appkey,
-                                                "pio_iid" => iid))
-    end
-
-    # :category: Synchronous Methods
-    # Synchronously request to get an item and block until a response is received.
-    #
-    # Creation time of the item will be returned as a Time object.
-    #
-    # If the result contains a latlng key, both latitude and longitude will also be available as separate keys.
-    #
-    # See also #aget_item.
-    #
-    # call-seq:
-    # get_item(iid)
-    # get_item(async_response)
-    def get_item(iid_or_res)
-      if iid_or_res.is_a?(PredictionIO::AsyncResponse)
-        response = iid_or_res.get
-      else
-        response = aget_item(iid_or_res).get
-      end
-      if response.is_a?(Net::HTTPOK)
-        res = JSON.parse(response.body)
-        if res["pio_latlng"]
-          latlng = res["pio_latlng"]
-          res["pio_latitude"] = latlng[0]
-          res["pio_longitude"] = latlng[1]
-        end
-        if res["pio_startT"]
-          startT = Rational(res["pio_startT"], 1000)
-          res["pio_startT"] = Time.at(startT)
-        end
-        if res["pio_endT"]
-          endT = Rational(res["pio_endT"], 1000)
-          res["pio_endT"] = Time.at(endT)
-        end
-        res
-      else
-        begin
-          msg = response.body
-        rescue Exception
-          raise ItemNotFoundError, response
-        end
-        raise ItemNotFoundError, msg
-      end
-    end
-
-    # :category: Asynchronous Methods
-    # Asynchronously request to delete an item and return a PredictionIO::AsyncResponse object immediately.
-    #
-    # Corresponding REST API method: DELETE /items/:iid
-    #
-    # See also #delete_item.
-    def adelete_item(iid)
-      @http.adelete(PredictionIO::AsyncRequest.new("/items/#{iid}.#{@apiformat}",
-                                                   "pio_appkey" => @appkey,
-                                                   "pio_iid" => iid))
-    end
-
-    # :category: Synchronous Methods
-    # Synchronously request to delete an item and block until a response is received.
-    #
-    # See also #adelete_item.
-    #
-    # call-seq:
-    # delete_item(iid)
-    # delete_item(async_response)
-    def delete_item(iid_or_res)
-      if iid_or_res.is_a?(PredictionIO::AsyncResponse)
-        response = iid_or_res.get
-      else
-        response = adelete_item(iid_or_res).get
-      end
-      unless response.is_a?(Net::HTTPOK)
-        begin
-          msg = response.body
-        rescue Exception
-          raise ItemNotDeletedError, response
-        end
-        raise ItemNotDeletedError, msg
-      end
-    end
-
-    # Set the user ID for use in all subsequent user-to-item action recording and user recommendation retrieval.
-    def identify(uid)
-      @apiuid = uid
-    end
-
-    # :category: Asynchronous Methods
-    # Asynchronously request to get the top n recommendations for a user from an ItemRec engine and return a PredictionIO::AsyncResponse object immediately.
-    #
-    # Corresponding REST API method: GET /engines/itemrec/:engine/topn
-    #
-    # See also #get_itemrec_top_n.
-    def aget_itemrec_top_n(engine, n, params = {})
-      rparams = Hash.new
-      rparams["pio_appkey"] = @appkey
-      rparams["pio_uid"] = @apiuid
-      rparams["pio_n"] = n
-      if params["pio_itypes"]
-        if params["pio_itypes"].kind_of?(Array) && params["pio_itypes"].any?
-          rparams["pio_itypes"] = params["pio_itypes"].join(",")
-        else
-          rparams["pio_itypes"] = params["pio_itypes"]
-        end
-      end
-      if params["pio_latitude"] && params["pio_longitude"]
-        rparams["pio_latlng"] = "#{params["pio_latitude"]},#{params["pio_longitude"]}"
-      end
-      rparams["pio_within"] = params["pio_within"] if params["pio_within"]
-      rparams["pio_unit"] = params["pio_unit"] if params["pio_unit"]
-      if params["pio_attributes"]
-        if params["pio_attributes"].kind_of?(Array) && params["pio_attributes"].any?
-          rparams["pio_attributes"] = params["pio_attributes"].join(",")
-        else
-          rparams["pio_attributes"] = params["pio_attributes"]
-        end
-      end
-      @http.aget(PredictionIO::AsyncRequest.new("/engines/itemrec/#{engine}/topn.#{@apiformat}", rparams))
-    end
-
-    # :category: Synchronous Methods
-    # Synchronously request to get the top n recommendations for a user from an ItemRec engine and block until a response is received.
-    #
-    # See #aget_itemrec_top_n for a description of special argument handling.
-    #
-    # call-seq:
-    # get_itemrec_top_n(engine, n, params = {})
-    # get_itemrec_top_n(async_response)
-    def get_itemrec_top_n(*args)
-      uid_or_res = args[0]
-      if uid_or_res.is_a?(PredictionIO::AsyncResponse)
-        response = uid_or_res
-      else
-        response = aget_itemrec_top_n(*args)
-      end
-      http_response = response.get
-      if http_response.is_a?(Net::HTTPOK)
-        res = JSON.parse(http_response.body)
-        if response.request.params.has_key?('pio_attributes')
-          attributes = response.request.params['pio_attributes'].split(',')
-          list_of_attribute_values = attributes.map { |attrib| res[attrib] }
-          res["pio_iids"].zip(*list_of_attribute_values).map { |v| Hash[(['pio_iid'] + attributes).zip(v)] }
-        else
-          res["pio_iids"]
-        end
-      else
-        begin
-          msg = response.body
-        rescue Exception
-          raise ItemRecNotFoundError, response
-        end
-        raise ItemRecNotFoundError, msg
-      end
-    end
-
-    # :category: Asynchronous Methods
-    # Asynchronously request to get the ranking for a user from an ItemRank engine and return a PredictionIO::AsyncResponse object immediately.
-    #
-    # Corresponding REST API method: GET /engines/itemrank/:engine/ranked
-    #
-    # See also #get_itemrank_ranked.
-    def aget_itemrank_ranked(engine, iids, params = {})
-      rparams = Hash.new
-      rparams["pio_appkey"] = @appkey
-      rparams["pio_uid"] = @apiuid
-      if iids.kind_of?(Array) && iids.any?
-        rparams["pio_iids"] = iids.join(",")
-      else
-        rparams["pio_iids"] = iids
-      end
-      if params["pio_attributes"]
-        if params["pio_attributes"].kind_of?(Array) && params["pio_attributes"].any?
-          rparams["pio_attributes"] = params["pio_attributes"].join(",")
-        else
-          rparams["pio_attributes"] = params["pio_attributes"]
-        end
-      end
-      @http.aget(PredictionIO::AsyncRequest.new("/engines/itemrank/#{engine}/ranked.#{@apiformat}", rparams))
-    end
-
-    # :category: Synchronous Methods
-    # Synchronously request to get the ranking for a user from an ItemRank engine and block until a response is received.
-    #
-    # See #aget_itemrank_ranked for a description of special argument handling.
-    #
-    # call-seq:
-    # get_itemrank_ranked(engine, n, params = {})
-    # get_itemrank_ranked(async_response)
-    def get_itemrank_ranked(*args)
-      uid_or_res = args[0]
-      if uid_or_res.is_a?(PredictionIO::AsyncResponse)
-        response = uid_or_res
-      else
-        response = aget_itemrank_ranked(*args)
-      end
-      http_response = response.get
-      if http_response.is_a?(Net::HTTPOK)
-        res = JSON.parse(http_response.body)
-        if response.request.params.has_key?('pio_attributes')
-          attributes = response.request.params['pio_attributes'].split(',')
-          list_of_attribute_values = attributes.map { |attrib| res[attrib] }
-          res["pio_iids"].zip(*list_of_attribute_values).map { |v| Hash[(['pio_iid'] + attributes).zip(v)] }
-        else
-          res["pio_iids"]
-        end
-      else
-        begin
-          msg = response.body
-        rescue Exception
-          raise ItemRankNotFoundError, response
-        end
-        raise ItemRankNotFoundError, msg
-      end
-    end
-
-    # :category: Asynchronous Methods
-    # Asynchronously request to get the top n similar items for an item from an ItemSim engine and return a PredictionIO::AsyncResponse object immediately.
-    #
-    # Corresponding REST API method: GET /engines/itemsim/:engine/topn
-    #
-    # See also #get_itemsim_top_n.
-    def aget_itemsim_top_n(engine, iid, n, params = {})
-      rparams = Hash.new
-      rparams["pio_appkey"] = @appkey
-      rparams["pio_iid"] = iid
-      rparams["pio_n"] = n
-      if params["pio_itypes"]
-        if params["pio_itypes"].kind_of?(Array) && params["pio_itypes"].any?
-          rparams["pio_itypes"] = params["pio_itypes"].join(",")
-        else
-          rparams["pio_itypes"] = params["pio_itypes"]
-        end
-      end
-      if params["pio_latitude"] && params["pio_longitude"]
-        rparams["pio_latlng"] = "#{params["pio_latitude"]},#{params["pio_longitude"]}"
-      end
-      rparams["pio_within"] = params["pio_within"] if params["pio_within"]
-      rparams["pio_unit"] = params["pio_unit"] if params["pio_unit"]
-      if params["pio_attributes"]
-        if params["pio_attributes"].kind_of?(Array) && params["pio_attributes"].any?
-          rparams["pio_attributes"] = params["pio_attributes"].join(",")
-        else
-          rparams["pio_attributes"] = params["pio_attributes"]
-        end
-      end
-      @http.aget(PredictionIO::AsyncRequest.new("/engines/itemsim/#{engine}/topn.#{@apiformat}", rparams))
-    end
-
-    # :category: Synchronous Methods
-    # Synchronously request to get the top n similar items for an item from an ItemSim engine and block until a response is received.
-    #
-    # See #aget_itemsim_top_n for a description of special argument handling.
-    #
-    # call-seq:
-    # get_itemsim_top_n(engine, iid, n, params = {})
-    # get_itemsim_top_n(async_response)
-    def get_itemsim_top_n(*args)
-      uid_or_res = args[0]
-      if uid_or_res.is_a?(PredictionIO::AsyncResponse)
-        response = uid_or_res
-      else
-        response = aget_itemsim_top_n(*args)
-      end
-      http_response = response.get
-      if http_response.is_a?(Net::HTTPOK)
-        res = JSON.parse(http_response.body)
-        if response.request.params.has_key?('pio_attributes')
-          attributes = response.request.params['pio_attributes'].split(',')
-          list_of_attribute_values = attributes.map { |attrib| res[attrib] }
-          res["pio_iids"].zip(*list_of_attribute_values).map { |v| Hash[(['pio_iid'] + attributes).zip(v)] }
-        else
-          res["pio_iids"]
-        end
-      else
-        begin
-          msg = response.body
-        rescue Exception
-          raise ItemSimNotFoundError, response
-        end
-        raise ItemSimNotFoundError, msg
-      end
-    end
-
-    # :category: Asynchronous Methods
-    # Asynchronously request to record an action on an item and return a PredictionIO::AsyncResponse object immediately.
-    #
-    # Corresponding REST API method: POST /actions/u2i
-    #
-    # See also #record_action_on_item.
-    def arecord_action_on_item(action, iid, params = {})
-      rparams = params
-      rparams["pio_appkey"] = @appkey
-      rparams["pio_action"] = action
-      rparams["pio_uid"] = @apiuid
-      rparams["pio_iid"] = iid
-      rparams["pio_t"] = ((params["pio_t"].to_r) * 1000).round(0).to_s if params["pio_t"]
-      if params["pio_latitude"] && params["pio_longitude"]
-        rparams["pio_latlng"] = "#{params["pio_latitude"]},#{params["pio_longitude"]}"
-      end
-      @http.apost(PredictionIO::AsyncRequest.new("/actions/u2i.#{@apiformat}", rparams))
-    end
-
-    # :category: Synchronous Methods
-    # Synchronously request to record an action on an item and block until a response is received.
-    #
-    # See also #arecord_action_on_item.
-    #
-    # call-seq:
-    # record_action_on_item(action, iid, params = {})
-    # record_action_on_item(async_response)
-    def record_action_on_item(*args)
-      action_or_res = args[0]
-      if action_or_res.is_a?(PredictionIO::AsyncResponse)
-        response = action_or_res.get
-      else
-        response = arecord_action_on_item(*args).get
-      end
-      unless response.is_a?(Net::HTTPCreated)
-        begin
-          msg = response.body
-        rescue Exception
-          raise U2IActionNotCreatedError, response
-        end
-        raise U2IActionNotCreatedError, msg
-      end
-    end
-  end
-end
