项目用到了express,vue3,axios
这个项目是和B站up主小满zs的pinia项目跟练的,下面就是这个项目一个总体框架和涉及的关键代码。up提供的数据的接口失效了,所以我在apifox自己mock了一些数据,主要就是关于总人口,死亡人口和出生人口。我的apifox链接在这里省份人口 - 个人项目
在做项目前需要补充的知识
一、express,下面是express的基本用法
const express=require('express')
const app=express()
const port=3000
// express.json()中间件,作用:用于解析json格式的请求体。有这个我们才可以获取他的req.body
// 中间件:自定义拓展express功能,请求前,响应前做相应的操作。
app.use(express.json())
app.get('/',(req,res)=>{
res.send({id:1,title:'jack'})
})
app.post('/',(req,res)=>{
console.log('收到请求体',req.body)
// 设置相应状态码
res.status(201).send()
})
app.put("/:code",(req,res)=>{
console.log("请求参数,id为",req.params.code)
console.log("请求体为",req.body)
res.send()
})
app.delete("/:code",(req,res)=>{
console.log('delete了一个文件',req.params.code)
res.status(204).send()
})
app.listen(port,()=>{
console.log('listen on port',port)
})
二、遇到问题:存在跨域(协议,域名,端口只要有一个不一样就是跨域)解决如下:后端设置CORS
(跨源资源共享)
import express from "express";
import axios from "axios";
const app = express()
// 解决跨域问题 app.use里面的* 匹配所有的请求路径
app.use("*",(req,res,next)=>{
//服务器允许来自任何域的请求,这个*的位置可以设置我们的地址
res.header('Access-Control-Allow-Origin',"*")
next()
})
下面就是代码详情
首先是node.js
提供充当服务器提供接口
import express from "express";
import axios from "axios";
const app = express()
// 解决跨域问题
app.use("*",(req,res,next)=>{
res.header('Access-Control-Allow-Origin',"*")
next()
})
const router = express.Router()
app.use('/api', router)
// 人口数据接口,我们这是就是使用express提供的请求格式/personlist+里面嵌套一层我们真正
//的请求路径,express的作用就是让前端
router.get('/personlist', async (req, res) => {
let result = await axios.get("<http://127.0.0.1:4523/m1/3739922-0-default/getperosn>")
// 将相应对象作为json格式发送给客户端
res.json({
data: result.data
})
})
app.listen(3333,()=>{
console.log('server listen')
})
接下来要通过pinia
来配置全局数据,里面使用axios
封装请求
import axios from "axios";
import { defineStore } from "pinia";
const server = axios.create({
baseURL: '<http://localhost:3333>'
})
const getpersonlist = () => {
// 这里必须要return一个promise对象
// return server.get('/api/list').then(res=>res.data) 这里就相当于直接返回了data值
return server.get('/api/personlist')
}
export const useListStore = defineStore('LIST', {
state: () => {
return {
personlist: {},
items: [],
pannellist: {}
}
},
actions: {
async getpersonlist() {
this.personlist = await getpersonlist()//这里await可以返回最终结果
}
}
})
最后就是我们的app.vue
在里面根据echart
做一个可视化大屏
<template>
</template>
<script setup>
import img from './assets/1.jpg'
import { onMounted } from 'vue';
import { useListStore } from './store';
import './assets/china.js'
import { geoCoordMap } from './assets/geoMap';
// 使用pinia调用方法
const store = useListStore()
import * as echarts from 'echarts';
onMounted(async () => {
// 调用pinia的方法,请求数据,后续可以根据stroe.personlist的数据来进行操作
await store.getpersonlist()
// 初始化地图
mapint()
// 初始化扇形图
cicleint()
lininit()
})
// 地图初始化
const mapint = () => {
const person = store.personlist.data.data.list
// 这里我们要初始化让表格有数据
store.items = person[1].children
let data = person.map(item => {
return {
name: item.province,
value: [...geoCoordMap[item.province], item.population],
children: item.children
}
})
let mychart = echarts.init(document.querySelector('#china'))
// 给元素里面添加数据
mychart.setOption(option)
// 给元素增加点击事件
mychart.on('click', (e) => {
store.items = e.data.children
store.pannellist=e.data
//每次点击都要刷新折线图和饼状图的数据
cicleint()
lininit()
})
}
</script>