简体   繁体   中英

Laravel 5.8: Auto refresh div becomes messy and laggy using ajax

I have this website that has comment section in every news. I want to update the div every x seconds using a ajax function. But when I put the ajax code in my scripts, the div becomes messy and my site becomes lag and there are so many errors in the console. Anybody has an idea about this? Here are my outputs:

Before I implemented the code : https://imgur.com/a/9unsq2c After: https://imgur.com/a/glBEiEU

shownews.blade.php

Comments area

     <h4 class="comments-title" > <span class="fas fa-comment-alt"></span>
                    {{$news->comments()->count()}}
                    Comments</h4>
                  <div class="row" >
                      <div class="col-md-12 col-md-offset-2" style="overflow-y: scroll; height: 400px;
                      width: 400px; " id="commentarea" >

                          @foreach($news->comments as $comment)
                            <div class="comment" style="background-color: #f6efef;" >
                          <div class="author-info">
                              <img src={{"https://www.gravatar.com/avatar/" . md5(strtolower(trim($comment->email))) . "?s=50&d=retro" }} class="author-image" id="image">

                              <div class="author-name">
                                   <h4>{{$comment->name}} </h4>
                                   <p class="author-time"> {{  date('jS F, Y - g:iA' ,strtotime($comment->created_at)) }}</p>
                              </div>
                          </div>
                            <div class="comment-content">
                                    {{$comment->comment}}
                            </div>
                            </div>
                          @endforeach
                      </div>
                  </div>


<script src="https://ajax.googleapis.com/ajax/libs/jquery/3.1.1/jquery.min.js"></script>
      <script>
            $(document).ready(function() {
             setInterval(function() {
                $('#commentarea').load('{{ action('NewsController@showNews', ['news' => $news->id]) }}');
             }, 5000);
            });
           </script>

NewsController.php

<?php

namespace App\Http\Controllers;
use DB;
use Illuminate\Http\Request;
use App\News;
use Validator;
use Image;
use View;
use Storage;
use Illuminate\Support\Facades\Input;
// use App\Http\Controllers\Controller;

class NewsController extends Controller
{

//Shownews method. This is where the individual news is shown with its comments.

    public function showNews($id)
    {

        $all = DB::table('news')->get();
        $news = News::find($id);
        return View::make('coin.shownews', compact('news','all'));
    }
}

CommentsController

<?php

namespace App\Http\Controllers;

use Illuminate\Http\Request;
use App\Comment;
use App\News;
use App\Graph;
use Validator;
use Session;


class CommentsController extends Controller
{
    public function store(Request $request, $news_id)
    {
        //
        $this->validate($request, array(
            'name'=> 'required | max:255',
            'email'=> 'required| email | max:255',
            'comment'=> 'required | min:5'
        ));

        $news = News::find($news_id);

        $comment = new Comment();

        $comment->name = $request->name;
        $comment->email = $request->email;
        $comment->comment = $request->comment;
        $comment->approved = true;
        $comment->news()->associate($news);

        $comment->save();


        // return $comment->toJson();

        return redirect()->route('article', [$news->id]);
}

The reason why its behave like this because you're loading the whole web page when you call your view. So you need to separate it and use ajax to call the data you can use @include in view.

Comments area

 <h4 class="comments-title" > <span class="fas fa-comment-alt"></span>
                {{$news->comments()->count()}}
                Comments</h4>
              <div class="row" >
                  <div class="col-md-12 col-md-offset-2" style="overflow-y: scroll; height: 400px;
                  width: 400px; " id="commentarea" >
                  @include('table_data')
                  </div>
              </div>


<script src="https://ajax.googleapis.com/ajax/libs/jquery/3.1.1/jquery.min.js"></script>
  <script>
        $(document).ready(function() {
         setInterval(function() {
           var page = window.location.href;
           $.ajax({
           url: page+'/table,
           success:function(data)
           {
            $('#commentarea').html(data);
           }
           });
         }, 5000);
       });
           </script>

Create the include blade then put the needed element of commentarea table_data.blade.php

                      @foreach($news->comments as $comment)
                        <div class="comment" style="background-color: #f6efef;" >
                         <div class="author-info">
                          <img src={{"https://www.gravatar.com/avatar/" . md5(strtolower(trim($comment->email))) . "?s=50&d=retro" }} class="author-image" id="image">

                          <div class="author-name">
                               <h4>{{$comment->name}} </h4>
                        <p class="author-time"> {{  date('jS F, Y - g:iA' ,strtotime($comment->created_at)) }}</p>
                         </div>
                        </div>
                        <div class="comment-content">
                                {{$comment->comment}}
                        </div>
                        </div>
                      @endforeach

Of course you need to have another route for it and another function in controller

<?php

namespace App\Http\Controllers;
use DB;
use Illuminate\Http\Request;
use App\News;
use Validator;
use Image;
use View;
use Storage;
use Illuminate\Support\Facades\Input;
// use App\Http\Controllers\Controller;

class NewsController extends Controller
{

//Shownews method. This is where the individual news is shown with its comments.



 public function showNews($id)
    {
        $new = News::find($id);
        return view('coin.shownews')->with('new', $new);
    }
 public function commentData($id);
    {
        $all = DB::table('news')->get();
        $news = News::find($id);
        return view('table_data', compact('news', 'all'))->render();
    }
}

then add the route on web.php

`Route::get('article/{id}/commentData', 'NewsController@commentData')`;
//you must change the name of the route base on your url just add the /table. Route can't be the same so you need to add that

Hope it helps!

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM