From 3c80fef152f5baa2ecc47a50dce051c1c453a52f Mon Sep 17 00:00:00 2001
From: Ollie Curtis <8831547+olliecurtis@users.noreply.github.com>
Date: Thu, 26 Oct 2023 15:38:15 +0100
Subject: [PATCH] [ARGG-799]: Migrates from bpk-tokens to bpk-foundations-web
(#85)
* [ARGG-799]: Migrates from bpk-tokens to bpk-foundations-web
* Remove console log
---
README.md | 3 +-
package-lock.json | 89 +++--
package.json | 2 +-
src/rules/use-components/use-components.js | 12 +-
.../use-components/use-components.test.js | 111 ------
.../use-components/use-native-components.js | 129 -------
src/rules/use-tokens/use-tokens.js | 126 ++-----
src/rules/use-tokens/use-tokens.test.js | 356 +++++-------------
8 files changed, 180 insertions(+), 648 deletions(-)
delete mode 100644 src/rules/use-components/use-native-components.js
diff --git a/README.md b/README.md
index 7bca62c..facdc7e 100644
--- a/README.md
+++ b/README.md
@@ -60,8 +60,7 @@ Available for colours and length values. Will prevent the use of a hardcoded col
"autoImport": true,
"platform": "web",
"tokensPackage": {
- "web": "bpk-tokens/tokens/base.es6",
- "native": "bpk-tokens/tokens/base.react.native",
+ "web": "@skyscanner/bpk-foundations-web/tokens/base.es6",
},
}]
}
diff --git a/package-lock.json b/package-lock.json
index b6cae9e..76d1c69 100644
--- a/package-lock.json
+++ b/package-lock.json
@@ -9,7 +9,7 @@
"version": "5.0.0",
"license": "Apache-2.0",
"dependencies": {
- "bpk-tokens": "^36.0.0",
+ "@skyscanner/bpk-foundations-web": "^17.3.0",
"lodash": "^4.17.21",
"tinycolor2": "^1.6.0"
},
@@ -619,6 +619,23 @@
"node": ">= 8"
}
},
+ "node_modules/@skyscanner/bpk-foundations-common": {
+ "version": "6.5.0",
+ "resolved": "https://registry.npmjs.org/@skyscanner/bpk-foundations-common/-/bpk-foundations-common-6.5.0.tgz",
+ "integrity": "sha512-nOk8DspPlbcAtswcQFzwaS8eg55ObJIY/pHl6ZCS3JaCZliTdEp4hJFl1Bb841z7TyMx+JwBOjIwvAN3x7lquw==",
+ "dependencies": {
+ "color": "^3.0.0"
+ }
+ },
+ "node_modules/@skyscanner/bpk-foundations-web": {
+ "version": "17.4.0",
+ "resolved": "https://registry.npmjs.org/@skyscanner/bpk-foundations-web/-/bpk-foundations-web-17.4.0.tgz",
+ "integrity": "sha512-JA8SE0Bzw4XnPx7PC5qvOiy49gswg7nSA3T6FfjR4AGXNME9fbEI6Ii5JM/IjcU2aJySt0iJQiN26/HsowZguw==",
+ "dependencies": {
+ "@skyscanner/bpk-foundations-common": "^6.5.0",
+ "color": "^3.0.0"
+ }
+ },
"node_modules/@ungap/structured-clone": {
"version": "1.2.0",
"resolved": "https://registry.npmjs.org/@ungap/structured-clone/-/structured-clone-1.2.0.tgz",
@@ -720,15 +737,6 @@
"node": ">=8"
}
},
- "node_modules/bpk-tokens": {
- "version": "36.0.0",
- "resolved": "https://registry.npmjs.org/bpk-tokens/-/bpk-tokens-36.0.0.tgz",
- "integrity": "sha512-gNir+QiHb4zYLrYMUH6xoYl34ZvRevigsCorHC3OdwhERV7qkROrf5SmeeWXuoXjFUv03Bz7tWYmNfW1FePaOQ==",
- "deprecated": "This package has now been deprecated and no longer supported as we move to foundations. Please install the platform specific token package as per the advice from https://github.com/Skyscanner/backpack-foundations\\#bpk-androidiosreact-nativeweb",
- "dependencies": {
- "color": "^3.0.0"
- }
- },
"node_modules/brace-expansion": {
"version": "1.1.11",
"resolved": "https://registry.npmjs.org/brace-expansion/-/brace-expansion-1.1.11.tgz",
@@ -883,12 +891,12 @@
}
},
"node_modules/color": {
- "version": "3.1.3",
- "resolved": "https://registry.npmjs.org/color/-/color-3.1.3.tgz",
- "integrity": "sha512-xgXAcTHa2HeFCGLE9Xs/R82hujGtu9Jd9x4NW3T34+OMs7VoPsjwzRczKHvTAHeJwWFwX5j15+MgAppE8ztObQ==",
+ "version": "3.2.1",
+ "resolved": "https://registry.npmjs.org/color/-/color-3.2.1.tgz",
+ "integrity": "sha512-aBl7dZI9ENN6fUGC7mWpMTPNHmWUSNan9tuWN6ahh5ZLNk9baLJOnSMlrQkHcrfFgz2/RigjUVAjdx36VcemKA==",
"dependencies": {
- "color-convert": "^1.9.1",
- "color-string": "^1.5.4"
+ "color-convert": "^1.9.3",
+ "color-string": "^1.6.0"
}
},
"node_modules/color-convert": {
@@ -905,9 +913,9 @@
"integrity": "sha1-p9BVi9icQveV3UIyj3QIMcpTvCU="
},
"node_modules/color-string": {
- "version": "1.5.4",
- "resolved": "https://registry.npmjs.org/color-string/-/color-string-1.5.4.tgz",
- "integrity": "sha512-57yF5yt8Xa3czSEW1jfQDE79Idk0+AkN/4KWad6tbdxUmAs3MvjxlWSWD4deYytcRfoZ9nhKyFl1kj5tBvidbw==",
+ "version": "1.9.1",
+ "resolved": "https://registry.npmjs.org/color-string/-/color-string-1.9.1.tgz",
+ "integrity": "sha512-shrVawQFojnZv6xM40anx4CkoDP+fZsw/ZerEMsW/pyzsRbElpsL/DBVW7q3ExxwusdNXI3lXpuhEZkzs8p5Eg==",
"dependencies": {
"color-name": "^1.0.0",
"simple-swizzle": "^0.2.2"
@@ -2438,7 +2446,7 @@
"node_modules/simple-swizzle": {
"version": "0.2.2",
"resolved": "https://registry.npmjs.org/simple-swizzle/-/simple-swizzle-0.2.2.tgz",
- "integrity": "sha1-pNprY1/8zMoz9w0Xy5JZLeleVXo=",
+ "integrity": "sha512-JA//kQgZtbuY83m+xT+tXJkmJncGMTFT+C+g2h2R9uxkYIrE2yy9sgmcLhCnw57/WSD+Eh3J97FPEDFnbXnDUg==",
"dependencies": {
"is-arrayish": "^0.3.1"
}
@@ -3157,6 +3165,23 @@
"fastq": "^1.6.0"
}
},
+ "@skyscanner/bpk-foundations-common": {
+ "version": "6.5.0",
+ "resolved": "https://registry.npmjs.org/@skyscanner/bpk-foundations-common/-/bpk-foundations-common-6.5.0.tgz",
+ "integrity": "sha512-nOk8DspPlbcAtswcQFzwaS8eg55ObJIY/pHl6ZCS3JaCZliTdEp4hJFl1Bb841z7TyMx+JwBOjIwvAN3x7lquw==",
+ "requires": {
+ "color": "^3.0.0"
+ }
+ },
+ "@skyscanner/bpk-foundations-web": {
+ "version": "17.4.0",
+ "resolved": "https://registry.npmjs.org/@skyscanner/bpk-foundations-web/-/bpk-foundations-web-17.4.0.tgz",
+ "integrity": "sha512-JA8SE0Bzw4XnPx7PC5qvOiy49gswg7nSA3T6FfjR4AGXNME9fbEI6Ii5JM/IjcU2aJySt0iJQiN26/HsowZguw==",
+ "requires": {
+ "@skyscanner/bpk-foundations-common": "^6.5.0",
+ "color": "^3.0.0"
+ }
+ },
"@ungap/structured-clone": {
"version": "1.2.0",
"resolved": "https://registry.npmjs.org/@ungap/structured-clone/-/structured-clone-1.2.0.tgz",
@@ -3231,14 +3256,6 @@
"integrity": "sha512-jDctJ/IVQbZoJykoeHbhXpOlNBqGNcwXJKJog42E5HDPUwQTSdjCHdihjj0DlnheQ7blbT6dHOafNAiS8ooQKA==",
"dev": true
},
- "bpk-tokens": {
- "version": "36.0.0",
- "resolved": "https://registry.npmjs.org/bpk-tokens/-/bpk-tokens-36.0.0.tgz",
- "integrity": "sha512-gNir+QiHb4zYLrYMUH6xoYl34ZvRevigsCorHC3OdwhERV7qkROrf5SmeeWXuoXjFUv03Bz7tWYmNfW1FePaOQ==",
- "requires": {
- "color": "^3.0.0"
- }
- },
"brace-expansion": {
"version": "1.1.11",
"resolved": "https://registry.npmjs.org/brace-expansion/-/brace-expansion-1.1.11.tgz",
@@ -3333,12 +3350,12 @@
}
},
"color": {
- "version": "3.1.3",
- "resolved": "https://registry.npmjs.org/color/-/color-3.1.3.tgz",
- "integrity": "sha512-xgXAcTHa2HeFCGLE9Xs/R82hujGtu9Jd9x4NW3T34+OMs7VoPsjwzRczKHvTAHeJwWFwX5j15+MgAppE8ztObQ==",
+ "version": "3.2.1",
+ "resolved": "https://registry.npmjs.org/color/-/color-3.2.1.tgz",
+ "integrity": "sha512-aBl7dZI9ENN6fUGC7mWpMTPNHmWUSNan9tuWN6ahh5ZLNk9baLJOnSMlrQkHcrfFgz2/RigjUVAjdx36VcemKA==",
"requires": {
- "color-convert": "^1.9.1",
- "color-string": "^1.5.4"
+ "color-convert": "^1.9.3",
+ "color-string": "^1.6.0"
}
},
"color-convert": {
@@ -3355,9 +3372,9 @@
"integrity": "sha1-p9BVi9icQveV3UIyj3QIMcpTvCU="
},
"color-string": {
- "version": "1.5.4",
- "resolved": "https://registry.npmjs.org/color-string/-/color-string-1.5.4.tgz",
- "integrity": "sha512-57yF5yt8Xa3czSEW1jfQDE79Idk0+AkN/4KWad6tbdxUmAs3MvjxlWSWD4deYytcRfoZ9nhKyFl1kj5tBvidbw==",
+ "version": "1.9.1",
+ "resolved": "https://registry.npmjs.org/color-string/-/color-string-1.9.1.tgz",
+ "integrity": "sha512-shrVawQFojnZv6xM40anx4CkoDP+fZsw/ZerEMsW/pyzsRbElpsL/DBVW7q3ExxwusdNXI3lXpuhEZkzs8p5Eg==",
"requires": {
"color-name": "^1.0.0",
"simple-swizzle": "^0.2.2"
@@ -4457,7 +4474,7 @@
"simple-swizzle": {
"version": "0.2.2",
"resolved": "https://registry.npmjs.org/simple-swizzle/-/simple-swizzle-0.2.2.tgz",
- "integrity": "sha1-pNprY1/8zMoz9w0Xy5JZLeleVXo=",
+ "integrity": "sha512-JA//kQgZtbuY83m+xT+tXJkmJncGMTFT+C+g2h2R9uxkYIrE2yy9sgmcLhCnw57/WSD+Eh3J97FPEDFnbXnDUg==",
"requires": {
"is-arrayish": "^0.3.1"
}
diff --git a/package.json b/package.json
index cc361a6..66ed23e 100644
--- a/package.json
+++ b/package.json
@@ -26,7 +26,7 @@
},
"license": "Apache-2.0",
"dependencies": {
- "bpk-tokens": "^36.0.0",
+ "@skyscanner/bpk-foundations-web": "^17.3.0",
"lodash": "^4.17.21",
"tinycolor2": "^1.6.0"
},
diff --git a/src/rules/use-components/use-components.js b/src/rules/use-components/use-components.js
index 5616643..3c8e169 100644
--- a/src/rules/use-components/use-components.js
+++ b/src/rules/use-components/use-components.js
@@ -17,19 +17,9 @@
const merge = require('lodash/merge');
const useWebComponents = require('./use-web-components');
-const useNativeComponents = require('./use-native-components');
-
-const BASE_CONFIG = {
- autoImport: true,
- platform: 'web',
-};
const createConfigForPlatform = (report, options) => {
- const config = merge({}, BASE_CONFIG, options[0]);
- if (config.platform === 'web') {
- return useWebComponents(report, options);
- }
- return useNativeComponents(report, options);
+ return useWebComponents(report, options);
};
module.exports = {
diff --git a/src/rules/use-components/use-components.test.js b/src/rules/use-components/use-components.test.js
index fb335d3..57310b6 100644
--- a/src/rules/use-components/use-components.test.js
+++ b/src/rules/use-components/use-components.test.js
@@ -20,8 +20,6 @@ const { RuleTester } = require('eslint');
const useComponents = require('./use-components');
-const BPK_PATH = 'backpack-react-native/';
-
const ruleTester = new RuleTester({
parserOptions: {
ecmaVersion: 2015,
@@ -30,115 +28,6 @@ const ruleTester = new RuleTester({
},
});
-/* platform: 'native' tests. */
-[
- ['ActivityIndicator', 'BpkSpinner', 'bpk-component-spinner'],
- ['Alert', 'BpkAlert', 'bpk-component-alert'],
- ['Button', 'BpkButton', 'bpk-component-button'],
- ['FlatList', 'BpkFlatList', 'bpk-component-flat-list'],
- ['Image', 'BpkImage', 'bpk-component-image'],
- ['Picker', 'BpkPicker', 'bpk-component-picker'],
- ['SectionList', 'BpkSectionList', 'bpk-component-section-list'],
- ['Switch', 'BpkSwitch', 'bpk-component-switch'],
- ['Text', 'BpkText', 'bpk-component-text'],
- ['TextInput', 'BpkTextInput', 'bpk-component-text-input'],
- [
- 'TouchableHighlight',
- 'BpkTouchableOverlay',
- 'bpk-component-touchable-overlay',
- ],
- [
- 'TouchableNativeFeedback',
- 'BpkTouchableNativeFeedback',
- 'bpk-component-touchable-native-feedback',
- ],
-].forEach(([Component, Substitute, pkg]) => {
- const pkgPath = BPK_PATH + pkg;
-
- ruleTester.run(`use-components (native) - ${Component}`, useComponents, {
- valid: [
- `<${Substitute}>I'm allowed${Substitute}>`,
- `
I'm allowed
`,
- `React.createElement(SomeElement, null)`,
- `React.createElement("div", null)`,
- ],
- invalid: [
- {
- options: [{ platform: 'native' }],
- code: `React.createElement(${Component}, null, "I'm not allowed")`,
- output: `
-import ${Substitute} from '${pkgPath}';
-React.createElement(${Substitute}, null, "I'm not allowed")`,
- errors: [
- {
- message: `Use the following Backpack component instead: ${Substitute}`,
- },
- ],
- },
- {
- options: [{ platform: 'native' }],
- code: `create(${Component}, null, "I'm not allowed")`,
- output: `
-import ${Substitute} from '${pkgPath}';
-create(${Substitute}, null, "I'm not allowed")`,
- errors: [
- {
- message: `Use the following Backpack component instead: ${Substitute}`,
- },
- ],
- },
- {
- options: [{ platform: 'native' }],
- code: `<${Component}>I'm not allowed${Component}>`,
- output: `
-import ${Substitute} from '${pkgPath}';
-<${Substitute}>I'm not allowed${Substitute}>`,
- errors: [
- {
- message: `Use the following Backpack component instead: ${Substitute}`,
- },
- ],
- },
- {
- options: [{ platform: 'native' }],
- code: `<${Component} children="I'm not allowed" />`,
- output: `
-import ${Substitute} from '${pkgPath}';
-<${Substitute} children="I'm not allowed" />`,
- errors: [
- {
- message: `Use the following Backpack component instead: ${Substitute}`,
- },
- ],
- },
- {
- options: [{ autoImport: false, platform: 'native' }],
- code: `<${Component} children="I'm not allowed" />`,
- output: `<${Substitute} children="I'm not allowed" />`,
- errors: [
- {
- message: `Use the following Backpack component instead: ${Substitute}`,
- },
- ],
- },
- {
- options: [{ platform: 'native' }],
- code: `
-import ${Substitute} from '${pkgPath}';
-<${Component} children="I'm not allowed" />`,
- output: `
-import ${Substitute} from '${pkgPath}';
-<${Substitute} children="I'm not allowed" />`,
- errors: [
- {
- message: `Use the following Backpack component instead: ${Substitute}`,
- },
- ],
- },
- ],
- });
-});
-
/* platform: 'web' tests */
const createImportStatement = (Substitute, useDefaultImport, pkgPath) =>
`import ${
diff --git a/src/rules/use-components/use-native-components.js b/src/rules/use-components/use-native-components.js
deleted file mode 100644
index 57684ac..0000000
--- a/src/rules/use-components/use-native-components.js
+++ /dev/null
@@ -1,129 +0,0 @@
-/*
- * Backpack - Skyscanner's Design System
- *
- * Copyright 2018-present Skyscanner Ltd
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-const merge = require('lodash/merge');
-
-const { addImport, getImportDefinition } = require('../../auto-import');
-
-const BPK_PATH = 'backpack-react-native/';
-
-const BPK_SUBSTITUTES = {
- ActivityIndicator: 'BpkSpinner',
- Alert: 'BpkAlert',
- Button: 'BpkButton',
- FlatList: 'BpkFlatList',
- Image: 'BpkImage',
- Picker: 'BpkPicker',
- SectionList: 'BpkSectionList',
- Switch: 'BpkSwitch',
- Text: 'BpkText',
- TextInput: 'BpkTextInput',
- TouchableHighlight: 'BpkTouchableOverlay',
- TouchableNativeFeedback: 'BpkTouchableNativeFeedback',
-};
-
-const PACKAGES = {
- BpkSpinner: 'bpk-component-spinner',
- BpkAlert: 'bpk-component-alert',
- BpkButton: 'bpk-component-button',
- BpkFlatList: 'bpk-component-flat-list',
- BpkImage: 'bpk-component-image',
- BpkPicker: 'bpk-component-picker',
- BpkSectionList: 'bpk-component-section-list',
- BpkSwitch: 'bpk-component-switch',
- BpkText: 'bpk-component-text',
- BpkTextInput: 'bpk-component-text-input',
- BpkTouchableOverlay: 'bpk-component-touchable-overlay',
- BpkTouchableNativeFeedback: 'bpk-component-touchable-native-feedback',
-};
-
-const BASE_CONFIG = {
- autoImport: true,
-};
-
-const ruleMessage = bpkComponent =>
- `Use the following Backpack component instead: ${bpkComponent}`;
-
-const fixAndMaybeImport = (fixer, options, node, identifier, fixes) => {
- const config = merge({}, BASE_CONFIG, options);
- const packageName = BPK_PATH + PACKAGES[identifier];
-
- if (!config.autoImport) {
- return fixes;
- }
-
- const importDef = getImportDefinition(node, identifier, {
- packageName,
- style: 'default',
- });
-
- if (importDef.isImported) {
- return fixes;
- }
-
- return [addImport(fixer, importDef)].concat(fixes);
-};
-
-module.exports = (report, options) => ({
- CallExpression: node => {
- const { arguments: args } = node;
-
- if (args.length >= 1 && args[0].type === 'Identifier') {
- const bpkSubstitute = BPK_SUBSTITUTES[args[0].name];
- if (!bpkSubstitute) {
- return;
- }
-
- report({
- node: args[0],
- message: ruleMessage(bpkSubstitute),
- fix: fixer =>
- fixAndMaybeImport(
- fixer,
- options[0],
- node,
- bpkSubstitute,
- fixer.replaceTextRange(
- [args[0].range[0], args[0].range[1]],
- bpkSubstitute,
- ),
- ),
- });
- }
- },
-
- JSXElement: node => {
- const { openingElement, closingElement } = node;
- const bpkSubstitute = BPK_SUBSTITUTES[openingElement.name.name];
- if (!bpkSubstitute) {
- return;
- }
-
- report({
- node: openingElement,
- message: ruleMessage(bpkSubstitute),
- fix(fixer) {
- const fixIt = toFix => fixer.replaceText(toFix.name, bpkSubstitute);
- const fixes = openingElement.selfClosing
- ? fixIt(openingElement)
- : [fixIt(openingElement), fixIt(closingElement)];
-
- return fixAndMaybeImport(fixer, options[0], node, bpkSubstitute, fixes);
- },
- });
- },
-});
diff --git a/src/rules/use-tokens/use-tokens.js b/src/rules/use-tokens/use-tokens.js
index b1d1f2e..4cbe3b7 100644
--- a/src/rules/use-tokens/use-tokens.js
+++ b/src/rules/use-tokens/use-tokens.js
@@ -17,24 +17,13 @@
const _ = require('lodash');
const tinycolor = require('tinycolor2');
-const { props: WEB_TOKENS } = require('bpk-tokens/tokens/base.raw.json');
-const { props: IOS_TOKENS } = require('bpk-tokens/tokens/base.raw.ios.json');
const {
- props: ANDROID_TOKENS,
-} = require('bpk-tokens/tokens/base.raw.android.json');
+ props: WEB_TOKENS,
+} = require('@skyscanner/bpk-foundations-web/tokens/base.raw.json');
const { addImport, getImportDefinition } = require('../../auto-import');
-const BASE_CONFIG = {
- autoImport: true,
- platform: 'web',
- tokensPackage: {
- web: 'bpk-tokens/tokens/base.es6',
- native: 'bpk-tokens/tokens/base.react.native',
- },
-};
-
-const COLOR_WHITELIST = ['transparent', null, undefined];
+const COLOR_ALLOWLIST = ['transparent', null, undefined];
const COLOR_PROPS = ['color', 'backgroundColor'];
const RADII_PROPS = [
@@ -59,44 +48,7 @@ const BORDER_PROPS = [
'borderWidth',
];
-const SPACING_PROPS = [
- 'bottom',
- 'end',
- 'height',
- 'left',
- 'margin',
- 'marginBottom',
- 'marginEnd',
- 'marginHorizontal',
- 'marginLeft',
- 'marginRight',
- 'marginStart',
- 'marginTop',
- 'marginVertical',
- 'maxHeight',
- 'maxWidth',
- 'minHeight',
- 'minWidth',
- 'padding',
- 'paddingBottom',
- 'paddingEnd',
- 'paddingHorizontal',
- 'paddingLeft',
- 'paddingRight',
- 'paddingStart',
- 'paddingTop',
- 'paddingVertical',
- 'right',
- 'start',
- 'top',
- 'width',
-];
-
-const TOKENS = _.merge(
- _.mapKeys(WEB_TOKENS, (value, key) => `WEB_${key}`),
- _.mapKeys(IOS_TOKENS, (value, key) => `IOS_${key}`),
- _.mapKeys(ANDROID_TOKENS, (value, key) => `ANDROID_${key}`),
-);
+const TOKENS = _.merge(_.mapKeys(WEB_TOKENS, (value, key) => `WEB_${key}`));
const tokensByCategory = category =>
_.chain(TOKENS)
@@ -107,56 +59,49 @@ const tokensByCategory = category =>
}))
.value();
-const COLORS = tokensByCategory('colors');
-const SPACING_NAMES = new Set(tokensByCategory('spacings').map(x => x.name));
+const tokensByType = type =>
+ _.chain(TOKENS)
+ .filter({ type: type })
+ .map(({ name, value, deprecated }) => ({
+ name: _.camelCase(name),
+ value,
+ deprecated,
+ }))
+ .value();
+
+const COLORS = tokensByType('color').filter(function(el) {
+ return el.deprecated !== true;
+});
+
const RADII_NAMES = new Set(tokensByCategory('radii').map(x => x.name));
const BORDER_NAMES = new Set(tokensByCategory('borders').map(x => x.name));
const checkColor = (node, context) => {
const { key, value } = node;
const isColor = COLOR_PROPS.includes(key.name) && value.type === 'Literal';
-
- if (!isColor) {
+ const allowedColor = COLOR_ALLOWLIST.filter(c => value.value === c).length;
+ // We check if the colour is in the allowlist, or if it's a valid Backpack token
+ if (!isColor || allowedColor) {
return;
}
const color = tinycolor(value.value);
- const expectedToken = _.find(COLORS, { value: color.toRgbString() });
-
- if (expectedToken) {
+ const matchedTokens = _.filter(COLORS, { value: color.toRgbString() });
+ if (matchedTokens.length > 1) {
context.report({
node,
- message: `Use the following Backpack token instead: ${expectedToken.name}`,
- fix: fixer => {
- const { options: userOptions } = context;
- const options = _.merge({}, BASE_CONFIG, userOptions[0] || {});
- const tokensPkg = options.tokensPackage[options.platform];
-
- if (!options.autoImport) {
- return fixer.replaceText(value, expectedToken.name);
- }
-
- const importDefinition = getImportDefinition(node, expectedToken.name, {
- packageName: tokensPkg,
- style: 'named',
- });
-
- if (importDefinition.isImported) {
- return fixer.replaceText(value, expectedToken.name);
- }
-
- return [
- addImport(fixer, importDefinition),
- fixer.replaceText(value, expectedToken.name),
- ];
- },
+ message: `Multiple colors matched for colour, refer to to https://www.skyscanner.design/latest/foundations/colours/usage-LJ0uHGQL for the right semantic token`,
+ });
+ } else if (matchedTokens.length === 0) {
+ context.report({
+ node,
+ message: `Unknown color detected not in our brand, refer to to https://www.skyscanner.design/latest/foundations/colours/usage-LJ0uHGQL for the right semantic token`,
});
} else {
- if (COLOR_WHITELIST.filter(c => value.value === c).length) return;
context.report({
node,
- message: `Unknown color, use a Backpack token instead`,
+ message: `Use the following Backpack token instead: ${matchedTokens[0].name}`,
});
}
};
@@ -170,9 +115,7 @@ const isLiteralNumber = node =>
*/
const isLengthIdentifier = node =>
node.type === 'Identifier' &&
- (SPACING_NAMES.has(node.name) ||
- RADII_NAMES.has(node.name) ||
- BORDER_NAMES.has(node.name));
+ (RADII_NAMES.has(node.name) || BORDER_NAMES.has(node.name));
/*
* Ensures that a complex expression i.e. not a literal is a
@@ -242,9 +185,7 @@ const isValidComplexLengthExpression = node => {
const checkLengths = (node, context) => {
const { key, value } = node;
const isLength =
- SPACING_PROPS.includes(key.name) ||
- RADII_PROPS.includes(key.name) ||
- BORDER_PROPS.includes(key.name);
+ RADII_PROPS.includes(key.name) || BORDER_PROPS.includes(key.name);
if (!isLength) {
return;
@@ -291,9 +232,6 @@ module.exports = {
web: {
type: 'string',
},
- native: {
- type: 'string',
- },
},
additionalProperties: false,
},
diff --git a/src/rules/use-tokens/use-tokens.test.js b/src/rules/use-tokens/use-tokens.test.js
index 6477408..421d36a 100644
--- a/src/rules/use-tokens/use-tokens.test.js
+++ b/src/rules/use-tokens/use-tokens.test.js
@@ -27,271 +27,143 @@ const ruleTester = new RuleTester({
ruleTester.run('use-tokens', useTokens, {
valid: [
`const styles = StyleSheet.create({
- foo: {
- color: colorWhite,
- },
- });`,
- `const styles = StyleSheet.create({
- foo: {
- color: colorSkyBlue,
- },
- });`,
- `const styles = StyleSheet.create({
- foo: {
- backgroundColor: colorWhite,
- },
- });`,
- `const styles = StyleSheet.create({
- foo: {
- backgroundColor: 'transparent',
- },
- });`,
- `const styles = StyleSheet.create({
- foo: {
- backgroundColor: null,
- },
- });`,
- `const styles = StyleSheet.create({
- foo: {
- backgroundColor: undefined,
- },
- });`,
- `const styles = StyleSheet.create({
- foo: {
- marginLeft: spacingSm,
- },
- });`,
- `const styles = StyleSheet.create({
- foo: {
- borderBottomStartRadius: spacingSm,
- },
- });`,
- `const styles = StyleSheet.create({
- foo: {
- borderBottomStartRadius: 0,
- },
- });`,
- `const styles = StyleSheet.create({
- foo: {
- marginLeft: spacingSm * 4,
- },
- });`,
- `const styles = StyleSheet.create({
- foo: {
- marginLeft: spacingSm * 5 * 3,
- },
- });`,
- `const styles = StyleSheet.create({
- foo: {
- marginLeft: (spacingSm * 5) * spacingBase,
- },
- });`,
- `const styles = StyleSheet.create({
- foo: {
- marginLeft: bar * 5,
- },
- });`,
- `const styles = StyleSheet.create({
- foo: {
- marginLeft: myMargin() * 5,
- },
- });`,
- `const styles = StyleSheet.create({
- foo: {
- marginLeft: spacingSm + spacingSm,
- },
- });`,
- `const styles = StyleSheet.create({
- foo: {
- paddingHorizontal: spacingMd - borderSizeSm,
- },
- });`,
- `const styles = StyleSheet.create({
- foo: {
- minHeight: spacingBase * 3,
- },
- });`,
- `const styles = StyleSheet.create({
- foo: {
- borderRadius: borderRadiusSm,
- },
- });`,
+ foo: {
+ color: canvasDay,
+ },
+ });`,
+ `const styles = StyleSheet.create({
+ foo: {
+ color: colorSkyBlue,
+ },
+ });`,
+ `const styles = StyleSheet.create({
+ foo: {
+ backgroundColor: canvasDay,
+ },
+ });`,
+ `const styles = StyleSheet.create({
+ foo: {
+ backgroundColor: 'transparent',
+ },
+ });`,
+ `const styles = StyleSheet.create({
+ foo: {
+ backgroundColor: null,
+ },
+ });`,
+ `const styles = StyleSheet.create({
+ foo: {
+ backgroundColor: undefined,
+ },
+ });`,
+ `const styles = StyleSheet.create({
+ foo: {
+ borderBottomStartRadius: 0,
+ },
+ });`,
+ `const styles = StyleSheet.create({
+ foo: {
+ marginLeft: bar * 5,
+ },
+ });`,
+ `const styles = StyleSheet.create({
+ foo: {
+ marginLeft: myMargin() * 5,
+ },
+ });`,
+ `const styles = StyleSheet.create({
+ foo: {
+ borderRadius: borderRadiusSm,
+ },
+ });`,
+ `const styles = StyleSheet.create({
+ foo: {
+ padding: 5,
+ },
+ });`,
],
invalid: [
{
code: `
-const styles = StyleSheet.create({
- foo: {
- color: '#ffffff',
- },
-});`,
- output: `
-import { colorWhite } from 'bpk-tokens/tokens/base.es6';
-
-const styles = StyleSheet.create({
- foo: {
- color: colorWhite,
- },
-});`,
- errors: [
- {
- message: 'Use the following Backpack token instead: colorWhite',
- },
- ],
- },
- {
- code: `
-const styles = StyleSheet.create({
- foo: {
- backgroundColor: '#ff00ff',
- color: '#ff00ff',
- },
-});`,
- errors: [
- {
- message: 'Unknown color, use a Backpack token instead',
- },
- {
- message: 'Unknown color, use a Backpack token instead',
- },
- ],
- },
-
- {
- code: `
-const styles = StyleSheet.create({
- foo: {
- backgroundColor: '#ffffff',
- },
-});`,
- output: `
-import { colorWhite } from 'bpk-tokens/tokens/base.es6';
-
-const styles = StyleSheet.create({
- foo: {
- backgroundColor: colorWhite,
- },
-});`,
+ const styles = StyleSheet.create({
+ foo: {
+ color: 'rgba(0, 0, 0, 0.8)',
+ },
+ });`,
errors: [
{
- message: 'Use the following Backpack token instead: colorWhite',
+ message:
+ 'Use the following Backpack token instead: privateMapMarkerViewedForegroundNight',
},
],
},
-
{
code: `
-const styles = StyleSheet.create({
- foo: {
- color: 'rgb(7, 112, 227)',
- },
-});`,
- output: `
-import { colorPrimaryGradientLight } from 'bpk-tokens/tokens/base.es6';
-
-const styles = StyleSheet.create({
- foo: {
- color: colorPrimaryGradientLight,
- },
-});`,
+ const styles = StyleSheet.create({
+ foo: {
+ color: '#ffffff',
+ },
+ });`,
errors: [
{
message:
- 'Use the following Backpack token instead: colorPrimaryGradientLight',
+ 'Multiple colors matched for colour, refer to to https://www.skyscanner.design/latest/foundations/colours/usage-LJ0uHGQL for the right semantic token',
},
],
},
-
{
- options: [{ autoImport: false }],
code: `
-const styles = StyleSheet.create({
- foo: {
- color: 'rgb(7, 112, 227)',
- },
-});`,
- output: `
-const styles = StyleSheet.create({
- foo: {
- color: colorPrimaryGradientLight,
- },
-});`,
+ const styles = StyleSheet.create({
+ foo: {
+ backgroundColor: '#ff00ff',
+ color: '#ff00ff',
+ },
+ });`,
errors: [
{
message:
- 'Use the following Backpack token instead: colorPrimaryGradientLight',
+ 'Unknown color detected not in our brand, refer to to https://www.skyscanner.design/latest/foundations/colours/usage-LJ0uHGQL for the right semantic token',
},
- ],
- },
-
- {
- options: [{ platform: 'native' }],
- code: `
-const styles = StyleSheet.create({
- foo: {
- color: 'rgb(7, 112, 227)',
- },
-});`,
- output: `
-import { colorPrimaryGradientLight } from 'bpk-tokens/tokens/base.react.native';
-
-const styles = StyleSheet.create({
- foo: {
- color: colorPrimaryGradientLight,
- },
-});`,
- errors: [
{
message:
- 'Use the following Backpack token instead: colorPrimaryGradientLight',
+ 'Unknown color detected not in our brand, refer to to https://www.skyscanner.design/latest/foundations/colours/usage-LJ0uHGQL for the right semantic token',
},
],
},
-
{
- options: [{ platform: 'native', tokensPackage: { native: './tokens' } }],
code: `
-const styles = StyleSheet.create({
- foo: {
- color: 'rgb(7, 112, 227)',
- },
-});`,
- output: `
-import { colorPrimaryGradientLight } from './tokens';
-
-const styles = StyleSheet.create({
- foo: {
- color: colorPrimaryGradientLight,
- },
-});`,
+ const styles = StyleSheet.create({
+ foo: {
+ backgroundColor: '#ffffff',
+ },
+ });`,
errors: [
{
message:
- 'Use the following Backpack token instead: colorPrimaryGradientLight',
+ 'Multiple colors matched for colour, refer to to https://www.skyscanner.design/latest/foundations/colours/usage-LJ0uHGQL for the right semantic token',
},
],
},
-
{
- code: `const styles = StyleSheet.create({
- foo: {
- marginLeft: 4,
- },
- });`,
+ code: `
+ const styles = StyleSheet.create({
+ foo: {
+ color: 'rgb(7, 112, 227)',
+ },
+ });`,
errors: [
{
message:
- "Don't use raw numbers for `marginLeft` instead use a Backpack token or multiples of a token",
+ 'Unknown color detected not in our brand, refer to to https://www.skyscanner.design/latest/foundations/colours/usage-LJ0uHGQL for the right semantic token',
},
],
},
-
{
code: `const styles = StyleSheet.create({
- foo: {
- borderBottomStartRadius: 4,
- },
- });`,
+ foo: {
+ borderBottomStartRadius: 4,
+ },
+ });`,
errors: [
{
message:
@@ -299,49 +171,6 @@ const styles = StyleSheet.create({
},
],
},
-
- {
- code: `const styles = StyleSheet.create({
- foo: {
- marginLeft: spacingSm * 4 + 4,
- },
- });`,
- errors: [
- {
- message:
- "Don't use raw numbers for `marginLeft` instead use a Backpack token or multiples of a token",
- },
- ],
- },
-
- {
- code: `const styles = StyleSheet.create({
- foo: {
- marginLeft: spacingSm * 4 + spacingBase + 2,
- },
- });`,
- errors: [
- {
- message:
- "Don't use raw numbers for `marginLeft` instead use a Backpack token or multiples of a token",
- },
- ],
- },
-
- {
- code: `const styles = StyleSheet.create({
- foo: {
- marginLeft: 5 * 4,
- },
- });`,
- errors: [
- {
- message:
- "Don't use raw numbers for `marginLeft` instead use a Backpack token or multiples of a token",
- },
- ],
- },
-
{
code: `const styles = StyleSheet.create({
foo: {
@@ -355,7 +184,6 @@ const styles = StyleSheet.create({
},
],
},
-
{
code: `const styles = StyleSheet.create({
foo: {