window监听到打印的beforePrint和afterPrint两个事件,但是无论点击打印还是取消都会触发afterPrint事件,所以只能通过这个事件的触发让用户自己判断是否打印成功,以此来记录数据是否打印或者是打印了几次,以下是打印的方法
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 158 159 160 161 162 163 164 165 166 167 168 169 170 171 172 173 174 175 176 177 178 179 180 181 182 183 184 185 186 187 188 189 190 191 192 193 194 195 196 197 198 199 200 201 202 203 204 205 206 207 208 |
// import Vue from "vue"; import { productionPlanPrint } from '@/api/prodPlan' const isDOM = (obj) => { return typeof HTMLElement === 'object' ? obj instanceof HTMLElement : obj && typeof obj === 'object' && obj.nodeType === 1 && typeof obj.nodeName === 'string' } /* const extend = (obj, obj2) => { for (const k in obj2) { if (obj2.hasOwnProperty(k)) obj[k] = obj2[k] } return obj } */ const isInBody = (node) => { return node === document.body ? false : document.body.contains(node) } const wrapperRefDom = (refDom) => { let prevDom = null let currDom = refDom if (!isInBody(currDom)) return currDom while (currDom) { if (prevDom) { const element = currDom.cloneNode(false) element.appendChild(prevDom) prevDom = element } else { prevDom = currDom.cloneNode(true) } currDom = currDom.parentElement } return prevDom } const getStyle = (options) => { let str = '' const styles = document.querySelectorAll('style,link') for (let i = 0; i < styles.length; i++) { str += styles[i].outerHTML } str += '<style>' + (options.noPrint ? options.noPrint : '.no-print') + '{display:none;}</style>' return str } const getHtml = (dom, options) => { const inputs = document.querySelectorAll('input') const textAreas = document.querySelectorAll('textarea') const selects = document.querySelectorAll('select') for (let k = 0; k < inputs.length; k++) { if (inputs[k].type === 'checkbox' || inputs[k].type === 'radio') { if (inputs[k].checked === true) { inputs[k].setAttribute('checked', 'checked') } else { inputs[k].removeAttribute('checked') } } else if (inputs[k].type === 'text') { inputs[k].setAttribute('value', inputs[k].value) } else { inputs[k].setAttribute('value', inputs[k].value) } } for (let k2 = 0; k2 < textAreas.length; k2++) { if (textAreas[k2].type === 'textarea') { textAreas[k2].innerHTML = textAreas[k2].value } } for (let k3 = 0; k3 < selects.length; k3++) { if (selects[k3].type === 'select-one') { const child = selects[k3].children for (const i in child) { if (child[i].tagName === 'OPTION') { if (child[i].selected === true) { child[i].setAttribute('selected', 'selected') } else { child[i].removeAttribute('selected') } } } } } return options.noPrintParent ? dom.outerHTML : wrapperRefDom(dom).outerHTML } // var flag = false const toPrint = (frameWindow, target, id) => { // var beforePrint = function() { // // console.log('beforePrint'); // } // var afterPrint = function() { // flag = true // // console.log('afterPrint') // // target.$confirm('是否打印成功', '提示', { // // confirmButtonText: '成功', // // cancelButtonText: '失败', // // type: 'warning' // // }).then(() => { // // flag = true // // // console.log('ddd',id) // // // productionPlanPrint({ id }).then(res =>{ // // // console.log('rrr', res) // // // if (res.code==200){ // // // target.$message({ // // // type: 'success', // // // message: '打印数据更新成功' // // // }) // // // } // // // }) // // }).catch(() => { // // target.$message({ // // type: 'info', // // message: '未成功打印' // // }) // // }) // // return flag // } // // if (frameWindow.matchMedia) { // 返回一个新的 MediaQueryList 对象,表示指定的媒体查询字符串解析后的结果。 // var mediaQueryList = frameWindow.matchMedia('print') // mediaQueryList.addListener(function(mql) { // // console.log('fff',mql) // if (mql.matches) { // beforePrint() // } else { // afterPrint() // } // }) // } // // window.onbeforeprint = beforePrint; // window.onafterprint = afterPrint; try { setTimeout(function() { frameWindow.focus() try { // var mediaQueryList = frameWindow.matchMedia('print') // mediaQueryList.addListener((mql)=> { // console.log('aaa',mql.matches) // // if (mql.matches) { // // beforePrint(); // // } else { // // afterPrint(); // // } // }) // console.log('打印',!frameWindow.document.execCommand('print', false, null)) if (!frameWindow.document.execCommand('print', false, null)) { frameWindow.print() // console.log('打印1') } } catch (e) { frameWindow.print() // console.log('打印2') } frameWindow.close() }, 10) } catch (err) { console.log('err', err) } } const writeIframe = (content, target, id) => { const iframe = document.createElement('iframe') const f = document.body.appendChild(iframe) iframe.id = 'myIframe' iframe.setAttribute( 'style', 'position:absolute;width:0;height:0;top:-10px;left:-10px;' ) const w = f.contentWindow || f.contentDocument const doc = f.contentDocument || f.contentWindow.document doc.open() doc.write(content) doc.close() iframe.onload = function() { // w.onafterprint = e=>{ // console.log('打印后',e) // } toPrint(w, target, id) setTimeout(function() { document.body.removeChild(iframe) // console.log('iii') }, 100) } return w } const Print = (dom, options, target, id) => { // console.log('ddd',target) options = { ...options, noPrint: '.no-print' } let targetDom if (typeof dom === 'string') { targetDom = document.querySelector(dom) } else { targetDom = isDOM(dom) ? dom : dom.$el } const content = getStyle(options) + getHtml(targetDom, options) const w = writeIframe(content, target, id) // console.log('ddd',flag) return w } export default Print |
调用方法后监听iframe的afterPrint事件
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 |
// 打印BOM清单 printTable(val) { let _this = this // console.log('打印',this.printTableData) // console.log('dd',this.printTableTitle.id) this.isShow = true setTimeout(async() => { const frameWindow = await VabPrint(this.$refs[val], { noPrintParent: true }, this,this.printTableTitle.id) // console.log('dddd',result) // 打印前 var beforePrint = function() { // console.log('beforePrint'); } // 打印后 var afterPrint = function() { // console.log('afterPrint') _this.$confirm('是否打印成功', '提示', { confirmButtonText: '成功', cancelButtonText: '失败', type: 'warning' }).then(() => { // console.log('ddd',id) productionPlanPrint({ id: _this.printTableTitle.id }).then(res => { // console.log('rrr', res) if (res.code==200){ _this.$message({ type: 'success', message: '打印数据更新成功' }) _this.drawer = false _this.handleQuery(_this.pageNum) } }) }).catch(() => { _this.$message({ type: 'info', message: '未成功打印' }) }) } if (frameWindow.matchMedia) { // 返回一个新的 MediaQueryList 对象,表示指定的媒体查询字符串解析后的结果。 var mediaQueryList = frameWindow.matchMedia('print') mediaQueryList.addListener(function(mql) { // console.log('fff',mql) if (mql.matches) { beforePrint() } else { afterPrint() } }) } this.isShow = false }, 10) } |
from:https://blog.csdn.net/soclear_/article/details/127439860
View Details今天利用闲余时间研究了一下Jquery Jqprint插件,使用该Jquery脚本可以轻而易举的实现打印网页指定区域内容的功能: 例子一:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 |
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Strict//EN""http://www.w3.org/TR/xhtml1/DTD/xhtml1-strict.dtd"> <html xmlns="http://www.w3.org/1999/xhtml"> <head> <title>Jquery Jqprint打印控件演示</title> <meta http-equiv="Content-Type" content="text/html; charset=UTF-8" /> <script language="javascript" src="./js/jquery-1.6.2.js"></script> <script language="javascript" src="./js/jquery.jqprint-0.3.js"></script> <style type="text/css"> html,body{margin:auto 15%;padding:0;} p{line-height: 18px;} </style> <script language="javascript"> function print(){ $("#printContainer").jqprint(); } </script> </head> <body> <div id="printContainer"> <center><p style="font-size: 21pt;font-weight: bold;">报任安书</p></center> <p> 太史公牛马走司马迁再拜言。少卿足下:曩者辱赐书,教以慎于接物,推贤进士为务。意气勤勤恳恳,若望仆不相师,而用流俗人之言。仆非敢如是也。请略陈固陋。阙然久不报,幸勿为过。</p> <p> 仆之先人,非有剖符丹书之功,文史星历,近乎卜祝之间,固主上所戏弄,倡优畜之,流俗之所轻也。假令仆伏法受诛,若九牛亡一毛,与蝼蚁何以异?而世又不与能死节者比,特以为智穷罪极,不能自免,卒就死耳。何也?素所自树立使然。人固有一死,或重于泰山,或轻于鸿毛,用之所趋异也。太上不辱先,其次不辱身,其次不辱理色,其次不辱辞令,其次诎体受辱,其次易服受辱,其次关木索、被棰楚受辱,其次剔毛发、婴金铁受辱,其次毁肌肤、断肢体受辱,最下腐刑极矣!传曰:“刑不上大夫。”此言士节不可不勉励也。猛虎处深山,百兽震恐,及在穽槛之中,摇尾而求食,积威约之渐也。故士有画地为牢,势不入;削木为吏,议不对,定计于鲜也。今交手足,受木索,暴肌肤,受榜棰,幽于圜墙之中。当此之时,见狱吏则头枪地,视徒隶则心惕息。何者?积威约之势也。及以至是,言不辱者,所谓强颜耳,曷足贵乎!且西伯,伯也,拘于羑里;李斯,相也,具于五刑;淮阴,王也,受械于陈;彭越、张敖,南向称孤,系狱具罪;绛侯诛诸吕,权倾五伯,囚于请室;魏其,大将也,衣赭衣、关三木;季布为朱家钳奴;灌夫受辱居室。此人皆身至王侯将相,声闻邻国,及罪至罔加,不能引决自裁,在尘埃之中,古今一体,安在其不辱也!此言之,勇怯,势也;强弱,形也。审矣,何足怪乎?且人不能早自裁绳墨之外,已稍陵迟,至于鞭棰之间,乃欲引节,斯不亦远乎!古人所以重施刑于大夫者,殆为此也。</p> <p> 夫人情莫不贪生恶死,念亲戚,顾妻子;至激于义理者不然,乃有所不得已也。今仆不幸,早失父母,无兄弟之亲,独身孤立,少卿视仆于妻子何如哉?且勇者不必死节,怯夫慕义,何处不勉焉!仆虽怯懦,欲苟活,亦颇识去就之分矣,何至自沉溺累绁之辱哉!且夫臧获婢妾,犹能引决,况若仆之不得已乎?所以隐忍苟活,幽于粪土之中而不辞者,恨私心有所不尽,鄙陋没世,而文采不表于后也。</p> <p> 古者富贵而名摩灭,不可胜记,唯倜傥非常之人称焉。盖西伯拘而演《周易》;仲尼厄而作《春秋》;屈原放逐,乃赋《离骚》;左丘失明,厥有《国语》;孙子膑脚,《兵法》修列;不韦迁蜀,世传《吕览》;韩非囚秦,《说难》、《孤愤》;《诗》三百篇,大底圣贤发愤之所为作也。此人皆意有所郁结,不得通其道,故述往事,思来者。乃如左丘无目,孙子断足,终不可用,退而论书策,以舒其愤,思垂空文以自见。</p> <p> 仆窃不逊,近自托于无能之辞,网罗天下放失旧闻,略考其行事,综其终始,稽其成败兴坏之纪。上计轩辕,下至于兹,为十表、本纪十二、书八章、世家三十、列传七十,凡百三十篇。亦欲以究天人之际,通古今之变,成一家之言。草创未就,会遭此祸,惜其不成,是以就极刑而无愠色。仆诚已著此书,藏之名山,传之其人,通邑大都。则仆偿前辱之责,虽万被戮,岂有悔哉!然此可为智者道,难为俗人言也。</p> <p> 且负下未易居,下流多谤议。仆以口语遇遭此祸,重为乡党所笑,以污辱先人,亦何面目复上父母之丘墓乎?虽累百世,垢弥甚耳!是以肠一日而九回,居则忽忽若有所亡,出则不知其所往。每念斯耻,汗未尝不发背沾衣也。身直为闺合之臣,宁得自引深藏于岩穴邪?故且从俗浮沉,与时俯仰,通其狂惑。今少卿乃教以推贤进士,无乃与仆私心剌谬乎?今虽欲自雕琢,曼辞以自饰,无益于俗,不信,适足取辱耳。要之死日,然后是非乃定。书不能悉意,略陈固陋。谨再拜。</p> </div> <center><input type="button" onclick="print()" value="打印文章"/></center> </body> </html> |
例子二:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 |
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Strict//EN""http://www.w3.org/TR/xhtml1/DTD/xhtml1-strict.dtd"> <html xmlns="http://www.w3.org/1999/xhtml"> <head> <title>Jquery Jqprint打印控件演示</title> <meta http-equiv="Content-Type" content="text/html; charset=UTF-8" /> <script language="javascript" src="./js/jquery-1.6.2.js"></script> <script language="javascript" src="./js/jquery.jqprint-0.3.js"></script> <style type="text/css"> html,body{margin:auto 15%;padding:0;} p{line-height: 18px;} </style> <script language="javascript"> function print(){ $("#printContainer").jqprint({ debug: false, //如果是true则可以显示iframe查看效果(iframe默认高和宽都很小,可以再源码中调大),默认是false importCSS: true, //true表示引进原来的页面的css,默认是true。(如果是true,先会找$("link[media=print]"),若没有会去找$("link")中的css文件) printContainer: true, //表示如果原来选择的对象必须被纳入打印(注意:设置为false可能会打破你的CSS规则)。 operaSupport: true//表示如果插件也必须支持歌opera浏览器,在这种情况下,它提供了建立一个临时的打印选项卡。默认是true }); } </script> </head> <body> <div id="printContainer"> <center><p style="font-size: 21pt;font-weight: bold;">报任安书</p></center> <p> 太史公牛马走司马迁再拜言。少卿足下:曩者辱赐书,教以慎于接物,推贤进士为务。意气勤勤恳恳,若望仆不相师,而用流俗人之言。仆非敢如是也。请略陈固陋。阙然久不报,幸勿为过。</p> <p> 仆之先人,非有剖符丹书之功,文史星历,近乎卜祝之间,固主上所戏弄,倡优畜之,流俗之所轻也。假令仆伏法受诛,若九牛亡一毛,与蝼蚁何以异?而世又不与能死节者比,特以为智穷罪极,不能自免,卒就死耳。何也?素所自树立使然。人固有一死,或重于泰山,或轻于鸿毛,用之所趋异也。太上不辱先,其次不辱身,其次不辱理色,其次不辱辞令,其次诎体受辱,其次易服受辱,其次关木索、被棰楚受辱,其次剔毛发、婴金铁受辱,其次毁肌肤、断肢体受辱,最下腐刑极矣!传曰:“刑不上大夫。”此言士节不可不勉励也。猛虎处深山,百兽震恐,及在穽槛之中,摇尾而求食,积威约之渐也。故士有画地为牢,势不入;削木为吏,议不对,定计于鲜也。今交手足,受木索,暴肌肤,受榜棰,幽于圜墙之中。当此之时,见狱吏则头枪地,视徒隶则心惕息。何者?积威约之势也。及以至是,言不辱者,所谓强颜耳,曷足贵乎!且西伯,伯也,拘于羑里;李斯,相也,具于五刑;淮阴,王也,受械于陈;彭越、张敖,南向称孤,系狱具罪;绛侯诛诸吕,权倾五伯,囚于请室;魏其,大将也,衣赭衣、关三木;季布为朱家钳奴;灌夫受辱居室。此人皆身至王侯将相,声闻邻国,及罪至罔加,不能引决自裁,在尘埃之中,古今一体,安在其不辱也!此言之,勇怯,势也;强弱,形也。审矣,何足怪乎?且人不能早自裁绳墨之外,已稍陵迟,至于鞭棰之间,乃欲引节,斯不亦远乎!古人所以重施刑于大夫者,殆为此也。</p> <p> 夫人情莫不贪生恶死,念亲戚,顾妻子;至激于义理者不然,乃有所不得已也。今仆不幸,早失父母,无兄弟之亲,独身孤立,少卿视仆于妻子何如哉?且勇者不必死节,怯夫慕义,何处不勉焉!仆虽怯懦,欲苟活,亦颇识去就之分矣,何至自沉溺累绁之辱哉!且夫臧获婢妾,犹能引决,况若仆之不得已乎?所以隐忍苟活,幽于粪土之中而不辞者,恨私心有所不尽,鄙陋没世,而文采不表于后也。</p> <p> 古者富贵而名摩灭,不可胜记,唯倜傥非常之人称焉。盖西伯拘而演《周易》;仲尼厄而作《春秋》;屈原放逐,乃赋《离骚》;左丘失明,厥有《国语》;孙子膑脚,《兵法》修列;不韦迁蜀,世传《吕览》;韩非囚秦,《说难》、《孤愤》;《诗》三百篇,大底圣贤发愤之所为作也。此人皆意有所郁结,不得通其道,故述往事,思来者。乃如左丘无目,孙子断足,终不可用,退而论书策,以舒其愤,思垂空文以自见。</p> <p> 仆窃不逊,近自托于无能之辞,网罗天下放失旧闻,略考其行事,综其终始,稽其成败兴坏之纪。上计轩辕,下至于兹,为十表、本纪十二、书八章、世家三十、列传七十,凡百三十篇。亦欲以究天人之际,通古今之变,成一家之言。草创未就,会遭此祸,惜其不成,是以就极刑而无愠色。仆诚已著此书,藏之名山,传之其人,通邑大都。则仆偿前辱之责,虽万被戮,岂有悔哉!然此可为智者道,难为俗人言也。</p> <p> 且负下未易居,下流多谤议。仆以口语遇遭此祸,重为乡党所笑,以污辱先人,亦何面目复上父母之丘墓乎?虽累百世,垢弥甚耳!是以肠一日而九回,居则忽忽若有所亡,出则不知其所往。每念斯耻,汗未尝不发背沾衣也。身直为闺合之臣,宁得自引深藏于岩穴邪?故且从俗浮沉,与时俯仰,通其狂惑。今少卿乃教以推贤进士,无乃与仆私心剌谬乎?今虽欲自雕琢,曼辞以自饰,无益于俗,不信,适足取辱耳。要之死日,然后是非乃定。书不能悉意,略陈固陋。谨再拜。</p> </div> <center><input type="button" onclick="print()" value="打印文章"/></center> </body> </html> |
from:https://blog.51cto.com/u_16099297/6962748
View DetailsWebpack 会为打包后的代码生成 Source Map 文件,以便在运行时可以调试源代码。然而,如果开发人员在生产环境中没有正确地配置 SourceMap,攻击者就可能获得敏感信息,例如源代码和服务器配置等。
攻击者可以通过发送 HTTP 请求来获取 Source Map 文件,并从中获取敏感信息。
View Details原理分析
提取操作:复制=>粘贴=>上传
在这个操作过程中,我们需要做的就是:监听粘贴事件=>获取剪贴板里的内容=>发请求上传
为方便理解下文,需要先明白几点:
我们只能上传网页图(在网页上右键图片,然后复制)和截图(截图工具截的图片,eg:qq截图),不能粘贴上传系统里的图片(从桌面上、硬盘里复制),他们是存在完全不同的地方的。
截图工具截的图与在网页点击右键复制的图是有些不同的,因此处理方式也不一样。
知悉paste event这个事件:当进行粘贴(右键paste/ctrl+v)操作时,该动作将触发名为’paste’的剪贴板事件,这个事件的触发是在剪贴板里的数据插入到目标元素之前。如果目标元素(光标所在位置)是可编辑的元素(eg:设置了contenteditable属性的div。textarea并不行。),粘贴动作将把剪贴板里的数据,以最合适的格式,插入到目标元素里;如果目标元素不可编辑,则不会插入数据,但依然触发paste event。数据在粘贴的过程中是只读的。此段是翻译于w3.org_the-paste-action。
可惜的是,经过试验,发现chrome(当前最新版)、firefox(当前最新版)、ie11对paste事件的实现并不是完全按照w3c来的,各自也有区别(w3c的paste标准也因此只是草案阶段)。
假设我们现在有这样一个需求:多人聊天室。我的思路是客户端发送消息给服务器,然后服务器把聊天信息全部返回,看起来比较简单哈,但是其中有一个问题,如果我不发消息的话,服务器怎么把其他人的聊天信息返回呢?一个比较笨的方法就是一直询问服务器,其他人是否发消息。出现这样的情况是因为http协议是单向通信,只支持客户端到服务端的通信,不支持服务端到客户端的通信,那我们有没有什么更简单的解决方案呢?为了解决实时数据传输和双向通信的需求,我们的主角WebSocket登场了。
View Details参考:https://blog.csdn.net/linysuccess/article/details/109223712 配合上篇文章,代码如下:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 |
<!DOCTYPE html> <html lang="zh-cn"> <head> <meta charset="UTF-8"> <meta name="viewport" content="width=device-width, initial-scale=1.0"> <title>WebSocket测试</title> <script> function initWebSocket(wsUri) { var websocket = new WebSocket(wsUri); websocket.onopen = function(evt) { console.log('连接建立中... '+wsUri); }; websocket.onclose = function(evt) { console.log('连接关闭中...', evt); }; websocket.onmessage = function(evt) { console.log('收到来自服务端的消息:', evt.data); }; websocket.onerror = function(evt) { console.log('发生错误...', evt); }; return websocket; } // 在此配置 websocket 的地址 var websocket = initWebSocket("ws://localhost:8020/ws"); var msg, i = 0; var loop = setInterval(function(){ msg = "Hello " + (i++); if(websocket.readyState == WebSocket.OPEN) { websocket.send(msg); console.log('已发送消息:' + msg); } else { clearInterval(loop); console.log('连接已关闭,拜拜~'); } }, 3000); </script> </head> <body> 请按 F12 打开控制台查看消息 </body> </html> |
from:http://www.manongjc.com/detail/22-lipyczhcovoolme.html
View Detailsjs获取当前毫秒数(+new date()) 前言 在看视频的时候发现老师获取当前日期的毫秒表示时使用了let t1 = +new date()的写法,起初没有明白代码的含义,经过测试发现为日期的毫秒表示; 详情 代码:
1 2 3 4 5 6 |
<script> let d1 = +new Date(); //1630316745222 let d2 = new Date(); //Mon Aug 30 2021 17:46:28 GMT+0800 (中国标准时间) console.log(typeof d1 +':'+ d1 ) console.log(typeof d1 +':'+ d2) </script> |
解释: 经测试和查阅后得知**+new Date ()**相当于调用 Date.prototype.valueOf ()方法,返回的是当下的时间距离1970年1月1日0时0分0秒的毫秒数 获取当前时间毫秒数的方法 +new Date() new Date().valueOf() new Date().getTime() Date.parse(new Date()) 注意:精确到秒,会将后三位舍弃为0
1 2 3 4 5 6 7 8 9 10 11 12 13 |
<script> //new Date().valueOf() let d1= new Date().valueOf(); console.log(d1) //1630318883445 // new Date().getTime() let d2= new Date().getTime(); console.log(d2) //1630318883445 //Date.parse(new Date()) let d3 = Date.parse(new Date()); console.log(d3) //1630318883000 </script> |
from:https://blog.csdn.net/Ldcrle/article/details/120002457
View Details说到博客大家一定都不陌生,不管你是深耕职场多年的老鸟,还是在学校努力的小鸟,应该都有过一段 “装扮” 博客的经历,比如:放上喜欢的图片、添加炫酷的交互、换上 DIY 的博客主题等等。但不管再怎么 “打扮”,也跳脱不出平面的 “凡胎”。
今天 HelloGitHub 给大家带来的是一款开源的 3D 博客项目,实话说我第一次访问这个博客的时候都惊呆了,颠覆了博客的认知。进去后需要通过操控一辆 3D 的小汽车,自己 “找到” 文章才可以阅读,特别有意思!
View Details一直运行很好的项目突然build报错了,错误信息如下:
1 2 3 |
ERROR in static/js/vendor.f1c68aa2d5e85847d30e.js from UglifyJs Unexpected token name «i», expected punc «;» [./node_modules/element-ui/src/utils/merge.js:2,0][static/js/vendor.f1c68aa2d5e85847d30e.js:17064,11] Build failed with errors. |
在 UglifyJs 的 github issues #78 找到了这样一个解决方案:由于 UglifyJs 只支持 ES5 而 element-ui 可能引入了一部分 ES6 的写法,所以导致 webpack 打包失败。issue 里最后给出的解决方案是用 beta 版本的Uglify-es 来代替 UglifyJs(Beta 版本引入了对 ES2015+)的支持。需要在前端工作目录下用执行命令 npm i -D uglifyjs-webpack-plugin@beta。 不过在尝试过后,发现 build error 的问题依然没有解决,在深入查找问题所在后,决定用 bable 来解析 element-ui, 要完成此操作只需要修改前端文件夹下的build/webpack.base.conf.js 文件即可,修改如下: 修改前
1 2 3 4 5 6 7 8 |
module: { rules: [ ... { test: /\.js$/, loader: 'babel-loader', include: [resolve('src'), resolve('test')] }, |
修改后
1 2 3 4 5 6 7 8 9 |
module: { rules: [ ... { test: /\.js$/, loader: 'babel-loader',//注意elementUI的源码使用ES6需要解析 include: [resolve('src'), resolve('test'),resolve('/node_modules/element-ui/src'),resolve('/node_modules/element-ui/packages')] }, ... |
相当于将 element-ui 加入需要 babel 解析的包中。 之后再次执行 npm run build, build 成功。 转载自以下文章: 原文地址 from:https://blog.csdn.net/sing_sing/article/details/79146265
View Details