-
Notifications
You must be signed in to change notification settings - Fork 261
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
[ACS-5290] create eslint rule to ensure components use none value for…
… encapsulation (#8585) * ACS-5290 Create rule which prevent using different encapsulation in components than None * ACS-5290 Added documentation * ACS-5290 Updated scripts * ACS-5290 Updated documentation * ACS-5290 Added autofix * ACS-5290 Formated code * ACS-5290 Fixed lint - removed redundant comma * ACS-5290 Renaming * ACS-5290 Renaming
- Loading branch information
1 parent
959f20b
commit 86e9f3f
Showing
16 changed files
with
357 additions
and
8 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
22 changes: 22 additions & 0 deletions
22
docs/eslint-angular/rules/use-none-component-view-encapsulation.md
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,22 @@ | ||
--- | ||
Title: Use none component view encapsulation | ||
Added: v6.0.0 | ||
Status: Active | ||
Last reviewed: 2023-05-23 | ||
--- | ||
|
||
# [Use none component view encapsulation](../../../lib/eslint-angular/src/rules/use-none-component-view-encapsulation/use-none-component-view-encapsulation.ts "Defined in use-none-component-view-encapsulation.ts") | ||
|
||
Custom ESLint rule which check if component uses ViewEncapsulation.None. It has been implemented because None encapsulation makes themes styling easier. | ||
It also allows to autofix. | ||
|
||
## Basic Usage | ||
Put this rule in eslintrc.json in rules. | ||
|
||
```json | ||
{ | ||
"rules": { | ||
"@alfresco/eslint-angular/use-none-component-view-encapsulation": "error" | ||
} | ||
} | ||
``` |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,26 @@ | ||
/*! | ||
* @license | ||
* Copyright © 2005-2023 Hyland Software, Inc. and its affiliates. All rights reserved. | ||
* | ||
* 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. | ||
*/ | ||
|
||
import useNoneEncapsulationRule, { | ||
RULE_NAME as useNoneEncapsulationRuleName | ||
} from './src/rules/use-none-component-view-encapsulation/use-none-component-view-encapsulation'; | ||
|
||
export = { | ||
rules: { | ||
[useNoneEncapsulationRuleName]: useNoneEncapsulationRule | ||
} | ||
}; |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,8 @@ | ||
{ | ||
"$schema": "../../node_modules/ng-packagr/ng-package.schema.json", | ||
"dest": "../../dist/libs/eslint-angular", | ||
"lib": { | ||
"entryFile": "src/public-api.ts", | ||
"flatModuleFile": "eslint-plugin-eslint-angular" | ||
} | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,19 @@ | ||
{ | ||
"name": "@alfresco/eslint-plugin-eslint-angular", | ||
"version": "6.0.0", | ||
"description": "Alfresco ADF eslint angular custom rules", | ||
"main": "main.js", | ||
"author": "Hyland Software, Inc. and its affiliates", | ||
"repository": { | ||
"type": "git", | ||
"url": "https://github.com/Alfresco/alfresco-ng2-components.git" | ||
}, | ||
"bugs": { | ||
"url": "https://github.com/Alfresco/alfresco-ng2-components/issues" | ||
}, | ||
"keywords": [ | ||
"eslint", | ||
"eslint-custom-rules" | ||
], | ||
"license": "Apache-2.0" | ||
} |
123 changes: 123 additions & 0 deletions
123
.../src/rules/use-none-component-view-encapsulation/use-none-component-view-encapsulation.ts
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,123 @@ | ||
/*! | ||
* @license | ||
* Copyright © 2005-2023 Hyland Software, Inc. and its affiliates. All rights reserved. | ||
* | ||
* 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. | ||
*/ | ||
|
||
import { ASTUtils, isNotNullOrUndefined, RuleFixes, Selectors } from '@angular-eslint/utils'; | ||
import type { TSESTree } from '@typescript-eslint/utils'; | ||
import { createESLintRule } from '../../utils/create-eslint-rule/create-eslint-rule'; | ||
|
||
export const RULE_NAME = 'use-none-component-view-encapsulation'; | ||
|
||
type MessageIds = 'useNoneComponentViewEncapsulation'| 'suggestAddViewEncapsulationNone'; | ||
type DecoratorForClass = TSESTree.Decorator & { | ||
parent: TSESTree.ClassDeclaration; | ||
}; | ||
type PropertyInClassDecorator = TSESTree.Property & { | ||
parent: TSESTree.CallExpression & { | ||
parent: TSESTree.ObjectExpression & { | ||
parent: TSESTree.Decorator & { | ||
parent: TSESTree.ClassDeclaration; | ||
}; | ||
}; | ||
}; | ||
}; | ||
|
||
const metadataPropertyName = 'encapsulation'; | ||
const viewEncapsulationNone = 'ViewEncapsulation.None'; | ||
const nodeToReport = (node: TSESTree.Node) => { | ||
if (!ASTUtils.isProperty(node)) { | ||
return node; | ||
} | ||
return ASTUtils.isMemberExpression(node.value) ? node.value.property : node.value; | ||
}; | ||
|
||
/** | ||
* Custom ESLint rule which check if component uses ViewEncapsulation.None. It has been implemented because None encapsulation makes themes styling easier. | ||
* It also allows to autofix. | ||
*/ | ||
export default createESLintRule<unknown[], MessageIds>({ | ||
name: RULE_NAME, | ||
meta: { | ||
type: 'suggestion', | ||
docs: { | ||
description: `Disallows using other encapsulation than \`${viewEncapsulationNone}\``, | ||
recommended: false | ||
}, | ||
hasSuggestions: true, | ||
schema: [], | ||
messages: { | ||
useNoneComponentViewEncapsulation: `Using encapsulation other than '${viewEncapsulationNone}' makes themes styling harder.`, | ||
suggestAddViewEncapsulationNone: `Add '${viewEncapsulationNone}'` | ||
} | ||
}, | ||
defaultOptions: [], | ||
create(context) { | ||
const encapsulationProperty = Selectors.metadataProperty( | ||
metadataPropertyName | ||
); | ||
const withoutEncapsulationProperty = | ||
`${Selectors.COMPONENT_CLASS_DECORATOR}:matches([expression.arguments.length=0], [expression.arguments.0.type='ObjectExpression']:not(:has(${encapsulationProperty})))` as const; | ||
const nonNoneViewEncapsulationNoneProperty = | ||
`${Selectors.COMPONENT_CLASS_DECORATOR} > CallExpression > ObjectExpression > ` + | ||
`${encapsulationProperty}:matches([value.type='Identifier'][value.name='undefined'], [value.object.name='ViewEncapsulation'][value.property.name!='None'])`; | ||
const selectors = [ | ||
withoutEncapsulationProperty, | ||
nonNoneViewEncapsulationNoneProperty | ||
].join(','); | ||
return { | ||
[selectors](node: DecoratorForClass | PropertyInClassDecorator) { | ||
context.report({ | ||
node: nodeToReport(node), | ||
messageId: 'useNoneComponentViewEncapsulation', | ||
suggest: [ | ||
{ | ||
messageId: 'suggestAddViewEncapsulationNone', | ||
fix: (fixer) => { | ||
if (ASTUtils.isProperty(node)) { | ||
return [ | ||
RuleFixes.getImportAddFix({ | ||
fixer, | ||
importName: 'ViewEncapsulation', | ||
moduleName: '@angular/core', | ||
node: node.parent.parent.parent.parent | ||
}), | ||
ASTUtils.isMemberExpression(node.value) | ||
? fixer.replaceText(node.value.property, 'None') | ||
: fixer.replaceText(node.value, viewEncapsulationNone) | ||
].filter(isNotNullOrUndefined); | ||
} | ||
|
||
return [ | ||
RuleFixes.getImportAddFix({ | ||
fixer, | ||
importName: 'ViewEncapsulation', | ||
moduleName: '@angular/core', | ||
node: node.parent | ||
}), | ||
RuleFixes.getDecoratorPropertyAddFix( | ||
node, | ||
fixer, | ||
`${metadataPropertyName}: ${viewEncapsulationNone}` | ||
) | ||
].filter(isNotNullOrUndefined); | ||
} | ||
} | ||
] | ||
}); | ||
} | ||
}; | ||
} | ||
}); |
20 changes: 20 additions & 0 deletions
20
lib/eslint-angular/src/utils/create-eslint-rule/create-eslint-rule.ts
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,20 @@ | ||
/*! | ||
* @license | ||
* Copyright © 2005-2023 Hyland Software, Inc. and its affiliates. All rights reserved. | ||
* | ||
* 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. | ||
*/ | ||
|
||
import { ESLintUtils } from '@typescript-eslint/utils'; | ||
|
||
export const createESLintRule = ESLintUtils.RuleCreator((ruleName) => ruleName); |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,24 @@ | ||
{ | ||
"compilerOptions": { | ||
"target": "ES2019", | ||
"module": "commonjs", | ||
"sourceMap": false, | ||
"outDir": "dist", | ||
"esModuleInterop": true, | ||
"forceConsistentCasingInFileNames": true, | ||
"strict": true, | ||
"noUnusedLocals": true, | ||
"skipLibCheck": true, | ||
"baseUrl": "src", | ||
"types": [ | ||
"node" | ||
] | ||
}, | ||
"include": [ | ||
"**/*" | ||
], | ||
"exclude": [ | ||
"node_modules", | ||
"tests" | ||
] | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,9 @@ | ||
{ | ||
"extends": "./tsconfig.json", | ||
"compilerOptions": { | ||
"outDir": "../../dist/out-tsc", | ||
"declarationMap": true | ||
}, | ||
"exclude": ["src/test.ts", "**/*.spec.ts", "**/*.test.ts"], | ||
"include": ["**/*.ts"] | ||
} |
Oops, something went wrong.