1. 项目背景与环境搭建
作为一个刚接触Vue3的前端开发者,我决定通过"小兔鲜"电商项目来系统学习现代前端开发技术栈。这个项目将使用Vue3作为核心框架,搭配ElementPlus组件库和axios进行数据交互,同时采用scss进行样式管理。
1.1 开发环境准备
首先需要安装Node.js环境,建议使用LTS版本(目前是18.x)。安装完成后,可以通过以下命令验证:
node -v npm -v接着安装Vue CLI工具:
npm install -g @vue/cli注意:如果遇到权限问题,可以在命令前加上sudo(Mac/Linux)或以管理员身份运行终端(Windows)
1.2 创建Vue3项目
使用Vue CLI创建新项目:
vue create xiaotuxian-frontend在交互式界面中,选择"Manually select features",然后勾选以下选项:
- Babel
- Router
- Vuex
- CSS Pre-processors
- Linter/Formatter
对于其他选项:
- 选择Vue3版本
- 使用history模式路由
- 选择Sass/SCSS作为CSS预处理器
- 选择ESLint + Prettier配置
- 选择Lint on save
项目创建完成后,进入项目目录并启动开发服务器:
cd xiaotuxian-frontend npm run serve2. 核心依赖安装与配置
2.1 ElementPlus集成
ElementPlus是Vue3生态中最流行的UI组件库之一,特别适合电商类项目:
npm install element-plus在main.js中全局引入:
import { createApp } from 'vue' import App from './App.vue' import ElementPlus from 'element-plus' import 'element-plus/dist/index.css' const app = createApp(App) app.use(ElementPlus) app.mount('#app')2.2 axios配置
安装axios并创建实例:
npm install axios创建src/utils/request.js文件:
import axios from 'axios' const service = axios.create({ baseURL: process.env.VUE_APP_BASE_API, timeout: 5000 }) // 请求拦截器 service.interceptors.request.use( config => { // 可在此处添加token等 return config }, error => { return Promise.reject(error) } ) // 响应拦截器 service.interceptors.response.use( response => { const res = response.data if (res.code !== 200) { // 处理业务错误 return Promise.reject(new Error(res.message || 'Error')) } return res }, error => { // 处理HTTP错误 return Promise.reject(error) } ) export default service2.3 SCSS全局样式配置
在src/assets/styles目录下创建以下文件:
- variables.scss:全局变量
- mixins.scss:混合宏
- index.scss:主样式文件
在vue.config.js中配置全局SCSS变量:
module.exports = { css: { loaderOptions: { scss: { additionalData: `@import "@/assets/styles/variables.scss";` } } } }3. 主题色定制实践
3.1 ElementPlus主题覆盖
ElementPlus默认使用蓝色作为主色调,我们可以通过SCSS变量覆盖来实现自定义主题。在variables.scss中添加:
/* 主题色 */ $--color-primary: #ff6700; // 小兔鲜品牌橙色 /* 覆盖ElementPlus变量 */ $--colors: ( 'primary': ( 'base': $--color-primary, ), ); @forward 'element-plus/theme-chalk/src/common/var.scss' with ( $colors: $--colors );3.2 动态主题切换方案
为了实现动态主题切换,我们需要创建一个主题管理工具:
- 创建src/utils/theme.js:
import { getCurrentInstance } from 'vue' export const useTheme = () => { const { appContext } = getCurrentInstance() const $ELEMENT = appContext.config.globalProperties.$ELEMENT || {} const changeTheme = (themeColor) => { const styleElement = document.getElementById('theme-style') const css = ` :root { --el-color-primary: ${themeColor}; } ` if (styleElement) { styleElement.innerHTML = css } else { const style = document.createElement('style') style.id = 'theme-style' style.innerHTML = css document.head.appendChild(style) } $ELEMENT.size = 'default' $ELEMENT.zIndex = 2000 } return { changeTheme } }- 在组件中使用:
import { useTheme } from '@/utils/theme' const { changeTheme } = useTheme() // 切换为橙色主题 changeTheme('#ff6700')4. 项目基础架构搭建
4.1 路由配置优化
在src/router/index.js中配置基础路由:
import { createRouter, createWebHistory } from 'vue-router' const routes = [ { path: '/', redirect: '/home' }, { path: '/home', name: 'Home', component: () => import('@/views/Home.vue'), meta: { title: '小兔鲜 - 新鲜每一天' } }, { path: '/category', name: 'Category', component: () => import('@/views/Category.vue'), meta: { title: '商品分类' } }, { path: '/cart', name: 'Cart', component: () => import('@/views/Cart.vue'), meta: { title: '购物车' } }, { path: '/user', name: 'User', component: () => import('@/views/User.vue'), meta: { title: '个人中心' } } ] const router = createRouter({ history: createWebHistory(process.env.BASE_URL), routes }) // 路由守卫 router.beforeEach((to, from, next) => { if (to.meta.title) { document.title = to.meta.title } next() }) export default router4.2 Vuex状态管理设计
电商项目通常需要管理用户、购物车等全局状态。创建src/store/index.js:
import { createStore } from 'vuex' export default createStore({ state: { userInfo: null, cartCount: 0 }, mutations: { SET_USER_INFO(state, payload) { state.userInfo = payload }, SET_CART_COUNT(state, payload) { state.cartCount = payload } }, actions: { async getUserInfo({ commit }) { try { const res = await getUserInfoApi() commit('SET_USER_INFO', res.data) } catch (error) { console.error(error) } }, updateCartCount({ commit }, count) { commit('SET_CART_COUNT', count) } }, getters: { isLogin: state => !!state.userInfo } })4.3 布局组件开发
创建基础布局组件src/layouts/MainLayout.vue:
<template> <div class="main-layout"> <header class="header"> <!-- 顶部导航栏 --> <div class="container"> <div class="logo"> <router-link to="/"> <img src="@/assets/images/logo.png" alt="小兔鲜"> </router-link> </div> <nav class="nav"> <router-link to="/home">首页</router-link> <router-link to="/category">分类</router-link> <router-link to="/cart">购物车</router-link> <router-link to="/user">我的</router-link> </nav> </div> </header> <main class="main-content"> <router-view /> </main> <footer class="footer"> <div class="container"> <p>© 2023 小兔鲜 All Rights Reserved</p> </div> </footer> </div> </template> <script> export default { name: 'MainLayout' } </script> <style lang="scss" scoped> .main-layout { display: flex; flex-direction: column; min-height: 100vh; .header { background-color: #fff; box-shadow: 0 2px 10px rgba(0, 0, 0, 0.1); padding: 15px 0; .container { display: flex; align-items: center; justify-content: space-between; max-width: 1200px; margin: 0 auto; padding: 0 20px; } .logo img { height: 40px; } .nav { a { margin-left: 20px; color: #333; text-decoration: none; &:hover { color: $--color-primary; } &.router-link-exact-active { color: $--color-primary; font-weight: bold; } } } } .main-content { flex: 1; padding: 20px 0; } .footer { background-color: #f5f5f5; padding: 20px 0; text-align: center; font-size: 14px; color: #666; } } </style>5. 开发工具与调试技巧
5.1 Vue Devtools安装与使用
Vue Devtools是Vue开发必备的浏览器扩展,可以方便地调试组件、查看状态和路由信息。
安装步骤:
- 在Chrome网上应用店搜索"Vue.js devtools"
- 点击"添加到Chrome"
- 安装完成后,在开发者工具中会出现Vue面板
提示:如果无法访问Chrome商店,可以从GitHub仓库直接下载编译版本:https://github.com/vuejs/devtools
5.2 VSCode插件推荐
- Volar - Vue3官方推荐的IDE支持
- Vue VSCode Snippets - 常用代码片段
- ESLint - 代码规范检查
- Prettier - 代码格式化
- SCSS IntelliSense - SCSS代码提示
5.3 常见问题解决
问题1:node-sass安装失败
解决方案:
- 使用dart-sass替代:
npm uninstall node-sass npm install sass --save-dev- 修改vue.config.js:
module.exports = { css: { loaderOptions: { scss: { implementation: require('sass') } } } }问题2:ElementPlus图标不显示
确保正确引入了图标组件:
import * as ElementPlusIconsVue from '@element-plus/icons-vue' const app = createApp(App) for (const [key, component] of Object.entries(ElementPlusIconsVue)) { app.component(key, component) }问题3:axios跨域问题
在开发环境中配置代理:
module.exports = { devServer: { proxy: { '/api': { target: 'http://backend-api.com', changeOrigin: true, pathRewrite: { '^/api': '' } } } } }6. 项目结构与代码规范
6.1 目录结构设计
src/ ├── api/ # API请求封装 ├── assets/ # 静态资源 │ ├── images/ # 图片 │ ├── styles/ # 全局样式 │ └── fonts/ # 字体文件 ├── components/ # 公共组件 │ ├── common/ # 全局通用组件 │ └── business/ # 业务组件 ├── composables/ # 组合式函数 ├── directives/ # 自定义指令 ├── router/ # 路由配置 ├── store/ # 状态管理 ├── utils/ # 工具函数 ├── views/ # 页面组件 ├── App.vue # 根组件 └── main.js # 入口文件6.2 ESLint与Prettier配置
.eslintrc.js示例配置:
module.exports = { root: true, env: { node: true }, extends: [ 'plugin:vue/vue3-essential', 'eslint:recommended', '@vue/prettier' ], parserOptions: { parser: '@babel/eslint-parser' }, rules: { 'no-console': process.env.NODE_ENV === 'production' ? 'warn' : 'off', 'no-debugger': process.env.NODE_ENV === 'production' ? 'warn' : 'off', 'vue/multi-word-component-names': 'off', 'prettier/prettier': [ 'error', { printWidth: 100, tabWidth: 2, useTabs: false, semi: false, singleQuote: true, trailingComma: 'none', bracketSpacing: true, arrowParens: 'avoid' } ] } }6.3 Git提交规范
推荐使用Angular提交规范:
- feat: 新功能
- fix: 修复bug
- docs: 文档变更
- style: 代码格式调整
- refactor: 代码重构
- perf: 性能优化
- test: 测试相关
- chore: 构建过程或辅助工具的变动
示例:
git commit -m "feat: 添加用户登录功能"7. 第一天开发总结
通过第一天的项目搭建,我们完成了以下工作:
- 搭建了基于Vue3的开发环境
- 集成了ElementPlus UI组件库
- 配置了axios请求拦截和响应处理
- 实现了SCSS全局样式管理和主题定制
- 设计了项目基础路由和状态管理结构
- 创建了基础布局组件
- 配置了代码规范和开发工具
在实际开发过程中,有几个关键点需要特别注意:
- ElementPlus按需引入:对于生产环境,建议使用按需引入减少包体积:
npm install -D unplugin-vue-components unplugin-auto-import然后在vite.config.js或vue.config.js中配置:
const AutoImport = require('unplugin-auto-import/webpack') const Components = require('unplugin-vue-components/webpack') const { ElementPlusResolver } = require('unplugin-vue-components/resolvers') module.exports = { configureWebpack: { plugins: [ AutoImport({ resolvers: [ElementPlusResolver()] }), Components({ resolvers: [ElementPlusResolver()] }) ] } }- 环境变量管理:不同环境需要不同的API地址,可以在项目根目录创建:
- .env.development
- .env.production
内容示例:
VUE_APP_BASE_API=/api VUE_APP_TITLE=小兔鲜(开发环境)- 性能优化准备:虽然第一天不需要过度优化,但应该提前考虑:
- 路由懒加载
- 组件异步加载
- 第三方库CDN引入
- 图片懒加载
在接下来的开发中,我们将重点实现电商核心功能模块,包括:
- 首页商品展示
- 分类筛选
- 商品详情
- 购物车功能
- 用户登录注册
通过这个项目,我深刻体会到Vue3的组合式API带来的开发效率提升,特别是setup语法糖让代码组织更加清晰。ElementPlus的组件丰富度完全能满足电商项目需求,而axios的拦截器机制则让全局请求处理变得非常简单。