首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >为什么Rails低巡洋舰关注导致模块失去它的常量?

为什么Rails低巡洋舰关注导致模块失去它的常量?
EN

Stack Overflow用户
提问于 2018-05-03 23:46:16
回答 1查看 84关注 0票数 2

在Rails 4.2中,我有一个可排序的关注点,它有一个不变的“完整”。app/models/concerns/orderable.rb

代码语言:javascript
复制
module Orderable
  extend ActiveSupport::Concern
  COMPLETE = "Complete"
end

在Rails控制台中,我能够运行Orderable.constants,它返回[:COMPLETE]。但是,如果我将可排序的关注点更改为 module中描述的“低巡洋洋”样式,如下所示:

代码语言:javascript
复制
concern :Orderable do
  COMPLETE = "Complete"
end

然后在Rails控制台中运行Orderable.constants返回[]。Rails文档说,“定义一个关注点的低端捷径.是等价的。”为什么这一项更改会影响对模块常量的访问?我需要重新定义他们吗?

EN

回答 1

Stack Overflow用户

回答已采纳

发布于 2018-05-04 11:03:31

实际上,这似乎是在如何实现“宏”方面的一个缺陷:

代码语言:javascript
复制
require 'active_support/concern'

class Module
    # A low-cruft shortcut to define a concern.
    #
    #   concern :EventTracking do
    #     ...
    #   end
    #
    # is equivalent to
    #
    #   module EventTracking
    #     extend ActiveSupport::Concern
    #
    #     ...
    #   end
    def concern(topic, &module_definition)
      const_set topic, Module.new {
        extend ::ActiveSupport::Concern
        module_eval(&module_definition)
      }
    end
  end
  include Concerning
end

此代码猴子将ruby对象转换为提供concern方法。

这里的关键是module_eval(&module_definition),它没有在正在定义的新模块的上下文中正确地计算块。

当你跑的时候会发生什么:

代码语言:javascript
复制
concern :Orderable do
  COMPLETE = "Complete"
end

::COMPLETE
# => "Complete"

是在主对象中声明常量COMPLETE。哦哦!

要正常工作,应该如下所示:

代码语言:javascript
复制
def concern(topic, &module_definition)
  const_set topic, Module.new do |m|
    extend ::ActiveSupport::Concern
    m.module_eval(&module_definition)
  end
end

我会避免使用“低巡洋舰”语法,直到这是固定的。

票数 1
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/50165220

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档