研究背景

在我们平常写demo的时候难免需要自己模拟一些数据去调用,那么如何请求本地的json数据呢,下面将要从0开始,讲一下请求本地json数据的详细过程,途中遇到的问题及解决方法

技术选型

我们选择那种方式来请求数据呢,是要根据当前项目环境来选择,一般来说常用的是jquery的$.getJSON( ) 方法 和 ajax/axios ,由于当前vue工程是由vue-cli搭建的,我们 选用axios去请求

步骤:

1、安装axios
npm install axios --save
2、在main.js中全局引入axios

使用vue2.x :

import axios from 'axios'
Vue.prototype.$axios = axios

完整main.js如下:

使用 vue3.0 :

import axios from 'axios'
app.config.globalProperties.$axios = axios

完整main.js如下:

3、存放静态资源

请求工具配置好了,我们应该准备需要的数据了,但是静态资源应该放在哪里呢,src/assets,static、public是我们知道存放静态资源的地方,但他们之间有什么区别呢

这里我们要看 Vue CLI 版本,旧版本包名vue-cli( 1.x或2.x),新版本包名@vue/cli(3.x或 4.x),在不同版本中存放静态文件的地方不同:

在旧版本中,我们的工程根目录下有static 和 src/assets,首先,assets文件夹和static文件夹在vue-cli生成的项目中,都是用来存放静态资源的。

它们的区别是:

A、assets目录中的文件会被webpack处理解析为模块依赖,只支持相对路径形式。build的时候由Webpack解析为模块依赖。
B、static/ 目录下的文件并不会被Webpack处理:它们会直接被复制到最终的打包目录(默认是dist/static)下。
必须使用绝对路径引用这些文件,这是通过在 项目vue.config.js文件中的 assetsPublicPath 和 assetsSubDirectory 连接来确定的。

任何放在 static/ 中文件需要以绝对路径的形式引用:/static/[filename],所以如果需要引用static目录下的图片及其他资源,应该使用绝对路径 如果你改变assetSubDirectory 为assets, 那么这些 URLs将需要被替换为 /assets/[filename].

所以我们在旧版本中,将数据放在根目录下的static中:

在新版本中,static文件夹被public文件夹替换,在vue.config.js中通过配置assetsDir和 publicPath来确定,引用方式同static,务必使用绝对路径的形式

我们将静态资源放在根目录下public中:

我目前使用的的是vue2.x版本,所以将数据放在了根目录下的static文件夹里

4、设置proxy请求代理

按道理讲,放置完资源我们就可以请求了,于是像这样往下写,根据目录结构,找到对应的文件,再去请求

结果报错了:404 请求接口不存在,访问不到资源

原因:请看上一个步骤的文字加粗部分:一定要使用绝对路径!!!

当你在 JavaScript、CSS 或 *.vue 文件中使用相对路径 (必须以 . 开头) 引用一个静态资源时,该资源将会被包含进入
webpack 的依赖图中。 它会作为一个相对模块请求被解释且基于你的文件系统中的目录结构进行解析。
-------引自vue-cli 官网 HTML 和静态资源

所以我们应该使用绝对路径,为避免每次都要写本地地址,选择proxy请求代理替我们处理访问阻碍

使用 旧版本脚手架时 vue.config.js中的配置:

module.exports = {
  dev: {
  //除了 index.html 之外的静态资源要存放的路径/ 把所有的静态资源打包到 dist下的该文件夹下
   assetsSubDirectory: 'static',  
   //代表打包后,index.html里面引用资源的的相对地址
   assetsPublicPath: '/',   
   proxyTable: {
      '/api': {
        //需要访问的域名
        target: 'http://localhost:8080',  
        //是否跨域
        changeOrigin: true, 
        //重写路径,是一个正则表达式,表示要匹配请求的url中,全部'http://localhost:8080/api' 转接为 http://localhost:8080/
        pathRewrite: { 
          '^/api': ''
        }
      }
    },
    host: 'localhost', // 
    port: 8080, // 
  },
}

使用新版本脚手架时 vue.config.js中的配置:

module.exports = {
  //assetsDir: 'public', //放置生成的静态资源 (js、css、img、fonts) 的 (相对于 outputDir 的) 目录。
  //publicPath: '/', //部署应用包时的基本 URL。  
  devServer: {
    proxy: {
      '/api': {
        target: 'http://localhost:8080',
        changeOrigin: true, //是否跨域
        pathRewrite: {
          '^/api': ''
        }
      }
    },
    host: 'localhost', //
    port: 8080, //
  },
}

一定要注意新旧版本中属性名发生了改变,另外附上vue.config.js文件的配置手册 vue.config.js文件配置参考

5、请求数据

现在proxy配置完成,我们终于可以请求数据了

vue2.x中:

this.$axios.get('/chinaData/100000.json').then(res => {  //此时相当于访问 http://localhost:8080/chinaData/100000.json
   console.log(res, '中国数据')
})

vue3.0中:

没有this,取而代之的是Composition API提供的getCurrentInstance方法,用来获取当前组件实例,然后通过ctx获取当前上下文。但是ctx只适合开发环境,在打包后会无法获取全局挂载方法,因此在线上环境需要将ctx换成proxy

import { getCurrentInstance } from "vue"
export default{
    const { ctx } = getCurrentInstance()
   ctx.$axios.get('/chinaData/100000.json').then((res) => {
        console.log(res, '返回的数据')
    })
}

最后看一下请求到的数据

vue2.x中请求到的:
在这里插入图片描述
vue3中请求到的:
在这里插入图片描述
现在整个请求本地json数据的任务就完成了,大家快去试试吧,有问题欢迎私信指出 ~

Logo

华为开发者空间,是为全球开发者打造的专属开发空间,汇聚了华为优质开发资源及工具,致力于让每一位开发者拥有一台云主机,基于华为根生态开发、创新。

更多推荐