私は素晴らしいApartment gemを使用したRails 4.2マルチテナントアプリを持っています。
各企業には独自のサブドメインがあります。私はカスタムの「エレベーター」を使用しています。これは完全なリクエスト ホストを調べて、どの「テナント」をロードする必要があるかを判断します。
新しい会社を作成するとき、適切なリクエスト ホストで新しいテナントを作成するための after_create フックがあります。
これには常に、開発と運用の両方でサーバーの再起動が必要なようです。そうしないと、Tenant Not Found エラーが発生します。
開発ではsqliteを使用し、本番ではpostgresを使用しています。
新しいテナントを作成するたびにサーバーを再起動する必要はありますか? これを行う自動化された方法はありますか?イニシャライザをリロードするだけでうまくいくかもしれませんが、それを行う方法がわかりません/それが可能かどうか?
私はこれを1か月間いじっていましたが、うまくいく解決策を見つけることができませんでした. 助けてください!
初期化子/アパートメント.rb
require 'apartment/elevators/host_hash'
config.tenant_names = lambda { Company.pluck :request_host }
Rails.application.config.middleware.use 'Apartment::Elevators::HostHash', Company.full_hosts_hash
初期化子/host_hash.rb
require 'apartment/elevators/generic'
module Apartment
module Elevators
class HostHash < Generic
def initialize(app, hash = {}, processor = nil)
super app, processor
@hash = hash
end
def parse_tenant_name(request)
if request.host.split('.').first == "www"
nil
else
raise TenantNotFound,
"Cannot find tenant for host #{request.host}" unless @hash.has_key?(request.host)
@hash[request.host]
end
end
end
end
end
会社のモデル
after_create :create_tenant
def self.full_hosts_hash
Company.all.inject(Hash.new) do |hash, company|
hash[company.request_host] = company.request_host
hash
end
end
private
def create_tenant
Apartment::Tenant.create(request_host)
end
何がうまくいったのか
エレベーターの構成を変更して、アパートの宝石にある HostHash の構成を回避し、完全にカスタムのものを使用しました。主にアパートメントの宝石 github の問題に基づいています: https://github.com/influitive/apartment/issues/280
初期化子/アパートメント.rb
Rails.application.config.middleware.use 'BaseSite::BaseElevator'
アプリ/ミドルウェア/base_site.rb
require 'apartment/elevators/generic'
module BaseSite
class BaseElevator < Apartment::Elevators::Generic
def parse_tenant_name(request)
company = Company.find_by_request_host(request.host)
return company.request_host unless company.nil?
fail StandardError, "No website found at #{request.host} not found"
end
end
end