class UserTweet include Mongoid::Document field :user_desc, type:String field :type, type:String field :tweet_uuid, type:String belongs_to :tweet scope :tweet_uuid_exists, ->(tweet_uuid){ where(tweet_uuid: tweet_uuid) } scope :type_exists, ->(type){ where(type: type) } scope :user_desc_exists, ->(user_desc){ where(user_desc: user_desc) } def self.params=(params) @params = params end def self.params @params end def self.criteria UserTweet.where(user_desc: params[:user_desc], type: params[:type], tweet_uuid: params[:tweet_uuid]) end def self.save if !criteria.exists? tweet = Tweet.find_by(uuid: params[:tweet_uuid]) tweet.user_tweets.create(Hash[params]) _success else _fail('already requested') end end def self.delete if criteria.exists? criteria.delete _success else _fail('resource not exists') end end private def self._success {:result => 1, :msg => 'success'} end private def self._fail(msg) {:result => 0, :msg => msg} end end
위의 코드를 보시면 아시겠지만 params의 setter/getter 함수에서 인스턴스 변수를 사용했습니다. 실제 컨트롤러에서는 다음과 같이 호출했습니다.
def set_params UserTweet.params = params.except(:action, :controller) end그럼 이제부터 model에서 instance variable이 갖는 의미를 알아보도록 하겠습니다.
먼저 @의 의미부터 알아봐야 될 것 같습니다.
만약 variable, @variable 2 가지의 변수가 있다고 해보겠습니다.
각각의 변수가 가지는 의미는 다음과 같습니다.
variable : 지역변수, 현재 블락에서만 사용 가능하다.
@variable : 인스턴스 변수 클래스내의 모든 메소드에서 사용 가능하다.
테스트를 해보겠습니다. 저 위의 코드에서 실제로 @params를 제거하면 "undefined method" 에러가 발생합니다. 실제로 attr_accessor 또한 인스턴스 gettter/setter를 생성시키므로 attr_accessor을 명시한다고 해도 같은 에러가 발생합니다. 따라서 params의 getter/settter에서 params 인스턴스 변수를 생성시킴으로써 모든 메소드에서 해당 변수에 접근할 수 있게 됩니다.
그럼 model에서 인스턴스 변수가 갖는 의미를 알아보겠습니다. model에서도 같은 의미를 사용될 수 있는데 저렇게 사용되면 각 객체의 변수라기 보다는 클래스의 변수라고 보면 됩니다. 그렇기 때문에 위 처럼 사용해도 문제가 없습니다.
그럼 상단의 코드를 좀 더 깔끔하게 수정해보겠습니다.
class UserTweet class << self
attr_accessor :params
endparams에 대한 getter/settter를 제거하고 위와 같이 변경하였습니다.
저렇게 변경해도 에러가 발생하지 않고 상단코드와 똑같은 의미를 가지게 됩니다.
그럼 저 코드를 분석해 보도록 하겠습니다.
상단의 코드는 params attribute_accessor를 인스턴스 레벨이 아닌 클래스 레벨에 추가하게 됩니다.
class << self는 self 싱글턴 클래스를 가져오게 되고 그러므로 self 안에 정의된 attr_accessor이 self 객체에 재 정의됩니다. 이 문법은 특히 메타클래스라 부릅니다. 그러므로 이 문법은 상단의 gettter/setter와 일치하게 됩니다.
감사합니다.
댓글 없음:
댓글 쓰기