С тех пор я столкнулся с вариантом использования в большом приложении Rails со сложным пространством имен.Упрощенный пример:
# app/models/invoice/dependents/item.rb
class Invoice
module Dependents
class Item
# Define invoice item
end
end
end
Здесь Invoice
является собственным классом, но также является хорошим пространством имен для его зависимых элементов.Мы не можем сказать module Invoice
, потому что эта константа уже определена как класс, но мы все равно можем использовать ее в качестве пространства имен.
Giant Caveat
Если вы используете класс в качестве пространства имени вы используете Rails, убедитесь, что вы случайно не объявили этот класс в другом месте .Автозагрузка испортит ваш день.Например:
# app/helpers/invoice/dependents/items_helper.rb
class Invoice # This line will cause you grief
module Dependents
module ItemsHelper
# view helper methods
end
end
end
Тот факт, что в этом файле указано class Invoice
, создает зависимость порядка загрузки;если строка class Invoice
этого файла выполняется до определения вашего предполагаемого класса, определение предполагаемого класса может работать неправильно .В этом примере я не могу объявить, что Invoice
sublcasses ActiveRecord::Base
, если Invoice
уже был объявлен без родительского класса.
Вы могли бы требовать вашего "истинного" классафайл определения в верхней части другого файла, но, по крайней мере, в сценарии автозагрузки Rails вам придется меньше спорить, если вы сделаете это вместо этого:
# app/helpers/invoice/dependents/items_helper.rb
module Invoice:Dependents::ItemsHelper
# view helper methods
end
С этим синтаксисом Rails увидит Invoice
константа и используйте автозагрузку, чтобы найти ее, найти в файле модели и определить, как вы хотели.