Как избежать глобальных изменений с помощью динамически загружаемых файлов ruby - PullRequest
0 голосов
/ 18 ноября 2011

Я сейчас нахожусь в положении, когда у меня есть папка плагинов, в которой может быть загружено 1 или 100 плагинов.

Теперь проблема в том, что каждому плагину требуется экземпляр определенного классав файле запуска ruby.

Действительно упрощенным примером будет:

#startup.rb

def load_plugins
    #... get each plugin file
    require each_plugin
end

class MuchUsedClass
    def do_something
        #...
    end
end

muchUsedInstance = MuchUsedClass.new
load_plugins

#some_plugin.rb

class SomePluginClass
    def initialize(muchUsedInstance)
        @muchUsedInstance = muchUsedInstance
    end

    def do_something_with_instance
        @muchUsedInstance.do_something
    end
end

somePluginInstance = SomePluginClass.new(muchUsedInstance)
somePluginInstance.do_something_with_instance

Основная проблема заключается в том, что когда вы вызываете require, он не имеет никакого представления о том, что произошло раньшеэто требуется.Так что мне неприятно делать глобальную переменную в файле запуска просто для удовлетворения всех остальных необходимых файлов, но кажется, что это единственный из способов передачи некоторых данных во включаемый файл, я также мог бы создать одноэлементный классразоблачить кое-что из этого, но это также кажется немного неприятным.

Поскольку я все еще плохо знаком с рубином и все еще смотрю через очки со статической типизацией, я, вероятно, упущу приличный шаблон для решения этой проблемы, вC # Я бы выбрал внедрение зависимости и просто подключил все таким образом ...

1 Ответ

2 голосов
/ 18 ноября 2011

Ваш пример кода не имеет глобальной переменной. Глобальные переменные имеют имена, начинающиеся с $. Код, который вы написали, не будет работать, потому что muchUsedInstance - это просто локальная переменная, которая не будет использоваться разными файлами Ruby.

Если вы никогда не собираетесь изменять экземпляр, вы можете легко сохранить его как константу:

MuchUsedInstance = MuchUsedClass.new

Вы можете хранить его как вложенную константу внутри класса:

MuchUsedClass::Instance = MuchUsedClass.new

Вы можете сохранить его как переменную экземпляра внутри объекта класса с помощью метода get, который автоматически создает его, если его там еще нет:

def MuchUsedClass.instance
  @instance ||= MuchUsedClass.new
end
...