关于vue-cli打包后,发布包在本地直接index运行, 及本地读取json文件(不依靠服务器纯本地读取)的问题

1,410 阅读4分钟

前言

最近由后台管理系统转向了智能设备的硬件开发,首先碰到的问题就是要讲vuecli打包文件,从服务器运行改为直接本地打开index.html运行(因为原生app要直接读取路径运行页面),这里简单记录下遇到的几个问题及解决的方法。

环境及版本

v-cli 4.x

vue 2.6.11

v-cli 打包后,直接本地index运行

这个相对简单展开了,直接放解决方法:

1.打包后直接从dist下的index运行时,会出现页面空白无法加载

image.png

image.png

2.解决方法: 修改vue.config.js中的配置,添加pulicpath

image.png

3.注意route模式也要改为hash,history模式会出现没有报错,但就是页面空白没有内容的现象

(猜测因为hash模式才允许直接地址跳转?有大佬讲一下么 (:з」∠)

P.S 奇怪的是同样是导出的配置,修改output.js并没有作用...(暂时没搞懂这里是为什么。。。)

image.png

image.png

4.完成后再次打包测试,成功运行

image.png

本地运行时,获取json文件的问题

获取json分为两种,

第一种是json文件在开发目录中(例如前端做一下模拟数据测试),这个json内容会在打包时同时编译,直接axios、import等任何引用方式都没有问题,缺点在于它是代码的一部分,不能在打包后直接外部修改;

最简单的比如 import lauguage_data from '@/assets/jsons/Language.json'

第二种是json文件在发布目录中(即打包后出现在打包文件夹中的部分),可以实时修改配置,但对它的引用就涉及到了本地引用文件时的跨域问题

这里展开第二种问题,例如此项目中,需要一个前置的json文件,从打包目录下获取到(方便打包后直接外部修改配置)

image.png

image.png

这段axios引用,在server时是正常的,在本地直接运行时却会报错:

image.png

原因是违反了跨域的安全问题,报错中可见允许通过的协议类型,其中并不包含本地直接引用的fill://协议;

因此无论用axios、fetch等等都是在直接引用fill,都会报错中止;

image.png

image.png

解决办法:

解决跨域通常的几种办法,使用服务代理,后端处理,前端处理,这里index直接运行没有服务器,后端处理在这里就是修改浏览器配置,也不现实;

暂时能想到的只有使用jsonp的方式跳过跨域限制,直接去获取文件内容;

1.修改原来的引用,发布时改用jsonp

image.png

2.打包后的dist中,修改index.html测试

image.png

image.png

注意,常规使用jsonp时,会在url后增加一个callback回调函数,这样服务器会处理其返回内容为回调函数(json内容),形式例如:

image.png

但当前情况是index.html本地运行,没有所谓服务器的概念,这里写了回调函数也没有意义,返回的还是原始的json数据,就会出现报错

image.png

image.png

必须修改json文件的形式,内容改为回调函数(json内容)

image.png

然后检测,可见json文件加载成功,并触发了回调函数

image.png

测试已走通,现在把必须写在dist/index的内容改回main.js, 不然每次打包都要重写一次

image.png

简化一下,可以把jsonp这块打包,写成 不需要服务器支持的纯本地引用方法, (加上之前忘记了的删除script)

image.png

image.png

到这里,因为修改了json文件本身,原先的axios引用也需要修改了, 反正都组件化了直接全部改成jsonp好了, 之后用到本地json的都可以直接调用这个组件;

使用时注意所在页面的具体vue指向; 加promise的话resolve要在回调中;

image.png

例如,常规页面中的引用方式:

image.png

总结:

jsonp的引用方式属于无可奈何的本地读取文件解决方案,缺陷在于很难监听到它的错误回调,这块之后有机会再改进下

P.S 获取本地文件时,指向的文件目录

axios、fetch、jsonp等写法,都需要一个地址,如 ./data/PlugList.json,这个地址

image.png

在server时指向 public下 作为根目录

在build时指向 dist下 作为根目录

没啥用,了解一下,因为正常情况下打包出来后两者是同步的 (public的内容会打包至dist下)