2015-06-09 2 views
0

У меня есть контроллер, который будет серверные виджеты:как DRY a reply_to то же самое во всех действиях?

class WidgetsController < ApplicationController 
    def widget1 
    respond_to do |format| 
     format.html 
     format.js { render js: js_constructor } 
    end 
    end 

    def widget2 
    respond_to do |format| 
     format.html 
     format.js { render js: js_constructor } 
    end 
    end 

    private 
    def js_constructor 
    content = render_to_string(params[:action], layout: false) 
    "document.write(#{content.to_json})" 
    end 
end 

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

respond_to do |format| 
    format.html 
    format.js { render js: js_constructor } 
end 

Любая идея?

EDIT: просто чтобы дать некоторый контекст ...

Маршрут гибок/динамическая: get 'widgets/:action', to: 'widgets#:action'

Так что, если я посещаю widgets/widget1 будет оказывать вид widget1.html.erb.

Если я включаю скрипт на другом сервере, он будет строить WIDGET1 там:

<script type='text/javascript' src='http://localhost:3000/widgets/widget1.js'></script> 
+3

Если нет буквально никакой разницы между виджетами, почему вы создаете несколько маршрутов для них? – Makoto

+1

Каждое действие возвращает содержимое соответствующего вида. Существует только один гибкий маршрут ('get 'widgets /: action', to: 'widgets #: action''). Таким образом, html-формат используется для разработки, а js будет строить представление в другом месте ('') , – gabrielhilal

+0

@Makoto: Я отредактировал свой вопрос, чтобы предоставить некоторый контекст. Надеюсь, теперь это ясно;) – gabrielhilal

ответ

1

Я хотел бы написать одно действие, который принимает «вид» в качестве параметра. Вы в основном делаете действие #show, которое отображает разные виды.

get 'widgets/:template', to: 'widgets#show'

class WidgetsController < ApplicationController 
    def show 
    respond_to do |format| 
     format.html { render params.require(:template) } 
     format.js { render js: js_constructor } 
    end 
    end 

    private 
    def js_constructor 
    content = render_to_string(params.require(:template), layout: false) 
    "document.write(#{content.to_json})" 
    end 
end 
+0

безупречный! спасибо;) – gabrielhilal

+0

с точки зрения безопасности и ремонтопригодности вы должны использовать массив, содержащий все допустимые шаблоны, и предоставить шаблон по умолчанию. – phoet

1

И ответ мета-программирования:

class WidgetsController < ApplicationController 
    [:widget1, :widget2].each do |name| 
    define_method(name) do 
     respond_to do |format| 
     format.html 
     format.js { render js: js_constructor } 
     end 
    end 
    end 

    private 

    def js_constructor 
    content = render_to_string(params[:action], layout: false) 
    "document.write(#{content.to_json})" 
    end 
end