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

A notice to cssnext users #32

Closed
jonathantneal opened this Issue May 23, 2018 · 24 comments

Comments

Projects
None yet
@jonathantneal
Collaborator

jonathantneal commented May 23, 2018

A third of a million weekly cssnext installs are about to get a deprecation notice redirecting them PostCSS Preset-Env, so let me explain what this project is, and what you need to know if you use cssnext.

What is PostCSS Preset-Env

PostCSS Preset-Env is a bundle of CSS polyfills and prollyfills applied at compile time. It is like Babel Preset-Env for CSS. And like Babel, there are less stable and more stable features you can use, but only the safer features are polyfilled by default. Related: The PostCSS Preset-Env homepage.

About features and changes

Disabling unstable features by default is an important departure from cssnext, and the change is to protect you and your team. This is because unstable features may change or disappear over time.

What should cssnext users do? They should take advantage of “stages”. Related: The cssdb staging process.

Like Babel, you can choose less stable or more stable features by specifying a “stage”. The stages are 0 - 4. The lower the stage number, the less stable the feature. Babel stages follow the TC39 staging process, and PostCSS stages follow the cssdb staging process.

cssnext users have been using many “Stage 0” features, and so the smoothest transition for your team may be to enable Stage 0 at first. Note: Nesting Rules are a Stage 0 feature.

Now, unlike Babel, PostCSS stages are not yet endorsed by or affiliated with a specification committee or browser vendor. If and when they are, that committee would likely be the CSSWG. I am actively trying to establish a partnership with them. Related: An issue to update cssdb with CSSWG feedback.

About browser support

Both Babel and PostCSS support a “browserslist”, which is a sharable configuration that determines the browsers your project is supporting. Babel and PostCSS use this configuration to omit polyfills for features that your target browsers already support.

About these projects

Babel and PostCSS were created to help developers accomplish real things with modern and emerging technologies. Both projects provide a great way for developers, authors, and implementors to communicate, thus improving the creation of standards, testing, feedback, and new use cases.

You can try PostCSS Preset-Env in the browser right now, and I hope you’ll consider using it in your next project. Thanks!

@Lysholm

This comment has been minimized.

Contributor

Lysholm commented May 25, 2018

@jonathantneal: Babel looks to be dropping stage 0 - 2 when babel 7 releases (For reasoning see: babel/babel#7770). I agree with their reasoning and think doing the same here would be a good idea (still include stage 0 - 2 features in preset-env but only expose them through the features option). What do you think? Doing that after release would probably annoy a great many people.

@jonathantneal

This comment has been minimized.

Collaborator

jonathantneal commented May 25, 2018

@Lysholm, thanks for bringing that to my attention. I have certain disagreements with the suggestion in that issue, based upon The Extensible Web Manifesto, and I’ve shared them back.

@Lysholm

This comment has been minimized.

Contributor

Lysholm commented May 25, 2018

@jonathantneal: I see your point but i think we have different high level preferences. Regardless of available stages, suggesting that everyone opt in for stage: 0 seems to invite misuse. Maybe suggest stage: 2 + nesting? Not that users of cssnext aren't used to it, looking at @apply.

@pietrofxq

This comment has been minimized.

pietrofxq commented May 31, 2018

@jonathantneal I have the current configuration of cssnext:

postcss.config.js

require('postcss-cssnext')({
      features: {
        customProperties: {
          variables: require('./src/css/variables')
        },
        customMedia: {
          extensions: require('./src/css/medias')
        }
      }
    })

I couldn't find a migration guide to help me move to postcss-preset-env since just replacing the module isn't working. What do I need to do to make this work with your module?

@jonathantneal

This comment has been minimized.

Collaborator

jonathantneal commented Jun 1, 2018

Great question, @pietrofxq. PostCSS Preset Env will takes options by the feature name. See https://github.com/csstools/postcss-preset-env#features

postcssPresetEnv({
  features: {
    'custom-properties': {
      variables: require('./src/css/variables')
    },
    'custom-media-queries': {
      extensions: require('./src/css/medias')
    }
  }
})

To benefit others, here is a list of PostCSS Preset Env options compared with cssnext options:

cssnext option preset-env option
customProperties custom-properties
imageSet image-set-function
nesting nesting-rules
customMedia custom-media-queries
mediaQueriesRange media-query-ranges
customSelectors custom-selectors
attributeCaseInsensitive case-insensitive-attributes
colorRebeccapurple rebeccapurple-color
colorHexAlpha hexadecimal-alpha-notation
colorFunction color-mod-function
fontFamilySystemUi system-ui
fontVariant font-variant-property
initial all-property
pseudoClassMatches matches-pseudo-class
pseudoClassNot not-pseudo-class
pseudoClassAnyLink any-link-pseudo-class
overflowWrap overflow-wrap-property
@pietrofxq

This comment has been minimized.

pietrofxq commented Jun 1, 2018

@jonathantneal Thanks, the variables are being recognized now. However, looks like the original statement with the variable isn't being removed:

image

Do I need to implement something else to fix this? (I don't have this issue with cssnext)

@pascalduez

This comment has been minimized.

pascalduez commented Jun 1, 2018

@pietrofxq CSSnext was using an older versions of postcss-custom-properties, now the preserve option is set to true by default. Just set it to false in your config.

@HerrBertling

This comment has been minimized.

HerrBertling commented Jun 5, 2018

My team found it rather hard to determine which stage to use – or whether it would be easier to stay with a certain stage and enable some features specifically.

So I ended up with a table of postcss-cssnext features, their postcss-preset-env counterparts (where I knew the option name) and the stage for each feature.

Here you go:

cssnext feature preset-env option stage
automatic vendor prefixes (link) done via autoprefixer /
custom properties & var() (link) custom-properties stage 3
custom properties set & @apply (link) 🚫 🚫 (removed, see here)
reduced calc() (link) 🚫 🚫 (removed)
custom media queries (link) custom-media-queries stage 1
media queries ranges (link) media-query-ranges stage 3
custom selectors (link) custom-selectors stage 1
nesting (link) nesting-rules stage 0
image-set() function (link) image-set-function stage 2
color() function (link) color-mod-function stage 2
hwb() function (link) color-functional-notation stage 2
gray() function (link) color-functional-notation stage 2
#rrggbbaa colors (link) hexadecimal-alpha-notation stage 2
rgba function (rgb fallback) (link) 🚫 🚫 (removed)
rebeccapurple color (link) rebeccapurple-color stage 2 💜
font-variant property (link) font-variant-property stage 3
filter property (link) 🚫 🚫 (too old 😉)
initial value (link) all-property stage 3
rem unit (px fallback) (link) 🚫 🚫 (removed)
:any-link pseudo-class (link) any-link-pseudo-class stage 2
:matches pseudo-class (link) matches-pseudo-class stage 2
:not pseudo-class (link) not-pseudo-class stage 2
:: pseudo syntax (: fallback) (link) 🚫 🚫 (removed)
overflow-wrap property (word-wrap fallback) (link) overflow-wrap-property stage 2
attribute case insensitive (link) case-insensitive-attributes stage 2
rgb() function (functional-notation) (link) color-functional-notation stage 1
hsl() function (functional-notation) (link) color-functional-notation stage 1
system-ui font-family (link) system-ui stage 2

We went with stage 2 and enabling nesting and custom-media-queries in the end :)

I threw all of this into a gist as well: https://gist.github.com/HerrBertling/fd69dcb5664eeb5543b761115d8b9ece

MoOx added a commit to MoOx/moox.io that referenced this issue Jun 5, 2018

@jonathantneal

This comment has been minimized.

Collaborator

jonathantneal commented Jun 5, 2018

Nice work, @HerrBertling. There are a lot of options, so I can see how this table you’ve created missed some from my original table.

rebeccapurple => rebeccapurple-color
font-variant => font-variant-property
:any-link => any-link-pseudo-class
:matches => matches-pseudo-class
:not => not-pseudo-class

And for all color functional notation => color-functional-notation

Some of the other items that were removed were already being removed from cssnext because they were rejected specs, or targeted very old browsers, or were optimizations not really related to the future.

EDIT: If you would, I’d prefer you fix your table above this comment, while my corrections can linger here for history-sake.

@HerrBertling

This comment has been minimized.

HerrBertling commented Jun 5, 2018

Perfect, thanks :) Regarding the old, outdated features, I already thought so. Especially for the filter() one, changed the comment on that :)

@LockeAG

This comment has been minimized.

LockeAG commented Jun 6, 2018

just noticed that for postcss.config.js , we should be calling the plugin like

    `'postcss-preset-env': {stage: 0,features: {'nesting-rules': true }},``

Right??

@HerrBertling

This comment has been minimized.

HerrBertling commented Jun 7, 2018

The readme says:

postcssPresetEnv({
  /* use stage 3 features + css nesting rules */
  stage: 3,
  features: {
    'nesting-rules': true
  }
})
@killtheliterate

This comment has been minimized.

killtheliterate commented Jun 8, 2018

Tried a few of the suggestions here, but cannot get custom-properties working with preset-env. It's copying the declaration that uses a variable, but not transforming the fallback. Was not able to get it working with the explicit {features: { 'custom-properties': ... either. In that example, what does the variable file look like?

Rollup config:

{
    plugins: [
      postcssImport(),
      postcssUrl(urlOptions),
      postcssPresetEnv({
        stage: 0
      })
    ]
}

Input:

.button {
  --button-border-color--base: #c4cacf;

  padding: 8px 12px;
  line-height: 1;
  border: 1px solid var(--button-border-color--base);

  background-color: transparent;
  border-radius: 3px;

  transition: all 0.3s ease 0s;
}

Output:

.button {
  padding: 8px 12px;
  line-height: 1;
  border: 1px solid var(--button-border-color--base);
  border: 1px solid var(--button-border-color--base);

  background-color: transparent;
  border-radius: 3px;

  transition: all 0.3s ease 0s
}
@Amareis

This comment has been minimized.

Amareis commented Jun 9, 2018

For brave souls - to reduce calc function as in cssnext you can use https://github.com/postcss/postcss-calc
Remember: you need to make preserve: false for custom properties plugin. Order of plugins matter, so in your postcss.config.json it will looks like

    'postcss-custom-properties': {preserve: false},
    'postcss-preset-env': {stage: 0},
    'postcss-calc': {},
@pascalduez

This comment has been minimized.

pascalduez commented Jun 9, 2018

@killtheliterate You must declare your custom properties in a :root selector for the variable like behaviour and fallback to work, postcss-custom-properties can't fully reproduce the native behaviour without a DOM.

Also adding postcss-reporter at the end of your plugin list might help, since this kind of thing is reported as a warning.

@killtheliterate

This comment has been minimized.

killtheliterate commented Jun 9, 2018

@pascalduez heya, thanks for the tip—I resolved the immediate issue by using postcss-import to @import '../variables.css', which contains:

:root {
  --foo: red;
}

This does lead to many duplicate declarations of :root in the output—is there a decent way to resolve this, maybe something that collapses them all down to the first one (so the cascade still works)?

Using the form { features: { 'custom-properties': { variables: require('./src/styles/variables.css') } } results in an error: ```
:root {
^

I assume this is an issue with requiring a CSS file as part of the css loader, chicken-before-the-egg.
@killtheliterate

This comment has been minimized.

@spnc-omz

This comment has been minimized.

spnc-omz commented Jun 19, 2018

Hi, thanks for this documentation, it's made transitioning a much smoother process.

One outstanding question, is there a pre-existing plugin to transform color() to color-mod() or am I stuck writing my own until I can convert my source code to use color-mod?

@jonathantneal

This comment has been minimized.

Collaborator

jonathantneal commented Jun 29, 2018

@spnc-omz, there is not an existing plugin to transform the pre-2015 color syntax into color-mod. I’ve wanted to devote some time to creating a plugin to analyze a css file and automatically update color methods, update range queries, and implement nesting, but I haven’t had the time, and don’t foresee having it very soon.

@spnc-omz

This comment has been minimized.

spnc-omz commented Jun 29, 2018

@jonathantneal thanks for the response. While awaiting a response I wrote a quick plugin to inline within my config that would update those. We’re working through rewriting our source now to alleviate that need. I can share the source if anyone would find it beneficial.

@OezlemYi

This comment has been minimized.

OezlemYi commented Jul 2, 2018

@jonathantneal I think the POSTCSS Preset Env option list campared with the nextcss options should be in the documentation. I searched 30 minutes how to set media queries option in stage 3 cause the option naming have changed and could be found nowhere else. In my opinion this is not an issue topic. This info should be globally accessible without searching.

@jonathantneal

This comment has been minimized.

Collaborator

jonathantneal commented Jul 21, 2018

Folks can still reference this thread, but I will be closing it as an active issue.

belgac added a commit to goldwasserexchange/public that referenced this issue Aug 21, 2018

chore(postcss-config): use postcss preset env instead of postcss-cssnext
affects: @goldwasserexchange/postcss-config

postcss-cssnext is deprecated and should be replaced with postcss-preset-env see
https://moox.io/blog/deprecating-cssnext/ and
csstools/postcss-preset-env#32

ISSUES CLOSED: #27

belgac added a commit to goldwasserexchange/public that referenced this issue Aug 22, 2018

chore(postcss-config): use postcss preset env instead of postcss-cssnext
affects: @goldwasserexchange/postcss-config

postcss-cssnext is deprecated and should be replaced with postcss-preset-env see
https://moox.io/blog/deprecating-cssnext/ and
csstools/postcss-preset-env#32

ISSUES CLOSED: #27
@Dan9boi

This comment has been minimized.

Dan9boi commented Sep 11, 2018

@jonathantneal how do you "require" (import) you custom-media and/or custom-properties (vars), like mentioned in #32 (comment) when using postcss.config.js?

@jonathantneal

This comment has been minimized.

Collaborator

jonathantneal commented Sep 11, 2018

I am working on that. It’s not a done feature and my time is limited. I’ve finished this work for Custom Selectors. I have a PR open for Custom Media. I have not started the work for Custom Properties.

@mor10 mor10 referenced this issue Nov 15, 2018

Merged

Restructure WP Rig for v2.0 #133

31 of 31 tasks complete
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment