如何让rails引擎与主App交互

Syl*_*Syl 4 gem ruby-on-rails

我正在创建一个用作支付服务接口的rails引擎.我必须处理支付服务在任何交易之外向我发送消息的用例.我将采用以下用例:

引擎收到一条消息,说明订阅FooBar42已正确计费(通过它自己的路由).我的引擎下一步做什么?如果我开始调用特定于我的应用程序的模型,我的引擎只适用于此应用程序.只有我能找到的例子是Devise,但在设计中,它只是为您的用户模型添加方法,引擎处理用户的存储方式和所有代码.

如何创建可重用的系统,我的引擎可以在主应用程序中调用/触发代码?

我是否覆盖发动机控制器?我是否使用空方法生成服务对象,将其用作引擎应用程序通信系统?

Die*_*zar 5

您需要有一种方法可以在初始化程序中或通过调用模型中的类方法来配置引擎,就像devise在User类的主体中调用时如何配置Devise以使用User模型:

class User < ActiveRecord::Base
  devise :database_authenticatable
end
Run Code Online (Sandbox Code Playgroud)

对于我的一个引擎,我使用初始化程序,它使用配置对象存储引擎与之交互的类.

给定一个配置对象:

class Configuration
  attr_reader :models_to_interact_with

  def initialize
    @models_to_interact_with = []
  end
end
Run Code Online (Sandbox Code Playgroud)

然后,您可以在lib的主引擎文件中提供配置挂钩作为模块方法:

require 'my_engine/configuration'

module MyEngine
  mattr_reader :config

  def self.configure(&block)
    self.config ||= Configuration.new
    block.call self.config
  end
end
Run Code Online (Sandbox Code Playgroud)

现在,当您进入主应用程序时,可以创建初始化程序config/initializers/my_engine.rb并将模型添加到配置中:

MyEngine.configure do |config|
  config.models_to_interact_with << User
  config.models_to_interact_with << SomeOtherModel
end
Run Code Online (Sandbox Code Playgroud)

现在您可以从引擎访问此引擎,而无需在引擎中对模型进行硬编码:

# in some controller in your engine:

def payment_webhook
  MyEngine.config.models_to_interact_with.each do |model|
    model.send_notification_or_something!
  end
end
Run Code Online (Sandbox Code Playgroud)

希望这能回答你的问题.