jasagiri @ ウィキ

甘えたアダプタ

最終更新:

jasagiri

- view
管理者のみ編集可

最近、 Simon Harris はアイデアを持っていました。: Ambition の nil? について。甘い砂糖(?)

作るのに何が必要か理解しましょう。

User.select { |x| x.nil? }

と同様に振舞います。

User.select { |x| x == nil }

Ambition では

Short and Sweet Simon のアプローチは to modify Ambition ディレクトリを変更し、nil? を追加することになりました。 これは確かに野心的です。 nil? は単なるメソッドです。特別なことはありません。 アダプタでどうやって使うか決めるはずです。

簡単です。ここで ActiveRecord アダプタの Select translator に加えたものがあります:

def nil?(column)
  left = "#{owner.table_name}.#{quote_column_name column}" 
  negated? ? not_equal(left, nil) : self.==(left, nil)
end

See it in action on lines 84 to 87. テストはもちろん types_test に見つけられる.

Chaining Stuffs さて、どうやってこれは動作しているのでしょう。

すべてのアダプタの Select translator は特別な chained_call メソッドを持っています。 Ambition は chained_call を呼び出し、chained.method.call が実行されたときにシンボルの配列を通ります。

この場合、 chain は m.name.nil? です。 Ambition は m が自分自身だと知って、無視します。 chained_call に [ :name, :nil? ] を渡します。

ActiveRecord adapter の chained_call メソッドは通された配列 を受け取って、2つ目の要素が見つかったら1つ目の要素を送ります。(?)

基本:

# methods = [ :name, :nil? ]
if respond_to? methods[1]
  send(methods[1], methods.first)
end

変換すると:

self.nil? :name

クール。 このようにアダプタはセットアップされる必要はありませんが ActiveRecord と動いています。

Notice: ActiveRecord アダプタは2つのメソッドを深くはサポートしません。2番目を呼んで、1番目を通し、残りは無視します。ほんとがっかりします。懸垂(?) – これは ActiveRecord の仕様です。 Ambition では任意の長さの連鎖をサポートしますし、あなたのアダプタもそうでしょう。

So array.include?, right?

The thing is, chained_call は、Ambition 自身のオブジェクトが実行されるときに、単に呼び出されるだけです。

User.select { |x| x.nil? }

上では、 Ambition は x を持っています。それ自身 as far as translator と関係があります。

User.select { |x| [1,2,3].include? x.id }

Ambition は配列自身ではなく、ただ x.id だけです。何が起こるでしょう。

Well, it’s the same as [1,2,3] == x.id to Ambition. The dude really doesn’t care. いつも 左辺 演算子 右辺 のようになっており、 Ambition はあなたの translator で op(left, right) を呼びます。.

呼び出しのアイデアはこうです:

include?([1,2,3], x.id)

運良く x.id はこれより先に翻訳されます。呼び出しは本当そっくりです。

include?([1,2,3], 'users.id')

ActiveRecord の translator に include? を定義するのはとても簡単です。:

def include?(left, right)
  left = left.map { |element| sanitize element }.join(', ')
  "#{right} IN (#{left})" 
end

すばらしい。


Join the Fun

While the Err twitter is great for general stuff, you should really hop on the Ambition mailing list if you want in on this action. Or just watch the project on GitHub.

ではまた。

記事メニュー
目安箱バナー