Problem/Motivation

Our CSS standards have a recommendation about the order of property declarations so we should apply it to core.

Proposed resolution

Add https://www.npmjs.com/package/stylelint-order and use the existing CSScomb config to configure it and use the --fix option to generate a patch.

Blocked on #3024518: Upgrade stylelint to the latest version

Once that has landed you can:

  1. $ cd core
  2. $ yarn add stylelint-order --dev
  3. Apply the patch here to core/.stylelintrc.json
    For example: $ curl https://www.drupal.org/files/issues/2019-03-08/3024527-4-28.patch | git apply --index --include=core/.stylelintrc.json
  4. $ yarn run lint:css --fix

Remaining tasks

User interface changes

None

API changes

None

Data model changes

None

Release notes snippet

CSS standards for ordering is now enforced using the stylelint-order plugin.

CommentFileSizeAuthor
#56 3024527-10-56.patch504.62 KBalexpott
#49 3024527-9-49.patch504.71 KBalexpott
#42 3024527-8-42.patch504.71 KBalexpott
#41 3024527-7-41.patch501.73 KBalexpott
#40 3024527-6-40.patch498.54 KBalexpott
#37 3024527-5-37.patch500.53 KBalexpott
#28 3024527-4-28.patch500.96 KBalexpott
#28 27-28-interdiff.txt1.88 KBalexpott
#28 21-28-interdiff.txt408 bytesalexpott
#27 interdiff_21-27.txt334.27 KBwaako
#27 3024527-27.patch499.09 KBwaako
#25 stylelint-order--after-fix.png.png121.18 KBmarkconroy
#24 stylelint-order--before-fix.png133.06 KBmarkconroy
#24 stylelint-order--after-fix.png.png121.85 KBmarkconroy
#21 interdiff_18-21.txt5.69 KBwaako
#21 3024527-21.patch500.96 KBwaako
#18 interdiff-14-18.txt682 bytesmarkconroy
#18 3024527-18.patch502.89 KBmarkconroy
#14 interdiff_3024527-3-5.txt2.94 KBoccupant
#14 3024527-5-14.patch502.89 KBoccupant
#12 3024527-4-12.patch502.89 KBoccupant
#9 3024527-3-9.patch502.24 KBalexpott
#8 3024527-2-8.patch502.24 KBalexpott
#7 interdiff-2-7--with-breakpoint.txt473 bytesmarkconroy
#7 interdiff-2-7.txt326 bytesmarkconroy
#7 3024527-7--with-breakpoint.patch647.33 KBmarkconroy
#7 3024527-7.patch647.3 KBmarkconroy
#3 3024527-2.patch647.25 KBalexpott
Support from Acquia helps fund testing for Drupal Acquia logo

Comments

alexpott created an issue. See original summary.

alexpott’s picture

Status: Active » Needs review
FileSize
647.25 KB

This was brought to my attention in #2992635: Pass all Umami CSS files through CSScomb to Ensure they Follow our CSS Coding Standards - so crediting @markconroy

Personally I think we should change the rule to be alphabetical because then at least human beings can know when it is correct. Or maybe not have a rule at all.

alexpott’s picture

Issue summary: View changes
lauriii’s picture

+1 on automating coding standards checks to reduce manual work developers have to do.

I'd like to express my opinions without wearing any hats since I don't think there's a right or wrong way to order selectors. I don't think ordering selectors alphabetically makes it much better than having properties in random order, whereas grouped by type actually makes it easier to read the CSS. It is also not as commonly used as grouping by type at least according to this poll.

alexpott’s picture

Issue summary: View changes

Okay given @lauriii's position in #5 I'm +1 on this patch. It makes it easy to enforce our standard.

markconroy’s picture

Hi Folks,

Great to see this progressing. I'm adding two patches for consideration here:

  1. Adds support for object-fit and object-position
  2. Adds support for object-fit and object-position and also @include breakpoint. Not sure if we want the breakpoint support in a core linter, but many people using sass use the breakpoint package for easier to write/read media queries, and like the $media property, we need these after our other declarations for mobile-first theming.
alexpott’s picture

Issue summary: View changes
FileSize
502.24 KB

Rerolled now the dependency has landed. Let's add breakpoint support there's not harm in making everything consistent even if core does not specifically use it.

No interdiff break this is a reroll.

alexpott’s picture

Issue summary: View changes
FileSize
502.24 KB

Re-rolled

occupant’s picture

#9 applied cleanly, passes linting.

Further to #8 and @alexpott's comment about breakpoint support, I'm wondering if there is a place here to add some additional rules for properties that aren't currently included in core, most notably grid, grid-area, grid-template, etc? These aren't used atm, but that could conceivably change considering the current state of support - caniuse grid support.

I guess this comes down to, should new properties be added when they come up as a failsafe, or should it just be focussed on what's currently in core?

If so, some additional properties (not including prefixes) could include:

all All @ MDN

grid
grid-area
grid-template
grid-template-areas
grid-template-rows
grid-template-columns
grid-row
grid-row-start
grid-row-end
grid-column
grid-column-start
grid-column-end
grid-auto-rows
grid-auto-columns
grid-auto-flow
grid-gap
grid-row-gap
grid-column-gap

perspective perspective @MDN perspective @ caniuse
perspective-origin

There may be more, but that's what I've noticed with this pass.

Happy to make a patch with these if there's a place for the additional properties.

markconroy’s picture

@occupant,

Thanks.

I would be 100% for adding grid support. I think anything that helps developers to use the tools from core (such as this linting set-up) without having to extend or fork it is a great help in getting everyone (automatically) following the coding standards.

If people have to extend or fork, we run a real risk of people just adopting some other standards in their own work because the things they want are in them, and then finding core/contrib harder to work with when they have to change tack.

So, for me, given the prevalence of CSS Grid, I think that should certainly be a part of this file.

occupant’s picture

@markconroy

I'd love to see this in there too. Here's a patch with the properties added. I had to change the order of align-self, as it's used in grid as well. I've also attempted adding the -ms prefixes as per how they're added by autoprefixer.

markconroy’s picture

Can you add an interdiff between this patch and the last one please, so we can see exactly what has changed?

occupant’s picture

Whoops, I should have done that. I've rerolled it again and created an interdiff between this and patch #3.

Edit: hmm, not sure I did that right. are the /core/package.json and /core/yarn.lock changes supposed to be in there?

alexpott’s picture

+++ b/core/.stylelintrc.json
@@ -56,12 +56,39 @@
-      "align-self",
...
+      "align-self",
...
+      "justify-self",

Are you sure that moving align-self is correct? And also is this really where justify-self belongs?

occupant’s picture

@alexpott they’re used by css grid and flexbox - css grid guide @css tricks, so my thinking was it doesn’t make sense to come before the grid property. I see I did miss align-content and justify-content however, which are both grouped above with flexbox atm. I would expect that these should appear lower as well.

That said, the exact order could very well be different than what I’ve proposed.

markconroy’s picture

Status: Needs review » Needs work

Let's put align-self back where it was, as it is a property of flexbox. https://developer.mozilla.org/en-US/docs/Web/CSS/align-self

And let's move justify-self to either directly above or directly below the flex properties as it is an alignment property that is not strictly part of flex or grid, can be used with position and display https://developer.mozilla.org/en-US/docs/Web/CSS/justify-self

markconroy’s picture

Status: Needs work » Needs review
FileSize
502.89 KB
682 bytes

Adding new patch for what I propsed above in #17

occupant’s picture

@markconroy I think it's actually a shared property, as per your link:

The align-self CSS property aligns flex items of the current flex line overriding the align-items value. If any of the item's cross-axis margin is set to auto, then align-self is ignored. In Grid layout align-self aligns the item inside the grid area.

So I think, as a shared property, I'd argue these should come either before or after both flex and grid properties to normalize the expected order.

I propose the following ordering of these shared properties:

place-content //shorthand for align-content and justify-content
place-items //shorthand for align-items and justify-items
align-content
align-items
align-self
justify-content
justify-items
justify-self

order

Thoughts?

occupant’s picture

Just looking through the flex properties, and it seems that the syntax is outdated.

Deprecated
flex-order // replaced by order https://developer.mozilla.org/en-US/docs/Web/CSS/flex-order
flex-pack // replaced by justify-content https://developer.mozilla.org/en-US/docs/Web/CSS/flex-pack
flex-align // replaced by justify-items https://developer.mozilla.org/en-US/docs/Web/CSS/flex-align
align // not foundhttps://developer.mozilla.org/en-US/docs/Web/CSS/align

Also, the flex-flow shorthand property is missing. With this and #19 in mind, I'd propose updating the flex properties to:

flex
flex-flow // shorthand for flex-direction and flex-wrap, so should precede both
flex-direction
flex-wrap
flex-basis
flex-grow
flex-shrink
waako’s picture

New patch with following changes:

Added "order/order" config to match CSSComb so that variables (and one-line sass @at-rules) sit before declarations but at-rules with blocks (@media, @supports, sass @include breakpoint) sit after declarations and before rules.

Worth noting that "order/properties-order" ignores variables ($sass, @less, --custom-property).
This means I don't think it's possible to have certain at-rules like @keyframe name {} block in between transform and animation declarations like it is in CSSComb.

Removed "$charset", "$import", "$namespace", "$extend", "$variable", "$include" from beginning of "order/properties-order" and "$media", "$include breakpoint", "$supports", "$document", "$page" and "$viewport" from end of "order/properties-order" as they area now dealt with by the "order/order" rules before.

However left other "$declaration" for reference in case we want to look at ordering them in a specific place.

Based on comments in #19 and #20 I've updated the flex properties, and moved the flexbox & grid shared alignment properties to below both, that does seem to make sense.

Status: Needs review » Needs work

The last submitted patch, 21: 3024527-21.patch, failed testing. View results

markconroy’s picture

Status: Needs work » Needs review

Setting back to 'Needs review' to get the tests to run again. I don't think the failures are anything to do with the patch (which looks great).

markconroy’s picture

I did a screenshare with @waako a few minutes ago and got him to show me this working. I'm _very_ impressed with it.

I'm happy with the ordering of items, the spacing between block sets, how custom variables (--black: #000;) are placed at the top of our rules, followed by any $dollar variables (for SASS, etc - $c-black: #000), then our general css (color: #000;), and then any media queries/supports/etc at the end.

Here's a screenshot of some made-up code before we run the stylelint:

CSS code before running stylelint

And here's a screenshot of this mess all cleaned up:

CSS code after running stylelint

I think this will make a great addition to Drupal core, and will mean sooo many developers across the world can use it as the base for their linting when developing Drupal websites, without having to fork it or extend it, given how it works for CSS/SCSS/etc.

Thanks @waako for this and @occupant for adding the grid stuff.

markconroy’s picture

FileSize
121.18 KB
markconroy’s picture

Status: Needs review » Reviewed & tested by the community

The tests are passing now. Looks like Drupal Infra had an issue.

I'm marking this as RTBC, it's a great improvement.

We might want to postpone running the linters until later in Beta/RC phase.

waako’s picture

Small change in "order/order" placing at-rule blocks after rules.

This doesn't impact on Drupal core CSS, but will help with preprocessors and nested rules being overriden inside @supports or @include breakpoint statements.
Without this change the @supports block would be placed before the nested rules it aims to override and be overriden themselves, defeating the purpose of the @supports altogether.

Updated 8.7.x branch locally, hence the large interdiff.

alexpott’s picture

@waako the interdiff at least contains unrelated change. Looks like the patch doesn't though so that's good - but confusing.

yarn install v1.12.3
[1/5] 🔍  Validating package.json...
[2/5] 🔍  Resolving packages...
[3/5] 🚚  Fetching packages...
[4/5] 🔗  Linking dependencies...
warning " > stylelint-order@2.1.0" has incorrect peer dependency "stylelint@^9.10.1".
[5/5] 📃  Building fresh packages...
✨  Done in 2.71s.

I wonder why we get a warning. Happens why you add stylelint-order anyway so /shrug.

Importantly #27 doesn't include the stylelint-order library so that needs fixing.

alexpott’s picture

alexpott’s picture

#3038562: Update stylelint to 9.10.1 will resolved the warning.

markconroy’s picture

@alexpott, can we mark this RTBC again? You happen with this new patch - bigger, better, newer!!!

alexpott’s picture

@markconroy a review of https://www.drupal.org/project/drupal/issues/3038562 would be great too as that takes away a warning generated when we do this one.

Version: 8.7.x-dev » 8.8.x-dev

Drupal 8.7.0-alpha1 will be released the week of March 11, 2019, which means new developments and disruptive changes should now be targeted against the 8.8.x-dev branch. For more information see the Drupal 8 minor version schedule and the Allowed changes during the Drupal 8 release cycle.

markconroy’s picture

Hi @alexpott

#3038562: Update stylelint to 9.10.1 is RTBC now as well.

waako’s picture

Thank you @alexpott for fixing those issues in #27.
I definitely got myself mixed up with my local git branches considering it was such a small change, compared to correct patch & interdiff I did in #21. I live and learn.

alexpott’s picture

@waako thank you for your contribution. I've messed up many patches - tools like composer and yarn make reviewing changes hard because there's a lot of noise.

alexpott’s picture

Re-made the patch due to conflicts as the per the instructions in the issue summary.

alexpott’s picture

Issue summary: View changes
Issue tags: +8.7.0 release notes
alexpott’s picture

I've added the necessary change record - see https://www.drupal.org/node/3041002

alexpott’s picture

rerererererereroll.....

alexpott’s picture

rerererererererererereerererererererereRerollll.......

alexpott’s picture

Rererererererererererererererererererererererererererererererolll....

pandaski’s picture

I am having the errors while testing the patch to the 8.8.x branch

error1:

Checking patch core/modules/quickedit/css/quickedit.theme.css...
error: while searching for:
 * In-place editors that don't use a popup.
 */
.quickedit-validation-errors .messages.error {
  box-shadow: 0 0 1px 1px red, 0 0 3px 3px rgba(153, 153, 153, 0.5);
  background-color: white;
}

/**
 * Styling specific to the 'form' in-place editor.
 */
.quickedit-form {
  box-shadow: 0 0 30px 4px #4f4f4f;
  background-color: white;
}

/**
 * Toolbars.
 */
.quickedit-toolbar-container {
  font-family: "Source Sans Pro", "Lucida Grande", sans-serif;
  padding-bottom: 7px;
  padding-top: 7px;
  -webkit-transition: all 1s;
  transition: all 1s;
}
.quickedit-toolbar-container > .quickedit-toolbar-content {
  background-image: -webkit-linear-gradient(top, #fff, #e4e4e4);
  background-image: linear-gradient(to bottom, #fff, #e4e4e4);
  box-sizing: border-box;
  color: black;
  padding: 0.1667em;
  position: relative;
  -webkit-user-select: none;
  -moz-user-select: none;
  -ms-user-select: none;
  user-select: none;
  z-index: 2;
}
.quickedit-toolbar-container > .quickedit-toolbar-pointer {
  background-color: #e4e4e4;
  bottom: 2px;
  box-shadow: 0 0 0 1px #818181, 0 0 0 4px rgba(150, 150, 150, 0.5);
  display: block;
  height: 16px;
  left: 18px; /* LTR */
  position: absolute;
  -webkit-transform: rotate(45deg);
  -ms-transform: rotate(45deg);
  transform: rotate(45deg);
  width: 16px;
  z-index: 1;
}
[dir="rtl"] .quickedit-toolbar-container > .quickedit-toolbar-pointer {
  left: auto;
  right: 18px;
}
.quickedit-toolbar-container.quickedit-toolbar-pointer-top > .quickedit-toolbar-pointer {
  bottom: auto;
  top: 2px;
}
.quickedit-toolbar-container > .quickedit-toolbar-lining {
  bottom: 7px;
  box-shadow: 0 0 0 1px #818181, 0 3px 0 1px rgba(150, 150, 150, 0.5);
  display: block;
  left: 0;
  position: absolute;
  right: 0;
  top: 7px;
  z-index: 0;
}

.quickedit-toolbar-label {
  font-style: italic;
  overflow: hidden;
  padding: 0.333em 0.4em;
  text-overflow: ellipsis;
  white-space: nowrap;
}
.quickedit-toolbar-label .field:after {
  content: " → "; /* LTR */

error: patch failed: core/modules/quickedit/css/quickedit.theme.css:83

error2:

Checking patch core/themes/stable/css/quickedit/quickedit.theme.css...
error: while searching for:
 * In-place editors that don't use a popup.
 */
.quickedit-validation-errors .messages.error {
  box-shadow: 0 0 1px 1px red, 0 0 3px 3px rgba(153, 153, 153, 0.5);
  background-color: white;
}

...
error: patch failed: core/themes/stable/css/quickedit/quickedit.theme.css:83
pandaski’s picture

We may need to re-patch the css files for quickedit styles

https://github.com/drupal/drupal/blob/8.8.x/core/modules/quickedit/css/q...

/**
 * In-place editors that don't use a popup.
 */
.quickedit-validation-errors .messages.error {
  box-shadow: 0 0 1px 1px red, 0 0 3px 3px rgba(153, 153, 153, 0.5);
  background-color: white;
}
pandaski’s picture

Status: Reviewed & tested by the community » Needs work
xjm’s picture

Issue tags: -8.7.0 release notes

The deadline for this for 8.7.x has passed, so untagging 'til next time. Thanks!

joelpittet’s picture

@xjm If this is not the right time to commit this kind of disruptive patch when is?

markconroy’s picture

Status: Needs work » Reviewed & tested by the community
Issue tags: +8.7.0 release notes

@xjm,

I'm adding back in the 8.7.0 release notes tag.

We deliberately didn't commit this early in the 8.7.x branch phase because it would be very disruptive to many CSS-based patches. We were leaving it until feature-freeze/beta/rc so it has as little disruption as possible, and then people working on CSS-based patches can use this when we transition to the 8.8.x branch.

@alexpott and @lauriii discussed this with me on Slack a few months back.

@Joseph Zhao - CSS files are broken. That's why we need this patch, so the coding standards will be automated. quickedit.css et all will be fixed automatically once this patch is committed. It won't apply directly against the quickedit module per se, it'll be run and that will update the quickedit.css file for us. Then when people do their next git pull, they'll have CSS files that follow our coding standards.

alexpott’s picture

A release manager has made a decision. So let's not put this in 8.7.x. Let's get this in 8.8.x now. That means we have the whole release cycle to find an issues (however unlikely or lilely that is - feels unlikely) and because we commit patches to 8.8.x first 8.7.x gets the benefit anyway!

Here's yet another reroll.

markconroy’s picture

That seems very strange. This has been RTBC pretty much for a month, but we held back on it then for no good reason it seems.

I hope the same doesn't happen in 6 months when we are trying to get it into 8.8.x

joelpittet’s picture

@xjm I don't mean to go against the decision. I'm just looking for clarity because I know these can be disruptive so timing is key so I just want to get it correct. Also for contrib projects I'm maintaining there is similar disruptive patches that would be nice to have a message for when the patch can make it in.

alexpott’s picture

@markconroy I'm suggesting we add the library now in 8.8.x and then we can choose whether to backport the allowed CSS changes to 8.7.x. That way 8.7.x benefits because we commit to 8.8.x first so all new patches will comply because 8.8.x has the library.

pandaski’s picture

@markconroy

thanks for the clarification.

Commit to 8.8.x then backported to 8.7.x makes sense

lauriii’s picture

Is the proposal to commit #49 to 8.8.x, and after that, we would create another patch where the library addition has been removed, but it still contains the same CSS changes and commit that to 8.7.x? I like the plan except I would prefer if we would create both patches at the same time, and only commit this to 8.8.x if we also commit the CSS changes to 8.7.x. If we end up in a situation where we committed these CSS changes only to 8.8.x, backporting CSS changes to 8.7.x would in most cases require a separate patch.

alexpott’s picture

@lauriii for 8.7.x you can do

$ curl https://www.drupal.org/files/issues/2019-03-30/3024527-9-49.patch | git apply --index   --exclude core/package.json --exclude core/yarn.lock --exclude core/.stylelintrc.json

No need to another patch atm :)

alexpott’s picture

  • lauriii committed 9a4a499 on 8.8.x
    Issue #3024527 by alexpott, markconroy, waako, occupant: Add and...

  • lauriii committed 32fd0e8 on 8.7.x
    Issue #3024527 by alexpott, markconroy, waako, occupant: Add and...
lauriii’s picture

Status: Reviewed & tested by the community » Fixed

Looks good for me. I talked with @catch on Slack who is another release manager and he didn't express any particular concerns on this approach. So committed the change with the library addition to Drupal 8.8.x with the CSS changes and only the CSS changes to 8.7.x

markconroy’s picture

@lauriii

Thanks for committing this. It'll be a great help to people to follow the coding standards.

I'm a little confused at the specific reason why we wouldn't include it in 8.7. if we are including the CSS that it generates. I don't see how anything would break and it will make following coding standards to be a lot easier for an extra six months.

alexpott’s picture

Version: 8.8.x-dev » 8.7.x-dev

Setting to 8.7.x as a version of the patch did make it into 8.7.x.

@markconroy the reason the library did not make it into 8.7.x is because the release managers have decided to not make library changes whilst in beta in order for stability both of production and development environments. A new library potentially means that someone might have to change their development pipeline in some way. Personally whilst I agree that PHP and JS dependencies (those in core/misc) should be treated this way I'm not 100% convinced the same is true for dependencies managed by core/package.json because these dependencies describe only the core JS build process. That said we do have a problem at the moment because DrupalCI treats core's dev tools as the baseline for all Drupal contrib dev tools so disruption to the toolchain can have unexpected effects. Again we've only seen this for PHP dev dependencies such as PHPCS but it is worth bearing in mind. Ideally things would not be so closely coupled.

xjm’s picture

Where's the separate issue for the library addition?

xjm’s picture

@lauriii clarified that he manually fixed 8.7.x without backporting the library rather than committing a separate patch, so the commit message there misled me.

WRT not backporting the library after beta, this is not an arbitrary release manager decision. It is documented core policy: library additions are only allowed in minor versions, and as such need to be completed before beta, as per:

The release of the first beta is a firm deadline for all feature and API additions. Even if an issue is pending in the RTBC queue when the commit freeze for the beta begins, it will be committed to the next minor release only.

I'd prefer not to make exceptions based on what kind of library it is because we have to explain or justify them; the whole point of the alpha and beta phases is that alpha is "with exceptions" and beta is "no exceptions".

In an ideal world, the library would have been added, but not used, before the beta deadline, and the cleanup would have been scheduled during beta.

Thanks!

Status: Fixed » Closed (fixed)

Automatically closed - issue fixed for 2 weeks with no activity.