<file_sep># 世紀商城 - 電商網站: 
> 一起來征服世紀吧! 這是一份 Vue Cli32 電商 side Project

![](https://i.imgur.com/qPsT9KG.jpg)

## Demo
https://chiachipai.github.io/empireShop/

## 簡介
此商城使用 Vue Cli3 製作的 SPA 網站
功能包括:
- 前台
    - 電商展示(商品分類、單一商品介紹)
    - 購物車
    - 下單、結帳
    - 優惠券
    - 最新消息(串接 Facebook 資訊)
- 後台
    - 登入系統
    - 商品管理(CRUD)
    - 訂單管理
    - 優惠卷管理 
## 使用技術
- Vue Cli 3
- Vue Router
- Vue Components
- RESTful APIs
- RWD
- Bootstrap 4
- JavaScript ES6
- SCSS
- ESlint basic
- Graph facebook

## 使用插件
- Vue-axios
- VeeValidate
- Vue-loading-overlay
- Vue-swiper

## 壹、前台介紹
### 一、首頁
- 點擊人像按鈕會下滑到對應的商品展示區

![](https://i.imgur.com/xVrjXzm.jpg)

- 商品展示使用 Vue-swiper 做商品展示，點擊時會隨機選出該分類六樣商品

![](https://i.imgur.com/n1JT9qu.jpg)

- 客戶好評會擷取訂單的留言資料展示在這

![](https://i.imgur.com/eKwfh5Q.png)

- 浮動購物車

![](https://i.imgur.com/BWAVNGc.jpg)

### 二、最新消息

最新消息會串接客戶的 Facebook 粉專，把最新的訊息展示出來

![](https://i.imgur.com/UB5LobH.jpg)

### 三、世紀商城

- 商品列表預設展示全部商品，點擊分類會篩選出該分類的商品
- 商品列表點擊商品的查看更多會跳到單一商品頁面

![](https://i.imgur.com/AhYZxl8.jpg)

- 單一商品頁面可選擇商品數量
- 右下角會隨機推薦商城商品

![](https://i.imgur.com/rqE8PR9.jpg)

### 四、購物車

- 購物車頁面能改變商品數量

![](https://i.imgur.com/DQq2IsP.jpg)

- 客戶填寫訊息驗證

![](https://i.imgur.com/nnQV8Sw.jpg)


- 結帳頁面

![](https://i.imgur.com/wliT9cJ.jpg)

## 貳、後台介紹

- 登入頁面

![](https://i.imgur.com/SdJjvI7.jpg)

- 商品列表

![](https://i.imgur.com/g8jiZOo.png)

- 編輯商品

![](https://i.imgur.com/wDRv0BM.png)

## 圖片來源
google、
[aoetw](http://www.aoetw.com/)、
[世紀帝國官方網站](https://www.ageofempires.com/)、
[VX 素材](https://sites.google.com/site/closetvx/picture/02)

## 聲明
此網站僅用於練習使用，不用於任何商業用途。

## 心得
沒想到有時看似簡單的功能後面原來有這麼多要處理的細節，有時一寫就忘了時間，常常寫到半夜，不過整體來說還滿享受的。


更多細節請至 [Demo](https://chiachipai.github.io/empireShop/) 觀看
<file_sep>import Vue from 'vue'

Vue.prototype.$bus = new Vue()

// Message
// vm.$bus.$emit('message:push', message, status)
// message(String): 訊息內容
// status(string): Alert 樣式內容

// 購物車 icon 更新狀態
// vm.$bus.$emit('updateCart')
<file_sep>import Vue from 'vue' // 第三方套件放在前面
import axios from 'axios'
import VueAxios from 'vue-axios'
import Loading from 'vue-loading-overlay'
import 'vue-loading-overlay/dist/vue-loading.css'
import 'bootstrap'
import VeeValidate, { Validator } from 'vee-validate' // 匯入檔案
import TW from 'vee-validate/dist/locale/zh_TW' // 匯入語言包
import VueAwesomeSwiper from 'vue-awesome-swiper'
import 'swiper/dist/css/swiper.css'

import App from './App.vue' // 自己寫的放後面
import router from './router'
import './bus'
import currencyFilter from './filter/Currency'
import toDate from './filter/toDate'
import toLocalDate from './filter/toLocalDate'

Vue.use(VeeValidate) // 啟用API
Validator.localize('zh-TW', TW) // 啟用語言包
Vue.use(VueAxios, axios)
Vue.use(VueAwesomeSwiper)

Vue.config.productionTip = false
axios.defaults.withCredentials = true

Vue.component('Loading', Loading) // 因為 Loading 是元件，必須被啟用，這邊用的是全域啟用
// 將元件載入，可以在 vue template 中運用該套件但資料、方法仍然與執行中的元件分離
/* eslint-disable no-new */
Vue.filter('currency', currencyFilter)
Vue.filter('toDate', toDate)
Vue.filter('toLocalDate', toLocalDate)

// validator 自訂手機號碼檢查
const cellphone = {
  validate: (value) => {
    const reg = /^09[0-9]{8}$/
    return reg.test(value)
  }
}
Validator.extend('cellphone', cellphone)

new Vue({
  router,
  render: h => h(App)
}).$mount('#app')

router.beforeEach((to, from, next) => {
  // 設定導航守衛，避免使用者在沒登入的狀態下，直接進入後台
  if (to.meta.requiresAuth) {
    // 在 to(指定要到的路徑下)，如果指定到的路徑下有設定 meta.requiresAuth，進入後端驗證
    const api = `${process.env.VUE_APP_APIPATH}/api/user/check`
    axios.post(api).then((response) => {
      // 因為不是在 component 的資料夾下，不能使用 this.$http，改用 axios
      console.log(response.data)
      if (response.data.success) { // 登入成功後，跳轉到原來要去的路徑
        next()
      } else {
        next({
          path: '/login' // 登入沒成功，回到原來的登入頁面
        })
      }
    })
  } else { // 如果沒有 meta.requiresAuth，直接到指定路徑
    next()
  }
})
