Sorry if my question is stupid, but I spent lot of time searching solution and I didn't find.

I'd like to create an ApiOutputsHandler model without database. So I've created an ActiveModel. This model will be used for custom responses of my API such as errors (but not only). I've used the send() method to add the attributes to this model, but think it's very crappy...

class ApiOutputsHandler

  attr_accessor :status, :type, :message, :api_code, :http_code, :template

  ERR_TYPES = {
    :permanent_quota_limit => { :type => 'PermanentLimitException', :message => 'Quota limit reached for this action', :api_code => 700, :http_code => 401 } 
  }

  def initialize(data)
    data.each do |name, value|        
      send("#{name}=", value)  
    end
  end

  def error()
    send('status=','error')
    send('template=','api/v1/api_outputs_handler/output')
    return self
  end

  def new
    return self
  end

end

Then, I instantiate my Object like this

@output = ApiOutputsHandler.new(ApiOutputsHandler::ERR_TYPES[:permanent_quota_limit]) 
return @output.error()

I'll avec a lot of ERR_TYPES (that's the interest). Do you think there's a better way to do that ?

When I inspect the created object, it lokks like this:

#<ApiOutputsHandler:0x000000036a6cd0 @type="PermanentLimitException", @message="Quota limit reached for this action">

Do you see the arobase in front of attributes? Why do I get that instead of the common:

#<ApiOutputsHandler:0x000000036a6cd0 type: "PermanentLimitException", message: "Quota limit reached for this action">

thanks for your help!

有帮助吗?

解决方案

Yes, there is a better way to do it. Here's how I would go about it:

class ApiOutputsHandler
  attr_accessor :status, :type, :message, :api_code, :http_code, :template

  ERR_TYPES = {
    :permanent_quota_limit => { :type => 'PermanentLimitException', :message => 'Quota limit reached for this action', :api_code => 700, :http_code => 401 } 
  }

  def initialize(data)
    # added it here so that you can pass symbol error code to initializer
    data = ERR_TYPES[data] if data.is_a?(Symbol)

    data.each do |name, value|        
      send("#{name}=", value)  
    end
  end

  def error
    self.status = 'error'
    self.template= 'api/v1/api_outputs_handler/output'
    self
  end
end

This way, you can just pass the symbol error code to the initializer, like this:

handler = ApiOutputsHandler.new(:permanent_quota_limit)

You also can change how your objects looks in console, you just need to redefine the #inspect method. In your case, it might look like this:

def inspect
  "#<#{self.class.name} type: #{type}, message: #{message}>" # etc
end
许可以下: CC-BY-SA归因
不隶属于 StackOverflow
scroll top