2

I am using less, postcss and cssnano (version 3.7.3). In less, I am using classes which inherit from a shared base and overriding some of the properties when needed. I am finding that cssnano is reordering the inherited\overridden properties causing unexpected differences in the style.

A trimmed down example .less looks like this:

.cell-label {
    font-size: 11px;
}
.heading-label-cell {
    .cell-label;
    color: @heading-colour;
    font-size: 13px;
}
.question-label-cell {
    .cell-label;
    color: @question-colour;
}

Which is then expanded to css looking like:

.heading-label-cell {
  font-size: 11px;
  font-size: 13px;
  color:#616161;
}
.question-label-cell {
  font-size: 11px;
  color: #0073d6;
}

But cssnano then does the following which has reordered the font-size property:

.heading-label-cell {
    color:#616161;
    font-size:13px
}
.heading-label-cell,.question-label-cell {
    font-size:11px;
}
.question-label-cell {
    color:#0073d6
}

Is there a different way I am expected to do inheritance/overrides that doesn't suffer this problem or is the fault in cssnano?

Ferdinand Prantl
  • 5,281
  • 34
  • 35
daw
  • 1,959
  • 1
  • 20
  • 25
  • My gut feeling says that the problem is with less, that the output of less is flawed, and cssnano doesn't know what to do with it. – Mr Lister Aug 05 '16 at 08:59
  • @MrLister: No, Less doesn't do anything like that. The output produced by the Less compiler would be same as indicated in question (the second code block). It can be verified in the official online compiler [here](http://lesscss.org/less-preview). cssnano is a minifier and so I'd expect it to be doing all such compression rules, create selector groups for common properties etc. – Harry Aug 05 '16 at 09:09
  • 1
    @Harry That's what I mean by the output being flawed: it repeats the styles in the nested class. Ideally I would have expected those styles to be suppressed if they are overridden by the new ones (the font-size in the OP's example). – Mr Lister Aug 05 '16 at 09:12
  • No, that's not what Less is about. Less will output whatever is written. The output is not flawed, its just GIGO. I'd question the author in this case, why write another font rule when using a mixin which sets a different font rule? (Even Sass won't do this second rule suppression for that matter.) – Harry Aug 05 '16 at 09:14
  • @harry this is a reduced example - in reality cell-label has a dozen more rules and there are 10 other sub-classes of cell-label. Its only one or two sub-classes that need to override one or two of the shared rules. – daw Aug 05 '16 at 09:22
  • @daw: I understand. I'd generally say that if its not common then don't put into a common class/mixin (maybe write a separate mixin for those two and call only where needed) but I can see your point too, if its just one or two then overriding just within those selectors also makes sense. Wait and see if somebody who knows about cssnano can answer. I don't have a solution to this. – Harry Aug 05 '16 at 09:26

1 Answers1

1

Reordering CSS properties is not always a safe operation, but it is enabled in the default preset. If you encounter problems, with it, disable it. This optimisation is called cssDeclarationSorter.

For example, the options to call cssnano with:

{
  preset: [
    'default',
    { cssDeclarationSorter: false }
  ]
}

Or if you use cssnano as a plugin for postcss, this is postcss.config.js:

module.exports = {
  plugins: {
    cssnano: {
      preset: [
        'default',
        { cssDeclarationSorter: false }
      ]
    }
  }
}
Ferdinand Prantl
  • 5,281
  • 34
  • 35