Vuex项目Example中的源码学习 (3)

Shopping cart

项目概述

在这里插入图片描述
从运行的截图上,不难看出是一个简单的商品购物的页面。products应该是从vuex中获得所有的商品数据。商品有一定的库存量,每次加入购物车一次,就会减少一个,只到为0的时候就不可以购买。your cart是购物车,每次点击购买的时候,购物车里会增加一个商品。同时会增加一件商品进入购物车,购物车有金额的汇总。然后点击结账,会偶尔成功,偶尔失败。

揣测程序的实现思路

个人认为在写代码本身是在解决问题。阅读代码是为了理解别人解决问题的思路。那么在阅读之前,最好是能自己想想,如果自己写这个代码,会如何写。然后再对照别人的代码,这样才能深入学习。

个人思路

可以建立两个Modules,一个存放products,一个存放shopping carts。

存放products的Module,在state中需要保存所有的商品数据,然后mutations中需要有一个addToCart的方法。还要有一个getters,需要获得所有的products。addTOCart负责减少仓库中商品的数量。而获得所有商品的getters需要获得所有仓库中的商品信息。

存放your cart的需要在state中存放所有的购物车数据,以及汇总金额,Mutations中需要有addToCart方法,来增加商品。Checkout负责清空所有的购物车。最好还要有一个getters来计算所有商品的价格。

然后页面上可以建立两个组件,一个商品列表,一个购物车。

项目的目录结构

在这里插入图片描述

项目实现

API 部分

const _products = [
  {
    
     'id': 1, 'title': 'iPad 4 Mini', 'price': 500.01, 'inventory': 2 },
  {
    
     'id': 2, 'title': 'H&M T-Shirt White', 'price': 10.99, 'inventory': 10 },
  {
    
     'id': 3, 'title': 'Charli XCX - Sucker CD', 'price': 19.99, 'inventory': 5 }
]

export default {
    
    
  getProducts (cb) {
    
    
    setTimeout(() => cb(_products), 100)
  },

  buyProducts (products, cb, errorCb) {
    
    
    setTimeout(() => {
    
    
      // simulate random checkout failure.
      (Math.random() > 0.5 || navigator.webdriver)
        ? cb()
        : errorCb()
    }, 100)
  }
}

这部分是我们思路中没有的,项目中思考更加全面和完善mock了服务器端。做了两个函数一个获得产品信息,一个递交购物车信息。然后用了回调函数来把从服务器端获得信息发送回去state中去。

products.js

import shop from '../../api/shop'

// initial state
const state = () => ({
    
    
  all: []
})

// getters
const getters = {
    
    }

// actions
const actions = {
    
    
  getAllProducts ({
    
     commit }) {
    
    
    shop.getProducts(products => {
    
    
      commit('setProducts', products)
    })
  }
}

// mutations
const mutations = {
    
    
  setProducts (state, products) {
    
    
    state.all = products
  },

  decrementProductInventory (state, {
    
     id }) {
    
    
    const product = state.all.find(product => product.id === id)
    product.inventory--
  }
}

export default {
    
    
  namespaced: true,
  state,
  getters,
  actions,
  mutations
}

比我们思路上增加一个action,用来调用获得所有的商品,并且commit到设置商品中去,当然也多了一个初始化商品数据的方法。另外没设置获得所有商品的方法。

cart.js

import shop from '../../api/shop'

// initial state
// shape: [{ id, quantity }]
const state = () => ({
    
    
  items: [],
  checkoutStatus: null
})

// getters
const getters = {
    
    
  cartProducts: (state, getters, rootState) => {
    
    
    return state.items.map(({
    
     id, quantity }) => {
    
    
      const product = rootState.products.all.find(product => product.id === id)
      return {
    
    
        title: product.title,
        price: product.price,
        quantity
      }
    })
  },

  cartTotalPrice: (state, getters) => {
    
    
    return getters.cartProducts.reduce((total, product) => {
    
    
      return total + product.price * product.quantity
    }, 0)
  }
}

// actions
const actions = {
    
    
  checkout ({
    
     commit, state }, products) {
    
    
    const savedCartItems = [...state.items]
    commit('setCheckoutStatus', null)
    // empty cart
    commit('setCartItems', {
    
     items: [] })
    shop.buyProducts(
      products,
      () => commit('setCheckoutStatus', 'successful'),
      () => {
    
    
        commit('setCheckoutStatus', 'failed')
        // rollback to the cart saved before sending the request
        commit('setCartItems', {
    
     items: savedCartItems })
      }
    )
  },

  addProductToCart ({
    
     state, commit }, product) {
    
    
    commit('setCheckoutStatus', null)
    if (product.inventory > 0) {
    
    
      const cartItem = state.items.find(item => item.id === product.id)
      if (!cartItem) {
    
    
        commit('pushProductToCart', {
    
     id: product.id })
      } else {
    
    
        commit('incrementItemQuantity', cartItem)
      }
      // remove 1 item from stock
      commit('products/decrementProductInventory', {
    
     id: product.id }, {
    
     root: true })
    }
  }
}

// mutations
const mutations = {
    
    
  pushProductToCart (state, {
    
     id }) {
    
    
    state.items.push({
    
    
      id,
      quantity: 1
    })
  },

  incrementItemQuantity (state, {
    
     id }) {
    
    
    const cartItem = state.items.find(item => item.id === id)
    cartItem.quantity++
  },

  setCartItems (state, {
    
     items }) {
    
    
    state.items = items
  },

  setCheckoutStatus (state, status) {
    
    
    state.checkoutStatus = status
  }
}

export default {
    
    
  namespaced: true,
  state,
  getters,
  actions,
  mutations
}


猜你喜欢

转载自blog.csdn.net/aofengdaxia/article/details/114583086