Ruby模块中的覆盖方法

时间:2020-07-12 00:47:05

标签: ruby-on-rails ruby spina-cms

在Spina中有一个Account

其中称为方法:

serialized_attr_accessor :google_analytics, :google_site_verification, :facebook, :twitter, :instagram, :youtube, :linkedin, :google_plus, :theme

我在我的 / app / models / spina 目录中创建了一个类 Account 的模块 Spina ,其代码与gem的帐户模型(唯一更改的行)是:

serialized_attr_accessor :google_analytics, :google_site_verification, :facebook, :twitter, :instagram, :youtube, :linkedin, :twitch, :github, :theme

(基本上增加了2个属性)

我非常确定,这是不正确的方法,并且缺乏有关思想在Rails中如何工作的知识。对于这些信息,我们将感到非常高兴,这里将是正确的解决方案/方法。

P.S。 Ruby和Rails的新手,所以请严格回答。

更新12.07.20-1 我创建了一个猴子补丁:

〜/ app / models / spina / account.rb

module Spina
  class Account < ApplicationRecord
    # here putted all code from [Account](https://github.com/SpinaCMS/Spina/blob/master/app/models/spina/account.rb)
  end
end

1 个答案:

答案 0 :(得分:1)

免责声明:我自己还没有使用过Spina,也不知道这个项目。

与其说是Rails问题,还不如说它是关于宝石以及它的作者如何设想对其进行定制的。

从查看gem here(第16-29行)的代码来看,serialized_attr_accessorSpina::Account的类方法,它遍历了提供的每个参数并添加了getter和动态设置方法。

通常来说,在Rails中可以添加文件app/models/spina/account.rb,然后重新打开类是正确的。但是,它不会取消其他文件中类的定义。因此,原始的serialized_attr_accessor调用仍会被调用-在这种特殊情况下,您不能忽略它。

只要您要添加属性而不删除任何属性,就可以执行以下代码,并且应该具有所需的行为。您可以将此代码放入初始化程序中(例如,在config/initializers/spina.rb下-config/initializers下的所有文件都是按字母顺序运行的,这是Rails引导过程的一部分)

Spina::Account.serialized_attr_accessor :twitch, :github

但是,尽管此修复程序可能今天对您有用,但是如果Spina的作者未指定该扩展性作为gem界面的一部分得到支持,那么您将冒着明天(更确切地说,在下一版Spina中)的风险。 ),它可能会破裂。作者很可能从未打算serialized_attr_accessor公开,而是可能在下一个版本中重命名/删除/更改其行为-破坏您的应用程序。

通常来说,打开类(称为“猴子修补”)和调用非公共方法(或非预期接口)是一种应谨慎使用的做法,即使它可以在Ruby中完成,因为您正在耦合代码与gem的实现有关。

此“修复”的另一点注意事项。您添加的这两个属性在数据库中不是永久的。它们仅存储在内存中。我不确定其他领域是否仍然存在,因为我对gem不熟悉。但是,如果需要它们保持持久性,则必须在Rails中添加迁移。您可以创建一个迁移来修改spina_accounts表,但这听起来是个坏主意,因为它将应用程序与实现紧密结合在一起。您还可以考虑创建自己的accounts表,通过引用帐户记录(例如spina_account_id)来扩展Spina帐户,并添加所需的其他字段。

无论哪种方式,我建议在gem的github页面上打开一个问题,并询问他们是否正式支持自定义帐户属性的功能。

相关问题