2016-08-05 11 views
0

データベースの一部のフィールドで暗号化を使用する必要があるアプリケーションがあります。これは現在、インクルードされたクラスのフィールドの暗号化と管理の詳細を処理する問題を使用して実装されています。システムがこの問題を含むクラスをプログラムで決定できることは重要ですが、さらに具体的にはプログラムによってどのフィールドが暗号化されているかを判断する良い方法が必要です。Ruby ActiveSupport :: Concernでクラス変数を使用する代わりに

今日、これは、このようなクラス変数を使用して、働いて、実装されています。

クラスに含ま
module EncryptedFields 

    extend ActiveSupport::Concern 

    included do 
     @@encrypted_attributes ||= {} 
     @@encrypted_attributes[self.to_s] ||= [] 

     def self.encrypted attribute, options={} 

      @@encrypted_attributes[self.to_s] << attribute 

      ### Other stuff 
     end 
    end 
end 

、次のように:

class SomeEcryptedModel 

    include EncryptedFields 

    encrypted :field_name, options 
    encrypted :other_field_name, options 

    #etc 
end 

クラス変数@@encrypted_attributesが正しくキーのハッシュをキャプチャします値をキーとして含むクラス名と値としての暗号化された属性の配列との値のペア。私は、暗号化されたモデルの登録システムを使って自分自身とその属性を登録し、その属性を登録することを検討しましたが、これに関連するオーバーヘッドがさらに増え、私のタイムラインでは、 。

これは現在のアプリケーションでうまく動作していますが、懸念やクラス変数に関する多くの経験がないため、これがどのように動作するかについて深刻な誤算をしたかどうかについて心配しています。ここには何がありますか?私はRubyを使って作業を始めて以来、プログラミングされてきました。クラス変数は一般的に回避されるべきです。

私は最初にこのクラスの変数@@encrypted_attributesが含まれているクラスのクラス変数になると考えていたので、これで既に噛まれました。これは明らかにそうではありませんでした。それを含む新しいモデルがすべてそれを上書きするので、私はこのクラス変数が明らかに懸念そのものであったという結論に達しました。少なくとも、これは私が目撃しているように見える行動です。暗号化されたモデルの完全なリストを得ることができるので、これは最終的により望ましい動作であることが判明しました。これは、ロードされたモデルの暗号化されたモデルと属性のリストのみを返すことができるという明らかな制限があります。

だから、私の質問:

が、これはクラス変数のための適切な使用のケースです、またはこれと同じ情報を取得するための代替(よりよい?)方法はありますか?これが許容可能なクラス変数のユースケースである場合、私が意図したとおりにコードが動作するようにするために加えるべき落とし穴や保護のいくつかはありますか?

たぶん私はあまりにも賢い人にしようとしています。助けてくれてありがとう!

答えて

2

あなたは懸念のアプローチに代わり、この道を行くことができます。

module EncryptedFields 
    @encrypted_attributes ||= {} 

    def self.included(klass) 
    @encrypted_attributes[klass.name] ||= [] 
    klass.extend(ClassMethods) 
    end 

    def self.add(class_name, attribute) 
    @encrypted_attributes[class_name] << attribute 
    end 

    module ClassMethods 
    def encrypted(attribute, options={}) 
     EncryptedFields.add(name, attribute) 
     # Other stuff 
    end 
    end 
end 

class Stuff 
    include EncryptedFields 

    encrypted :ololo 
    encrypted :new_name 
end 

EncryptedFields.instance_variable_get(:@encrypted_attributes) 
=> {"Stuff"=>[:ololo, :new_name]} 

あなたがここにクラス変数は必要ありません。モジュールインスタンス変数で十分です。あなたには継承はなく、モジュールのインスタンスを実際に作成することはできません。したがって、常にという変数が定義される場所は1つだけです。 http://www.railstips.org/blog/archives/2006/11/18/class-and-instance-variables-in-ruby/

+0

ありがとう:クラス変数とクラスのインスタンス変数の違いについて

良い記事。これは教育的な答えでした。質問のためにコードを簡略化したので、これは正確にはうまくいかないかもしれませんが、私は新しい方向に考えていました。 – BoringJangles

関連する問題