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

🐛 Pug resolves component tag wrongly in Vue files #1089

Closed
Hammster opened this issue Mar 28, 2018 · 7 comments
Closed

🐛 Pug resolves component tag wrongly in Vue files #1089

Hammster opened this issue Mar 28, 2018 · 7 comments
Labels

Comments

@Hammster
Copy link
Contributor

To load dynamic components into a vue component, the component tag is used. Those tags are handled as singluar tags <component id="componentName"/> or closed tags <component id="componentName"></component>

If i use pug to define the template of my component, it sometimes transpiles it correctly and sometimes the tag is not closed at all e.g <component id="componentName">

🤔 Expected Behavior

.myclass
  component.myspecialcomponent(is="fancyName")

transpiles to

<div class="myclass">
  <component is="fancyName" class="myspecialcomponent"></component>
</div>
😯 Current Behavior

Sometimes the Expected Behavior and sometimes this

<div class="myclass">
  <component is="fancyName" class="myspecialcomponent">
</div>

🌍 Your Environment

Software Version(s)
Parcel master
Node 8.2.1
npm/Yarn 1.5.1
Operating System Win 10
@Hammster
Copy link
Contributor Author

Hammster commented Mar 28, 2018

I narrowed the error down, it happens if the component has a svg use inside of it that uses a xlink:href

Example

.pane
  .pane-tabs
    ui-button(v-for="paneContent in paneContentList" @click="setPaneContent(paneContent)") {{paneContent}}
  .pane-content
    component(:is="paneContentVisible" v-if="paneContentVisible === 'ui-button'") Teststring
    svg
      use(xlink:href="../../svg/symbols.svg#ei-close")

@DeMoorJasper
Copy link
Member

DeMoorJasper commented Mar 29, 2018

Try with latest npm version and let us know the exact command u used

@Hammster
Copy link
Contributor Author

Hammster commented Mar 29, 2018

Same issue on node 9.10.0 also i use [email protected] which is the latest

I have a build script that uses the parcel API, basicall i run node build/parcel.js

const Bundler = require('parcel-bundler')
const path = require('path')
const chalk = require('chalk')
// Entrypoint file location
const file = {
  electron: path.join(__dirname, '../src/electron/index.js'),
  renderer: path.join(__dirname, '../src/renderer/index.html')
}

// Bundler options
const options = {
  electron : {
    outDir: './dist/electron',
    outFile: 'index.js',
    publicUrl: './',
    watch: false,
    cache: false,
    minify: false,
    target: 'electron',
    https: false,
    logLevel: 3,
    sourceMaps: true
  },
  renderer: {
    outDir: './dist/renderer',
    outFile: 'index.html',
    publicUrl: './',
    watch: true,
    cache: false,
    minify: false,
    target: 'electron',
    logLevel: 3,
    hmrPort: 0,
    sourceMaps: true,
    hmr: true,
    hmrHostname: '',
    detailedReport: false
  }
}

// Initialises a bundler using the entrypoint location and options provided
const bundler = {
  electron: new Bundler(file.electron, options.electron),
  renderer: new Bundler(file.renderer, options.renderer)
}

async function resolveBundles () {
  const resolvedBundles = {}
  for (const bundleName of ['electron', 'renderer']) {
    // Awaiting one bundle after another
    console.log(chalk.cyan.bold('■  Bundel: ') + bundleName + '\n')
    resolvedBundles[bundleName] = await bundler[bundleName].bundle()
  }
}

resolveBundles()

This is the precise error the cli is outputting

×  C:\Workspace\Secretproject\Frontend\src\renderer\components\script-view\index.vue: tag <component> has no matching end tag.
    at VueAsset.compileTemplate (C:\Workspace\Secretproject\Frontend\node_modules\parcel-bundler\src\assets\VueAsset.js:131:15)
    at VueAsset.postProcess (C:\Workspace\Secretproject\Frontend\node_modules\parcel-bundler\src\assets\VueAsset.js:77:26)
    at Pipeline.processAsset (C:\Workspace\Secretproject\Frontend\node_modules\parcel-bundler\src\Pipeline.js:70:31)
    at <anonymous>

@Hammster
Copy link
Contributor Author

Hammster commented Mar 29, 2018

Okay so i've found the issue but i don't know how to handle it properly.

posthtml-renderer filters the component tag out as a a single tag because posthtml uses it. This does not apply to vue's component tag which can hold content.

here the code from posthtml-renderer, as you can see "component" is hardcoded to be a singular tag

https://github.com/posthtml/posthtml-render/blob/cbd69ea709034a18eb64749407322a6199e588e5/lib/index.js

The parsing to posthtml-renderer happens in the HTMLAsset.js on line 164 when the ast is dirty. This happens if a use with the xlink:href attribute is present.

@Hammster
Copy link
Contributor Author

Hammster commented Apr 3, 2018

For anyone that needs a temporary fix to this.

  • create a parcel-htmlhotfix.js file with this content
const HTMLAsset = require('parcel-bundler/src/assets/HTMLAsset')

class FixedAsset extends HTMLAsset {
  generate() {
    // Prevent posthtml-renderer from beein called, and simply 
    // return the content as a temporary fix.
    return this.contents
  }
}

module.exports = FixedAsset;
  • create a parcel.js file in the same directory
const Bundler = require('parcel-bundler')
const Path = require('path')

// adjust the entry point file here
const file = Path.join(__dirname, './index.js')
const bundler = new Bundler(file, options)

// override the html asset type.
bundler.addAssetType('html', require.resolve('./parcel-htmlhotfix.js'))
bundler.bundle()
  • Instead of running parcel directly call the parcel.js
node ./parcel.js

Be aware that this can create non-validated markup since the ast is not parsed through the posthtml-renderer. Also it will not replace <script src="file.js"></script>` with the coresponding created file.

@Hammster
Copy link
Contributor Author

Hammster commented Apr 3, 2018

Issue will be is fixed in [email protected]
@DeMoorJasper @devongovett can this be in the next patch ?

@Hammster
Copy link
Contributor Author

I made a pullrequest that sets [email protected] as the minimal version

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

No branches or pull requests

2 participants