我正在尝试在页面的页脚中创建一个联系表单,以便它在我的应用程序视图中。
我的应用程序控制器如下所示:
class ApplicationController < ActionController::Base
# Prevent CSRF attacks by raising an exception.
# For APIs, you may want to use :null_session instead.
protect_from_forgery with: :exception
before_filter :configure_permitted_parameters, if: :devise_controller?
protected
@contact = Contact.new(contact_params)
if @contact.save
name = params[:contact][:name]
email = params[:contact][:email]
body = params[:contact][:comments]
ContactMailer.contact_email(name, email, body).deliver
flash[:success] = 'Message sent.'
redirect_to ""
else
flash[:success] = 'Error occured, message has not been sent.'
redirect_to ""
end
def configure_permitted_parameters
devise_parameter_sanitizer.for(:sign_up) { |u| u.permit(:name, :stripe_card_token, :email, :password, :password_confirmation) }
end
private
def contact_params
params.require(:contact).permit(:name, :email, :comments)
end
end
我目前使用的局部视图在我的应用程序视图中看起来像这样:
<%= form_for @contact do |f| %>
<div class="form-group">
<%= f.label :name %>
<%= f.text_field :name, class: 'form-control' %>
</div>
<div class="form-group">
<%= f.label :email %>
<%= f.email_field :email, class: 'form-control' %>
</div>
<div class="form-group">
<%= f.label :comments %>
<%= f.text_area :comments, class: 'form-control' %>
</div>
<%= f.submit 'Submit', class: 'btn btn-default' %>
<% end %>
我确定它有问题,但我无法理解控制器和模型是如何协同工作的。
答案 0 :(得分:0)
protected
和private
之间的所有代码都在类的上下文中运行,因此在应用程序加载文件时。它应该抛出异常undefined method or variable params for ApplicationController:Class
您需要按请求运行它,例如:
class ApplicationController < ActionController::Base
# Prevent CSRF attacks by raising an exception.
# For APIs, you may want to use :null_session instead.
protect_from_forgery with: :exception
before_filter :configure_permitted_parameters, if: :devise_controller?
before_filter :set_contact
private
def set_contact
@contact = Contact.new
end
def configure_permitted_parameters
devise_parameter_sanitizer.for(:sign_up) { |u| u.permit(:name, :stripe_card_token, :email, :password, :password_confirmation) }
end
end
before_filter
是一种告诉控制器在每次请求之前应该做什么的方法。您只需要设置@contact
实例变量来显示并绑定表单,但是应该提交以在ContactsController
上创建操作:
class ContactsController < ApplicationController
def create
@contact = Contact.new(contact_params)
if @contact.save
ContactMailer.contact_email(@contact.name, @contact.email, @contact.body).deliver
flash[:success] = 'Message sent.'
redirect_to :back
else
flash[:success] = 'Error occurred, message has not been sent.'
redirect_to :back
end
end
private
def contact_params
params.require(:contact).permit(:name, :email, :comments)
end
end
需要注意的一点是,before_filter
将在每个操作之前运行,无论响应类型如何(即使是重定向,当您不显示任何内容时)。显然这是一种浪费,这就是为什么做以下事情可能更好:
class ApplicationController < ActionController::Base
# Prevent CSRF attacks by raising an exception.
# For APIs, you may want to use :null_session instead.
protect_from_forgery with: :exception
before_filter :configure_permitted_parameters, if: :devise_controller?
helper_method :new_contact
private
def new_contact
Contact.new
end
def configure_permitted_parameters
devise_parameter_sanitizer.for(:sign_up) { |u| u.permit(:name, :stripe_card_token, :email, :password, :password_confirmation) }
end
end
#form
<%= form_for new_contact do %>
这样,只有在需要时才会在内存中构建新的联系人。
答案 1 :(得分:0)
也许你应该为联系人创建一个新的控制器:
# /app/controllers/contacts_controller.rb
class ContactsController < ApplicationController
def new
@contact = Contact.new
end
def create
@contact = Contact.new(contact_params)
if @contact.save
ContactMailer.contact_email(@contact.name, @contact.email, @contact.comments).deliver
# Or you can send @contact object and find name, email etc. values in mailer
# ContactMailer.contact_email(@contact).deliver
flash[:success] = 'Message sent.'
redirect_to ""
else
flash[:success] = 'Error occured, message has not been sent.'
redirect_to ""
end
end
private
def contact_params
params.require(:contact).permit(:name, :email, :comments)
end
end
您的表单将进入app/views/contacts/new.html.erb
。页脚链接如下:
<%= 'Contact Us', new_contact_path %>