Skip to content

Commit

Permalink
refactor: optimize postcss task (#5085)
Browse files Browse the repository at this point in the history
  • Loading branch information
vladitasev authored Apr 19, 2022
1 parent 67565d5 commit c29e91f
Show file tree
Hide file tree
Showing 9 changed files with 223 additions and 17 deletions.
12 changes: 8 additions & 4 deletions .reuse/dep5
Original file line number Diff line number Diff line change
Expand Up @@ -30,10 +30,6 @@ Copyright: 2020 SAP SE or an SAP affiliate company and OpenUI5 contributors
License: Apache-2.0


Files: packages/playground/assets/js/webcomponentsjs/* packages/ie11/src/thirdparty/Array.from.js packages/ie11/src/thirdparty/events-polyfills.js packages/ie11/src/thirdparty/Object.assign.js packages/ie11/src/thirdparty/template.js packages/ie11/src/thirdparty/webcomponents-sd-ce-pf.js
Copyright: 2018 The Polymer Project Authors
License: BSD-3-Clause-Clear

Files: packages/base/dist/sap/ui/thirdparty/caja-html-sanitizer.js
Copyright: Google Inc.
License: Apache-2.0
Expand All @@ -46,3 +42,11 @@ License: MIT
Files: packages/playground/assets/js/vendor/lunr.min.js
Copyright: 2017 Oliver Nightingale
License: MIT

Files: packages/tools/lib/copy-and-watch/index.js
Copyright: 2017 Aleksandr Zonov
License: MIT

Files: packages/tools/lib/postcss-combine-duplicated-selectors/index.js
Copyright: 2016 Christian Murphy
License: MIT
2 changes: 1 addition & 1 deletion packages/base/hash.txt
Original file line number Diff line number Diff line change
@@ -1 +1 @@
X8vjgfCUlDRvJz9L9e5OzLqCCdQ=
owW4JG1/w/h6BH4GK+Akd5v6xzc=
2 changes: 1 addition & 1 deletion packages/theming/config/postcss.themes/postcss.config.js
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
const combineSelectors = require('postcss-combine-duplicated-selectors');
const combineSelectors = require('@ui5/webcomponents-tools/lib/postcss-combine-duplicated-selectors/index.js');
const postcssImport = require('postcss-import');
const cssnano = require('cssnano');
const postcssCSStoJSON = require('@ui5/webcomponents-tools/lib/postcss-css-to-json/index.js');
Expand Down
1 change: 0 additions & 1 deletion packages/theming/package.json
Original file line number Diff line number Diff line change
Expand Up @@ -40,7 +40,6 @@
"json-beautify": "^1.1.1",
"nps": "^5.10.0",
"postcss": "^8.4.5",
"postcss-combine-duplicated-selectors": "^10.0.3",
"postcss-import": "^14.0.2",
"resolve": "^1.20.0"
},
Expand Down
2 changes: 1 addition & 1 deletion packages/tools/components-package/postcss.themes.js
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
const postcssImport = require('postcss-import');
const combineSelectors = require('postcss-combine-duplicated-selectors');
const combineSelectors = require('../lib/postcss-combine-duplicated-selectors/index.js');
const postcssCSStoJSON = require('../lib/postcss-css-to-json/index.js');
const postcssCSStoESM = require('../lib/postcss-css-to-esm/index.js');
const cssnano = require('cssnano');
Expand Down
24 changes: 24 additions & 0 deletions packages/tools/lib/copy-and-watch/index.js
Original file line number Diff line number Diff line change
@@ -1,3 +1,27 @@
/*
MIT License
Copyright (c) 2017
Permission is hereby granted, free of charge, to any person obtaining a copy
of this software and associated documentation files (the "Software"), to deal
in the Software without restriction, including without limitation the rights
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
copies of the Software, and to permit persons to whom the Software is
furnished to do so, subject to the following conditions:
The above copyright notice and this permission notice shall be included in all
copies or substantial portions of the Software.
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
SOFTWARE.
*/

const fs = require('fs');
const path = require('path');
const chokidar = require('chokidar');
Expand Down
178 changes: 178 additions & 0 deletions packages/tools/lib/postcss-combine-duplicated-selectors/index.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,178 @@
/*
The MIT License (MIT)
Copyright (c) 2016 Christian Murphy
Permission is hereby granted, free of charge, to any person obtaining a copy
of this software and associated documentation files (the "Software"), to deal
in the Software without restriction, including without limitation the rights
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
copies of the Software, and to permit persons to whom the Software is
furnished to do so, subject to the following conditions:
The above copyright notice and this permission notice shall be included in all
copies or substantial portions of the Software.
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
SOFTWARE.
*/

const parser = require('postcss-selector-parser');
const name = "postcss-combine-duplicated-selectors";

/**
* Ensure that attributes with different quotes match.
* @param {Object} selector - postcss selector node
*/
function normalizeAttributes(selector) {
selector.walkAttributes((node) => {
if (node.value) {
// remove quotes
node.value = node.value.replace(/'|\\'|"|\\"/g, '');
}
});
}

/**
* Sort class and id groups alphabetically
* @param {Object} selector - postcss selector node
*/
function sortGroups(selector) {
selector.each((subSelector) => {
subSelector.nodes.sort((a, b) => {
// different types cannot be sorted
if (a.type !== b.type) {
return 0;
}

// sort alphabetically
return a.value < b.value ? -1 : 1;
});
});

selector.sort((a, b) => (a.nodes.join('') < b.nodes.join('') ? -1 : 1));
}

/**
* Remove duplicated properties
* @param {Object} selector - postcss selector node
* @param {Boolean} exact
*/
function removeDupProperties(selector, exact) {
if (!exact) { // Remove duplicated properties, regardless of value
const retainedProps = new Set();

for (let actIndex = selector.nodes.length - 1; actIndex >= 1; actIndex--) {
const prop = selector.nodes[actIndex].prop;
if (prop !== undefined) {
if (!retainedProps.has(prop)) {
retainedProps.add(prop); // Mark the prop as retained, all other occurrences must be removed
} else {
selector.nodes[actIndex].remove(); // This occurrence of the prop must be removed
}
}
}
} else {
// Remove duplicated properties from bottom to top ()
for (let actIndex = selector.nodes.length - 1; actIndex >= 1; actIndex--) {
for (let befIndex = actIndex - 1; befIndex >= 0; befIndex--) {
if (
selector.nodes[actIndex].prop === selector.nodes[befIndex].prop &&
selector.nodes[actIndex].value === selector.nodes[befIndex].value
) {
selector.nodes[befIndex].remove();
actIndex--;
}
}
}
}
}

const uniformStyle = parser((selector) => {
normalizeAttributes(selector);
sortGroups(selector);
});

const defaultOptions = {
removeDuplicatedProperties: false,
};

module.exports = (options) => {
options = Object.assign({}, defaultOptions, options);
return {
postcssPlugin: name,
prepare() {
// Create a map to store maps
const mapTable = new Map();
// root map to store root selectors
mapTable.set('root', new Map());

return {
Rule: (rule) => {
let map;
// Check selector parent for any at rule
if (rule.parent.type === 'atrule') {
// Use name and query params as the key
const query =
rule.parent.name.toLowerCase() +
rule.parent.params.replace(/\s+/g, '');

// See if this query key is already in the map table
map = mapTable.has(query) ? // If it is use it
mapTable.get(query) : // if not set it and get it
mapTable.set(query, new Map()).get(query);
} else {
// Otherwise we are dealing with a selector in the root
map = mapTable.get('root');
}

// create a uniform selector
const selector = uniformStyle.processSync(rule.selector, {
lossless: false,
});

if (map.has(selector)) {
// store original rule as destination
const destination = map.get(selector);

// check if node has already been processed
if (destination === rule) return;

// move declarations to original rule
while (rule.nodes.length > 0) {
destination.append(rule.nodes[0]);
}
// remove duplicated rule
rule.remove();

if (
options.removeDuplicatedProperties ||
options.removeDuplicatedValues
) {
removeDupProperties(
destination,
options.removeDuplicatedValues,
);
}
} else {
if (
options.removeDuplicatedProperties ||
options.removeDuplicatedValues
) {
removeDupProperties(rule, options.removeDuplicatedValues);
}
// add new selector to symbol table
map.set(selector, rule);
}
},
};
},
};
};

module.exports.postcss = true;
2 changes: 1 addition & 1 deletion packages/tools/package.json
Original file line number Diff line number Diff line change
Expand Up @@ -56,8 +56,8 @@
"nps": "^5.10.0",
"postcss": "^8.4.5",
"postcss-cli": "^9.1.0",
"postcss-combine-duplicated-selectors": "^10.0.3",
"postcss-import": "^14.0.2",
"postcss-selector-parser": "^6.0.10",
"properties-reader": "^2.2.0",
"recursive-readdir": "^2.2.2",
"resolve": "^1.20.0",
Expand Down
17 changes: 9 additions & 8 deletions yarn.lock
Original file line number Diff line number Diff line change
Expand Up @@ -5611,13 +5611,6 @@ postcss-colormin@^4.0.3:
postcss "^7.0.0"
postcss-value-parser "^3.0.0"

postcss-combine-duplicated-selectors@^10.0.3:
version "10.0.3"
resolved "https://registry.yarnpkg.com/postcss-combine-duplicated-selectors/-/postcss-combine-duplicated-selectors-10.0.3.tgz#71e8b6783e99cd560cf08ba7b896ad0db318c11c"
integrity sha512-IP0BmwFloCskv7DV7xqvzDXqMHpwdczJa6ZvIW8abgHdcIHs9mCJX2ltFhu3EwA51ozp13DByng30+Ke+eIExA==
dependencies:
postcss-selector-parser "^6.0.4"

postcss-convert-values@^4.0.1:
version "4.0.1"
resolved "https://registry.yarnpkg.com/postcss-convert-values/-/postcss-convert-values-4.0.1.tgz#ca3813ed4da0f812f9d43703584e449ebe189a7f"
Expand Down Expand Up @@ -5860,7 +5853,15 @@ postcss-selector-parser@^3.0.0:
indexes-of "^1.0.1"
uniq "^1.0.1"

postcss-selector-parser@^6.0.2, postcss-selector-parser@^6.0.4:
postcss-selector-parser@^6.0.10:
version "6.0.10"
resolved "https://registry.yarnpkg.com/postcss-selector-parser/-/postcss-selector-parser-6.0.10.tgz#79b61e2c0d1bfc2602d549e11d0876256f8df88d"
integrity sha512-IQ7TZdoaqbT+LCpShg46jnZVlhWD2w6iQYAcYXfHARZ7X1t/UGhhceQDs5X0cGqKvYlHNOuv7Oa1xmb0oQuA3w==
dependencies:
cssesc "^3.0.0"
util-deprecate "^1.0.2"

postcss-selector-parser@^6.0.2:
version "6.0.9"
resolved "https://registry.yarnpkg.com/postcss-selector-parser/-/postcss-selector-parser-6.0.9.tgz#ee71c3b9ff63d9cd130838876c13a2ec1a992b2f"
integrity sha512-UO3SgnZOVTwu4kyLR22UQ1xZh086RyNZppb7lLAKBFK8a32ttG5i87Y/P3+2bRSjZNyJ1B7hfFNo273tKe9YxQ==
Expand Down

0 comments on commit c29e91f

Please sign in to comment.