Ruby on rails 如何定义与Rails autoloader一起使用的嵌套控制器?
假设我有两个定义为控制器的标准rails资源,每个都有自己的CRUD操作(Ruby on rails 如何定义与Rails autoloader一起使用的嵌套控制器?,ruby-on-rails,constants,autoload,Ruby On Rails,Constants,Autoload,假设我有两个定义为控制器的标准rails资源,每个都有自己的CRUD操作(index,show,等等) EmployeesController Employees::AssignmentController 目录看起来像- app/ controllers/ - employees_controller.rb employees/ - assignment_controller.rb 我正试图找出如何最好地定义第二个嵌套控制器来与Rails autoload
index
,show
,等等)
EmployeesController
Employees::AssignmentController
app/
controllers/
- employees_controller.rb
employees/
- assignment_controller.rb
我正试图找出如何最好地定义第二个嵌套控制器来与Rails autoloader一起工作
选项A-命名空间常量
如果我这样做-
class Employees::AssignmentController
在运行集成测试时,我的应用程序日志中出现以下错误:
LoadError:无法自动加载常量Employees::AssignmentController,应为/Users/jeeves/git/my project/app/controllers/Employees/assignment\u controller.rb来定义它>
它不喜欢将常量定义为单个命名空间-Employees::AssignmentController
选项B-模块内的嵌套常量
如果我这样做-
模块员工
类赋值控制器<应用程序控制器
结束
结束
我实际上得到了与上面相同的LoadError
错误
选项C-类内的嵌套常量
最后,如果我这样做了-
类员工
类赋值控制器<应用程序控制器
结束
结束
我得到TypeError:Employees不是一个类,这是有意义的,因为外部类没有定义。我试图通过添加一个带有空文件的显式类定义来修复它
app/
controllers/
- employees_controller.rb
+ - employees.rb
employees/
- assignment_controller.rb
类员工
结束
这是有效的。但是让这个额外的虚拟文件挂在app/controllers
中感觉很傻,尤其是当它本身不是控制器的时候
问题:
有没有正确的方法来处理上述情况?选项C是我唯一的选择吗?我是否正确地使用了名称空间,还是应该同时避免使用它们
谢谢
使用显式
筑巢。使用范围解析运算符可能会导致意外的结果
由于Ruby的词法范围(取决于
模块嵌套在定义点。
这种令人惊讶的行为的一个例子是:
class Employees::AssignmentController
def index
@rate = Rate.find(...)
end
end
您希望Rate解析为Employees::Rate
,但实际上它解析为::Rate
,因为词法范围是::
这是首选方法:
module Employees
class AssignmentController
def index
@rate = Rate.find(...) # resolves to Employees::Rate
end
end
end
它将重新打开模块,并在正确的词法范围内定义一个新常量
至于备选方案C——这是可能的,因为Ruby中的类是模块(如果你不相信我的话,请检查Class.concedens
),但它不被认为是好的形式,因为类应该是可以实例化的东西
rails生成器使用scoperesolution操作符以“错误”的方式完成此操作,但这实际上只是由于文件模板系统中的限制
那为什么会出现加载错误呢?
我真的不知道。这是首选的方法,没有明显的理由说明它在这种情况下不起作用。仔细检查一切。通过运行spring stop
重新启动spring,然后重新启动服务器 这里需要注意的一点是,您使用的是singularAssignmentController
,如果您声明的是singular resource,这是很好的,但如果用户可以有许多工作分配,并且您使用的是resources:assignments
,则情况并非如此。