Devise error messages missing after custom redirect - forms

I have a custom redirects in place for my devise sign up forms, I have two forms, one for an individual and another for a company. I have added this in the create action of the registrations controller:
if resource.company_form
redirect_to new_user_registration_path(company: true)
else
redirect_to new_user_registration_path
end
In doing this though I have lost all the devise error messages, as in the don't display any validation errors, so I need to send the error messages along with the redirect, don't I? However, I am not sure how.
So far I have tried printing the error messages to the console:
ap(resource.errors.full_messages)
[
[0] "Email can't be blank",
[1] "Password can't be blank",
[2] "Company name can't be blank"
]
Whereas this:
ap(resource.errors)
#messages={:email=>["can't be blank"], :password=>["can't be blank"], :company_name=>["can't be blank"]}
How would I get the error messages to be displayed above the form again?

The magic of devise error messages is made with respond_with method.
Hence you can change the redirect_to for a respond_with block
respond_with(resource) do |format|
if resource.company_form
format.html { render 'new', locals: { is_organisation: true } }
else
format.html { render 'new' }
end
end
and in your view
<% params[:organisation] ||= is_organisation -%>

Not sure if this will help, but you can customize this even further with your messages. First things first it's a good idea to actually ensure this works first. Then customize it further.
Add your toastr gem to your gemfile.
gem 'toastr-rails', '~> 1.0'
In your application.js you will need to add //= require toastr
In your stylesheet.scss you will need to import toastr #import "toastr";
Then run bundle in your terminal
In your views/devise/registrations/ folder and views/devise/password/ folder, the pages inside are your devise views that show the error messages. There you will find the error messages by devise. <%= devise_error_messages! %>
So what you wanna do, is customize these messages.
Now go to views/shared and create a new file and name it _devisemes.html.erb
<% unless resource.errors.empty? %>
<script type="text/javascript">
<% resource.errors.full_messages.each do |value| %>
toastr.error('<%= value %>')
<% end %>
</script>
<% end %>
After you have saved this file. Just go to the following files and find
<%= devise_error_messages! %>
Replace it with <%= render 'shared/devisemes' %> in the following files below:
views/devise/registrations/edit.html.erb
views/devise/registrations/new.html.erb
views/devise/password/new.html.erb
views/devise/password/edit.html.erb
Now logout and go to create an account and without an email, or password and test it. You will notice all the error messages from devise showing up with toastr.

Related

Redirection after Form Submission

In Silverstripe < 3 you can do smth like this in a form action
Director::redirect(Director::baseURL(). $this->URLSegment . "/?success=1");
and then in Template you can check with <% if Success %> if the Form is submitted.
in >3.1 you'll get
Fatal error: Call to undefined method Director::redirect()
somehow one shold use SS_HTTPRequest but i do not get it how to use this guy.
I want to show a simple success message after form submission.
Assuming you are handling the form submission in a Controller to redirect you could use
$this->redirect( Director::baseURL() . $this->URLSegment . "/?success=1" );

Ruby on Rails redirect_to with own params/values

i have a very similar question like this one:
Rails redirect_to with params
so, i learned from this thread, that i can add Params to the Controllers redirect_to like this:
format.html { redirect_to #order, :test => "test", notice: 'Order was successfully created.' }
As far as i understood it, with this, i should be able to show the value of :test in the view.
But if i try to access it like this
<p>
<b>Zahlungsart:</b>
<%= params[:test] %>
</p>
nothing happens.
Also it doesn´t seem to be a part of the parameters cause
<%= params.inspect %>
just shows
{"action"=>"show", "controller"=>"orders", "id"=>"32"}
I don´t know what exactly went wrong here.... the redirect_to is the one, which is called by default by the Controller´s "create" action.
So far, i fixed this by just defining $test which is accessible with <%= $test %> in the view... but this seems to be very ugly for me (isn´t it???).
Just to make it clear, the parameter i want to pass to the view is not an instance of a class like the #order in the default definition of the controller is. it´s just a varialbe with a value that i want to pass to the view.
what would be the normal (RESTful <- if i´m understanding this expression in the right way...) way of just adding a param???
Thanks in advance for enlightening me once again ;-)
Greetings
Tobi
You should use it like this
format.html { redirect_to order_path(#order, :test => "test"), notice: 'Order was successfully created.' }

RefineryCMS, Upload Image on FrontEnd side

Sorry about quite silly question but after several days of searching I still don't have the answer and I'm realy stackoverfloved about it.
I have refinerycms extension. Like this:
$ rails generate refinery:engine shop name:string logo:image
I want it to be controlled from both backend and frontend of my application.
Have no problems with backend. (Thank you for refinerycms team.)
Have no problems with frontend when the form contains only "name". (Or any other attribute that doesn't have image type).
Have problems with image type attributes.
I don't want frontend user to have the same image editing form as backend users does.
I want the form to be smth like this:
<div class='field'>
<%= f.label :logo , "Logo"%>
<%= f.file_field :logo %>
</div>
And I want images loaded by frontend user to be saved with Refinery::Image.
I bet the problem is only in my frontend controller create action for shops, but I have no clue how it should be overwritten.
Thanks a lot for any suggestion.
In the controller, you will have to pass the 'logo' param to the model as a Refinery::Image instance. To do so, you create an instance of Refinery::Image and merge it to the model.
Example:
logo = Refinery::Image.create(image: params[:shop][:logo])
#shop = Refinery::Shops::Shop.create(params[:shop].merge({logo: logo}))
I have FE form with file_field (:logo) on FE and in my normal controller (not the admin one) I have this method to handle params from request:
def model_params
permitted = params.require(:model).permit!
permitted[:logo] = Refinery::Image.create(image: permitted[:logo])
return permitted
end
to permits params and create image form file.
And then in my create method:
def create
if (#new_beer = ::Refinery::Models::Model.create(model_params))
#do some stuff when it succeeds to create it
redirect_to SOMEWHERE
else
redirect_to SOMEWHERE, notice: "Something went wrong!"
end
end
Hope it can help! :)

Add a honeypot-field to Devise registration form

I will add a honeypot-field to the devise registration form (as a simple captcha). Where is the best place to check if data has been entered into this field?
If a bot has entered something into this field, he should be sent back to the index page without notification. As I am still far from being fluent in Rails, it would be helpful to see the syntax for this too.
I think the best place to do that is at the model, because it may be a business logic to accept only records from "verified humans".
You can create a validation method that does this:
class Comment < ActiveRecord::Base
validate :honeypot_absence
def honeypot_absence
record.errors.add :invisible_field, "You should not fill the invisible field" unless invisible.field.blank?
end
end
I had a similar issue with bots signing up via my Devise registration form so tackled it by doing the following:
Added a simple honeypot input to the view. (You will have needed to generate the views before you can do this - rails generate devise:views)
# app/views/devise/registrations/new.html.erb
<div class="form__honeypot">
If you see this, leave it blank. Only bots should see this
<input type="text" name="body" value="" />
</div>
Hid the field using CSS.
.form {
position: relative;
&__honeypot {
position: absolute;
visibility: hidden;
left: -5000px;
top: -5000px;
}
}
Generate the Devise controllers so you can tap into the create method.
rails g devise:controllers users -c=registrations
You can generate them all or just the one you need using the -c flag.
In the newly generated controller, added the following code:
# app/controllers/users/registrations_controller.rb
class Users::RegistrationsController < Devise::RegistrationsController
before_action :configure_sign_up_params, only: [:create]
def create
if params[:body].present?
return redirect_to root_path
end
super
end
def configure_sign_up_params
devise_parameter_sanitizer.permit(:sign_up, keys: [:body])
end
end
Essentially this is going to redirect anyone (hopefully bots), who populate the hidden field on the form, back to the root_url
Finally in the routes.rb, added the line let Devise know to use our generated controller to handle registrations.
# config/routes.rb
Rails.application.routes.draw do
devise_for :users, controllers: { registrations: 'users/registrations' }
end

TinyMCE and ActiveAdmin for Rails

I am reacquainting myself with Rails and I am really liking Active Admin. I would like to get tinyMCE working with it for use in text areas. However, any instructions I find are incomplete. For some reason, I think that I am missing something really simple here.
So, for example, I have tinymce-rails installed (3.4.9) and followed the instructions (https://github.com/spohlenz/tinymce-rails). However, here's where I think I failed: actually initiating tinyMCE. According to the doc, I have two options:
use the <%= tinymce %> helper or...
initialize it like the following tinyMCE.init({
mode: 'textareas',
theme: 'advanced'
});
I tried adding the latter to my active_admin.js file to no avail.
If someone could guide me on this, I would be most appreciative.
I got it working doing the following things (outside of the install described at the repo)
In admin/my_class.rb:
ActiveAdmin.register MyClass do
form do |f|
f.inputs do
f.input :body, :input_html => { :class => "tinymce" }
end
end
end
In initializers/active_admin.rb:
...
config.register_javascript 'tinymce.js'
This was what actually got the tinymce.js script to show up in the head of the admin layout.
In javascripts/active_admin.js:
//= require active_admin/base
//= require tinymce
$(document).ready(function() {
tinyMCE.init({
mode: 'textareas',
theme: 'advanced'
});
});
After doing those things, that body input (text area) had a fully functioning editor on it.
Do your textarea inputs have a 'class' attribute or something that tinyMCE can hook into? Does it work from the javascript console (firefox/chrome)? Have you checked the presence of tinymce.js in the head(source) of your page.
I got it working with a form partial, and I had to give a class to the input element so tinymce could hook to it.
<%= f.input :literature_nld, :input_html => { :class => 'tinymce', :size => "80x4" } %>
Good luck