iT邦幫忙

2017 iT 邦幫忙鐵人賽
DAY 29
0
Modern Web

Vue.js 30天系列 第 29

Vue.js 29 - 搭配後端 - Laravel(Vue檔案結構)

搭配後端 - Laravel分為三篇


檔案結構

專案預設的Vue檔案非常簡單,他放置的位置在專案目錄中的js assets內

resources/assets/js

結構像這樣

└── VueSite/resources/assets
    └── js
        ├── components
        |	  └── Example.vue
        ├── bootstrap.js
        └── app.js

裡面包含

  • 名為 Example組件(Component)
  • 名為 boostrap 的初始流程,載入相關函式庫及Vue主程式初始設定
    (跟你常用的那個Bootstrap無關)
  • 名為 app 的主檔案

讓我們倒過來講,從 app.js 開始

/**
 * 首先載入 vue app 起始所需的函式庫
 * 從你常用的 jQuery、工具包 lodash、以及主角 Vue & Vue-resource
 * 接著載入Vue全域設定
 */

require('./bootstrap');
/* oops! 不小心把 bootstrap.js 講完了 */

/**
 * 接著載入 Vue app 需要的 Components
 * 產生一個新的 Vue app,掛載在id為 app 的tag上
 * 供 laravel 頁面使用
 */


Vue.component('example', require('./components/Example.vue'));

const app = new Vue({
    el: '#app'
});

接著是初始流程 bootstrap.js


/* 載入lodash,掛到全域 */
window._ = require('lodash');

/* 載入jquery,掛到全域 */
window.$ = window.jQuery = require('jquery');
/* 載入bootstrap 的 jQuery plugin */
require('bootstrap-sass');

/* 載入Vue跟vue-resource */
window.Vue = require('vue');
require('vue-resource');

/** 
 * Laravel透過CSRF TOKEN驗證,記得設定
 * 讓每個透過vue-resources送出的請求順利送達
 */
Vue.http.interceptors.push((request, next) => {
    request.headers.set('X-CSRF-TOKEN', Laravel.csrfToken);

    next();
});

最後介紹一下Example組件,內容不重要,但待會可以測試App有沒有順利掛上

<template>
    <div class="container">
        <div class="row">
            <div class="col-md-8 col-md-offset-2">
                <div class="panel panel-default">
                    <div class="panel-heading">Example Component</div>

                    <div class="panel-body">
                        I'm an example component!
                    </div>
                </div>
            </div>
        </div>
    </div>
</template>

<script>
    export default {
        mounted() {
            console.log('Component ready.')
        }
    }
</script>

替 Laravel View 新增demo頁面

這是為了跟原本的首頁區隔

一個頁面可以簡單區分為共用部份,及每個頁面獨有的View

resources/views/demo.blade.php

@extends('layouts.app')

@section('content')
  <div id="app">
    @{{ state }}
    <example></example>
  </div>
@endsection

這邊有點有趣,Laravel View的預設樣板Blade,和Vue一樣用雙大括號({{ }})
所以當你要讓Blade跳過編譯,得在雙大括號前加個@ - @{{ }}

共用部分的樣板 - layout
先放在views/layouts/底下,跟其他view區隔。

resources/views/layouts/app.blade.php

<!DOCTYPE html>
<html lang="en">
<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>{{ config('app.name', 'Laravel') }}</title>

    <!-- Styles -->
    <link href="/css/app.css" rel="stylesheet">

    <!-- Scripts -->
    <script>
        window.Laravel = <?php echo json_encode([
            'csrfToken' => csrf_token(),
        ]); ?>
    </script>
</head>
<body>
    <div>
        <nav class="navbar navbar-default navbar-static-top">
            <div class="container">
                <div class="navbar-header">

                    <!-- Collapsed Hamburger -->
                    <button type="button" class="navbar-toggle collapsed" data-toggle="collapse" data-target="#app-navbar-collapse">
                        <span class="sr-only">Toggle Navigation</span>
                        <span class="icon-bar"></span>
                        <span class="icon-bar"></span>
                        <span class="icon-bar"></span>
                    </button>

                    <!-- Branding Image -->
                    <a class="navbar-brand" href="{{ url('/') }}">
                        {{ config('app.name', 'Laravel') }}
                    </a>
                </div>

                <div class="collapse navbar-collapse" id="app-navbar-collapse">
                    <!-- Left Side Of Navbar -->
                    <ul class="nav navbar-nav">
                        &nbsp;
                    </ul>

                    <!-- Right Side Of Navbar -->
                    <ul class="nav navbar-nav navbar-right">
                        <!-- Authentication Links -->
                        @if (Auth::guest())
                            <li><a href="{{ url('/login') }}">Login</a></li>
                            <li><a href="{{ url('/register') }}">Register</a></li>
                        @else
                            <li class="dropdown">
                                <a href="#" class="dropdown-toggle" data-toggle="dropdown" role="button" aria-expanded="false">
                                    {{ Auth::user()->name }} <span class="caret"></span>
                                </a>

                                <ul class="dropdown-menu" role="menu">
                                    <li>
                                        <a href="{{ url('/logout') }}"
                                            onclick="event.preventDefault();
                                                     document.getElementById('logout-form').submit();">
                                            Logout
                                        </a>

                                        <form id="logout-form" action="{{ url('/logout') }}" method="POST" style="display: none;">
                                            {{ csrf_field() }}
                                        </form>
                                    </li>
                                </ul>
                            </li>
                        @endif
                    </ul>
                </div>
            </div>
        </nav>

        <!-- 載入demo頁的內容 -->
        @yield('content')
    </div>

    <!-- Scripts -->
    <script src="/js/app.js"></script>
</body>
</html>

在這頁面載入了編譯好的css & js

當然,門牌記得掛上,外面的人才找得到

routes/web.php

Route::get('/', function () {
    return view('welcome');
});

Route::get('/', function () {
    return view('demo');
});

Oops!

若你發現不能正常顯示,檢查看看css & js
試試在專案目錄下,重新編譯一次

$ npm install
$ gulp watch

大功告成

連進去 localhost:8000 or 127.0.0.1:8000/demo,看看成果吧。


上一篇
Vue.js 28 - 搭配後端 - Laravel(環境建置)
下一篇
Vue.js 30 - 搭配後端 - Laravel(編譯流程跟設定)
系列文
Vue.js 30天30
圖片
  直播研討會
圖片
{{ item.channelVendor }} {{ item.webinarstarted }} |
{{ formatDate(item.duration) }}
直播中

尚未有邦友留言

立即登入留言