irpas技术客

Vue TypeScript 使用eval函数的坑_jiyanglin

irpas 6640

? ? ? ?正常情况下,项目里不会用eval函数,但是万一要调用一个全局的js库,就需要用eval做些骚操作,这个时候编译会提示:?is strongly discouraged as it poses security risks and may cause issues with minification.

? ? ? 警告是可以忽略,刚开始我也没当回事,有风险就有风险,可控,我知道自己写的是啥。但是,今天我改代码的时候出了问题。就是dev时候正常,但是打包以后,不按照预期执行,编译出来的代码就不是我要的逻辑。

问题的关键是:使用eval的函数不能是全局函数(需要包装在一个对象里),然后这个函数内容要简单,不要里面定义各种变量,然后被eval调用,免得被编译时候优化掉

简单的代码实例问题

上一段简单的代码:

<template> <div> <button @click="btn">测试</button> </div> </template> <script setup lang="ts"> function myfun(param:number){ let ret = 0 eval("ret = param+1") return ret; } function btn() { let ret = myfun(1); console.log(ret); } </script>

dev运行在浏览器点击按钮,输出2,没毛病

然后打包以后,运行就会是这样,输出为NaN

缩成一坨的这个代码里面,把我的myfun函数编译成了这样,也没毛病:

function myfun(param){let ret=0;return eval("ret = param+1"),ret }

但是,调用时候变成了这样!!!!

myfun调用的时候,传入的参数哪里去了???

let e=myfun();console.log(e)

因为没有参数进入,eval里的param+1结果就变成了NaN

解决方法

把代码改成这样,函数包装到一个对象里面:

<template> <div> <button @click="btn">测试</button> </div> </template> <script setup lang="ts"> const FunPack = { myfun(param:number){ let ret = 0 eval("ret = param+1") return ret; } } function btn() { let ret = FunPack.myfun(1); console.log(ret); } </script>

?然后打包运行,输出为2正常:

这个时候调用变成这样,myfun的时候传的参数正常

let e=FunPack.myfun(1);console.log(e) 问题的原理

感觉上,对于调用一个不在对象里的函数,typescript编译时候进行了更多优化,对于myfun函数,里面eval函数那一行没有类型系统,等于没有,所以编译时候理解成下面这样,等于没有eval那一行。等于param没有被使用,所以调用函数时候,觉得这个参数没有用,就给吃了。。。

function myfun(param:number){ let ret = 0 return ret; }

同理,如果myfun里面定义了别的变量,用来给eval使用,但是别的地方没有使用,编译时候,这个变量就会被编译器认为无效,然后被吃掉,比如myfun定义成这样,打包运行就会报错dat is not defined

function myfun(param:number){ ? ? let ret = 0 ? ? let dat = param + 10; ? ? eval("ret = dat+1") ? ? return ret; } 一劳永逸的方法

虽然通过把函数封装到对象,可以解决问题,但是,也说不好ts编译器后续会不会关于对象的方法调用也进行这种优化。

所以还有一个解决方法,就是在函数里把param用一下,让编译器觉得它被使用了,别吃掉。

比如改成这样,把param输出一下。。。

function myfun(param:number){ let ret = 0 console.debug(param); eval("ret = param+1") return ret; }


1.本站遵循行业规范,任何转载的稿件都会明确标注作者和来源;2.本站的原创文章,会注明原创字样,如未注明都非原创,如有侵权请联系删除!;3.作者投稿可能会经我们编辑修改或补充;4.本站不提供任何储存功能只提供收集或者投稿人的网盘链接。

标签: #Vue #Typescript #使用eval函数的坑 #is #strongly #discouraged #as