【问题标题】:rails - flash messages not displaying until page reload?rails - 在页面重新加载之前不显示闪存消息?
【发布时间】:2015-12-26 00:19:57
【问题描述】:

我在我的 Rails 应用程序中使用渲染/重定向,我有以下控制器操作

class MessagesController < ApplicationController

 def create
    @message = Message.new(body: params[:message])
    if @message.save
      head :created
    else
      flash[:notice] = "failed!"
      render "home/index"
    end

  end

这是我的 home/index.html.erb 文件

<% if flash[:notice] %>
    <div class="notice"><%= flash[:notice] %></div>
  <% end %>

<form>
  <textarea name="message" id="message" placeholder="Type your message..."></textarea>
  <input type="submit"></input>
</form>

我正在使用 jquery 提交表单:

$(document).ready(function(){
  $('form').submit(function(e){
    e.preventDefault();
    var message_body = $('#message').val();
    $('#message').val('');
    $('#message').focus();
     $.ajax({
       url:    '/messages',
       method: 'post',
       data:   {message: message_body}
     });
  });
});

我的表单模型中有一个验证,可确保消息正文不能为空白validates :body, presence: true

所以当我创建一个空消息并点击提交时,它会呈现主页/索引模板。 (应该)

在 chrome 中,在开发控制台的预览/响应选项卡中,我可以看到 flash 消息,但是在我的实际应用程序中,我无法看到 flash 通知,直到我刷新页面......然后它才会显示出来。

我是否误解了关于页面呈现方式/render/redirect_to 之间的差异,或者这是一个涡轮链接问题?我尝试通过从我的 application.js 文件中删除 //= require turbolinks 并重新启动我的服务器来删除 turbo 链接.. 仍然是同样的问题。

有什么想法吗?

【问题讨论】:

    标签: javascript jquery ruby-on-rails ajax turbolinks


    【解决方案1】:

    你肯定误解了 flash_messages 在 Rails 中的处理方式。

    flash 消息是渲染或重定向(然后渲染)的一次性计时器。

    如果你设置了 flash[:notice] ,下次 rails 渲染某些东西时,flash_message 将可用(并且在它消失后立即消失)。

    由于您要异步提交表单,您应该返回状态,然后在您的 ajaxcall 中,您可以通过状态码为用户提供一些反馈

    这样的事情是可能的(未经测试)

    ajax({url, method, statusCodes: function() {
     200: function() {
       //success
     },
     500: function() {
      //failure
     }
    });
    

    然后在你的控制器内部返回一个 500 http 代码和对象的错误

    else
      render status: 500, json: {errors: @message.errors}
    end
    

    【讨论】:

    • 谢谢,但是我将如何访问我的 ajax 状态码函数中的 @message.errors 呢?
    • 好吧,只需给 500: functon(data),然后创建一个 console.log(data),您就会看到如何使用它。实际上它只是一个 json,所以你可以输入每个键,获取错误消息并打印出来
    • 你一定会喜欢这个的! stefan.haflidason.com/…
    【解决方案2】:

    在玩了一会儿之后,在答案的帮助下,这就是我解决这个问题的方法:

    我的消息控制器:

     def create
        @message = Message.new(body: params[:message])
        if @message.save
          head :created
        else
          render status: 422, json: { errors: @message.errors.full_messages}
        end
      end
    

    我的 ajax 调用:

    $(document).ready(function(){
      $('form').submit(function(e){
        e.preventDefault();
        var message_body = $('#message').val();
    
        $('#message').val('');
        $('#message').focus();
    
        $.ajax({
          url:      '/messages',
          method:   'post',
          data:     {message: message_body},
    
          error: function(data){
            console.log(data);
              var response = jQuery.parseJSON(data.responseText);
              var error_message = response.errors.join("\n");
              alert(error_message);
          }
    
        }); //end of ajax function 
    
      });   //end of submit function
    
    });     //end of document.ready
    

    【讨论】:

    • 嗯,是这样的。我个人不追求成功和错误,而是追求 statusCodes,但你正在抛出 422,这对于你正在做的事情来说绝对是错误的 (!) statusCode。 422 是不可处理的实体。你应该抛出一个 500 (如果“出现问题”,这也是 rails 抛出的默认值)
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2012-01-14
    • 2015-01-29
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多