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

[parcel 2] does not minify css imported with bundle-text: #5755

Closed
danieltroger opened this issue Feb 2, 2021 · 16 comments · Fixed by #6379
Closed

[parcel 2] does not minify css imported with bundle-text: #5755

danieltroger opened this issue Feb 2, 2021 · 16 comments · Fixed by #6379

Comments

@danieltroger
Copy link
Contributor

🐛 bug report

When importing css as string into javascript with bundle-text: as described here the css does not get processed at all.

🎛 Configuration (.babelrc, package.json, cli command)

Cli command:
npm run build

Please see attached .zip file for the rest.

🤔 Expected Behavior

The inlined css code should be minified and look like this:

!function(){var n,e=(n="body{background:red}")&&n.__esModule?n.default:n;const d=document.createElement("style"),t=()=>document.body.append(d);d.type="text/css",d.append(e),document.body?t():window.addEventListener("DOMContentLoaded",t)}();

😯 Current Behavior

The inlined css code looks just like before.

!function(){var n,e=(n="/* THIS IS A COMMENT*/\n\n\n/*\nh\ne\nr\ne\n\nh\ne\nr\ne\n\n\nb\ne\n\nw\nh\ni\nt\ne\ns\np\na\nc\ne\ns\n*/\n\n\n\n\n\n\n\n\nbody                                                                                                  {\n                        background: red;\n}\n\n")&&n.__esModule?n.default:n;const d=document.createElement("style"),t=()=>document.body.append(d);d.type="text/css",d.append(e),document.body?t():window.addEventListener("DOMContentLoaded",t)}();

💁 Possible Solution

Process the css

🔦 Context

#5751

💻 Code Sample

parcel-no-css-postpro.zip

🌍 Your Environment

Software Version(s)
Parcel 2.0.0-nightly.562+fbca3a93
Node v15.6.0
npm/Yarn 7.4.0
Operating System macOS High Sierra 10.13.6
@mischnic
Copy link
Member

mischnic commented Feb 2, 2021

It probably has to do something with the parcelrc matching of optimizers for named pipelines, both of these cases aren't minified:

// import x from 'bundle-text:./styles.css';
import x from 'url:./styles.css';
console.log(x);
body: {








	color: red;
	color: red;
}

@mischnic
Copy link
Member

mischnic commented Feb 2, 2021

As I've speculated, this is because if a request has a pipeline, it has to exactly match an entry in the parcelrc.

Commenting this out "fixes" it, but the question is how parcelrc matching should behave in general...

@danieltroger
Copy link
Contributor Author

Commenting this out "fixes" it,

Can confirm it works. The file is in node_modules/@parcel/core/lib/ParcelConfig.js on a normal installation. And just the line containing return [] has to be removed. Also don't forget to remove --no-optimize.

Wooo-hooooo, minified css here I come :D

@danieltroger
Copy link
Contributor Author

Hey @mischnic dunno if this is the right place to ask, but css imported with bundle-text: get wrapped into $parcel$interopDefault which looks like this

function $parcel$interopDefault(a) {
    return a && a.__esModule ? a.default : a;
  }

So it basically just returns the string again.

Could it be included as a string directly instead?

I stumbled upon a script which includes css based on a variable in a config section and the interopDefault wrapping of the string confuses terser (or whatever does the magic) so it no longer removes the css if it isn't needed in that build. When importing it as a normal ts file which exports it like this export default = 'csshere'; it just got included unwrapped and optimized away because it's in an if(false).

@mischnic
Copy link
Member

mischnic commented Feb 3, 2021

We should probably add a pure comment to the interop call, Terser removes everything here:

!(function () {
  const css = "body{background:red}";
  function $parcel$interopDefault(a) {
    return a && a.__esModule ? a.default : a;
  }
  const $css$interop = /*@__PURE__ */$parcel$interopDefault(css);
  // console.log($css$interop);
})();

Would that fix your case?

@danieltroger
Copy link
Contributor Author

That would be amazing! TIL about pure comments

@mischnic
Copy link
Member

mischnic commented Feb 3, 2021

-> #5765

@danieltroger
Copy link
Contributor Author

the question is parcelrc matching should behave in general...

Is there something I can put in my parcelrc to work around this bug instead of editing parcel?

@mischnic
Copy link
Member

mischnic commented Feb 3, 2021

(I haven't tested this)

{
	"extends": "@parcel/config-default",
	"optimizers": {
	    "bundle-text:*.css": ["@parcel/optimizer-cssnano"]
	}
}

@danieltroger
Copy link
Contributor Author

Works beautifully, thanks!

@ProLoser
Copy link

ProLoser commented Feb 7, 2021

Shouldn't you use the '...' feature?

@danieltroger
Copy link
Contributor Author

@ProLoser can you elaborate?

@ProLoser
Copy link

ProLoser commented Feb 9, 2021

Nevermind @mischnic solution is better, I was thinking maybe bundle-text: should do ["...", "bundle-text"] so that all src files are still processed normally

@mischnic
Copy link
Member

mischnic commented Feb 9, 2021

Yeah. You still shouldn't have to actually list out all pipelines in the optimizers object though...

@devongovett
Copy link
Member

This should be fixed in #6379. Basically it will only try to match pipelines that actually exist in the optimizers config. See a2a7da1. Does this logic make sense to you?

@danieltroger
Copy link
Contributor Author

@devongovett Idk what pipelines and optimizers are but sounds good. Once it's out I will test it and see if it works.

BTW could you update SWC like this but to the newest version? That should fix #6356

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

Successfully merging a pull request may close this issue.

4 participants