vue3+node(koa2)写一个网站-前端篇
程序员文章站
2022-06-25 11:24:10
采用vue-cli 4.5.0生成项目目录。新版本的脚手架生成的项目 main.js与之前旧版本略有不同,新版本如下://main.jsimport { createApp } from 'vue';import App from './App.vue';import router from './router';// 法一const app = createApp(App);app.use(router)app.mount('#app')//法二//createApp(App...
采用vue-cli 4.5.0生成项目目录。项目中采用vue3的新语法来写代码,当然你还是用原来的vue 2.x语法也不会有问题。
新版本的脚手架生成的项目 main.js与之前旧版本略有不同,新版本如下:
//main.js
import { createApp } from 'vue';
import App from './App.vue';
import router from './router';
// 法一
const app = createApp(App);
app.use(router)
app.mount('#app')
//法二
//createApp(App).use(router).mount('#app')
新版本中路由的使用方式也不太一样:
// router/index.js
import { createRouter, createWebHashHistory } from 'vue-router';
import Home from '@/views/Home'
const router = createRouter({
history: createWebHashHistory(),
routes: [
{
path: '',
redirect: '/home'
},
{
path: '/home',
name: 'home',
component: Home
}
]
});
export default router;
//页面中监听路由和使用路由的变化
import { watch } from "vue";
import { useRoute, useRouter } from "vue-router";
export default {
name: "my-header",
setup() {
const route = useRoute();
const router = useRouter();
const activeRoute = ref("");
watch(
() => route.path,
(curPath) => {
activeRoute.value = curPath;
}
)
function toPage(path) {
router.push(path);
}
return {
activeRoute,
toPage
};
}
};
vue3一个比较大的亮点就是composition api, 之前选项的写法只能数据写一块,处理逻辑写一块,维护起来效率不高。现在通过新语法,某个功能的数据和逻辑能封装到一块 维护性、复用性得到大大提高。 别说 用起来还真香。
// blog.js
//获取博客相关的数据和逻辑封装到一起
import { ref } from "vue";
import { getBlogList } from "@/api/blog";
import { formatTime } from "@/utils";
export function getBlogListLogic() {
const blogList = ref([]);
async function getBlog(keyword) {
const {
data: { data, errno }
} = await getBlogList({ keyword: keyword && keyword.value });
if (errno === 0) {
data.forEach(item => {
item.createtime = formatTime(item.createtime);
});
blogList.value = data;
}
}
return { blogList, getBlog };
}
//页面中使用示例
import { ref, onMounted } from "vue";
import { useRouter } from "vue-router";
import { getBlogListLogic } from "@/common/blog";
export default {
name: "Home",
setup() {
const keyword = ref("");
const router = useRouter();
const { blogList, getBlog } = getBlogListLogic();
function onSearch(key) {
keyword.value = key;
getBlog(keyword);
}
function toDetail(blog) {
router.push({
path: "/blog/detail",
query: {
id: blog.id
}
});
}
onMounted(() => {
getBlog();
});
return {
blogList,
keyword,
onSearch,
toDetail
};
}
};
有时候我们需要通过ref来获取元素或自定义组件的引用,在vue3语法中使用方式也不太一样了。
//xxx.vue
<template>
<div class="content-wrap">
<quill-editor
:ref="q => quill = q"
:value="postData.content"
></quill-editor>
</div>
</template>
<script>
import QuillEditor from "@/components/QuillEditor";
import { ref, reactive } from "vue";
export default {
name: "handleblog",
components: {
QuillEditor
},
setup() {
const quill = ref(null);
const postData = reactive({
description: "",
title: "",
content: ""
});
async function onSaveClick() {
//通过ref调用quill-eidtor组件中的getContent方法
postData.content = quill.value.getContent();
}
return {
quill,
postData,
onSaveClick
};
}
};
</script>
setup函数也接受两个参数 props 和 context。 props是响应式的,context是普通的js对象包含3个属性 attrs, slots, emit。
export default {
setup(props, context) {
...
}
}
export default {
setup(props, { attrs, slots, emit }) {
//向外触发事件
emit('change')
}
}
登录的处理。有些页面我门需要登录后才让访问,可以在路由导航守卫进行拦截判断是否登录,如果需要登录权限但没登录就去登录。接口报401的时候让跳转到登录页。
//router/index.js
router.beforeEach((to, from, next) => {
//因为如果登录了,服务端代码会加上cookie,所以可以通过有没有cookies来判断是否已登录
if (to.meta.needLogin && !getCookie('koa.sid')) {
next('/login')
} else {
next()
}
})
//axios封装处
import Axios from 'axios';
import router from '@/router/index';
import { message } from 'ant-design-vue';
const fetch = Axios.create({
baseURL: ''
});
fetch.interceptors.request.use(function (config) {
return config;
}, function (error) {
return Promise.reject(error);
});
// 添加响应拦截器
fetch.interceptors.response.use(function (response) {
return response;
}, function (error) {
const { status, data } = error.response;
switch (status) {
case 401:
message.warn(data.message)
router.push('/login');
break;
default:
message.error(data.message)
return Promise.reject(data);
}
});
export default fetch;
本文地址:https://blog.csdn.net/weixin_41804429/article/details/108950088