我们已经学习过了vue的基础语法,也有了一点点的项目经验,下面要尝试自己搭建一个vue博客啦。
项目环境
在开始之前,先来了解一下这个项目依赖的环境。
最基础的工具有npm、nodejs、nvm(切换node的工具,不是必须但很方便)
vue当然不必多说,除了vue外,还需要vite。
根据官方文档可知,vite是一种快速的新型的前端构建工具,性能好效率高,也是vue3推荐的构建工具。具体实现原理暂时看不懂,但是我们知道相比于Vue CLI3内置的npm run serve
命令,vite提供的npm run dev
要快上不少。
vite的安装也很简单,执行npm install vite -g
即可。安装完vite再创建vue项目,就会默认捆绑vue了。
项目创建
做项目的第一步当然是初始化!
在终端中打开想要创建项目的文件夹,然后npm init vue
就可以创建我们要的项目了(也可以使用npm init vite@latest 项目名 -- --template vue
)。
然后根据需要选择需要的库。我这里选了使用ts、eslint和prettier。其他的库等用到再安装。
接着进入我们的项目文件夹,npm install
安装运行web应用所需要的库。
最后就可以通过npm run dev
命令运行项目啦!(默认端口是5173)
需要注意的是,vite要求node的版本要>=18,否则会报错TypeError: crypto$2.getRandomValues is not a function
,我就遇到了,用nvm把node版本改成20才解决。
项目结构
先来大致看一下整个项目的基本结构
vueblog
├─ .editorconfig // 项目编码规范
├─ .prettierrc.json
├─ eslint.config.ts
├─ tsconfig.json // ts配置文件
├─ env.d.ts
├─ tsconfig.app.json
├─ tsconfig.node.json
├─ package.json // 项目依赖和脚本配置
├─ package-lock.json // 锁定安装时的npm包版本号
├─ README.md // 项目文档
├─ index.html // 项目入口文件
├─ public // 存放静态资源的目录
│ └─ favicon.ico
├─ src // 源码目录
│ ├─ App.vue // vue根组件
│ ├─ assets // 美术资源目录
│ │ ├─ base.css
│ │ ├─ logo.svg
│ │ └─ main.css
│ ├─ components //组件目录
│ │ ├─ HelloWorld.vue
│ │ ├─ icons
│ │ │ ├─ IconCommunity.vue
│ │ │ ├─ IconDocumentation.vue
│ │ │ ├─ IconEcosystem.vue
│ │ │ ├─ IconSupport.vue
│ │ │ └─ IconTooling.vue
│ │ ├─ TheWelcome.vue
│ │ └─ WelcomeItem.vue
│ └─ main.ts // node应用入口文件
└─ vite.config.ts // vite配置文件
下面来具体分析几个重要的文件
package.json
{
"name": "vueblog", // 项目名称
"version": "0.0.0", // 项目版本
"private": true, // 是否公开
"type": "module", // 采用ESModule规范
"scripts": { // 脚本命令
"dev": "vite",
"build": "run-p type-check \"build-only {@}\" --",
"preview": "vite preview",
"build-only": "vite build",
"type-check": "vue-tsc --build",
"lint": "eslint . --fix",
"format": "prettier --write src/"
},
"dependencies": { // 开发时依赖的包和版本
"vue": "^3.5.13"
},
"devDependencies": { // 生产环境中依赖的包和版本
"@tsconfig/node22": "^22.0.0",
"@types/node": "^22.13.1",
"@vitejs/plugin-vue": "^5.2.1",
"@vue/eslint-config-prettier": "^10.1.0",
"@vue/eslint-config-typescript": "^14.3.0",
"@vue/tsconfig": "^0.7.0",
"eslint": "^9.18.0",
"eslint-plugin-vue": "^9.32.0",
"jiti": "^2.4.2",
"npm-run-all2": "^7.0.2",
"prettier": "^3.4.2",
"typescript": "~5.7.3",
"vite": "^6.0.11",
"vite-plugin-vue-devtools": "^7.7.1",
"vue-tsc": "^2.2.0"
}
}
index.html
index.html是整个项目的入口文件,负责加载整个应用。浏览器访问vue项目时,实际上时访问的index.html,通过这个文件,浏览器找到并加载vue应用的其他组件和资源。
<!DOCTYPE html>
<html lang="">
<head>
<meta charset="UTF-8">
<link rel="icon" href="/favicon.ico">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<title>Vite App</title>
</head>
<body>
<!-- vue根实例的挂载点 -->
<div id="app"></div>
<!-- 引入main.ts文件作为node应用入口 -->
<script type="module" src="/src/main.ts"></script>
</body>
</html>
main.ts
正常来说应该是js文件,但是我们使用的ts规范,所以后缀就是ts。
main.ts项目入口的ts文件,引入所需要的组件并创建vue实例,再挂载到id为app的html元素中(正是index.html里那个)。也可以在其中设置vue应用的全局变量、路由等。
import './assets/main.css'
import { createApp } from 'vue'
import App from './App.vue'
createApp(App).mount('#app')
App.vue
这个我们就很熟悉了,vue项目的根组件嘛,它是整个vue应用的骨架。所有的页面都是在这个组件下进行切换的,所有的路由都是这个组件的子组件。id是app,接管index.html中div要渲染的内容。
// js脚本
<script setup lang="ts">
import HelloWorld from './components/HelloWorld.vue'
import TheWelcome from './components/TheWelcome.vue'
</script>
// html页面
<template>
<header>
<img alt="Vue logo" class="logo" src="./assets/logo.svg" width="125" height="125" />
<div class="wrapper">
<HelloWorld msg="You did it!" />
</div>
</header>
<main>
<TheWelcome />
</main>
</template>
// css样式
<style scoped>
header {
line-height: 1.5;
}
.logo {
display: block;
margin: 0 auto 2rem;
}
@media (min-width: 1024px) {
header {
display: flex;
place-items: center;
padding-right: calc(var(--section-gap) / 2);
}
.logo {
margin: 0 2rem 0 0;
}
header .wrapper {
display: flex;
place-items: flex-start;
flex-wrap: wrap;
}
}
</style>