2016-09-02 52 views
0

我试图让attr_encrypted在将某些数据保存到数据库之前隐藏一些数据。我需要稍后处理记录器输出,但目前我只想从提交的表单获取字段数据,对其进行加密并保存。Rails使用attr_encrypted访问私有方法

这里是我的模型:

class Agreement < ApplicationRecord 
    attr_encrypted :test_field, key: :encryption_key 

    private 

    def encryption_key 
     ENV['super_secret_key'] 
    end 
end 

我注意到,当我注释掉private似乎一切都按预期运行。但我显然不希望公开访问该信息(你知道:超级密钥),所以我想要它是私人的。但是,当我包含private时,出现错误。具体来说:NoMethodError (undefined method 'bytesize' for :encryption_key:Symbol)。我已经钻研的是attr_encrypted正在抛出一个错误,因为它没有得到传递给它的密钥,因为私有方法没有被正确访问。

理论上,在attr_encrypted位,我可以只设置key: ENV['super_secret_key']而不是调用一个方法,但这里的目标是实际创建一个带有相应数据库表的新类,通过该类可以保存,存储和旋转我的密钥,而后者又被一个环境变量混淆以获得额外的安全层。

所以我真正的问题是:我的私人方法发生了什么,为什么private令人沮丧,甚至在模型的范围内?我想我正在做一些基本上不正确的事情,但我也遵循了其他人的例子,所以对我的错误的任何指导都将不胜感激!

回答

1

问题是attr_encrypted调用是在类级别,而encryption_key方法是实例级别。尝试这样做,而不是:

class Agreement < ApplicationRecord 
    attr_encrypted :test_field, key: ENV['super_secret_key']] 
end 

承认未经测试,但它应该工作。

真的,虽然私人不会再保护它。你通过从配置文件通过env加载它。只要它没有在你的仓库中硬编码,那主要是你需要做的。

+0

感谢您的回复!不幸的是,似乎并没有这样做。 1)我在这里错过了什么(显然是基本的东西)?你怎么知道'attr_encrypted'是在课堂级别,而'encryption_key'是在实例级别?为什么删除'私人'使其工作? 2)不管这是否有效,私人为什么不再保护它?谢谢! – DanielNordby

+0

我应该更仔细地阅读错误。您需要调用该方法并将结果传递给attr_encrypted。所以你可以这样做:'attr_encrypted:test_field,key:encryption_key'。注意我删除了这个符号,并且只有方法名。但是,相反,因为它在应用程序加载时调用一次,为什么即使有这个方法呢?所以我更新了我的答案,只是输出环境。 – agmcleod

+0

要回答你的第二个问题,保持它的安全将不会暴露在任何控制器渲染调用中。只要你在模型中访问它,它应该没问题。鉴于它在ENV []中,您可以在应用程序的任何地方访问它。 – agmcleod