cainiaoblog 23.2.171

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (401) hide show
  1. package/CNAME +1 -0
  2. package/MP_verify_o6dHCK5mIkxNpzvZ.txt +1 -0
  3. package/README.md +8 -0
  4. package/about/index.html +54 -0
  5. package/ads.txt +1 -0
  6. package/app/manual.html +104 -0
  7. package/appConfigs/config +1 -0
  8. package/archives/2018/index.html +48 -0
  9. package/archives/2019/index.html +48 -0
  10. package/archives/2019/page/2/index.html +48 -0
  11. package/archives/2020/index.html +48 -0
  12. package/archives/2021/index.html +48 -0
  13. package/archives/2022/index.html +48 -0
  14. package/archives/2023/index.html +48 -0
  15. package/archives/index.html +48 -0
  16. package/archives/page/2/index.html +48 -0
  17. package/archives/page/3/index.html +48 -0
  18. package/article/10047.html +148 -0
  19. package/article/10164.html +64 -0
  20. package/article/10624.html +436 -0
  21. package/article/10745.html +586 -0
  22. package/article/11674.html +71 -0
  23. package/article/11939.html +72 -0
  24. package/article/12238.html +86 -0
  25. package/article/1230.html +533 -0
  26. package/article/13265.html +69 -0
  27. package/article/13823.html +78 -0
  28. package/article/14125.html +72 -0
  29. package/article/14192.html +561 -0
  30. package/article/14375.html +85 -0
  31. package/article/14744.html +83 -0
  32. package/article/14936.html +451 -0
  33. package/article/1518.html +250 -0
  34. package/article/15428.html +71 -0
  35. package/article/15518.html +288 -0
  36. package/article/15569.html +418 -0
  37. package/article/1566.html +122 -0
  38. package/article/16017.html +156 -0
  39. package/article/16947.html +440 -0
  40. package/article/17096.html +82 -0
  41. package/article/17246.html +89 -0
  42. package/article/17575.html +350 -0
  43. package/article/179.html +757 -0
  44. package/article/18039.html +233 -0
  45. package/article/18071.html +375 -0
  46. package/article/18142.html +71 -0
  47. package/article/19909.html +160 -0
  48. package/article/20014.html +89 -0
  49. package/article/20021.html +389 -0
  50. package/article/20037.html +280 -0
  51. package/article/20056.html +95 -0
  52. package/article/20093.html +404 -0
  53. package/article/2021.html +607 -0
  54. package/article/20459.html +115 -0
  55. package/article/20613.html +263 -0
  56. package/article/20635.html +71 -0
  57. package/article/21317.html +71 -0
  58. package/article/21320.html +90 -0
  59. package/article/21782.html +548 -0
  60. package/article/22230.html +435 -0
  61. package/article/22237.html +347 -0
  62. package/article/22398.html +109 -0
  63. package/article/22422.html +270 -0
  64. package/article/22565.html +300 -0
  65. package/article/23046.html +250 -0
  66. package/article/23083.html +215 -0
  67. package/article/23195.html +297 -0
  68. package/article/23301.html +835 -0
  69. package/article/23589.html +285 -0
  70. package/article/23655.html +338 -0
  71. package/article/23864.html +76 -0
  72. package/article/23914.html +96 -0
  73. package/article/24169.html +135 -0
  74. package/article/24581.html +349 -0
  75. package/article/2475.html +500 -0
  76. package/article/24826.html +77 -0
  77. package/article/24924.html +247 -0
  78. package/article/25164.html +1495 -0
  79. package/article/25318.html +394 -0
  80. package/article/25710.html +1129 -0
  81. package/article/25734.html +83 -0
  82. package/article/26083.html +174 -0
  83. package/article/26147.html +283 -0
  84. package/article/26291.html +110 -0
  85. package/article/26354.html +71 -0
  86. package/article/26624.html +145 -0
  87. package/article/26639.html +298 -0
  88. package/article/26850.html +138 -0
  89. package/article/26940.html +258 -0
  90. package/article/27796.html +190 -0
  91. package/article/27800.html +161 -0
  92. package/article/28963.html +159 -0
  93. package/article/28976.html +247 -0
  94. package/article/29042.html +72 -0
  95. package/article/29596.html +81 -0
  96. package/article/29619.html +183 -0
  97. package/article/29623.html +329 -0
  98. package/article/29829.html +205 -0
  99. package/article/29abbd1c.html +112 -0
  100. package/article/30215.html +178 -0
  101. package/article/30552.html +78 -0
  102. package/article/30818.html +201 -0
  103. package/article/31330.html +364 -0
  104. package/article/3154.html +577 -0
  105. package/article/31695.html +348 -0
  106. package/article/31826.html +71 -0
  107. package/article/31843.html +132 -0
  108. package/article/32280.html +212 -0
  109. package/article/32431.html +74 -0
  110. package/article/32443.html +72 -0
  111. package/article/32732.html +122 -0
  112. package/article/3286.html +251 -0
  113. package/article/32960.html +198 -0
  114. package/article/33713.html +72 -0
  115. package/article/33899.html +615 -0
  116. package/article/34351.html +74 -0
  117. package/article/34372.html +89 -0
  118. package/article/34410.html +74 -0
  119. package/article/34431.html +118 -0
  120. package/article/3447.html +75 -0
  121. package/article/34474.html +142 -0
  122. package/article/34871.html +147 -0
  123. package/article/35397.html +175 -0
  124. package/article/3544.html +199 -0
  125. package/article/35503.html +115 -0
  126. package/article/35624.html +84 -0
  127. package/article/35697.html +384 -0
  128. package/article/35863.html +73 -0
  129. package/article/36037.html +253 -0
  130. package/article/36118.html +71 -0
  131. package/article/3621.html +119 -0
  132. package/article/36251.html +296 -0
  133. package/article/36642.html +352 -0
  134. package/article/37102.html +763 -0
  135. package/article/37336.html +351 -0
  136. package/article/37351.html +89 -0
  137. package/article/3760.html +294 -0
  138. package/article/37749.html +75 -0
  139. package/article/37789.html +83 -0
  140. package/article/38005.html +765 -0
  141. package/article/38009.html +284 -0
  142. package/article/38269.html +194 -0
  143. package/article/38344.html +88 -0
  144. package/article/38359.html +334 -0
  145. package/article/38423.html +379 -0
  146. package/article/38530.html +213 -0
  147. package/article/38743.html +268 -0
  148. package/article/38753.html +204 -0
  149. package/article/38881.html +71 -0
  150. package/article/39087.html +414 -0
  151. package/article/39309.html +84 -0
  152. package/article/39486.html +74 -0
  153. package/article/39637.html +306 -0
  154. package/article/39839.html +72 -0
  155. package/article/39937.html +152 -0
  156. package/article/39970.html +71 -0
  157. package/article/402.html +559 -0
  158. package/article/40698.html +71 -0
  159. package/article/40811.html +71 -0
  160. package/article/40964.html +462 -0
  161. package/article/41011.html +322 -0
  162. package/article/41152.html +78 -0
  163. package/article/41696.html +71 -0
  164. package/article/41717.html +281 -0
  165. package/article/41777.html +149 -0
  166. package/article/419.html +985 -0
  167. package/article/4233.html +136 -0
  168. package/article/4292.html +86 -0
  169. package/article/43302.html +96 -0
  170. package/article/43397.html +106 -0
  171. package/article/43724.html +281 -0
  172. package/article/43999.html +224 -0
  173. package/article/44426.html +77 -0
  174. package/article/44964.html +137 -0
  175. package/article/45004.html +123 -0
  176. package/article/4510.html +83 -0
  177. package/article/45156.html +320 -0
  178. package/article/45157.html +52 -0
  179. package/article/45267.html +87 -0
  180. package/article/45641.html +207 -0
  181. package/article/45960.html +75 -0
  182. package/article/46100.html +1262 -0
  183. package/article/46366.html +74 -0
  184. package/article/46771.html +96 -0
  185. package/article/46911.html +517 -0
  186. package/article/46948.html +137 -0
  187. package/article/46ee4850.html +349 -0
  188. package/article/47019.html +84 -0
  189. package/article/47532.html +94 -0
  190. package/article/4783.html +429 -0
  191. package/article/47972.html +72 -0
  192. package/article/48216.html +127 -0
  193. package/article/48252.html +185 -0
  194. package/article/48520.html +74 -0
  195. package/article/48722.html +75 -0
  196. package/article/48807.html +99 -0
  197. package/article/49126.html +323 -0
  198. package/article/50001.html +88 -0
  199. package/article/50058.html +151 -0
  200. package/article/50343.html +410 -0
  201. package/article/50510.html +82 -0
  202. package/article/51082.html +98 -0
  203. package/article/51677.html +111 -0
  204. package/article/5204.html +1085 -0
  205. package/article/52500.html +538 -0
  206. package/article/52689.html +259 -0
  207. package/article/52877.html +569 -0
  208. package/article/53125.html +191 -0
  209. package/article/53428.html +251 -0
  210. package/article/53524.html +74 -0
  211. package/article/53698.html +322 -0
  212. package/article/53803e6.html +93 -0
  213. package/article/53924.html +291 -0
  214. package/article/53962.html +253 -0
  215. package/article/54006.html +71 -0
  216. package/article/54018.html +88 -0
  217. package/article/54161.html +83 -0
  218. package/article/54178.html +69 -0
  219. package/article/54258.html +327 -0
  220. package/article/54295.html +214 -0
  221. package/article/54313.html +1976 -0
  222. package/article/54351.html +90 -0
  223. package/article/54604.html +80 -0
  224. package/article/54632.html +71 -0
  225. package/article/54912.html +756 -0
  226. package/article/54918.html +129 -0
  227. package/article/55119.html +136 -0
  228. package/article/55756.html +118 -0
  229. package/article/55769.html +136 -0
  230. package/article/55870.html +161 -0
  231. package/article/56139.html +92 -0
  232. package/article/56557.html +69 -0
  233. package/article/56604.html +69 -0
  234. package/article/56816.html +266 -0
  235. package/article/56926.html +153 -0
  236. package/article/57747.html +409 -0
  237. package/article/57965.html +475 -0
  238. package/article/58816.html +78 -0
  239. package/article/59059.html +435 -0
  240. package/article/59095.html +350 -0
  241. package/article/59349.html +244 -0
  242. package/article/59402.html +216 -0
  243. package/article/59448.html +55 -0
  244. package/article/59870.html +94 -0
  245. package/article/59877.html +208 -0
  246. package/article/5dbb6f41.html +86 -0
  247. package/article/6008.html +75 -0
  248. package/article/60327.html +126 -0
  249. package/article/6035.html +76 -0
  250. package/article/60428.html +71 -0
  251. package/article/60544.html +128 -0
  252. package/article/61319.html +95 -0
  253. package/article/61367.html +93 -0
  254. package/article/624d1918.html +292 -0
  255. package/article/62543.html +71 -0
  256. package/article/62887.html +169 -0
  257. package/article/63074.html +120 -0
  258. package/article/63266.html +311 -0
  259. package/article/63351.html +74 -0
  260. package/article/63542.html +104 -0
  261. package/article/63824.html +275 -0
  262. package/article/64051.html +653 -0
  263. package/article/64189b69.html +72 -0
  264. package/article/64354.html +75 -0
  265. package/article/64869.html +79 -0
  266. package/article/64923.html +596 -0
  267. package/article/65128.html +95 -0
  268. package/article/65295.html +79 -0
  269. package/article/6888.html +75 -0
  270. package/article/7065.html +84 -0
  271. package/article/7455.html +85 -0
  272. package/article/7a3ef8f.html +315 -0
  273. package/article/8140.html +188 -0
  274. package/article/8190.html +85 -0
  275. package/article/8225.html +78 -0
  276. package/article/84c9ccd6.html +159 -0
  277. package/article/8f9a9ae3.html +82 -0
  278. package/article/9174.html +73 -0
  279. package/article/9738.html +294 -0
  280. package/article/a4145266.html +71 -0
  281. package/article/bedea419.html +72 -0
  282. package/article/bf7e7421.html +78 -0
  283. package/article/c1867fbf.html +103 -0
  284. package/article/c5576490.html +70 -0
  285. package/article/dcb0db28.html +76 -0
  286. package/article/fc3b727a.html +79 -0
  287. package/atom.xml +445 -0
  288. package/baidusitemap.xml +1079 -0
  289. package/blocks/dns.txt +264 -0
  290. package/blocks/filter.txt +1070 -0
  291. package/blocks/script.js +42 -0
  292. package/categories/CDN/index.html +48 -0
  293. package/categories/IDE/index.html +48 -0
  294. package/categories/git/index.html +48 -0
  295. package/categories/hexo/index.html +48 -0
  296. package/categories//345/205/254/345/205/261/350/212/202/346/227/245/index.html +48 -0
  297. package/categories//345/210/206/344/272/253/index.html +48 -0
  298. package/categories//345/211/215/347/253/257/index.html +48 -0
  299. package/categories//345/211/215/347/253/257/page/2/index.html +48 -0
  300. package/categories//345/211/215/347/253/257//346/265/217/350/247/210/345/231/250/index.html +48 -0
  301. package/categories//345/211/215/347/253/257//346/265/217/350/247/210/345/231/250//347/275/221/347/273/234/345/215/217/350/256/256/index.html +48 -0
  302. package/categories//345/215/232/345/256/242/index.html +48 -0
  303. package/categories//345/267/245/345/205/267/index.html +48 -0
  304. package/categories//345/271/277/345/221/212/350/277/207/346/273/244/index.html +48 -0
  305. package/categories//345/271/277/345/221/212/350/277/207/346/273/244//350/247/206/351/242/221/347/224/265/350/247/206/345/260/217/350/257/264/346/274/253/347/224/273/350/265/204/350/256/257/351/237/263/344/271/220/index.html +48 -0
  306. package/categories//346/255/243/345/210/231/index.html +48 -0
  307. package/categories//346/265/217/350/247/210/345/231/250/index.html +48 -0
  308. package/categories//347/256/227/346/263/225/index.html +48 -0
  309. package/categories//350/265/204/350/256/257/index.html +48 -0
  310. package/categories//350/275/273/346/235/276/344/270/200/345/210/273/index.html +48 -0
  311. package/cdn/css/font-awesome.min.css +4 -0
  312. package/cdn/css/grids-responsive-min.css +7 -0
  313. package/cdn/css/normalize.css +349 -0
  314. package/cdn/css/pure-min.css +11 -0
  315. package/cdn/fonts/fontawesome-webfont.eot +0 -0
  316. package/cdn/fonts/fontawesome-webfont.svg +2671 -0
  317. package/cdn/fonts/fontawesome-webfont.ttf +0 -0
  318. package/cdn/fonts/fontawesome-webfont.woff +0 -0
  319. package/cdn/fonts/fontawesome-webfont.woff2 +0 -0
  320. package/cdn/js/Valine.min.js +17 -0
  321. package/cdn/js/canvas-nest.js +1 -0
  322. package/cdn/js/clipboard.min.js +7 -0
  323. package/cdn/js/crypto-js.js +25 -0
  324. package/cdn/js/jquery.min.js +2 -0
  325. package/css/default.css +1144 -0
  326. package/css/donate.css +338 -0
  327. package/css/hbe.style.css +749 -0
  328. package/css/style.css +2095 -0
  329. package/donate/index.html +39 -0
  330. package/google917dcf72f6e5c7f5.html +1 -0
  331. package/guestbook/index.html +68 -0
  332. package/hosts/ads.txt +149 -0
  333. package/hosts/flash.txt +9 -0
  334. package/hosts/github.txt +6 -0
  335. package/hosts/google.txt +16936 -0
  336. package/hosts/winrar.txt +2 -0
  337. package/img/alipay.svg +46 -0
  338. package/img/bitcoin.svg +135 -0
  339. package/img/blog.ico +0 -0
  340. package/img/blog.png +0 -0
  341. package/img/gaba.png +0 -0
  342. package/img/github.svg +1 -0
  343. package/img/like.svg +1 -0
  344. package/img/mp-mini.jpg +0 -0
  345. package/img/mp.png +0 -0
  346. package/img/paypal.svg +63 -0
  347. package/img/upy_logo.svg +59 -0
  348. package/img/wechat.svg +49 -0
  349. package/index.html +48 -0
  350. package/jd_root.txt +1 -0
  351. package/js/codeblock-resizer.js +51 -0
  352. package/js/dark.js +12 -0
  353. package/js/donate.js +87 -0
  354. package/js/fixedPage.js +106 -0
  355. package/js/gitment.browser.js +3751 -0
  356. package/js/search.js +86 -0
  357. package/js/share.js +60 -0
  358. package/js/smartresize.js +32 -0
  359. package/js/totop.js +12 -0
  360. package/kankan/index.html +77 -0
  361. package/lib/hbe.js +293 -0
  362. package/package.json +25 -0
  363. package/page/10/index.html +49 -0
  364. package/page/11/index.html +59 -0
  365. package/page/12/index.html +67 -0
  366. package/page/13/index.html +63 -0
  367. package/page/14/index.html +66 -0
  368. package/page/15/index.html +60 -0
  369. package/page/16/index.html +60 -0
  370. package/page/17/index.html +62 -0
  371. package/page/18/index.html +61 -0
  372. package/page/19/index.html +58 -0
  373. package/page/2/index.html +48 -0
  374. package/page/20/index.html +57 -0
  375. package/page/21/index.html +61 -0
  376. package/page/22/index.html +55 -0
  377. package/page/23/index.html +64 -0
  378. package/page/24/index.html +60 -0
  379. package/page/25/index.html +58 -0
  380. package/page/26/index.html +48 -0
  381. package/page/27/index.html +58 -0
  382. package/page/3/index.html +48 -0
  383. package/page/4/index.html +48 -0
  384. package/page/5/index.html +51 -0
  385. package/page/6/index.html +51 -0
  386. package/page/7/index.html +51 -0
  387. package/page/8/index.html +53 -0
  388. package/page/9/index.html +48 -0
  389. package/randomcall/README.html +1 -0
  390. package/randomcall/lucker.html +290 -0
  391. package/randomcall/lucky.png +0 -0
  392. package/robots.txt +22 -0
  393. package/search.xml +6740 -0
  394. package/sitemap.xml +2669 -0
  395. package/tags//345/216/237/345/210/233/index.html +48 -0
  396. package/tags//345/250/261/344/271/220/index.html +48 -0
  397. package/tags//346/211/213/345/206/231/index.html +48 -0
  398. package/tags//347/226/253/346/203/205/index.html +48 -0
  399. package/tags//350/275/254/350/275/275/index.html +48 -0
  400. package/tags//350/275/254/350/275/275/page/2/index.html +48 -0
  401. package/v.html +90 -0
@@ -0,0 +1,607 @@
1
+ <!DOCTYPE html><html lang="zh-CN" data-dark><head><meta http-equiv="Content-Type" content="text/html; charset=UTF-8"><meta content="width=device-width, initial-scale=1.0, maximum-scale=1.0, user-scalable=0" name="viewport"><meta content="yes" name="apple-mobile-web-app-capable"><meta content="black-translucent" name="apple-mobile-web-app-status-bar-style"><meta content="telephone=no" name="format-detection"><meta name="description" content="前端壹菜鸟,记录工作难题,关注前端知识,收集精彩博文,做技术的搬运工"><meta name="msvalidate.01" content="0FE4D8B3381D3D87088996B886E1E2BD"><title>不容错过的 Babel7 知识 | 前端壹菜鸟</title><link rel="stylesheet" type="text/css" href="//cdn.staticaly.com/gh/npljy/npljy.github.io/main/css/style.min.css"><link rel="stylesheet" type="text/css" href="//cdn.jsdelivr.net/npm/normalize.css@latest/normalize.min.css"><link rel="stylesheet" type="text/css" href="//cdn.jsdelivr.net/npm/purecss@latest/build/pure-min.min.css"><link rel="stylesheet" type="text/css" href="//cdn.jsdelivr.net/npm/purecss@latest/build/grids-responsive-min.css"><link rel="stylesheet" type="text/css" href="//cdn.jsdelivr.net/npm/font-awesome@4.7.0/css/font-awesome.min.css"><link rel="icon" mask="" sizes="any" href="//cdn.staticaly.com/gh/npljy/npljy.github.io/main/img/blog.ico"><link rel="Shortcut Icon" type="image/x-icon" href="//cdn.staticaly.com/gh/npljy/npljy.github.io/main/img/blog.ico"><link rel="apple-touch-icon" href="//cdn.staticaly.com/gh/npljy/npljy.github.io/main/img/blog.png"><link rel="apple-touch-icon-precomposed" href="//cdn.staticaly.com/gh/npljy/npljy.github.io/main/img/blog.png"><link rel="alternate" type="application/atom+xml" href="/atom.xml"><script type="text/javascript" src="//cdn.jsdelivr.net/npm/jquery@latest/dist/jquery.min.js"></script><script async src="https://pagead2.googlesyndication.com/pagead/js/adsbygoogle.js?client=ca-pub-8385136408348258"></script><script src="https://busuanzi.ibruce.info/busuanzi/2.3/busuanzi.pure.mini.js" async></script><script>(function(){
2
+ var bp = document.createElement('script');
3
+ var curProtocol = window.location.protocol.split(':')[0];
4
+ if (curProtocol === 'https'){
5
+ bp.src = 'https://zz.bdstatic.com/linksubmit/push.js';
6
+ }
7
+ else{
8
+ bp.src = 'http://push.zhanzhang.baidu.com/push.js';
9
+ }
10
+ var s = document.getElementsByTagName("script")[0];
11
+ s.parentNode.insertBefore(bp, s);
12
+ })();
13
+ </script><script>(function(){
14
+ var src = 'https://jspassport.ssl.qhimg.com/11.0.1.js?d182b3f28525f2db83acfaaf6e696dba';
15
+ document.write('<script src="' + src + '" id="sozz"><\/script>');
16
+ })();
17
+ </script><script>var _hmt=_hmt||[];(function(){var hm=document.createElement("script");hm.src='https://hm.baidu.com/hm.js?011f0b44e8452bfa57fbfa23c5fe7683';var s=document.getElementsByTagName("script")[0];s.parentNode.insertBefore(hm, s);})();
18
+ </script><script async src="https://www.googletagmanager.com/gtag/js?id=UA-150860401-1"></script><script>window.dataLayer=window.dataLayer||[];function gtag(){dataLayer.push(arguments);};gtag('js',new Date());gtag('config','UA-150860401-1');
19
+ </script><script type="text/javascript" src="//cdn.staticaly.com/gh/npljy/npljy.github.io/main/js/fixedPage.min.js"></script><meta name="generator" content="Hexo 6.3.0"></head><body><div class="body_container"><div id="header"><div class="site-name"><a id="logo" href="/.">前端壹菜鸟</a><p class="description">关注前端知识,收集精彩博文,做技术的搬运工</p></div><div id="nav-menu"><a class="current" href="/." target="_self"><i class="fa fa-home"> 首页</i></a><a href="/archives/" target="_self"><i class="fa fa-archive"> 归档</i></a><a href="/guestbook/" target="_self"><i class="fa fa-comments"> 留言</i></a><a href="/about/" target="_self"><i class="fa fa-user"> 关于</i></a><a href="https://laonongmin.online/" target="_target"><i class="fa fa-group"> 看看</i></a><a href="https://love.xuehuayu.cn/" target="_target"><i class="fa fa-heart"> LOVE</i></a></div></div><div class="pure-g" id="layout"><div class="pure-u-1 pure-u-md-3-4"><div class="content_container"><div class="post"><h1 class="post-title c-post">不容错过的 Babel7 知识</h1><div class="post-meta"><span class="date">2019-12-05</span><span> | </span><span class="tag"><a href="/tags/%E8%BD%AC%E8%BD%BD/">转载 </a></span><span> | </span><span class="category"><a href="/categories/%E5%89%8D%E7%AB%AF/">前端 </a></span><span id="busuanzi_container_page_pv"> | <span id="busuanzi_value_page_pv"><i class="fa fa-spinner"></i></span><span> 阅读</span></span><span class="post-time"><span class="post-meta-item-text"> | </span><span class="post-meta-item-icon"><i class="fa fa-keyboard-o"></i><span class="post-count"> 5.7k</span><span class="post-meta-item-text"> 字</span></span></span><span class="post-time"> | <span class="post-meta-item-icon"><i class="fa fa-hourglass-half"></i><span class="post-count"> 23</span><span class="post-meta-item-text"> 分钟</span></span></span></div><a class="disqus-comment-count" href="/article/2021.html#vcomment"><span class="waline-comment-count" data-path="/article/2021.html"></span><span> 条评论</span></a><div class="post-content"><p><code>原文地址:https://juejin.im/post/5ddff3abe51d4502d56bd143</code></p>
20
+ <p>对 <code>Babel</code> 的配置项的作用不那么了解,是否会影响日常开发呢?老实说,大多情况下没有特别大的影响(毕竟有搜索引擎)。</p>
21
+ <p>不过呢,还是想更进一步了解下,于是最近认真阅读了 <code>Babel</code> 的文档,外加不断编译验证,输出了本篇文章,为了更好的阅读体验,修修改改,最终算是以我个人比较喜欢的方式推进了每个知识点(每一个配置的引入都是有原因的),希望能够帮助你对 <code>Babel</code> 的各种配置有一个更清晰的认识 (已经很懂的小伙伴,无视本文) 。</p>
22
+ <span id="more"></span>
23
+
24
+ <blockquote>
25
+ <p>Babel 是一个 JS 编译器</p>
26
+ </blockquote>
27
+ <p>Babel 是一个工具链,主要用于将 ECMAScript 2015+ 版本的代码转换为向后兼容的 JavaScript 语法,以便能够运行在当前和旧版本的浏览器或其他环境中。</p>
28
+ <p>我们先看看 <code>Babel</code> 能够做什么:</p>
29
+ <ul>
30
+ <li>语法转换</li>
31
+ <li>通过 <code>Polyfill</code> 方式在目标环境中添加缺失的特性(<code>@babel/polyfill模块</code>)</li>
32
+ <li>源码转换(codemods)</li>
33
+ </ul>
34
+ <p>本篇文章的目的是搞明白 <code>Babel</code> 的使用和配置,搞清楚 <code>@babel/runtime</code>,<code>@babel/polyfill</code>,<code>@babel/plugin-transform-runtime</code> 这些作用是什么,插件和预设都是用来干什么的,我们为什么需要配置它们,而不是讲如何进行 <code>AST</code> 转换,如果你对 <code>AST</code> 转换非常感兴趣,欢迎阅读我们的 <a target="_blank" rel="noopener" href="https://github.com/areslabs/alita">RN转小程序引擎 Alita</a> 的源码,其中应用了大量的 <code>AST</code> 转换。</p>
35
+ <blockquote>
36
+ <p>更多文章可戳(如Star,谢谢你):<a target="_blank" rel="noopener" href="https://github.com/YvetteLau/Blog">https://github.com/YvetteLau/Blog</a></p>
37
+ </blockquote>
38
+ <p>为了更清晰的了解每一步,首先创建一个新项目,例如 <code>babelTemp</code>(你爱取啥名取啥名),使用 <code>npm init -y</code> 进行初始化,创建 <code>src/index.js</code>,文件内容如下(你也可以随便写点什么):</p>
39
+ <pre><code>const fn = () =&gt; &#123;
40
+ console.log(&#39;a&#39;);
41
+ &#125;;
42
+ 复制代码
43
+ </code></pre>
44
+ <p>OK,创建好的项目先放在一边,先了解下理论知识:</p>
45
+ <h3 id="核心库-babel-x2F-core"><a href="#核心库-babel-x2F-core" class="headerlink" title="核心库 @babel&#x2F;core"></a>核心库 @babel&#x2F;core</h3><p>Babel 的核心功能包含在 <code>@babel/core</code> 模块中。看到 <code>core</code> 这个词了吧,意味着<strong>核心</strong>,没有它,在 <code>babel</code> 的世界里注定寸步难行。不安装 <code>@babel/core</code>,无法使用 <code>babel</code> 进行编译。</p>
46
+ <h3 id="CLI命令行工具-babel-x2F-cli"><a href="#CLI命令行工具-babel-x2F-cli" class="headerlink" title="CLI命令行工具 @babel&#x2F;cli"></a>CLI命令行工具 @babel&#x2F;cli</h3><p><code>babel</code> 提供的命令行工具,主要是提供 <code>babel</code> 这个命令,适合安装在项目里。</p>
47
+ <p><code>@babel/node</code> 提供了 <code>babel-node</code> 命令,但是 <code>@babel/node</code> 更适合全局安装,不适合安装在项目里。</p>
48
+ <pre><code>npm install --save-dev @babel/core @babel/cli
49
+ 复制代码
50
+ </code></pre>
51
+ <p>现在你就可以在项目中使用 <code>babel</code> 进行编译啦(如果不安装 <code>@babel/core</code>,会报错噢)</p>
52
+ <p>将命令配置在 <code>package.json</code> 文件的 <code>scripts</code> 字段中:</p>
53
+ <pre><code>//...
54
+ &quot;scripts&quot;: &#123;
55
+ &quot;compiler&quot;: &quot;babel src --out-dir lib --watch&quot;
56
+ &#125;
57
+ 复制代码
58
+ </code></pre>
59
+ <p>使用 <code>npm run compiler</code> 来执行编译,现在我们没有配置任何插件,编译前后的代码是完全一样的。</p>
60
+ <p>因为 <code>Babel</code> 虽然开箱即用,但是什么动作也不做,如果想要 <code>Babel</code> 做一些实际的工作,就需要为其添加插件(<code>plugin</code>)。</p>
61
+ <h3 id="插件"><a href="#插件" class="headerlink" title="插件"></a>插件</h3><p><code>Babel</code> 构建在插件之上,使用现有的或者自己编写的插件可以组成一个转换通道,<code>Babel</code> 的插件分为两种: 语法插件和转换插件。</p>
62
+ <blockquote>
63
+ <p>语法插件</p>
64
+ </blockquote>
65
+ <p>这些插件只允许 <code>Babel</code><strong>解析(parse)</strong> 特定类型的语法(不是转换),可以在 <code>AST</code> 转换时使用,以支持解析新语法,例如:</p>
66
+ <pre><code>import * as babel from &quot;@babel/core&quot;;
67
+ const code = babel.transformFromAstSync(ast, &#123;
68
+ //支持可选链
69
+ plugins: [&quot;@babel/plugin-proposal-optional-chaining&quot;],
70
+ babelrc: false
71
+ &#125;).code;
72
+ 复制代码
73
+ </code></pre>
74
+ <blockquote>
75
+ <p>转换插件</p>
76
+ </blockquote>
77
+ <p>转换插件会启用相应的语法插件(因此不需要同时指定这两种插件),这点很容易理解,如果不启用相应的语法插件,意味着无法解析,连解析都不能解析,又何谈转换呢?</p>
78
+ <h4 id="插件的使用"><a href="#插件的使用" class="headerlink" title="插件的使用"></a>插件的使用</h4><p>如果插件发布在 <code>npm</code> 上,可以直接填写插件的名称, <code>Babel</code> 会自动检查它是否已经被安装在 <code>node_modules</code> 目录下,在项目目录下新建 <code>.babelrc</code> 文件 (下文会具体介绍配置文件),配置如下:</p>
79
+ <pre><code>//.babelrc
80
+ &#123;
81
+ &quot;plugins&quot;: [&quot;@babel/plugin-transform-arrow-functions&quot;]
82
+ &#125;
83
+ 复制代码
84
+ </code></pre>
85
+ <p>也可以指定插件的相对&#x2F;绝对路径</p>
86
+ <pre><code>&#123;
87
+ &quot;plugins&quot;: [&quot;./node_modules/@babel/plugin-transform-arrow-functions&quot;]
88
+ &#125;
89
+ 复制代码
90
+ </code></pre>
91
+ <p>执行 <code>npm run compiler</code>,可以看到箭头函数已经被编译OK, <code>lib/index.js</code> 内容如下:</p>
92
+ <pre><code>const fn = function () &#123;
93
+ console.log(&#39;a&#39;);
94
+ &#125;;
95
+ 复制代码
96
+ </code></pre>
97
+ <p>现在,我们仅支持转换箭头函数,如果想将其它的新的JS特性转换成低版本,需要使用其它对应的 <code>plugin</code> 。如果我们一个个配置的话,会非常繁琐,因为你可能需要配置几十个插件,这显然非常不便,那么有没有什么办法可以简化这个配置呢?</p>
98
+ <p>有!预设!(感谢强大的 <code>Babel</code>)<br><img src="https://user-gold-cdn.xitu.io/2019/12/2/16ec5de7ffa174b4?imageView2/0/w/1280/h/960/format/webp/ignore-error/1" alt="xuehuayu.cn"></p>
99
+ <h3 id="预设"><a href="#预设" class="headerlink" title="预设"></a>预设</h3><p>通过使用或创建一个 <code>preset</code> 即可<strong>轻松</strong>使用一组插件。</p>
100
+ <blockquote>
101
+ <p>官方 Preset</p>
102
+ </blockquote>
103
+ <ul>
104
+ <li>@babel&#x2F;preset-env</li>
105
+ <li>@babel&#x2F;preset-flow</li>
106
+ <li>@babel&#x2F;preset-react</li>
107
+ <li>@babel&#x2F;preset-typescript</li>
108
+ </ul>
109
+ <p><strong>注:</strong> 从 Babel v7 开始,所以针对标准提案阶段的功能所编写的预设(stage preset)都已被弃用,官方已经移除了 <code>@babel/preset-stage-x</code>。</p>
110
+ <h4 id="babel-x2F-preset-env"><a href="#babel-x2F-preset-env" class="headerlink" title="@babel&#x2F;preset-env"></a>@babel&#x2F;preset-env</h4><p><code>@babel/preset-env</code> 主要作用是对我们所使用的并且目标浏览器中缺失的功能进行代码转换和加载 <code>polyfill</code>,在不进行任何配置的情况下,<code>@babel/preset-env</code> 所包含的插件将支持所有最新的JS特性(ES2015,ES2016等,不包含 stage 阶段),将其转换成ES5代码。例如,如果你的代码中使用了可选链(目前,仍在 stage 阶段),那么只配置 <code>@babel/preset-env</code>,转换时会抛出错误,需要另外安装相应的插件。</p>
111
+ <pre><code>//.babelrc
112
+ &#123;
113
+ &quot;presets&quot;: [&quot;@babel/preset-env&quot;]
114
+ &#125;
115
+ 复制代码
116
+ </code></pre>
117
+ <p>需要说明的是,<code>@babel/preset-env</code> 会根据你配置的目标环境,生成插件列表来编译。对于基于浏览器或 <code>Electron</code> 的项目,官方推荐使用 <code>.browserslistrc</code> 文件来指定目标环境。默认情况下,如果你没有在 <code>Babel</code> 配置文件中(如 .babelrc)设置 <code>targets</code> 或 <code>ignoreBrowserslistConfig</code>,<code>@babel/preset-env</code> 会使用 <code>browserslist</code> 配置源。</p>
118
+ <p>如果你不是要兼容所有的浏览器和环境,推荐你指定目标环境,这样你的编译代码能够保持最小。</p>
119
+ <p>例如,仅包括浏览器市场份额超过0.25%的用户所需的 <code>polyfill</code> 和代码转换(忽略没有安全更新的浏览器,如 IE10 和 BlackBerry):</p>
120
+ <pre><code>//.browserslistrc
121
+ &gt; 0.25%
122
+ not dead
123
+ 复制代码
124
+ </code></pre>
125
+ <p>查看 <a target="_blank" rel="noopener" href="https://github.com/browserslist/browserslist"><code>browserslist</code> 的更多配置</a></p>
126
+ <p>例如,你将 <code>.browserslistrc</code> 的内容配置为: </p>
127
+ <pre><code>last 2 Chrome versions
128
+ 复制代码
129
+ </code></pre>
130
+ <p>然后再执行 <code>npm run compiler</code>,你会发现箭头函数不会被编译成ES5,因为 <code>chrome</code> 的最新2个版本都能够支持箭头函数。现在,我们将 <code>.browserslistrc</code> 仍然换成之前的配置。</p>
131
+ <p>就咱们目前的代码来说,当前的配置似乎已经是OK的了。<br><img src="https://ss2.bdstatic.com/70cFvnSh_Q1YnxGkpoWK1HF6hhy/it/u=1274521111,316080499&amp;fm=26&amp;gp=0.jpg" alt="xuehuayu.cn"><br>我们修改下 <code>src/index.js</code>。</p>
132
+ <pre><code>const isHas = [1,2,3].includes(2);
133
+
134
+ const p = new Promise((resolve, reject) =&gt; &#123;
135
+ resolve(100);
136
+ &#125;);
137
+ 复制代码
138
+ </code></pre>
139
+ <p>编译出来的结果为:</p>
140
+ <pre><code>&quot;use strict&quot;;
141
+
142
+ var isHas = [1, 2, 3].includes(2);
143
+ var p = new Promise(function (resolve, reject) &#123;
144
+ resolve(100);
145
+ &#125;);
146
+ 复制代码
147
+ </code></pre>
148
+ <p>这个编译出来的代码在低版本浏览器中使用的话,显然是有问题的,因为低版本浏览器中数组实例上没有 <code>includes</code> 方法,也没有 <code>Promise</code> 构造函数。</p>
149
+ <p>这是为什么呢?因为语法转换只是将高版本的语法转换成低版本的,但是新的内置函数、实例方法无法转换。这时,就需要使用 <code>polyfill</code> 上场了,顾名思义,<code>polyfill</code>的中文意思是垫片,所谓垫片就是垫平不同浏览器或者不同环境下的差异,让新的内置函数、实例方法等在低版本浏览器中也可以使用。<br><img src="https://user-gold-cdn.xitu.io/2019/12/2/16ec5df2444f996e?imageView2/0/w/1280/h/960/format/webp/ignore-error/1" alt="xuehuayu.cn"></p>
150
+ <h3 id="Polyfill"><a href="#Polyfill" class="headerlink" title="Polyfill"></a>Polyfill</h3><p><code>@babel/polyfill</code> 模块包括 <code>core-js</code> 和一个自定义的 <code>regenerator runtime</code> 模块,可以模拟完整的 ES2015+ 环境(不包含第4阶段前的提议)。</p>
151
+ <p>这意味着可以使用诸如 <code>Promise</code> 和 <code>WeakMap</code> 之类的新的内置组件、 <code>Array.from</code> 或 <code>Object.assign</code> 之类的静态方法、<code>Array.prototype.includes</code> 之类的实例方法以及生成器函数(前提是使用了 <code>@babel/plugin-transform-regenerator</code> 插件)。为了添加这些功能,<code>polyfill</code> 将添加到全局范围和类似 <code>String</code> 这样的内置原型中(会对全局环境造成污染,后面我们会介绍不污染全局环境的方法)。</p>
152
+ <p>补充说明 (2020&#x2F;01&#x2F;07):V7.4.0 版本开始,<code>@babel/polyfill</code> 已经被废弃(前端发展日新月异),需单独安装 <code>core-js</code> 和 <code>regenerator-runtime</code> 模块。</p>
153
+ <p>首先,安装 <code>@babel/polyfill</code> 依赖: </p>
154
+ <pre><code>npm install --save @babel/polyfill
155
+ 复制代码
156
+ </code></pre>
157
+ <p>注意:不使用 <code>--save-dev</code>,因为这是一个需要在源码之前运行的垫片。</p>
158
+ <p>我们需要将完整的 <code>polyfill</code> 在代码之前加载,修改我们的 <code>src/index.js</code>: </p>
159
+ <pre><code>import &#39;@babel/polyfill&#39;;
160
+
161
+ const isHas = [1,2,3].includes(2);
162
+
163
+ const p = new Promise((resolve, reject) =&gt; &#123;
164
+ resolve(100);
165
+ &#125;);
166
+ 复制代码
167
+ </code></pre>
168
+ <p><code>@babel/polyfill</code> 需要在其它代码之前引入,我们也可以在 <code>webpack</code> 中进行配置。</p>
169
+ <p>例如:</p>
170
+ <pre><code>entry: [
171
+ require.resolve(&#39;./polyfills&#39;),
172
+ path.resolve(&#39;./index&#39;)
173
+ ]
174
+ 复制代码
175
+ </code></pre>
176
+ <p><code>polyfills.js</code> 文件内容如下:</p>
177
+ <pre><code>//当然,还可能有一些其它的 polyfill,例如 stage 4之前的一些 polyfill
178
+ import &#39;@babel/polyfill&#39;;
179
+ 复制代码
180
+ </code></pre>
181
+ <p>现在,我们的代码不管在低版本还是高版本浏览器(或node环境)中都能正常运行了。不过,很多时候,我们未必需要完整的 <code>@babel/polyfill</code>,这会导致我们最终构建出的包的体积增大,<code>@babel/polyfill</code>的包大小为89K (当前 <code>@babel/polyfill</code> 版本为 7.7.0)。</p>
182
+ <p>我们更期望的是,如果我使用了某个新特性,再引入对应的 <code>polyfill</code>,避免引入无用的代码。</p>
183
+ <p>值得庆幸的是, <code>Babel</code> 已经考虑到了这一点。<br><img src="https://ss1.bdstatic.com/70cFvXSh_Q1YnxGkpoWK1HF6hhy/it/u=3716863604,3698030703&amp;fm=26&amp;gp=0.jpg" alt="xuehuayu.cn"><br><code>@babel/preset-env</code> 提供了一个 <code>useBuiltIns</code> 参数,设置值为 <code>usage</code> 时,就只会包含代码需要的 <code>polyfill</code> 。有一点需要注意:配置此参数的值为 <code>usage</code> ,必须要同时设置 <code>corejs</code> (如果不设置,会给出警告,默认使用的是”corejs”: 2) ,注意: 这里仍然需要安装 <code>@babel/polyfill</code>(当前 <code>@babel/polyfill</code> 版本默认会安装 “corejs”: 2):</p>
184
+ <p>首先说一下使用 <code>core-js@3</code> 的原因,<code>core-js@2</code> 分支中已经不会再添加新特性,新特性都会添加到 <code>core-js@3</code>。例如你使用了 <code>Array.prototype.flat()</code>,如果你使用的是 <code>core-js@2</code>,那么其不包含此新特性。为了可以使用更多的新特性,建议大家使用 <code>core-js@3</code>。</p>
185
+ <p>安装依赖依赖:</p>
186
+ <pre><code>npm install --save core-js@3
187
+ 复制代码
188
+ </code></pre>
189
+ <blockquote>
190
+ <p><a target="_blank" rel="noopener" href="https://github.com/zloirock/core-js">core-js (点击了解更多)</a> : JavaScript 的模块化标准库,包含 <code>Promise</code>、<code>Symbol</code>、<code>Iterator</code>和许多其他的特性,它可以让你仅加载必需的功能。</p>
191
+ </blockquote>
192
+ <p>现在,修改 <code>Babel</code> 的配置文件如下:</p>
193
+ <pre><code>//.babelrc
194
+ const presets = [
195
+ [
196
+ &quot;@babel/env&quot;,
197
+ &#123;
198
+ &quot;useBuiltIns&quot;: &quot;usage&quot;,
199
+ &quot;corejs&quot;: 3
200
+ &#125;
201
+ ]
202
+ ]
203
+ 复制代码
204
+ </code></pre>
205
+ <p><code>Babel</code> 会检查所有代码,以便查找在目标环境中缺失的功能,然后仅仅把需要的 <code>polyfill</code> 包含进来。</p>
206
+ <p>例如,<code>src/index.js</code> 代码不变:</p>
207
+ <pre><code>const isHas = [1,2,3].includes(2);
208
+
209
+ const p = new Promise((resolve, reject) =&gt; &#123;
210
+ resolve(100);
211
+ &#125;);
212
+ 复制代码
213
+ </code></pre>
214
+ <p>我们看看编译出来的文件(<code>lib/index</code>): </p>
215
+ <pre><code>&quot;use strict&quot;;
216
+
217
+ require(&quot;core-js/modules/es.array.includes&quot;);
218
+
219
+ require(&quot;core-js/modules/es.object.to-string&quot;);
220
+
221
+ require(&quot;core-js/modules/es.promise&quot;);
222
+
223
+ var isHas = [1, 2, 3].includes(2);
224
+ var p = new Promise(function (resolve, reject) &#123;
225
+ resolve(100);
226
+ &#125;);
227
+ 复制代码
228
+ </code></pre>
229
+ <p>同样的代码,我们用 <code>webpack</code> 构建一下(<code>production</code> 模式),能看到最终的代码大小仅为: 20KB。而如果我们引入整个 <code>@babel/polyfill</code> 的话,构建出的包大小为:89KB</p>
230
+ <p>前面曾提到,在 <code>useBuiltIns</code> 参数值为 <code>usage</code> 时,仍然需要安装 <code>@babel/polyfill</code>,虽然我们上面的代码转换中看起来并没有使用到,但是,如果我们源码中使用到了 <code>async/await</code>,那么编译出来的代码需要 <code>require(&quot;regenerator-runtime/runtime&quot;)</code>,在 <code>@babel/polyfill</code> 的依赖中,当然啦,你也可以只安装 <code>regenerator-runtime/runtime</code> 取代安装 <code>@babel/polyfill</code>。</p>
231
+ <p>到了这一步,已经很棒棒了,是不是想跳起来转个圈圈?<br><img src="https://user-gold-cdn.xitu.io/2019/12/2/16ec5e07c41b767b?imageslim" alt="xuehuayu.cn"><br>下面我要说的内容,也许你已经知道,也许你还不知道,这都不重要,但是此刻起,你要知道了: <code>Babel</code> 会使用很小的辅助函数来实现类似 <code>_createClass</code> 等公共方法。默认情况下,它将被添加(<code>inject</code>)到需要它的每个文件中。</p>
232
+ <p>假如,我们的 <code>src/index.js</code> 是这样的:</p>
233
+ <pre><code>class Point &#123;
234
+ constructor(x, y) &#123;
235
+ this.x = x;
236
+ this.y = y;
237
+ &#125;;
238
+ getX() &#123;
239
+ return this.x;
240
+ &#125;
241
+ &#125;
242
+
243
+ let cp = new ColorPoint(25, 8);
244
+ 复制代码
245
+ </code></pre>
246
+ <p>编译出来的 <code>lib/index.js</code>,如下所示:</p>
247
+ <pre><code>&quot;use strict&quot;;
248
+
249
+ require(&quot;core-js/modules/es.object.define-property&quot;);
250
+
251
+ function _classCallCheck(instance, Constructor) &#123; if (!(instance instanceof Constructor)) &#123; throw new TypeError(&quot;Cannot call a class as a function&quot;); &#125; &#125;
252
+
253
+ function _defineProperties(target, props) &#123; for (var i = 0; i &lt; props.length; i++) &#123; var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if (&quot;value&quot; in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); &#125; &#125;
254
+
255
+ function _createClass(Constructor, protoProps, staticProps) &#123; if (protoProps) _defineProperties(Constructor.prototype, protoProps); if (staticProps) _defineProperties(Constructor, staticProps); return Constructor; &#125;
256
+
257
+ var Point =
258
+ /*#__PURE__*/
259
+ function () &#123;
260
+ function Point(x, y) &#123;
261
+ _classCallCheck(this, Point);
262
+
263
+ this.x = x;
264
+ this.y = y;
265
+ &#125;
266
+
267
+ _createClass(Point, [&#123;
268
+ key: &quot;getX&quot;,
269
+ value: function getX() &#123;
270
+ return this.x;
271
+ &#125;
272
+ &#125;]);
273
+
274
+ return Point;
275
+ &#125;();
276
+
277
+ var cp = new ColorPoint(25, 8);
278
+ 复制代码
279
+ </code></pre>
280
+ <p>看起来,似乎并没有什么问题,但是你想一下,如果你有10个文件中都使用了这个 <code>class</code>,是不是意味着 <code>_classCallCheck</code>、<code>_defineProperties</code>、<code>_createClass</code> 这些方法被 <code>inject</code> 了10次。这显然会导致包体积增大,最关键的是,我们并不需要它 <code>inject</code> 多次。</p>
281
+ <p>这个时候,就是 <code>@babel/plugin-transform-runtime</code> 插件大显身手的时候了,使用 <code>@babel/plugin-transform-runtime</code> 插件,所有帮助程序都将引用模块 <code>@babel/runtime</code>,这样就可以避免编译后的代码中出现重复的帮助程序,有效减少包体积。<br><img src="https://ss2.bdstatic.com/70cFvnSh_Q1YnxGkpoWK1HF6hhy/it/u=471863559,2772828065&amp;fm=26&amp;gp=0.jpg" alt="xuehuayu.cn"></p>
282
+ <h3 id="babel-x2F-plugin-transform-runtime"><a href="#babel-x2F-plugin-transform-runtime" class="headerlink" title="@babel&#x2F;plugin-transform-runtime"></a>@babel&#x2F;plugin-transform-runtime</h3><p><code>@babel/plugin-transform-runtime</code> 是一个可以重复使用 <code>Babel</code> 注入的帮助程序,以节省代码大小的插件。</p>
283
+ <blockquote>
284
+ <p>注意:诸如 <code>Array.prototype.flat()</code> 等实例方法将不起作用,因为这需要修改现有的内置函数(可以使用 <code>@babel/polyfill</code> 来解决这个问题) ——&gt; 对此需要说明的是如果你配置的是<code>corejs3</code>, <strong><code>core-js@3</code> 现在已经支持原型方法,同时不污染原型</strong>。</p>
285
+ </blockquote>
286
+ <p>另外,<code>@babel/plugin-transform-runtime</code> 需要和 <code>@babel/runtime</code> 配合使用。</p>
287
+ <p>首先安装依赖,<code>@babel/plugin-transform-runtime</code> 通常仅在开发时使用,但是运行时最终代码需要依赖 <code>@babel/runtime</code>,所以 <code>@babel/runtime</code> 必须要作为生产依赖被安装,如下 :</p>
288
+ <pre><code>npm install --save-dev @babel/plugin-transform-runtime
289
+ npm install --save @babel/runtime
290
+ 复制代码
291
+ </code></pre>
292
+ <p>除了前文所说的,<code>@babel/plugin-transform-runtime</code> 可以减少编译后代码的体积外,我们使用它还有一个好处,它可以为代码创建一个沙盒环境,如果使用 <code>@babel/polyfill</code> 及其提供的内置程序(例如 <code>Promise</code> ,<code>Set</code> 和 <code>Map</code> ),则它们将污染全局范围。虽然这对于应用程序或命令行工具可能是可以的,但是如果你的代码是要发布供他人使用的库,或者无法完全控制代码运行的环境,则将成为一个问题。</p>
293
+ <p><code>@babel/plugin-transform-runtime</code> 会将这些内置别名作为 <code>core-js</code> 的别名,因此您可以无缝使用它们,而无需 <code>polyfill</code>。</p>
294
+ <p>修改 <code>.babelrc</code> 的配置,如下:</p>
295
+ <pre><code>//.babelrc
296
+ &#123;
297
+ &quot;presets&quot;: [
298
+ [
299
+ &quot;@babel/preset-env&quot;,
300
+ &#123;
301
+ &quot;useBuiltIns&quot;: &quot;usage&quot;,
302
+ &quot;corejs&quot;: 3
303
+ &#125;
304
+ ]
305
+ ],
306
+ &quot;plugins&quot;: [
307
+ [
308
+ &quot;@babel/plugin-transform-runtime&quot;
309
+ ]
310
+ ]
311
+ &#125;
312
+ 复制代码
313
+ </code></pre>
314
+ <p>重新编译 <code>npm run compiler</code> , 现在,编译出来的内容为(<code>lib/index.js</code>):</p>
315
+ <pre><code>&quot;use strict&quot;;
316
+
317
+ var _interopRequireDefault = require(&quot;@babel/runtime/helpers/interopRequireDefault&quot;);
318
+
319
+ var _classCallCheck2 = _interopRequireDefault(require(&quot;@babel/runtime/helpers/classCallCheck&quot;));
320
+
321
+ var _createClass2 = _interopRequireDefault(require(&quot;@babel/runtime/helpers/createClass&quot;));
322
+
323
+ var Point =
324
+ /*#__PURE__*/
325
+ function () &#123;
326
+ function Point(x, y) &#123;
327
+ (0, _classCallCheck2.default)(this, Point);
328
+ this.x = x;
329
+ this.y = y;
330
+ &#125;
331
+
332
+ (0, _createClass2.default)(Point, [&#123;
333
+ key: &quot;getX&quot;,
334
+ value: function getX() &#123;
335
+ return this.x;
336
+ &#125;
337
+ &#125;]);
338
+ return Point;
339
+ &#125;();
340
+
341
+ var cp = new ColorPoint(25, 8);
342
+ 复制代码
343
+ </code></pre>
344
+ <p>可以看出,帮助函数现在不是直接被 <code>inject</code> 到代码中,而是从 <code>@babel/runtime</code> 中引入。前文说了使用 <code>@babel/plugin-transform-runtime</code> 可以避免全局污染,我们来看看是如何避免污染的。</p>
345
+ <p>修改 <code>src/index.js</code> 如下:</p>
346
+ <pre><code>let isHas = [1,2,3].includes(2);
347
+
348
+ new Promise((resolve, reject) =&gt; &#123;
349
+ resolve(100);
350
+ &#125;);
351
+ 复制代码
352
+ </code></pre>
353
+ <p>编译出来的代码如下(<code>lib/index.js</code>):</p>
354
+ <pre><code>&quot;use strict&quot;;
355
+
356
+ require(&quot;core-js/modules/es.array.includes&quot;);
357
+
358
+ require(&quot;core-js/modules/es.object.to-string&quot;);
359
+
360
+ require(&quot;core-js/modules/es.promise&quot;);
361
+
362
+ var isHas = [1, 2, 3].includes(2);
363
+ new Promise(function (resolve, reject) &#123;
364
+ resolve(100);
365
+ &#125;);
366
+ 复制代码
367
+ </code></pre>
368
+ <p><code>Array.prototype</code> 上新增了 <code>includes</code> 方法,并且新增了全局的 <code>Promise</code> 方法,污染了全局环境,这跟不使用 <code>@babel/plugin-transform-runtime</code> 没有区别嘛。<br><img src="https://ss0.bdstatic.com/70cFuHSh_Q1YnxGkpoWK1HF6hhy/it/u=1755034433,3242202717&amp;fm=15&amp;gp=0.jpg" alt="xuehuayu.cn"><br>如果我们希望 <code>@babel/plugin-transform-runtime</code> 不仅仅处理帮助函数,同时也能加载 <code>polyfill</code> 的话,我们需要给 <code>@babel/plugin-transform-runtime</code> 增加配置信息。</p>
369
+ <p>首先新增依赖 <code>@babel/runtime-corejs3</code>:</p>
370
+ <pre><code>npm install @babel/runtime-corejs3 --save
371
+ 复制代码
372
+ </code></pre>
373
+ <p>修改配置文件如下(移除了 <code>@babel/preset-env</code> 的 <code>useBuiltIns</code> 的配置,不然不就重复了嘛嘛嘛,不信的话,你用 <code>async/await</code> 编译下试试咯):</p>
374
+ <pre><code>&#123;
375
+ &quot;presets&quot;: [
376
+ [
377
+ &quot;@babel/preset-env&quot;
378
+ ]
379
+ ],
380
+ &quot;plugins&quot;: [
381
+ [
382
+ &quot;@babel/plugin-transform-runtime&quot;,&#123;
383
+ &quot;corejs&quot;: 3
384
+ &#125;
385
+ ]
386
+ ]
387
+ &#125;
388
+ 复制代码
389
+ </code></pre>
390
+ <p>然后重新编译,看一下,编译出来的结果(<code>lib/index.js</code>): </p>
391
+ <pre><code>&quot;use strict&quot;;
392
+
393
+ var _interopRequireDefault = require(&quot;@babel/runtime-corejs3/helpers/interopRequireDefault&quot;);
394
+
395
+ var _promise = _interopRequireDefault(require(&quot;@babel/runtime-corejs3/core-js-stable/promise&quot;));
396
+
397
+ var _includes = _interopRequireDefault(require(&quot;@babel/runtime-corejs3/core-js-stable/instance/includes&quot;));
398
+
399
+ var _context;
400
+
401
+ var isHas = (0, _includes.default)(_context = [1, 2, 3]).call(_context, 2);
402
+ new _promise.default(function (resolve, reject) &#123;
403
+ resolve(100);
404
+ &#125;);
405
+ 复制代码
406
+ </code></pre>
407
+ <p>可以看出,没有直接去修改 <code>Array.prototype</code>,或者是新增 <code>Promise</code> 方法,避免了全局污染。如果上面 <code>@babel/plugin-transform-runtime</code> 配置的 <code>core-js</code> 是 “2”,其中不包含实例的 <code>polyfill</code> 需要单独引入。</p>
408
+ <blockquote>
409
+ <p>划重点:如果我们配置的 <code>corejs</code> 是 <code>3</code> 版本,那么不管是实例方法还是全局方法,都不会再污染全局环境。</p>
410
+ </blockquote>
411
+ <p>看到这里,不知道大家有没有这样一个疑问?给 <code>@babel/plugin-transform-runtime</code> 配置 <code>corejs</code> 是如此的完美,既可以将帮助函数变成引用的形式,又可以动态引入 <code>polyfill</code>,并且不会污染全局环境。何必要给 <code>@babel/preset-env</code> 提供 <code>useBuiltIns</code> 功能呢,看起来似乎不需要呀。</p>
412
+ <p>带着这样的疑问,我新建了几个文件(内容简单且基本一致,使用了些新特性),然后使用 <code>webpack</code> 构建,以下是我对比的数据:<br>序号.babelrc 配置webpack mode production0不使用 <code>@babel/plugin-transform-runtime</code>36KB1使用<code>@babel/plugin-transform-runtime</code>,并配置参数 <code>corejs</code>: 3。不会污染全局环境37KB2使用<code>@babel/plugin-transform-runtime</code>,不配置 <code>corejs</code>22KB<br>我猜测是 <code>@babel/runtime-corejs3/XXX</code> 的包本身比 <code>core-js/modules/XXX</code> 要大一些~<br><img src="https://ss2.bdstatic.com/70cFvnSh_Q1YnxGkpoWK1HF6hhy/it/u=1989230665,1274957629&amp;fm=26&amp;gp=0.jpg" alt="xuehuayu.cn"></p>
413
+ <h3 id="插件-x2F-预设补充知识"><a href="#插件-x2F-预设补充知识" class="headerlink" title="插件&#x2F;预设补充知识"></a>插件&#x2F;预设补充知识</h3><blockquote>
414
+ <p><strong>插件的排列顺序很重要!!!</strong></p>
415
+ </blockquote>
416
+ <p>如果两个转换插件都将处理“程序(Program)”的某个代码片段,则将根据转换插件或 <code>preset</code> 的排列顺序依次执行。</p>
417
+ <ul>
418
+ <li>插件在 Presets 前运行。</li>
419
+ <li>插件顺序从前往后排列。</li>
420
+ <li>Preset 顺序是颠倒的(从后往前)。</li>
421
+ </ul>
422
+ <p>例如:</p>
423
+ <pre><code>&#123;
424
+ &quot;plugins&quot;: [&quot;@babel/plugin-proposal-class-properties&quot;, &quot;@babel/plugin-syntax-dynamic-import&quot;]
425
+ &#125;
426
+ 复制代码
427
+ </code></pre>
428
+ <p>先执行 <code>@babel/plugin-proposal-class-properties</code>,后执行 <code>@babel/plugin-syntax-dynamic-import</code></p>
429
+ <pre><code>&#123;
430
+ &quot;presets&quot;: [&quot;@babel/preset-env&quot;, &quot;@babel/preset-react&quot;]
431
+ &#125;
432
+ 复制代码
433
+ </code></pre>
434
+ <p><code>preset</code> 的执行顺序是<strong>颠倒</strong>的,先执行 <code>@babel/preset-react</code>, 后执行 <code>@babel/preset-env</code>。</p>
435
+ <h4 id="插件参数"><a href="#插件参数" class="headerlink" title="插件参数"></a>插件参数</h4><p>插件和 <code>preset</code> 都可以接受参数,参数由插件名和参数对象组成一个数组。<code>preset</code> 设置参数也是这种格式。</p>
436
+ <p>如: </p>
437
+ <pre><code>&#123;
438
+ &quot;plugins&quot;: [
439
+ [
440
+ &quot;@babel/plugin-proposal-class-properties&quot;,
441
+ &#123; &quot;loose&quot;: true &#125;
442
+ ]
443
+ ]
444
+ &#125;
445
+ 复制代码
446
+ </code></pre>
447
+ <h4 id="插件的短名称"><a href="#插件的短名称" class="headerlink" title="插件的短名称"></a>插件的短名称</h4><p>如果插件名称为 <code>@babel/plugin-XXX</code>,可以使用短名称<code>@babel/XXX</code> :</p>
448
+ <pre><code>&#123;
449
+ &quot;plugins&quot;: [
450
+ &quot;@babel/transform-arrow-functions&quot; //同 &quot;@babel/plugin-transform-arrow-functions&quot;
451
+ ]
452
+ &#125;
453
+ 复制代码
454
+ </code></pre>
455
+ <p>如果插件名称为 <code>babel-plugin-XXX</code>,可以使用端名称 <code>XXX</code>,该规则同样适用于带有 <code>scope</code> 的插件:</p>
456
+ <pre><code>&#123;
457
+ &quot;plugins&quot;: [
458
+ &quot;newPlugin&quot;, //同 &quot;babel-plugin-newPlugin&quot;
459
+ &quot;@scp/myPlugin&quot; //同 &quot;@scp/babel-plugin-myPlugin&quot;
460
+ ]
461
+ &#125;
462
+ 复制代码
463
+ </code></pre>
464
+ <h4 id="创建-Preset"><a href="#创建-Preset" class="headerlink" title="创建 Preset"></a>创建 Preset</h4><blockquote>
465
+ <p>可以简单的返回一个插件数组</p>
466
+ </blockquote>
467
+ <pre><code>module.exports = function() &#123;
468
+ return &#123;
469
+ plugins: [
470
+ &quot;A&quot;,
471
+ &quot;B&quot;,
472
+ &quot;C&quot;
473
+ ]
474
+ &#125;
475
+ &#125;
476
+ 复制代码
477
+ </code></pre>
478
+ <blockquote>
479
+ <p><code>preset</code> 中也可以包含其他的 <code>preset</code>,以及带有参数的插件。</p>
480
+ </blockquote>
481
+ <pre><code>module.exports = function() &#123;
482
+ return &#123;
483
+ presets: [
484
+ require(&quot;@babel/preset-env&quot;)
485
+ ],
486
+ plugins: [
487
+ [require(&quot;@babel/plugin-proposal-class-properties&quot;), &#123; loose: true &#125;],
488
+ require(&quot;@babel/plugin-proposal-object-rest-spread&quot;)
489
+ ]
490
+ &#125;
491
+ &#125;
492
+ 复制代码
493
+ </code></pre>
494
+ <h3 id="配置文件"><a href="#配置文件" class="headerlink" title="配置文件"></a>配置文件</h3><p>Babel 支持多种格式的配置文件。这部分内容补充了解下即可,谁管你用哪种配置文件,只要你的配置是OK的就可以了(敷衍)~</p>
495
+ <p>所有的 <code>Babel</code> API 参数都可以被配置,但是如果该参数需要使用的 JS 代码,那么可能需要使用 JS 代码版的配置文件。</p>
496
+ <blockquote>
497
+ <p>根据使用场景可以选择不同的配置文件:</p>
498
+ </blockquote>
499
+ <p>如果希望以编程的方式创建配置文件或者希望编译 <code>node_modules</code> 目录下的模块:那么 <code>babel.config.js</code> 可以满足你的需求。</p>
500
+ <p>如果只是需要一个简单的并且中用于单个软件包的配置:那么 <code>.babelrc</code> 即可满足你的需求。</p>
501
+ <h4 id="babel-config-js"><a href="#babel-config-js" class="headerlink" title="babel.config.js"></a>babel.config.js</h4><p>在项目根目录下创建一个名为 <code>babel.config.js</code> 的文件。</p>
502
+ <pre><code>module.exports = function(api) &#123;
503
+ api.cache(true);
504
+
505
+ const presets = [...];
506
+ const plugins = [...];
507
+
508
+ return &#123;
509
+ presets,
510
+ plugins
511
+ &#125;;
512
+ &#125;
513
+ 复制代码
514
+ </code></pre>
515
+ <p>具体的配置可以查看:<a target="_blank" rel="noopener" href="https://www.babeljs.cn/docs/config-files#project-wide-configuration">babel.config.js 文档</a></p>
516
+ <h4 id="babelrc"><a href="#babelrc" class="headerlink" title=".babelrc"></a>.babelrc</h4><p>在项目根目录下创建一个名为 <code>.babelrc</code> 的文件:</p>
517
+ <pre><code>&#123;
518
+ &quot;presets&quot;: [],
519
+ &quot;plugins&quot;: []
520
+ &#125;
521
+ 复制代码
522
+ </code></pre>
523
+ <p>具体的配置可以参考 <a target="_blank" rel="noopener" href="https://www.babeljs.cn/docs/config-files#file-relative-configuration">.babelrc 文档 </a></p>
524
+ <h4 id="package-json"><a href="#package-json" class="headerlink" title="package.json"></a>package.json</h4><p>可以将 <code>.babelrc</code> 中的配置信息作为 <code>babel</code> 键(key) 添加到 <code>package.json</code> 文件中:</p>
525
+ <pre><code>&#123;
526
+ &quot;name&quot;: &quot;my-package&quot;,
527
+ &quot;babel&quot;: &#123;
528
+ &quot;presets&quot;: [],
529
+ &quot;plugins&quot;: []
530
+ &#125;
531
+ &#125;
532
+ 复制代码
533
+ </code></pre>
534
+ <h4 id="babelrc-js"><a href="#babelrc-js" class="headerlink" title=".babelrc.js"></a>.babelrc.js</h4><p>与 <code>.babelrc</code> 配置相同,但是可以使用JS编写。</p>
535
+ <pre><code>//可以在其中调用 Node.js 的API
536
+ const presets = [];
537
+ const plugins = [];
538
+
539
+ module.exports = &#123; presets, plugins &#125;;
540
+ 复制代码
541
+ </code></pre>
542
+ <p><img src="https://user-gold-cdn.xitu.io/2019/12/2/16ec5e136d6ca9d1?imageslim" alt="xuehuayu.cn"><br>不知道是否全面,不过真的写不动了(如有不全,后续再补充)<del>就酱</del>如果有错误,欢迎指正。</p>
543
+ <blockquote>
544
+ <p>参考链接</p>
545
+ </blockquote>
546
+ <ol>
547
+ <li><p><a target="_blank" rel="noopener" href="https://www.babeljs.cn/docs/">babel文档</a></p>
548
+ </li>
549
+ <li><p><a target="_blank" rel="noopener" href="https://www.jianshu.com/p/cbd48919a0cc">babel 7 的使用的个人理解</a></p>
550
+ </li>
551
+ <li><p><a target="_blank" rel="noopener" href="https://juejin.im/post/5c19c5e0e51d4502a232c1c6">一口(很长的)气了解 babel</a></p>
552
+ </li>
553
+ <li><p><a target="_blank" rel="noopener" href="https://www.cnblogs.com/sefaultment/p/11631314.html">core-js@3带来的惊喜</a></p>
554
+ </li>
555
+ </ol>
556
+ <hr>
557
+ <h3 id="关注公众号,加入技术交流群"><a href="#关注公众号,加入技术交流群" class="headerlink" title="关注公众号,加入技术交流群"></a>关注公众号,加入技术交流群</h3><p><img src="https://user-gold-cdn.xitu.io/2019/9/8/16d1120a80282ab5?imageView2/0/w/1280/h/960/format/webp/ignore-error/1" alt="xuehuayu.cn"></p>
558
+ </div><iframe src="/donate/?AliPayQR=https://store.xuehuayu.cn/store/public/alipay_qr.jpg&amp;WeChatQR=https://store.xuehuayu.cn/store/public/wechat_qr.png&amp;UnionPayQR=null&amp;GitHub=null&amp;BTCQR=null&amp;BTCKEY=null&amp;PayPal=https://www.paypal.com/paypalme/OrdinaryPerson" style="overflow-x:hidden; overflow-y:hidden; border:0xp none #fff; min-height:240px; width:100%;" frameborder="0" scrolling="no"></iframe><div><ul class="post-copyright"><li class="post-copyright-author"><strong>本文作者:</strong>雪花雨</li><li class="post-copyright-link"><strong>本文链接:</strong><a href="/article/2021.html">https://xuehuayu.cn/article/2021.html</a></li><li class="post-copyright-license"><strong>版权声明:</strong>① 标为原创的文章为博主原创,遵循 CC 4.0 BY-SA 版权协议,转载请附上原文出处链接。② 转载文章来自网络,已标明出处,<a href="mailto:cainiaoblog@126.com">侵删</a>。</li></ul></div><br><div class="tags"><a href="/tags/%E8%BD%AC%E8%BD%BD/">转载</a></div><div class="post-nav"><a class="pre" href="/article/17246.html">OPTIONS请求时设置了Header请求和token可是后台接收不到,为什么?</a><a class="next" href="/article/22237.html">轻松理解webpack热更新原理</a></div><div id="vcomment"></div><link rel="stylesheet" href="https://cdn.jsdelivr.net/npm/@waline/client@v2/dist/waline.min.css"><script src="//cdn.jsdelivr.net/npm/@waline/client@v2/dist/waline.js"></script><script>const origin = window.location.origin
559
+ const serverURL = origin.includes('cainiaoblog') ? 'https://cmts.cainiaoblog.cn' : 'https://cmts.xuehuayu.cn'
560
+ const locale = {
561
+ placeholder: '请正确填写昵称和邮箱,方便接收回复通知~',
562
+ sofa: '沙发空缺中,还不快抢~',
563
+ };
564
+ Waline.init({
565
+ el: '#vcomment',
566
+ serverURL: serverURL,
567
+ pageSize: '20',
568
+ visitor: true, // 阅读量统计
569
+ requiredMeta: ['nick', 'mail'],
570
+ emoji: [
571
+ 'https://cdn.jsdelivr.net/gh/walinejs/emojis@1.0.0/weibo',
572
+ 'https://cdn.jsdelivr.net/gh/walinejs/emojis@1.0.0/qq',
573
+ 'https://cdn.jsdelivr.net/gh/walinejs/emojis@1.0.0/tw-emoji',
574
+ ],
575
+ locale,
576
+ pageview: true
577
+ })
578
+ </script></div></div></div><div class="pure-u-1 pure-u-md-1-4 fixed-search hidden_mid_and_down"><div id="sidebar"><script type="text/javascript" src="//cdn.staticaly.com/gh/npljy/npljy.github.io/main/js/search.min.js"></script><div class="widget"><div class="widget-search"><input class="search" type="radio" name="search" value="baidu" id="baidu" checked="checked"/><label class="label" for="baidu" title="百度全站搜索">百度</label><input class="search" type="radio" name="search" value="google" id="google"/><label class="label" for="google" title="谷歌全站搜索">谷歌</label><input class="search" type="radio" name="search" value="self" id="self"/><label class="label" for="self" title="使用站内搜索">站内</label></div><div class="widget" id="search"><form class="search-form" action="//www.baidu.com/baidu" method="get" accept-charset="utf-8" target="_blank"><input type="search" name="word" maxlength="30" placeholder="百度全站搜索"/><input type="hidden" name="si" value="xuehuayu.cn"/><input type="hidden" name="cl" value="3"/><input type="hidden" name="ct" value="2097152"/><input type="hidden" name="s" value="on"/><input class="search-submit" type="submit" value=""/></form></div></div><script>$('input[type=radio][name=search]').change(function() {
579
+ var val = $(this).val()
580
+ var self = '<div class="search-form"><input id="local-search-input" placeholder="站内搜索,首次慢" type="search" name="q" results="0"><input class="search-submit" type="submit" value=""/><div id="local-search-result"></div></div>'
581
+ var google = '<form class="search-form" action="//www.google.com/search" method="get" accept-charset="utf-8" target="_blank"><input type="search" name="q" maxlength="30" placeholder="谷歌全站搜索"><input type="hidden" name="sitesearch" value="xuehuayu.cn"><input class="search-submit" type="submit" value=""/></form>'
582
+ var baidu = '<form class="search-form" action="//www.baidu.com/baidu" method="get" accept-charset="utf-8" target="_blank"><input type="search" name="word" maxlength="30" placeholder="百度全站搜索"><input type="hidden" name="si" value="xuehuayu.cn"><input type="hidden" name="cl" value="3"><input type="hidden" name="ct" value="2097152"><input type="hidden" name="s" value="on"><input class="search-submit" type="submit" value=""/></form>'
583
+
584
+ if (val === 'self') {
585
+ $('#search').html(self)
586
+ var search_path = 'search.xml';
587
+ if (search_path.length == 0) {
588
+ search_path = 'search.xml';
589
+ }
590
+ var path = 'https://cdn.staticaly.com/gh/npljy/npljy.github.io/main/' + search_path;
591
+ searchFunc(path, 'local-search-input', 'local-search-result');
592
+ } else if (val === 'baidu') {
593
+ $('#search').html(baidu)
594
+ } else if (val === 'google') {
595
+ $('#search').html(google)
596
+ }
597
+ })</script><div class="widget widget-wxmp"><img alt="微信公众号" width="100%" src="//cdn.staticaly.com/gh/npljy/npljy.github.io/main/img/mp-mini.jpg"/></div><div class="widget widget-categories"><div class="widget-title"><i class="fa fa-folder-o"> 分类</i></div><ul class="category-list"><li class="category-list-item"><a class="category-list-link" href="/categories/CDN/">CDN</a><span class="category-list-count">2</span></li><li class="category-list-item"><a class="category-list-link" href="/categories/IDE/">IDE</a><span class="category-list-count">1</span></li><li class="category-list-item"><a class="category-list-link" href="/categories/git/">git</a><span class="category-list-count">2</span></li><li class="category-list-item"><a class="category-list-link" href="/categories/hexo/">hexo</a><span class="category-list-count">1</span></li><li class="category-list-item"><a class="category-list-link" href="/categories/%E5%85%AC%E5%85%B1%E8%8A%82%E6%97%A5/">公共节日</a><span class="category-list-count">1</span></li><li class="category-list-item"><a class="category-list-link" href="/categories/%E5%88%86%E4%BA%AB/">分享</a><span class="category-list-count">29</span></li><li class="category-list-item"><a class="category-list-link" href="/categories/%E5%89%8D%E7%AB%AF/">前端</a><span class="category-list-count">191</span><ul class="category-list-child"><li class="category-list-item"><a class="category-list-link" href="/categories/%E5%89%8D%E7%AB%AF/%E6%B5%8F%E8%A7%88%E5%99%A8/">浏览器</a><span class="category-list-count">1</span><ul class="category-list-child"><li class="category-list-item"><a class="category-list-link" href="/categories/%E5%89%8D%E7%AB%AF/%E6%B5%8F%E8%A7%88%E5%99%A8/%E7%BD%91%E7%BB%9C%E5%8D%8F%E8%AE%AE/">网络协议</a><span class="category-list-count">1</span></li></ul></li></ul></li><li class="category-list-item"><a class="category-list-link" href="/categories/%E5%8D%9A%E5%AE%A2/">博客</a><span class="category-list-count">3</span></li><li class="category-list-item"><a class="category-list-link" href="/categories/%E5%B7%A5%E5%85%B7/">工具</a><span class="category-list-count">2</span></li><li class="category-list-item"><a class="category-list-link" href="/categories/%E5%B9%BF%E5%91%8A%E8%BF%87%E6%BB%A4/">广告过滤</a><span class="category-list-count">8</span><ul class="category-list-child"><li class="category-list-item"><a class="category-list-link" href="/categories/%E5%B9%BF%E5%91%8A%E8%BF%87%E6%BB%A4/%E8%A7%86%E9%A2%91%E7%94%B5%E8%A7%86%E5%B0%8F%E8%AF%B4%E6%BC%AB%E7%94%BB%E8%B5%84%E8%AE%AF%E9%9F%B3%E4%B9%90/">视频电视小说漫画资讯音乐</a><span class="category-list-count">2</span></li></ul></li><li class="category-list-item"><a class="category-list-link" href="/categories/%E6%AD%A3%E5%88%99/">正则</a><span class="category-list-count">5</span></li><li class="category-list-item"><a class="category-list-link" href="/categories/%E6%B5%8F%E8%A7%88%E5%99%A8/">浏览器</a><span class="category-list-count">5</span></li><li class="category-list-item"><a class="category-list-link" href="/categories/%E7%AE%97%E6%B3%95/">算法</a><span class="category-list-count">2</span></li><li class="category-list-item"><a class="category-list-link" href="/categories/%E8%B5%84%E8%AE%AF/">资讯</a><span class="category-list-count">16</span></li><li class="category-list-item"><a class="category-list-link" href="/categories/%E8%BD%BB%E6%9D%BE%E4%B8%80%E5%88%BB/">轻松一刻</a><span class="category-list-count">1</span></li></ul></div><div class="widget widget-tags"><div class="widget-title"><i class="fa fa-star-o"> 标签</i></div><div class="tagcloud"><a href="/tags/%E5%8E%9F%E5%88%9B/" style="font-size: 15px;">原创</a> <a href="/tags/%E8%BD%AC%E8%BD%BD/" style="font-size: 15px;">转载</a> <a href="/tags/%E6%89%8B%E5%86%99/" style="font-size: 15px;">手写</a> <a href="/tags/%E7%96%AB%E6%83%85/" style="font-size: 15px;">疫情</a> <a href="/tags/%E5%A8%B1%E4%B9%90/" style="font-size: 15px;">娱乐</a></div></div><div class="widget widget-recent-posts"><div class="widget-title"><i class="fa fa-file-o"> 最近文章</i></div><ul class="post-list"><li class="post-list-item"><a class="post-list-link" href="/article/c5576490.html">面试准备</a></li><li class="post-list-item"><a class="post-list-link" href="/article/84c9ccd6.html">精读《SolidJS》</a></li><li class="post-list-item"><a class="post-list-link" href="/article/53803e6.html">git提交注释规范</a></li><li class="post-list-item"><a class="post-list-link" href="/article/a4145266.html">前端数组拍平flat一行代码</a></li><li class="post-list-item"><a class="post-list-link" href="/article/bedea419.html">一道前端this面试题</a></li><li class="post-list-item"><a class="post-list-link" href="/article/bf7e7421.html">git多账号配置</a></li></ul></div><div class="widget widget-links"><div class="widget-title"><i class="fa fa-external-link"> 友情链接</i></div><ul></ul><a href="https://github.com/npljy?utm_source=xuehuayu.cn" title="GitHub" target="_blank">GitHub</a><ul></ul><a href="https://laonongmin.online?utm_source=xuehuayu.cn" title="看看" target="_blank">看看</a><ul></ul><a href="https://cainiaoblog.cn?utm_source=xuehuayu.cn" title="菜鸟博客" target="_blank">菜鸟博客</a><ul></ul><a href="mailto:cainiaoblog@126.com" title="友链联系" target="_blank">友链联系</a></div></div></div><div class="pure-u-1 pure-u-md-3-4"><div id="footer"><div class="flex-block justify-center align-center flex-wrap"><a class="gxba-link" id="gxba" rel="nofollow" target="_blank" href="http://beian.miit.gov.cn/">京ICP备20007647号-2</a><a class="gaba-link" id="gaba-link" rel="nofollow" target="_blank" href="http://www.beian.gov.cn/portal/registerSystemInfo?recordcode=11010802031264"><img class="nofancybox" src="//cdn.staticaly.com/gh/npljy/npljy.github.io/main/img/gaba.png" alt=""/><span id="gaba">京公网安备 11010802031264号</span><span style="padding-right: 10px;"></span></a><span>Copyright © 2023 </span><a href="/." rel="nofollow">前端壹菜鸟. </a><script>(function(){
598
+ var cnb =window.location.origin.indexOf('cainiaoblog') !==-1
599
+ if (cnb) {
600
+ var gxba =document.getElementById('gxba')
601
+ var gaba =document.getElementById('gaba')
602
+ var gabaLink =document.getElementById('gaba-link')
603
+ gxba.innerText ='京ICP备20007647号-1'
604
+ gaba.innerText ='京公网安备 11010802031254号'
605
+ gabaLink.setAttribute('href','http://www.beian.gov.cn/portal/registerSystemInfo?recordcode=11010802031254')
606
+ }
607
+ })()</script></div><div class="flex-block justify-center align-center flex-wrap"><a rel="nofollow" target="_blank" href="https://v6.51.la/s/Guz3lwHCsVme9Cu"><div class="busuanzi_container" id="busuanzi_container"><span class="busuanzi_container_site_pv" id="busuanzi_container_site_pv">访问量:<span id="busuanzi_value_site_pv"><i class="fa fa-spinner"></i></span></span><span class="busuanzi_container_site_uv" id="busuanzi_container_site_uv">访客数:<span id="busuanzi_value_site_uv"><i class="fa fa-spinner"></i></span></span><span style="padding-right: 10px;"></span></div></a><a rel="nofollow" target="_blank" href="https://www.upyun.com/?utm_source=lianmeng&amp;utm_medium=referral"><span style="font-weight:bold;letter-spacing: 1px;">本网站由 </span><img class="nofancybox" height="32" style="vertical-align: middle" src="//cdn.staticaly.com/gh/npljy/npljy.github.io/main/img/upy_logo.min.svg" alt=""/><span style="font-weight:bold;letter-spacing: 1px;">提供CDN加速/云存储服务</span></a><span style="padding-right: 10px;"></span><a rel="nofollow" style="font-size:18px;font-weight:bold;vertical-align: middle" target="_blank" title="注册就送代金券可直接使用" href="https://console.upyun.com/register/?invite=HyDsjZHIL">注册</a></div></div></div></div><a class="show" id="rocket" href="#top"></a><div class="darkmode-toggle">🌓</div><script type="text/javascript" src="//cdn.staticaly.com/gh/npljy/npljy.github.io/main/js/totop.min.js" async></script><script type="text/javascript" src="//cdn.staticaly.com/gh/npljy/npljy.github.io/main/js/dark.min.js" async></script><script type="text/javascript" src="//cdn.staticaly.com/gh/npljy/npljy.github.io/main/js/codeblock-resizer.min.js"></script><script type="text/javascript" src="//cdn.staticaly.com/gh/npljy/npljy.github.io/main/js/smartresize.min.js"></script></div></body></html>