2010-01-15 39 views
5

我正在開發一個Rails應用程序,默認情況下會將用戶帳戶設置爲他們選擇的子域。作爲選項,他們將能夠將自己的完整域映射到他們的帳戶。如何將完整域映射到基於子域的Rails應用程序帳戶?

到目前爲止,這是我如何設置的東西。我使用subdomain-fu供電路由:

# routes.rb 
map.with_options :conditions => {:subdomain => true} do |app| 
    app.resources # User's application routes are all mapped here 
end 

map.with_options :conditions => {:subdomain => false} do |www| 
    www.resources # Public-facing sales website routes are mapped here 
end 

除此之外,我使用的是method described here獲得被訪問的帳戶,通過子域或全域:

before_filter :set_current_account 

def set_current_account 
    if request.host.ends_with? current_domain 
    # via subdomain 
    @current_club = Club.find_by_subdomain(current_subdomain) 
    else 
    # via full domain 
    @current_club = Club.find_by_mapped_domain(request.host) 
    end 
end 

我沒有已經遠遠落後於構建這個過程,但已經可以看到我將遇到路由問題。如果request.host是一些random.com域,那麼subdomain-fu不會路由適當的路線?

我假設這不是一個不尋常的問題,所以任何人都可以分享他們如何解決這個問題,或者我將如何配置我的路線去做我需要的東西?

回答

2

我遇到了這個問題,試圖在單個應用程序中做太多。你會開始在非常奇怪的地方做你不應該的條件。我決定將2個獨立的Rails應用程序的通配符域指向用戶的應用程序,然後將www.domain.comdomain.com指向公共端。我知道這並不能直接「回答」你的問題。

小碼味那裏,我可以幫你解決,如果您添加到該方法的頂部:

return @current_club if defined?(@current_club) 

它不會讓查詢中的每個嘗試訪問@current_club時間,它將返回你已經返回的結果。

+0

謝謝您的回答。在試用另一個解決方案後,我得出結論,你是對的,爲了簡單起見,最好的辦法是將其分成兩個應用程序,並取消subdomain-fu。 – aaronrussell 2010-01-16 15:47:40

3

您可以編寫一個Rack中間件,在將域打入Rails應用程序之前將其轉換爲子域。

class AccountDetector 
    def initialize(app) 
    @app = app 
    end 

    def call(env) 
    account = Club.find_by_mapped_domain(env["HTTP_HOST"]) 
    if account 
     env["HTTP_HOST"] = "#{account.subdomain}.yourdomain.com" 
    end 

    @app.call(env) 
    end 
end 

然後添加到environment.rb

config.middleware.use AccountDetector 
+0

謝謝。我喜歡這個答案,所以做了一些測試。您的中間件腳本運行良好,但不幸的是,它會在會話中使用一些奇怪的連鎖效應(使用Authlogic)。 我決定 - 不情願 - 將應用程序分成兩個獨立的應用程序。 – aaronrussell 2010-01-16 15:45:12