Membuat Fitur Loadmore di Laravel 7 dan Vue Js
- Webserver (Laragon), Optional XAMPP, WAMP, Nginx dan lain-lain.
- Composer
- Node Js
composer create-project --prefer-dist laravel/laravel laravel7_loadmore_vuejs
cd laravel7_loadmore_vuejs
composer require laravel/ui
php artisan ui vue
npm install
npm install vue-axios
npm install vue-router
npm install moment --save
routes/web.php
. For example, saya akan menambahkan script di bawah ini:Route::get('/{any}', function () { return view('app'); })->where('any', '.*');
routes/api.php
. So, ketik kode berikut ini:Route::get('/user', 'Api\UserController@index');
app.blade.php
dan simpan di resources/views
. Silahkan ketik kode berikut:
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
| <! DOCTYPE html> < html lang="{{ app()->getLocale() }}"> < head > < meta charset = "utf-8" > < meta http-equiv = "X-UA-Compatible" content = "IE=edge" > < meta name = "viewport" content = "width=device-width, initial-scale=1" > <!-- CSRF Token --> < meta name = "csrf-token" content = "{{ csrf_token() }}" > < title >Laravel 7 Loadmore with Vue Js</ title > <!-- Styles --> < link href = "{{ asset('css/app.css') }}" rel = "stylesheet" > </ head > < body > < div id = "app" ></ div > < script src = "{{ asset('js/app.js') }}" ></ script > </ body > </ html > |
php artisan make:controller Api/UserController
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
| <?php namespace App\Http\Controllers\Api; use App\Http\Controllers\Controller; use Illuminate\Http\Request; use Illuminate\Http\JsonResponse; class UserController extends Controller { public function index(Request $request ): JsonResponse { $users = \App\User::orderBy( 'name' )->simplePaginate((int) $request ->get( 'limit' , 10)); return response()->json( $users )->withCallback( $request ->callback); } } |
loadmore
justru kita tidak menghilangkan tampilan sebelumnya. Justru malah menambahkan data berikutnya.Request $request
setiap kali ada permintaan tampilan data dari client.withCallback($name)
berfungsi untuk merender output yang kita inginkan menjadi JSONP. JSONP memiliki fungsi untuk menghindari kesalahan cross domain dari AJAX request apabila frontend dan backend berada di domain yang berbeda. Output JSONP akan dieksekusi jika menerima request dengan nama callback, seperti query string ?callback=users
misalnya. (Sumber: Medium Laravel Id)return response()->jsonp($request->callback, $user);
php artisan make:seeder UserSeeder
UserSeeder.php
yang ada di direktori database/seeds
. For example, saya akan memodifikasi filenya sebagai berikut:
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
| <? php use Illuminate\Database\Seeder; class UserSeeder extends Seeder { /** * Run the database seeds. * * @return void */ public function run() { factory(App\User::class, 100)->create(); } } |
.env
dan modifikasi bagian konfigurasi databasenya. For example, ketik kode berikut:DB_CONNECTION=mysql DB_HOST=127.0.0.1 DB_PORT=3306 DB_DATABASE=laravel7_loadmore_vuejs DB_USERNAME=root DB_PASSWORD=
php artisan migrate
php artisan db:seed --class="UserSeeder"
php artisan serve
localhost:8000/api/user
app.js
, file components/App.vue
dan components/user/Index.vue
.app.js
, berikut isi kodenya:
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
| /** * First we will load all of this project's JavaScript dependencies which * includes Vue and other libraries. It is a great starting point when * building robust, powerful web applications using Vue and Laravel. */ require('./bootstrap '); window.Vue = require(' vue '); import VueRouter from ' vue-router '; import VueAxios from ' vue-axios '; import axios from ' axios '; import moment from ' moment '; import App from ' ./components/App.vue '; import UserIndex from ' ./components/user/Index.vue '; Vue.filter(' formatDate ', function(value) { if (value) { return moment(String(value)).format(' DD/MM/YYYY '); } }); Vue.use(VueRouter); Vue.use(VueAxios, axios); const routes = [ { name: ' home ', path: ' / ', component: UserIndex } ]; const router = new VueRouter({ mode: ' history ', routes: routes}); const app = new Vue(Vue.util.extend({ router }, App)).$mount(' #app'); |
App.vue
silahkan ketik kode berikut:
1
2
3
4
5
6
7
8
9
10
| < template > < div class = "page" > < nav class = 'navbar navbar-dark bg-dark' > < div class = 'container' > < router-link :to = "{ name: 'home' }" class = "navbar-brand" >Ilmu Coding</ router-link > </ div > </ nav > < router-view ></ router-view > </ div > </ template > |
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
| < template > < div class = 'container py-4' > < div class = 'row justify-content-center' > < div class = 'col-md-8' > < div class = 'card' > < div class = 'card-header' >All User</ div > < div class = 'card-body' > < div class = "table-responsive" > < table class = "table table-bordered table-hover" > < thead > < tr > < th width = "50" class = "text-center" >No</ th > < th >Name</ th > < th >Email</ th > < th >Created At</ th > </ tr > </ thead > < tbody > < tr v-for = "(user, index) in users.data" :key = "user.id" > < td width = "50" class = "text-center" >{{ index + 1 }}</ td > < td >{{ user.name }}</ td > < td >{{ user.email }}</ td > < td >{{ user.created_at | formatDate}}</ td > </ tr > </ tbody > </ table > </ div > < div v-if = "users.next_page_url" class = "card-footer" > < button @ click.prevent = "paginate(users.next_page_url)" type = "button" class = "btn btn-primary btn-block" >Load More</ button > </ div > </ div > </ div > </ div > </ div > </ div > </ template > < script > export default { data() { return { users: {} } }, created() { this.paginate(); }, methods: { paginate(url = ''){ this.axios.get(url ? url : 'api/user') .then(response => { if(!this.users.data){ this.users = response.data; } else { this.users.data.push(...response.data.data) this.users.next_page_url = response.data.next_page_url } }).catch(error => console.log(error)); } } } </ script > |
npm run dev
php artisan serve
localhost:8000