Vue 项目开发规范
一、项目结构规范
1. 基础目录结构
src/
├── api/ # 接口请求
├── assets/ # 静态资源
│ ├── fonts/ # 字体文件
│ ├── images/ # 图片资源
│ └── styles/ # 全局样式
├── components/ # 公共组件
│ ├── common/ # 全局通用组件
│ └── business/ # 业务组件
├── composables/ # 组合式函数 (Vue3)
├── directives/ # 自定义指令
├── router/ # 路由配置
├── store/ # 状态管理
├── utils/ # 工具函数
├── views/ # 页面组件
├── App.vue # 根组件
└── main.js # 入口文件
2. 文件命名规范
- 组件文件:大驼峰式 (PascalCase),如
UserInfoCard.vue - JS/TS文件:小驼峰式 (camelCase),如
userApi.js - 样式文件:短横线连接 (kebab-case),如
user-info.scss - 图片资源:小写+短横线,如
user-avatar.png
二、代码风格规范
1. 组件规范
<template>
<!-- 1. 单根元素 -->
<div class="user-card">
<!-- 2. 组件名使用大驼峰 -->
<UserAvatar :src="avatar" />
<!-- 3. 属性多行书写 -->
<UserInfo
:name="user.name"
:age="user.age"
:gender="user.gender"
/>
</div>
</template>
<script>
// 4. 组件名与文件名一致
export default {
name: 'UserCard',
// 5. 使用组件继承
extends: BaseComponent,
// 6. 属性定义规范
props: {
userId: {
type: Number,
required: true
},
showDetail: {
type: Boolean,
default: false
}
},
// 7. 数据初始化
data() {
return {
loading: false,
user: {}
}
},
// 8. 生命周期钩子顺序
created() {},
mounted() {},
// 9. 方法按功能分组
methods: {
// 数据相关
fetchUser() {},
// UI相关
showDetail() {}
}
}
</script>
<style scoped>
/* 10. 使用scoped样式 */
.user-card {
/* 11. BEM命名规范 */
&__header {
font-size: 16px;
}
}
</style>
2. Vue3 Composition API 规范
<script setup>
// 1. 导入顺序:Vue > 第三方库 > 本地模块
import { ref, computed } from 'vue'
import { useRouter } from 'vue-router'
import { fetchUser } from '@/api/user'
import UserAvatar from './UserAvatar.vue'
// 2. 响应式数据
const loading = ref(false)
const user = ref({})
// 3. 计算属性
const fullName = computed(() => {
return `${user.value.firstName} ${user.value.lastName}`
})
// 4. 方法
const getUser = async () => {
loading.value = true
try {
user.value = await fetchUser()
} finally {
loading.value = false
}
}
// 5. 生命周期
onMounted(() => {
getUser()
})
</script>
3. 路由规范
// router/index.js
const routes = [
{
path: '/user',
name: 'User', // 路由命名使用大驼峰
component: () => import('@/views/User/Index.vue'),
meta: {
requiresAuth: true,
title: '用户中心'
},
children: [
{
path: 'profile',
name: 'UserProfile',
component: () => import('@/views/User/Profile.vue')
}
]
}
]
三、状态管理规范 (Pinia/Vuex)
1. Pinia 规范
// stores/user.js
import { defineStore } from 'pinia'
export const useUserStore = defineStore('user', {
state: () => ({
token: null,
info: {}
}),
getters: {
isLogin: (state) => !!state.token
},
actions: {
async login(payload) {
const res = await api.login(payload)
this.token = res.token
this.info = res.user
}
}
})
2. 使用规范
<script setup>
import { useUserStore } from '@/stores/user'
const userStore = useUserStore()
// 直接解构会失去响应性,使用storeToRefs
const { token } = storeToRefs(userStore)
</script>
四、代码提交规范
1. Git Commit 规范
<type>(<scope>): <subject>
<body>
<footer>
常用 type:
- feat: 新功能
- fix: 修复bug
- docs: 文档变更
- style: 代码格式
- refactor: 代码重构
- perf: 性能优化
- test: 测试相关
- chore: 构建/依赖变更
示例:
feat(user): add user profile page
Add new user profile page with avatar upload function
Close #123
五、最佳实践
1. 性能优化
// 1. 组件懒加载
const UserList = () => import('@/views/User/List.vue')
// 2. 图片懒加载
<img v-lazy="imageUrl" />
// 3. 长列表虚拟滚动
<VirtualList :items="largeData" />
// 4. 防抖/节流
import { debounce } from 'lodash'
methods: {
search: debounce(function(query) {
// 搜索逻辑
}, 500)
}
2. 安全实践
// 1. 防止XSS
<div v-html="sanitizeHtml(content)"></div>
// 2. API请求安全
axios.interceptors.request.use(config => {
config.headers.Authorization = `Bearer ${store.token}`
return config
})
// 3. 路由守卫
router.beforeEach((to, from, next) => {
if (to.meta.requiresAuth && !store.isLoggedIn) {
next('/login')
} else {
next()
}
})
3. 错误处理
// 1. 全局错误处理
app.config.errorHandler = (err, vm, info) => {
console.error('Vue error:', err)
trackError(err)
}
// 2. API错误统一处理
axios.interceptors.response.use(
response => response,
error => {
if (error.response.status === 401) {
router.push('/login')
}
return Promise.reject(error)
}
)
六、工具配置
1. ESLint 配置 (.eslintrc.js)
module.exports = {
root: true,
env: {
node: true
},
extends: [
'plugin:vue/vue3-essential',
'eslint:recommended',
'@vue/typescript/recommended'
],
rules: {
'vue/multi-word-component-names': 'off',
'vue/component-name-in-template-casing': ['error', 'PascalCase'],
'vue/attribute-hyphenation': ['error', 'always'],
'vue/html-self-closing': ['error', {
html: {
void: 'always',
normal: 'never',
component: 'always'
}
}]
}
}
2. Prettier 配置 (.prettierrc)
{
"semi": false,
"singleQuote": true,
"printWidth": 100,
"trailingComma": "none",
"arrowParens": "avoid",
"htmlWhitespaceSensitivity": "ignore"
}
以上规范可根据团队实际情况进行调整,重要的是保持团队内部的一致性。建议配合代码审查(Code Review)流程确保规范执行。
No Comments