I was trying to get the flash message that is common in Rails, but I can't get only flash.now. .. ..
For example, write the following code to log in as a user in SessionController.
def create
@user = User.find_by(login_id: params[:session][:login_id])
if @user && @user.authenticate(params[:session][:password])
log_in(@user)
redirect_to @user, success: 'You are now logged'
else
flash.now[:danger] = 'I failed to login.'
render :new
end
end
When the login was successful, that is, "Login" is displayed after redirect_to, but when the login fails, that is, "Login failed" is not displayed at all.
In conclusion, it was because I didn't add local: true to form_with. So I added local: true as below and it worked.
= form_with scope: :session, url: login_path, local: true do |f|
= f.label :login_id, 'Login ID'
= f.text_field :login_id, { class: 'form-control' }
= f.label :password, 'password'
= f.password_field :password, { class: 'form-control' }
= f.submit 'Login', class: 'btn btn-primary'
By the way, I knew that form_with had a local option. When using form_with, I implemented it while investigating various things, so the information to be referred to was mostly local: true.
However, even if you don't have local: true, you can set up a login session normally, and you don't have to. I noticed that, so I removed local: true. However, since I hit such a wall this time, I thought it was not good to leave this local: true as it is, so I will dig a little deeper.
Let's take a look at the Rails documentation for now. https://railsdoc.com/page/form_with Then it says "local: invalid remote transmission". This alone is refreshing.
I wanted to see it in a little more detail, so I hit this one. https://techracho.bpsinc.jp/hachi8833/2020_03_09/39502#6 Then, there is a description that "If you specify local: true, remote + unobtrusive XHR submission of the form is disabled (remote + unobtrusive XHR is enabled in the default form)".
If you look at this, it's just a question mark, but "unobtrusive XHR transmission" is Ajax communication. So, the local option in form_with is "whether form_with in the relevant part disables (true) or enables (false) Ajax communication".
By the way, from here on, it's completely speculative, so I think it's an incorrect description. Please use it as a reference. By the way, the detailed description about Ajax is a little different from the main story, so I will omit it. If you want to know more details, please see Reference at the end of this article.
--If local is not specified in form_with, local: false is set by default, that is, Ajax communication is enabled. ――The code I wrote this time is also the same. --As a result, the process of creating a login session is performed by asynchronous communication. --Because of asynchronous communication, even if you go to generate a login session from the client side to the server side, whether it worked or not is not returned from the server side to the client side. --For example, information such as HTTP status 200 or 404 is not returned. --In this case, "flash.now [: danger]" is not executed because the information "login failed" is not returned from the server side.
By the way, as I wrote at the beginning, "Why did I get the message" I logged in "when I did not get the result of going to generate a login session from the server side without local: true, and the screen after login. The next question arises: "Does it transition to?"
I think this is the difference between the render method and the redirect_to method. Roughly speaking, render doesn't send HTTP requests to the server, and redirect_to sends HTTP requests to the server.
In this case, redirect_to is executed after the login process, that is, the request is sent from the server. Since the redirect_to method returns HTML in response to the request to the client, screen transition occurs on the client side.
It's the inside out of the above, but by setting local: true and disabling Ajax communication, that is, performing synchronous communication, the result of whether you could log in from the server will be returned properly. It will be able to detect it and issue a flash message.
MDN https://developer.mozilla.org/ja/docs/Web/Guide/AJAX/Getting_Started
Qiita articles that are easier to understand than MDN https://qiita.com/hisamura333/items/e3ea6ae549eb09b7efb9
render and redirect_to https://qiita.com/january108/items/54143581ab1f03deefa1