Ruby On Rails - 在加载视图模板后呈现HTML

时间:2017-03-18 17:47:36

标签: html ruby-on-rails ajax twitter-oauth

我之前发过一个类似问题,但我认为最好先用一个更简单的例子来了解AJAX的工作原理。

基本上,应用程序向twitter发出API调用,并在推文文本中搜索包含“@youtube”的所有推文。问题是,有时搜索可能需要一段时间,所以不是等待搜索完成然后渲染视图,我想呈现包含空div的视图模板,然后在控制器方法完成后用HTML填充此div运行

到目前为止,这就是我所拥有的:

routes.rb

Rails.application.routes.draw do
  get '/auth/:provider/callback', to: 'sessions#create'

  root to: 'pages#index'
  get 'index' => 'pages#index'
  get 'tweets' => 'pages#tweets'
end

pages_controller.rb

class PagesController < ApplicationController

  def tweets
    html = ''
    tweets = TweetController.load_tweets(current_user)
    tweets.each {|tweet| html << "<p>#{tweet.text}</p>"}
    render :html => html.html_safe, :layout => false
  end

end

tweet_controller.rb

class TweetController < ApplicationController

  def self.load_tweets(auth_user)
    tweets = User.twitter.search('to:youtube', result_type: 'recent').collect.sort_by &:created_at
    return !auth_user.nil? ? tweets : [].to_enum
  end

end

tweets.html.erb

<script>
  $.ajax({
      url: 'tweets',
      cache: false,
      success: function (html) {
          $('#tweet_view').append(html)
      }
  });
</script>

<div id='tweet_view'></div>

因此,在用户按下索引页面上的按钮后,它们将被发送到Twitter API授权页面,然后重定向回tweets.html.erb

然而,不是首先加载模板然后用HTML填充div,它似乎仍在加载所有推文然后呈现页面,但我不太确定我做错了什么。

1 个答案:

答案 0 :(得分:0)

实际上有两种方法可以解决这个问题。

  1. 使用两个操作:只需将tweets.html.erb中的所有内容移至pages / index.html.erb
  2. pages_controller.rb

    class PagesController < ApplicationController
    
      def index
      end 
    
      def tweets
        html = ''
        tweets = TweetController.load_tweets(current_user)
        tweets.each {|tweet| html << "<p>#{tweet.text}</p>"}
        render :html => html.html_safe, :layout => false
      end
    
    end
    

    pages / index.html.erb

       <script>
      $.ajax({
          url: 'tweets',
          cache: false,
          success: function (html) {
              $('#tweet_view').append(html)
          }
      });
    </script>
    
    <div id='tweet_view'></div>
    

    tweet_controller.rb

    class TweetController < ApplicationController
    
      def self.load_tweets(auth_user)
        tweets = User.twitter.search('to:youtube', result_type: 'recent').collect.sort_by &:created_at
        return !auth_user.nil? ? tweets : [].to_enum
      end
    
    end
    

    并确保当用户按下按钮页面时,应将其重定向回来自Twitter API授权页面的页面#index action。

    编辑或:

    1. 使用参数分隔符区分API重定向和推文加载请求。
    2. pages_controller.rb

      class PagesController < ApplicationController
      
        def tweets
          if(params[:load_tweets] == 'true')
           html = ''
           tweets = TweetController.load_tweets(current_user)
           tweets.each {|tweet| html << "<p>#{tweet.text}</p>"}
           render :html => html.html_safe, :layout => false
          end
        end
      
      end
      

      pages / tweets.html.erb

         <script>
        $.ajax({
            url: 'tweets?load_tweets=true',
            cache: false,
            success: function (html) {
                $('#tweet_view').append(html)
            }
        });
      </script>
      
      <div id='tweet_view'></div>
      

      tweet_controller.rb

      class TweetController < ApplicationController
      
        def self.load_tweets(auth_user)
          tweets = User.twitter.search('to:youtube', result_type: 'recent').collect.sort_by &:created_at
          return !auth_user.nil? ? tweets : [].to_enum
        end
      
      end