Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

[Bug Report] 使用vux-loader之后所有vue组件script标签内的代码都会执行两次 #65

Open
ghost opened this issue Jun 20, 2018 · 4 comments

Comments

@ghost
Copy link

ghost commented Jun 20, 2018

vux-loader version

1.2.9

OS/Browsers version

MacOS Chrome

Vue version

2.5.16

Code

<template>
  <div id="app">
    hello world
  </div>
</template>

<script>
console.log('重复执行测试')
export default {
  name: 'App'
}
</script>

Steps to reproduce

  1. 通过vue-cli的webpack模版初始化一个空项目
  2. 在App.vue的<script>标签内添加console.log('重复执行测试')
  3. npm run dev将项目跑起来,在浏览器控制台查看,只打印了一行“重复执行测试”
  4. 安装vux和vux-loader,按照文档配置webpack,https://doc.vux.li/zh-CN/vux-loader/install.html
  5. 重新执行npm run dev将项目跑起来,在浏览器控制台查看,会打印两次“重复执行测试”

What is Expected?

vue组件script标签内的代码只会执行一次

What is actually happening?

vue组件script标签内的代码执行了二次

image

@wych1987
Copy link

我也发现了这个bug。。1.2.0无此bug。。1.2.1之后有这个bug

@ghost
Copy link
Author

ghost commented Jun 21, 2018

@wych1987 摊手╮(╯▽╰)╭

@wcldyx
Copy link

wcldyx commented Jun 23, 2018

很久之前就发现这个问题,还以为是我哪里配置不对

@Eurkidu
Copy link

Eurkidu commented Nov 15, 2018

@wych1987 查看了下1.2.1的改动 d230eaf

问题寻找

测试发现确实是添加的这段代码造成的问题

if (content.indexOf('export * from') !== -1) {
  let loaders = content.split('!')
  loaders = loaders.map(function (item) {
    if (item === 'babel-loader') {
      item += '!' + SCRIPT
    }
    return item
  })
  content = loaders.join('!')
}

可以看这段代码所在的函数

const _addScriptLoader = function (content, SCRIPT) {
  // get script type
  if (/type=script/.test(content)) {
    // split loaders
    var loaders = content.split('!')
    loaders = loaders.map(function (item) {
      if (/type=script/.test(item)) {
        item = SCRIPT + '!' + item
      }
      return item
    }).join('!')
    content = loaders
  } else if (/require\("!!babel-loader/.test(content)) {
    content = content.replace('!!babel-loader!', `!!babel-loader!${SCRIPT}!`)
  } else if (/import\s__vue_script__\sfrom\s"!!babel\-loader!\.\/(.*?)"/.test(content)) {
    let loaders = content.split('!')
    loaders = loaders.map(function (item) {
      if (item === 'babel-loader') {
        item += '!' + SCRIPT
      }
      return item
    })
    content = loaders.join('!')
  }

  if (content.indexOf('export * from') !== -1) {
    let loaders = content.split('!')
    loaders = loaders.map(function (item) {
      if (item === 'babel-loader') {
        item += '!' + SCRIPT
      }
      return item
    })
    content = loaders.join('!')
  }
  return content
}

可以看到前面判断条件中有一种情况是

content = content.replace('!!babel-loader!', `!!babel-loader!${SCRIPT}!`)

这种情况下,再跑后面添加的这段代码,会造成 vux-loader 注入了2遍 导致最后打包的代码重复

问题测试

可以打印这个函数的输入输出
当输入为

export * from "!!babel-loader!../node_modules/[email protected]@vue-loader/lib/selector?type=script&index=0!./App.vue"

输出为

export * from "!!babel-loader!../node_modules/[email protected]@vux-loader/src/script-loader.js!../node_modules/[email protected]@vux-loader/src/script-loader.js!../node_modules/[email protected]@vue-loader/lib/selector?type=script&index=0!./App.vue"

明显看到 vux-loader 注入了2遍

解决方案

因为并不清楚当初作者添加这段代码的具体意义, 但问题的原因很清楚就是 SCRIPT 重复添加导致的, 估修改这段代码外层的if判断条件

if (content.indexOf('export * from') !== -1 && content.indexOf(SCRIPT) === -1) {
  let loaders = content.split('!')
  loaders = loaders.map(function (item) {
    if (item === 'babel-loader') {
      item += '!' + SCRIPT
    }
    return item
  })
  content = loaders.join('!')
}

添加了 content.indexOf(SCRIPT) === -1 判断条件, 当存在的时候不重复添加
经测试, 已经不会重复打包代码
希望作者可以修复一下 @airyland

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

3 participants