eslint-plugin-smarthr 2.4.0 → 2.5.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (78) hide show
  1. package/CHANGELOG.md +7 -0
  2. package/package.json +2 -2
  3. package/rules/a11y-anchor-has-href-attribute/index.js +1 -0
  4. package/rules/a11y-clickable-element-has-text/index.js +1 -0
  5. package/rules/a11y-delegate-element-has-role-presentation/index.js +2 -0
  6. package/rules/a11y-form-control-in-form/index.js +1 -0
  7. package/rules/a11y-heading-in-sectioning-content/README.md +16 -1
  8. package/rules/a11y-heading-in-sectioning-content/index.js +7 -2
  9. package/rules/a11y-help-link-with-support-href/index.js +2 -1
  10. package/rules/a11y-image-has-alt-attribute/index.js +2 -0
  11. package/rules/a11y-input-has-name-attribute/index.js +6 -3
  12. package/rules/a11y-input-in-form-control/index.js +11 -4
  13. package/rules/a11y-numbered-text-within-ol/index.js +5 -0
  14. package/rules/a11y-prohibit-checkbox-or-radio-in-table-cell/index.js +2 -1
  15. package/rules/a11y-prohibit-input-maxlength-attribute/index.js +5 -4
  16. package/rules/a11y-prohibit-input-placeholder/index.js +7 -3
  17. package/rules/a11y-prohibit-sectioning-content-in-form/index.js +2 -0
  18. package/rules/a11y-prohibit-useless-sectioning-fragment/index.js +2 -1
  19. package/rules/a11y-trigger-has-button/index.js +4 -2
  20. package/rules/best-practice-for-async-current-target/index.js +2 -2
  21. package/rules/best-practice-for-button-element/index.js +1 -0
  22. package/rules/best-practice-for-data-test-attribute/index.js +1 -0
  23. package/rules/best-practice-for-date/index.js +2 -0
  24. package/rules/best-practice-for-layouts/index.js +22 -10
  25. package/rules/best-practice-for-nested-attributes-array-index/index.js +1 -0
  26. package/rules/best-practice-for-remote-trigger-dialog/index.js +2 -1
  27. package/rules/best-practice-for-tailwind-prohibit-root-margin/index.js +2 -1
  28. package/rules/best-practice-for-tailwind-variants/index.js +6 -3
  29. package/rules/component-name/README.md +11 -3
  30. package/rules/component-name/index.js +7 -2
  31. package/rules/design-system-guideline-prohibit-double-icons/index.js +1 -0
  32. package/rules/format-import-path/index.js +2 -1
  33. package/rules/jsx-start-with-spread-attributes/index.js +2 -1
  34. package/rules/no-import-other-domain/index.js +2 -1
  35. package/rules/prohibit-export-array-type/index.js +1 -0
  36. package/rules/prohibit-file-name/index.js +2 -1
  37. package/rules/prohibit-import/index.js +4 -2
  38. package/rules/prohibit-path-within-template-literal/index.js +2 -1
  39. package/rules/require-barrel-import/index.js +2 -1
  40. package/rules/require-declaration/index.js +4 -2
  41. package/rules/require-export/index.js +2 -1
  42. package/rules/require-i18n-text/index.js +4 -2
  43. package/rules/require-import/index.js +2 -1
  44. package/rules/trim-props/index.js +2 -1
  45. package/test/a11y-anchor-has-href-attribute.js +1 -0
  46. package/test/a11y-clickable-element-has-text.js +1 -0
  47. package/test/a11y-delegate-element-has-role-presentation.js +2 -0
  48. package/test/a11y-form-control-in-form.js +1 -0
  49. package/test/a11y-heading-in-sectioning-content.js +7 -2
  50. package/test/a11y-help-link-with-support-href.js +2 -1
  51. package/test/a11y-image-has-alt-attribute.js +2 -0
  52. package/test/a11y-input-has-name-attribute.js +30 -15
  53. package/test/a11y-input-in-form-control.js +15 -1
  54. package/test/a11y-numbered-text-within-ol.js +29 -0
  55. package/test/a11y-prohhibit-input-placeholder.js +19 -9
  56. package/test/a11y-prohibit-checkbox-or-radio-in-table-cell.js +21 -11
  57. package/test/a11y-prohibit-input-maxlength-attribute.js +5 -4
  58. package/test/a11y-prohibit-useless-sectioning-fragment.js +2 -1
  59. package/test/a11y-trigger-has-button.js +12 -6
  60. package/test/best-practice-for-async-current-target.js +2 -2
  61. package/test/best-practice-for-button-element.js +2 -0
  62. package/test/best-practice-for-data-test-attribute.js +1 -0
  63. package/test/best-practice-for-date.js +2 -0
  64. package/test/best-practice-for-layouts.js +26 -12
  65. package/test/best-practice-for-nested-attributes-array-index.js +1 -0
  66. package/test/best-practice-for-remote-trigger-dialog.js +6 -3
  67. package/test/best-practice-for-tailwind-prohibit-root-margin.js +2 -2
  68. package/test/best-practice-for-tailwind-variants.js +8 -4
  69. package/test/component-name.js +7 -2
  70. package/test/design-system-guideline-prohibit-double-icons.js +1 -0
  71. package/test/prohibit-file-name.js +4 -2
  72. package/test/prohibit-import.js +14 -7
  73. package/test/prohibit-path-within-template-literal.js +4 -2
  74. package/test/require-declaration.js +11 -5
  75. package/test/require-export.js +6 -3
  76. package/test/require-i18n-text.js +4 -3
  77. package/test/require-import.js +13 -7
  78. package/test/trim-props.js +18 -15
@@ -11,7 +11,8 @@ module.exports = {
11
11
  context.report({
12
12
  node,
13
13
  message: `${node.parent.name.name}の${node.name.name}属性には直接文字列を指定してください。
14
- - 変数などは利用できません(これは関連するTriggerとDialogを検索しやすくするためです)`,
14
+ - 詳細: https://github.com/kufu/tamatebako/tree/master/packages/eslint-plugin-smarthr/rules/best-practice-for-remote-trigger-dialog
15
+ - 変数などは利用できません(これは関連するTriggerとDialogを検索しやすくするためです)`,
15
16
  })
16
17
  }
17
18
 
@@ -13,7 +13,8 @@ module.exports = {
13
13
  ':matches(ArrowFunctionExpression,FunctionDeclaration,ReturnStatement)>JSXElement>JSXOpeningElement JSXAttribute[name.name="className"][value.value=/( |^)shr-m[trbl]?-/]': (node) => {
14
14
  context.report({
15
15
  node,
16
- message: 'コンポーネントのルート要素に外側への余白(margin)を設定しないでください。外側の余白は使用する側で制御するべきです。',
16
+ message: `コンポーネントのルート要素に外側への余白(margin)を設定しないでください。外側の余白は使用する側で制御するべきです。
17
+ - 詳細: https://github.com/kufu/tamatebako/tree/master/packages/eslint-plugin-smarthr/rules/best-practice-for-tailwind-prohibit-root-margin`,
17
18
  })
18
19
  },
19
20
  }
@@ -43,7 +43,8 @@ module.exports = {
43
43
  if (node.source.value === TV_COMPONENTS && node.specifiers.some(findValidImportNameNode)) {
44
44
  context.report({
45
45
  node,
46
- message: `${TV_COMPONENTS} をimportする際は、名称が"${TV_COMPONENTS_METHOD}" となるようにしてください。例: "import { ${TV_COMPONENTS_METHOD} } from '${TV_COMPONENTS}'"`,
46
+ message: `${TV_COMPONENTS} をimportする際は、名称が"${TV_COMPONENTS_METHOD}" となるようにしてください。例: "import { ${TV_COMPONENTS_METHOD} } from '${TV_COMPONENTS}'"
47
+ - 詳細: https://github.com/kufu/tamatebako/tree/master/packages/eslint-plugin-smarthr/rules/best-practice-for-tailwind-variants`,
47
48
  });
48
49
  }
49
50
  },
@@ -54,13 +55,15 @@ module.exports = {
54
55
  if (idNode && !TV_RESULT_CONST_NAME_REGEX.test(idNode.id.name)) {
55
56
  context.report({
56
57
  node: idNode,
57
- message: `${TV_COMPONENTS_METHOD}の実行結果を格納する変数名は "${idNode.id.name}" ではなく "${TV_RESULT_CONST_NAME_REGEX}"にmatchする名称に統一してください。`,
58
+ message: `${TV_COMPONENTS_METHOD}の実行結果を格納する変数名は "${idNode.id.name}" ではなく "${TV_RESULT_CONST_NAME_REGEX}"にmatchする名称に統一してください。
59
+ - 詳細: https://github.com/kufu/tamatebako/tree/master/packages/eslint-plugin-smarthr/rules/best-practice-for-tailwind-variants`,
58
60
  });
59
61
  }
60
62
  } else if (TV_RESULT_CONST_NAME_REGEX.test(node.callee.name) && !findNodeUseMemo(node.parent)) {
61
63
  context.report({
62
64
  node,
63
- message: `"${node.callee.name}" を実行する際、useMemoでラップし、メモ化してください`,
65
+ message: `"${node.callee.name}" を実行する際、useMemoでラップし、メモ化してください
66
+ - 詳細: https://github.com/kufu/tamatebako/tree/master/packages/eslint-plugin-smarthr/rules/best-practice-for-tailwind-variants`,
64
67
  });
65
68
  }
66
69
  },
@@ -20,13 +20,18 @@
20
20
  // import 時のasをチェック
21
21
  import { HogeSelect as Fuga } from 'any'
22
22
 
23
- // selectと勘違いしてしまうような名称はNG
23
+ // 特定の要素と勘違いしてしまうような名称はNG
24
+ // 例: select要素ではないにも関わらずselectを予想してしまう名称を設定している
24
25
  const HogeSelect = styled.div
25
26
  const HogeSelect = styled(Hoge)
26
27
 
27
- // selectとわからないような名称はNG
28
+ // 拡張前の要素がわからないような名称はNG
29
+ // 例: select要素であることがHogeから想像できない
28
30
  const Hoge = styled.select
29
31
  const Hoge = styled(FugaSelect)
32
+
33
+ // Modalでは意味が通らないパターンがあるためDialogに統一する方針のためNG
34
+ const HogeModal = styled(Any)
30
35
  ```
31
36
 
32
37
  ## ✅ Correct
@@ -38,7 +43,10 @@ import { HogeSelect as FugaSelect } from 'any'
38
43
  import { type HogeSelect as Fuga } from 'any'
39
44
  import type { HogeSelect as Fuga } from 'any'
40
45
 
41
- // 継承元がselectであることがわかるためOK
46
+ // あたらしい名称が継承元の要素を予想できるためOK
42
47
  const HogeSelect = styled.select
43
48
  const HogeSelect = styled(FugaSelect)
49
+
50
+ // ModalではなくDialogが利用されているためOK
51
+ const HogeDialog = styled(Any)
44
52
  ```
@@ -13,7 +13,8 @@ const checkImportStyledComponents = (node, context) => {
13
13
  if (invalidNameNode) {
14
14
  context.report({
15
15
  node: invalidNameNode,
16
- message: `${STYLED_COMPONENTS} をimportする際は、名称が"${STYLED_COMPONENTS_METHOD}" となるようにしてください。例: "import ${STYLED_COMPONENTS_METHOD} from '${STYLED_COMPONENTS}'"`,
16
+ message: `${STYLED_COMPONENTS} をimportする際は、名称が"${STYLED_COMPONENTS_METHOD}" となるようにしてください。例: "import ${STYLED_COMPONENTS_METHOD} from '${STYLED_COMPONENTS}'"
17
+ - 詳細: https://github.com/kufu/tamatebako/tree/master/packages/eslint-plugin-smarthr/rules/component-name`,
17
18
  });
18
19
  }
19
20
  }
@@ -127,6 +128,7 @@ const EXPECTED_NAMES = {
127
128
  }
128
129
 
129
130
  const unexpectedMessageTemplate = `{{extended}} は smarthr-ui/{{expected}} をextendすることを期待する名称になっています
131
+ - 詳細: https://github.com/kufu/tamatebako/tree/master/packages/eslint-plugin-smarthr/rules/component-name
130
132
  - childrenにHeadingを含まない場合、コンポーネントの名称から"{{expected}}"を取り除いてください
131
133
  - childrenにHeadingを含み、アウトラインの範囲を指定するためのコンポーネントならば、smarthr-ui/{{expected}}をexendしてください
132
134
  - "styled(Xxxx)" 形式の場合、拡張元であるXxxxコンポーネントの名称の末尾に"{{expected}}"を設定し、そのコンポーネント内でsmarthr-ui/{{expected}}を利用してください`
@@ -203,7 +205,8 @@ module.exports = {
203
205
  if (base.match(b) && !extended.match(e)) {
204
206
  context.report({
205
207
  node,
206
- message: `${extended}を正規表現 "${e.toString()}" がmatchする名称に変更してください。${isImport ? `
208
+ message: `${extended}を正規表現 "${e.toString()}" がmatchする名称に変更してください。
209
+ - 詳細: https://github.com/kufu/tamatebako/tree/master/packages/eslint-plugin-smarthr/rules/component-name${isImport ? `
207
210
  - ${base}が型の場合、'import type { ${base} as ${extended} }' もしくは 'import { type ${base} as ${extended} }' のように明示的に型であることを宣言してください。名称変更が不要になります` : ''}`,
208
211
  });
209
212
  }
@@ -243,6 +246,7 @@ module.exports = {
243
246
  message: m ? m
244
247
  .replaceAll('{{extended}}', extended)
245
248
  .replaceAll('{{expected}}', expected) : `${extended} は ${b.toString()} にmatchする名前のコンポーネントを拡張することを期待している名称になっています
249
+ - 詳細: https://github.com/kufu/tamatebako/tree/master/packages/eslint-plugin-smarthr/rules/component-name
246
250
  - ${extended} の名称の末尾が"${expected}" という文字列ではない状態にしつつ、"${base}"を継承していることをわかる名称に変更してください
247
251
  - もしくは"${base}"を"${extended}"の継承元であることがわかるような${isBareTag ? '適切なタグや別コンポーネントに差し替えてください' : '名称に変更するか、適切な別コンポーネントに差し替えてください'}
248
252
  - 修正例1: const ${extended.replace(expected, '')}Xxxx = ${sampleFixBase}
@@ -257,6 +261,7 @@ module.exports = {
257
261
  context.report({
258
262
  node,
259
263
  message: `コンポーネント名や変数名に"Modal"という名称は使わず、"Dialog"に統一してください
264
+ - 詳細: https://github.com/kufu/tamatebako/tree/master/packages/eslint-plugin-smarthr/rules/component-name
260
265
  - Modalとは形容詞であり、かつ"現在の操作から切り離して専用の操作を行わせる" という意味合いを持ちます
261
266
  - そのためDialogでなければ正しくない場合がありえます(smarthr-ui/ModelessDialogのように元々の操作も行えるDialogなどが該当)
262
267
  - DialogはModalなダイアログ、Modelessなダイアログすべてを含有した名称のため、統一することを推奨しています`
@@ -14,6 +14,7 @@ module.exports = {
14
14
  context.report({
15
15
  node,
16
16
  message: `${node.name.name} には prefix と suffix は同時に設定できません。
17
+ - 詳細: https://github.com/kufu/tamatebako/tree/master/packages/eslint-plugin-smarthr/rules/design-system-guideline-prohibit-double-icons
17
18
  - どちらにもアイコンをつけられそうな場合は、prefixを優先してください。`,
18
19
  })
19
20
  }
@@ -130,7 +130,8 @@ module.exports = {
130
130
  if (importPath !== fixedImportPath) {
131
131
  context.report({
132
132
  node,
133
- message: `${fixedImportPath} に修正してください`,
133
+ message: `${fixedImportPath} に修正してください
134
+ - 詳細: https://github.com/kufu/tamatebako/tree/master/packages/eslint-plugin-smarthr/rules/format-import-path`,
134
135
  fix: (fixer) => fixer.replaceText(
135
136
  node,
136
137
  context.sourceCode.getText(node).replace(new RegExp(`from '${importPath}'$`), `from '${fixedImportPath}'`)
@@ -39,7 +39,8 @@ module.exports = {
39
39
 
40
40
  context.report({
41
41
  node,
42
- message: `"${attributeCode}" は意図しない上書きを防ぐため、spread attributesでない属性より先に記述してください`,
42
+ message: `"${attributeCode}" は意図しない上書きを防ぐため、spread attributesでない属性より先に記述してください
43
+ - 詳細: https://github.com/kufu/tamatebako/tree/master/packages/eslint-plugin-smarthr/rules/jsx-start-with-spread-attributes`,
43
44
  fix: option?.fix ? (fixer) => {
44
45
  const elementNode = node.parent
45
46
  const sortedAttributes = [...elementNode.attributes].reduce((p, a, i) => {
@@ -122,7 +122,8 @@ module.exports = {
122
122
 
123
123
  context.report({
124
124
  node,
125
- message: `別ドメインから ${importPath}${deniedModules.length ? ` の ${deniedModules.join(', ')}` : ''} がimportされています。`,
125
+ message: `別ドメインから ${importPath}${deniedModules.length ? ` の ${deniedModules.join(', ')}` : ''} がimportされています。
126
+ - 詳細: https://github.com/kufu/tamatebako/tree/master/packages/eslint-plugin-smarthr/rules/no-import-other-domain`,
126
127
  })
127
128
  }
128
129
  },
@@ -12,6 +12,7 @@ module.exports = {
12
12
  context.report({
13
13
  node,
14
14
  message: `型をexportする際、配列ではなくアイテムの型をexportしてください。
15
+ - 詳細: https://github.com/kufu/tamatebako/tree/master/packages/eslint-plugin-smarthr/rules/prohibit-export-array-type
15
16
  - 型を配列でexportすると、その型が配列かどうかを判定するための情報は名称のみになります
16
17
  - 名称から配列かどうかを判定しにくい場合があるため、利用するファイル内で配列として型を設定してください`,
17
18
  })
@@ -34,7 +34,8 @@ module.exports = {
34
34
  matcher = context.filename.match(new RegExp(path))
35
35
 
36
36
  if (matcher) {
37
- messages.push([...matcher].reduce(((prev, k, index) => prev.replaceAll(`\$${index}`, k)), message))
37
+ messages.push([...matcher].reduce(((prev, k, index) => prev.replaceAll(`\$${index}`, k)), `${message}
38
+ - 詳細: https://github.com/kufu/tamatebako/tree/master/packages/eslint-plugin-smarthr/rules/prohibit-file-name`))
38
39
  }
39
40
  })
40
41
 
@@ -33,7 +33,8 @@ const SCHEMA = [{
33
33
 
34
34
  const CWD = process.cwd()
35
35
 
36
- const defaultReportMessage = (moduleName, exportName) => `${moduleName}${typeof exportName == 'string' ? `/${exportName}`: ''} は利用しないでください`
36
+ const defaultReportMessage = (moduleName, exportName) => `${moduleName}${typeof exportName == 'string' ? `/${exportName}`: ''} は利用しないでください
37
+ - 詳細: https://github.com/kufu/tamatebako/tree/master/packages/eslint-plugin-smarthr/rules/prohibit-import`
37
38
 
38
39
  /**
39
40
  * @type {import('@typescript-eslint/utils').TSESLint.RuleModule<''>}
@@ -84,7 +85,8 @@ module.exports = {
84
85
  if (useImported) {
85
86
  context.report({
86
87
  node,
87
- message: reportMessage ? reportMessage.replaceAll('{{module}}', node.source.value).replaceAll('{{export}}', useImported) : defaultReportMessage(node.source.value, useImported)
88
+ message: reportMessage ? `${reportMessage.replaceAll('{{module}}', node.source.value).replaceAll('{{export}}', useImported)}
89
+ - 詳細: https://github.com/kufu/tamatebako/tree/master/packages/eslint-plugin-smarthr/rules/prohibit-import` : defaultReportMessage(node.source.value, useImported)
88
90
  });
89
91
  }
90
92
  }
@@ -46,7 +46,8 @@ module.exports = {
46
46
  if (name) {
47
47
  context.report({
48
48
  node: exp,
49
- message: `${name}は \`\` で囲まないでください。queryStringを結合するなどのURL生成は ${name} 内で行います。 (例: ${name}({ query: { hoge: 'abc' } })`,
49
+ message: `${name}は \`\` で囲まないでください。queryStringを結合するなどのURL生成は ${name} 内で行います。 (例: ${name}({ query: { hoge: 'abc' } })
50
+ - 詳細: https://github.com/kufu/tamatebako/tree/master/packages/eslint-plugin-smarthr/rules/prohibit-path-within-template-literal`,
50
51
  });
51
52
  }
52
53
  })
@@ -185,7 +185,8 @@ module.exports = {
185
185
 
186
186
  context.report({
187
187
  node,
188
- message: deniedModules.length ? `${deniedModules.join(', ')} は ${noExt} からimportしてください` : `${noExt} からimportするか、${barrel} のbarrelファイルを削除して直接import可能にしてください`,
188
+ message: `${deniedModules.length ? `${deniedModules.join(', ')} は ${noExt} からimportしてください` : `${noExt} からimportするか、${barrel} のbarrelファイルを削除して直接import可能にしてください`}
189
+ - 詳細: https://github.com/kufu/tamatebako/tree/master/packages/eslint-plugin-smarthr/rules/require-barrel-import`,
189
190
  });
190
191
  }
191
192
  },
@@ -103,7 +103,8 @@ module.exports = {
103
103
  if (!hit) {
104
104
  context.report({
105
105
  node,
106
- message: localOption.reportMessage || `${localOption.type} ${requireDeclaration}が宣言されていません`,
106
+ message: `${localOption.reportMessage || `${localOption.type} ${requireDeclaration}が宣言されていません`}
107
+ - 詳細: https://github.com/kufu/tamatebako/tree/master/packages/eslint-plugin-smarthr/rules/require-declaration`,
107
108
  })
108
109
  } else if (localOption.use) {
109
110
  const code = context.sourceCode.getText(hit)
@@ -113,7 +114,8 @@ module.exports = {
113
114
  if (!useRegex(u).test(code) && (!localOption.reportMessage || !reported)) {
114
115
  context.report({
115
116
  node: hit,
116
- message: localOption.reportMessage || `${localOption.type} ${requireDeclaration} では ${u} を利用してください`,
117
+ message: `${localOption.reportMessage || `${localOption.type} ${requireDeclaration} では ${u} を利用してください`}
118
+ - 詳細: https://github.com/kufu/tamatebako/tree/master/packages/eslint-plugin-smarthr/rules/require-declaration`,
117
119
  })
118
120
  reported = true
119
121
  }
@@ -79,7 +79,8 @@ module.exports = {
79
79
  if (notExistsExports.length) {
80
80
  context.report({
81
81
  node,
82
- message: `${notExistsExports.join(', ')} をexportしてください`,
82
+ message: `${notExistsExports.join(', ')} をexportしてください
83
+ - 詳細: https://github.com/kufu/tamatebako/tree/master/packages/eslint-plugin-smarthr/rules/require-export`,
83
84
  })
84
85
  }
85
86
  })
@@ -55,7 +55,8 @@ module.exports = {
55
55
  const reportAttributeError = (node) => {
56
56
  context.report({
57
57
  node,
58
- message: `${node.parent.name.name}の${node.name.name}属性に文字列リテラルが指定されています。多言語化対応のため、翻訳関数を使用してください`,
58
+ message: `${node.parent.name.name}の${node.name.name}属性に文字列リテラルが指定されています。多言語化対応のため、翻訳関数を使用してください
59
+ - 詳細: https://github.com/kufu/tamatebako/tree/master/packages/eslint-plugin-smarthr/rules/require-i18n-text`,
59
60
  })
60
61
  }
61
62
 
@@ -83,7 +84,8 @@ module.exports = {
83
84
  handlers['JSXText[value=/\\S/]'] = (node) => {
84
85
  context.report({
85
86
  node,
86
- message: '子要素に文字列リテラルが指定されています。多言語化対応のため、翻訳関数を使用してください',
87
+ message: `子要素に文字列リテラルが指定されています。多言語化対応のため、翻訳関数を使用してください
88
+ - 詳細: https://github.com/kufu/tamatebako/tree/master/packages/eslint-plugin-smarthr/rules/require-i18n-text`,
87
89
  })
88
90
  }
89
91
 
@@ -80,7 +80,8 @@ module.exports = {
80
80
  const reporter = (item) => {
81
81
  context.report({
82
82
  node,
83
- message: reportMessage ? reportMessage.replaceAll('{{module}}', actualTarget).replaceAll('{{export}}', item) : defaultReportMessage(actualTarget, item)
83
+ message: `${reportMessage ? reportMessage.replaceAll('{{module}}', actualTarget).replaceAll('{{export}}', item) : defaultReportMessage(actualTarget, item)}
84
+ - 詳細: https://github.com/kufu/tamatebako/tree/master/packages/eslint-plugin-smarthr/rules/require-import`
84
85
  })
85
86
  }
86
87
 
@@ -27,7 +27,8 @@ module.exports = {
27
27
  if (!searchBubbleUp(node.parent)) {
28
28
  return context.report({
29
29
  node,
30
- message: '属性に設定している文字列から先頭、末尾の空白文字を削除してください',
30
+ message: `属性に設定している文字列から先頭、末尾の空白文字を削除してください
31
+ - 詳細: https://github.com/kufu/tamatebako/tree/master/packages/eslint-plugin-smarthr/rules/trim-props`,
31
32
  fix: (fixer) => fixer.replaceText(node, context.sourceCode.getText(node).replace(/^('|"|`)\s+/, '$1').replace(/\s+('|"|`)$/, '$1')),
32
33
  })
33
34
  }
@@ -11,6 +11,7 @@ const ruleTester = new RuleTester({
11
11
  },
12
12
  })
13
13
  const generateErrorText = (name) => `${name} に href 属性を正しく設定してください
14
+ - 詳細: https://github.com/kufu/tamatebako/tree/master/packages/eslint-plugin-smarthr/rules/a11y-anchor-has-href-attribute
14
15
  - onClickなどでページ遷移する場合でもhref属性に遷移先のURIを設定してください
15
16
  - Cmd + clickなどのキーボードショートカットに対応出来ます
16
17
  - onClickなどの動作がURLの変更を行わない場合、button要素でマークアップすることを検討してください
@@ -11,6 +11,7 @@ const ruleTester = new RuleTester({
11
11
  },
12
12
  })
13
13
  const defaultErrorMessage = `a, buttonなどのクリッカブルな要素内にはテキストを設定してください
14
+ - 詳細: https://github.com/kufu/tamatebako/tree/master/packages/eslint-plugin-smarthr/rules/a11y-clickable-element-has-text
14
15
  - 要素内にアイコン、画像のみを設置する場合はaltなどの代替テキスト用属性を指定してください
15
16
  - SVG component の場合、altを属性として受け取れるようにした上で '<svg role="img" aria-label={alt}>' のように指定してください
16
17
  - クリッカブルな要素内に設置しているコンポーネントがテキストを含んでいる場合、"XxxxText" のように末尾に "Text" もしくは "Message" という名称を設定してください`
@@ -17,6 +17,7 @@ const messageNonInteractiveEventHandler = (nodeName, onAttrs, interactiveCompone
17
17
  const onAttrsText = onAttrs.join(', ')
18
18
 
19
19
  return `${nodeName} に${onAttrsText}を設定するとブラウザが正しく解釈が行えず、ユーザーが利用することが出来ない場合があるため、以下のいずれかの対応をおこなってください。
20
+ - 詳細: https://github.com/kufu/tamatebako/tree/master/packages/eslint-plugin-smarthr/rules/a11y-delegate-element-has-role-presentation
20
21
  - 方法1: ${nodeName}がinput、buttonやaなどのインタラクティブな要素の場合、コンポーネント名の末尾をインタラクティブなコンポーネントであることがわかる名称に変更してください
21
22
  - "${interactiveComponentRegex}" の正規表現にmatchするコンポーネントに差し替える、もしくは名称を変更してください
22
23
  - 方法2: ${onAttrsText} がコンポーネント内の特定のインタラクティブな要素に設定される場合、名称を具体的なものに変更してください
@@ -29,6 +30,7 @@ const messageNonInteractiveEventHandler = (nodeName, onAttrs, interactiveCompone
29
30
  - 'role="presentation"' を設定する適切な要素が存在しない場合、div、またはspanでイベントが発生する要素を囲んだ上でrole属性を設定してください`
30
31
  }
31
32
  const messageRolePresentationNotHasInteractive = (nodeName, onAttrs, interactiveComponentRegex = defaultInteractiveRegex) => `${nodeName}に 'role="presentation"' が設定されているにも関わらず、子要素にinput、buttonやaなどのインタラクティブな要素が見つからないため、ブラウザが正しく解釈が行えず、ユーザーが利用することが出来ない場合があるため、以下のいずれかの対応をおこなってください。
33
+ - 詳細: https://github.com/kufu/tamatebako/tree/master/packages/eslint-plugin-smarthr/rules/a11y-delegate-element-has-role-presentation
32
34
  - 方法1: 子要素にインタラクティブな要素が存在するにも関わらずこのエラーが表示されている場合、子要素の名称を変更してください
33
35
  - "${interactiveComponentRegex}" の正規表現にmatchするよう、インタラクティブな子要素全てを差し替える、もしくは名称を変更してください
34
36
  - 方法2: ${nodeName}自体がインタラクティブな要素の場合、'role="presentation"'を削除した上で名称を変更してください
@@ -11,6 +11,7 @@ const ruleTester = new RuleTester({
11
11
  },
12
12
  })
13
13
  const generateErrorText = (elementName) => `${elementName}をform要素で囲むようにマークアップしてください。
14
+ - 詳細: https://github.com/kufu/tamatebako/tree/master/packages/eslint-plugin-smarthr/rules/a11y-form-control-in-form
14
15
  - form要素で囲むことでスクリーンリーダーに入力フォームであることが正しく伝わる、入力要素にfocusした状態でEnterを押せばsubmitできる、inputのpattern属性を利用できるなどのメリットがあります
15
16
  - 以下のいずれかの方法で修正をおこなってください
16
17
  - 方法1: form要素で ${elementName} を囲んでください。smarthr-ui/ActionDialog、もしくはsmarthr-ui/RemoteTriggerActionDialogを利用している場合、smarthr-ui/FormDialog、smarthr-ui/RemoteTriggerFormDialogに置き換えてください
@@ -12,14 +12,19 @@ const ruleTester = new RuleTester({
12
12
  })
13
13
 
14
14
  const lowerMessage = `smarthr-ui/Headingと紐づく内容の範囲(アウトライン)が曖昧になっています。
15
+ - 詳細: https://github.com/kufu/tamatebako/tree/master/packages/eslint-plugin-smarthr/rules/a11y-heading-in-sectioning-content
15
16
  - smarthr-uiのArticle, Aside, Nav, SectionのいずれかでHeadingコンポーネントと内容をラップしてHeadingに対応する範囲を明確に指定してください。`
16
17
  const message = `${lowerMessage}
17
18
  - Headingをh1にしたい場合(機能名、ページ名などこのページ内でもっとも重要な見出しの場合)、smarthr-ui/PageHeadingを利用してください。その場合はSectionなどでアウトラインを示す必要はありません。`
18
- const pageMessage = 'smarthr-ui/PageHeading が同一ファイル内に複数存在しています。PageHeadingはh1タグを出力するため最も重要な見出しにのみ利用してください。'
19
- const pageInSectionMessage = 'smarthr-ui/PageHeadingはsmarthr-uiのArticle, Aside, Nav, Sectionで囲まないでください。囲んでしまうとページ全体の見出しではなくなってしまいます。'
19
+ const pageMessage = `smarthr-ui/PageHeading が同一ファイル内に複数存在しています。PageHeadingはh1タグを出力するため最も重要な見出しにのみ利用してください。
20
+ - 詳細: https://github.com/kufu/tamatebako/tree/master/packages/eslint-plugin-smarthr/rules/a11y-heading-in-sectioning-content`
21
+ const pageInSectionMessage = `smarthr-ui/PageHeadingはsmarthr-uiのArticle, Aside, Nav, Sectionで囲まないでください。囲んでしまうとページ全体の見出しではなくなってしまいます。
22
+ - 詳細: https://github.com/kufu/tamatebako/tree/master/packages/eslint-plugin-smarthr/rules/a11y-heading-in-sectioning-content`
20
23
  const noTagAttrMessage = `tag属性を指定せず、smarthr-uiのArticle, Aside, Nav, Sectionのいずれかの自動レベル計算に任せるよう、tag属性を削除してください。
24
+ - 詳細: https://github.com/kufu/tamatebako/tree/master/packages/eslint-plugin-smarthr/rules/a11y-heading-in-sectioning-content
21
25
  - tag属性を指定することで意図しないレベルに固定されてしまう可能性があります。`
22
26
  const notHaveHeadingMessage = (elementName, isNav) => `${elementName} はHeading要素を含んでいません。
27
+ - 詳細: https://github.com/kufu/tamatebako/tree/master/packages/eslint-plugin-smarthr/rules/a11y-heading-in-sectioning-content
23
28
  - SectioningContentはHeadingを含むようにマークアップする必要があります
24
29
  - ${elementName}に設定しているいずれかの属性がHeading,もしくはHeadingのテキストに該当する場合、その属性の名称を /^(heading|title)$/ にマッチする名称に変更してください
25
30
  - Headingにするべき適切な文字列が存在しない場合、 ${elementName} は削除するか、SectioningContentではない要素に差し替えてください${isNav ? `
@@ -10,7 +10,8 @@ const ruleTester = new RuleTester({
10
10
  },
11
11
  },
12
12
  })
13
- const errorText = `ヘルプページ用のリンクは smarthr-ui/HelpLink コンポーネントを利用してください`
13
+ const errorText = `ヘルプページ用のリンクは smarthr-ui/HelpLink コンポーネントを利用してください
14
+ - 詳細: https://github.com/kufu/tamatebako/tree/master/packages/eslint-plugin-smarthr/rules/a11y-help-link-with-support-href`
14
15
 
15
16
  ruleTester.run('a11y-help-link-with-support-href', rule, {
16
17
  valid: [
@@ -11,12 +11,14 @@ const ruleTester = new RuleTester({
11
11
  },
12
12
  })
13
13
  const messageNotExistAlt = `画像にはalt属性を指定してください。
14
+ - 詳細: https://github.com/kufu/tamatebako/tree/master/packages/eslint-plugin-smarthr/rules/a11y-image-has-alt-attribute
14
15
  - コンポーネントが画像ではない場合、img or image を末尾に持たない名称に変更してください。
15
16
  - ボタンやリンクの先頭・末尾などに設置するアイコンとしての役割を持つ画像の場合、コンポーネント名の末尾を "Icon" に変更してください。
16
17
  - SVG component の場合、altを属性として受け取れるようにした上で '<svg role="img" aria-label={alt}>' のように指定してください。
17
18
  - 文字情報が多い場合や画像の前後の画像と同じ内容を設定したい場合などは aria-describedby属性を利用することもできます。
18
19
  - aria-describedby属性を利用する場合でもalt属性を併用することができます。`
19
20
  const messageNullAlt = `画像の情報をテキストにした代替テキスト('alt')を設定してください。
21
+ - 詳細: https://github.com/kufu/tamatebako/tree/master/packages/eslint-plugin-smarthr/rules/a11y-image-has-alt-attribute
20
22
  - 装飾目的の画像など、alt属性に指定すべき文字がない場合は背景画像にすることを検討してください。`
21
23
 
22
24
  ruleTester.run('a11y-image-has-alt-attribute', rule, {
@@ -32,24 +32,39 @@ ruleTester.run('a11y-input-has-name-attribute', rule, {
32
32
  { code: '<Input {...args} hoge="fuga" />', options: [{ checkType: 'allow-spread-attributes' }] },
33
33
  ],
34
34
  invalid: [
35
- { code: '<input />', errors: [ { message: `input にname属性を指定してください${MESSAGE_SUFFIX}` } ] },
36
- { code: '<input type="date" />', errors: [ { message: `inputname属性を指定してください${MESSAGE_SUFFIX}` } ] },
37
- { code: '<Input type="checkbox" />', errors: [ { message: `Input にname属性を指定してください${MESSAGE_SUFFIX}` } ] },
38
- { code: '<input type="radio" />', errors: [ { message: `input にグループとなる他のinput[radio]と同じname属性を指定してください${MESSAGE_RADIO_SUFFIX}` } ] },
39
- { code: '<HogeInput type="radio" />', errors: [ { message: `HogeInput にグループとなる他のinput[radio]と同じname属性を指定してください${MESSAGE_RADIO_SUFFIX}` } ] },
40
- { code: '<HogeInput type="text" />', errors: [ { message: `HogeInput にname属性を指定してください${MESSAGE_SUFFIX}` } ] },
41
- { code: '<HogeRadioButton />', errors: [ { message: `HogeRadioButton にグループとなる他のinput[radio]と同じname属性を指定してください${MESSAGE_RADIO_SUFFIX}` } ] },
42
- { code: '<select />', errors: [ { message: `select にname属性を指定してください${MESSAGE_SUFFIX}` } ] },
43
- { code: '<HogeSelect />', errors: [ { message: `HogeSelect name属性を指定してください${MESSAGE_SUFFIX}` } ] },
44
- { code: '<textarea />', errors: [ { message: `textarea にname属性を指定してください${MESSAGE_SUFFIX}` } ] },
45
- { code: '<HogeTextarea />', errors: [ { message: `HogeTextarea にname属性を指定してください${MESSAGE_SUFFIX}` } ] },
46
- { code: '<input type="radio" name="ほげ" />', errors: [ { message: 'input のname属性の値(ほげ)はブラウザの自動補完が適切に行えない可能性があるため"/^[a-zA-Z0-9_\\[\\]]+$/"にmatchするフォーマットで命名してください' } ] },
47
- { code: '<select name="hoge[fuga][0][あいうえお]" />', errors: [ { message: 'select のname属性の値(hoge[fuga][0][あいうえお])はブラウザの自動補完が適切に行えない可能性があるため"/^[a-zA-Z0-9_\\[\\]]+$/"にmatchするフォーマットで命名してください' } ] },
35
+ { code: '<input />', errors: [ { message: `input にname属性を指定してください${MESSAGE_SUFFIX}
36
+ - 詳細: https://github.com/kufu/tamatebako/tree/master/packages/eslint-plugin-smarthr/rules/a11y-input-has-name-attribute` } ] },
37
+ { code: '<input type="date" />', errors: [ { message: `input にname属性を指定してください${MESSAGE_SUFFIX}
38
+ - 詳細: https://github.com/kufu/tamatebako/tree/master/packages/eslint-plugin-smarthr/rules/a11y-input-has-name-attribute` } ] },
39
+ { code: '<Input type="checkbox" />', errors: [ { message: `Input name属性を指定してください${MESSAGE_SUFFIX}
40
+ - 詳細: https://github.com/kufu/tamatebako/tree/master/packages/eslint-plugin-smarthr/rules/a11y-input-has-name-attribute` } ] },
41
+ { code: '<input type="radio" />', errors: [ { message: `input にグループとなる他のinput[radio]と同じname属性を指定してください${MESSAGE_RADIO_SUFFIX}
42
+ - 詳細: https://github.com/kufu/tamatebako/tree/master/packages/eslint-plugin-smarthr/rules/a11y-input-has-name-attribute` } ] },
43
+ { code: '<HogeInput type="radio" />', errors: [ { message: `HogeInput にグループとなる他のinput[radio]と同じname属性を指定してください${MESSAGE_RADIO_SUFFIX}
44
+ - 詳細: https://github.com/kufu/tamatebako/tree/master/packages/eslint-plugin-smarthr/rules/a11y-input-has-name-attribute` } ] },
45
+ { code: '<HogeInput type="text" />', errors: [ { message: `HogeInput にname属性を指定してください${MESSAGE_SUFFIX}
46
+ - 詳細: https://github.com/kufu/tamatebako/tree/master/packages/eslint-plugin-smarthr/rules/a11y-input-has-name-attribute` } ] },
47
+ { code: '<HogeRadioButton />', errors: [ { message: `HogeRadioButton にグループとなる他のinput[radio]と同じname属性を指定してください${MESSAGE_RADIO_SUFFIX}
48
+ - 詳細: https://github.com/kufu/tamatebako/tree/master/packages/eslint-plugin-smarthr/rules/a11y-input-has-name-attribute` } ] },
49
+ { code: '<select />', errors: [ { message: `select にname属性を指定してください${MESSAGE_SUFFIX}
50
+ - 詳細: https://github.com/kufu/tamatebako/tree/master/packages/eslint-plugin-smarthr/rules/a11y-input-has-name-attribute` } ] },
51
+ { code: '<HogeSelect />', errors: [ { message: `HogeSelect にname属性を指定してください${MESSAGE_SUFFIX}
52
+ - 詳細: https://github.com/kufu/tamatebako/tree/master/packages/eslint-plugin-smarthr/rules/a11y-input-has-name-attribute` } ] },
53
+ { code: '<textarea />', errors: [ { message: `textarea にname属性を指定してください${MESSAGE_SUFFIX}
54
+ - 詳細: https://github.com/kufu/tamatebako/tree/master/packages/eslint-plugin-smarthr/rules/a11y-input-has-name-attribute` } ] },
55
+ { code: '<HogeTextarea />', errors: [ { message: `HogeTextarea にname属性を指定してください${MESSAGE_SUFFIX}
56
+ - 詳細: https://github.com/kufu/tamatebako/tree/master/packages/eslint-plugin-smarthr/rules/a11y-input-has-name-attribute` } ] },
57
+ { code: '<input type="radio" name="ほげ" />', errors: [ { message: `input のname属性の値(ほげ)はブラウザの自動補完が適切に行えない可能性があるため"/^[a-zA-Z0-9_\\[\\]]+$/"にmatchするフォーマットで命名してください
58
+ - 詳細: https://github.com/kufu/tamatebako/tree/master/packages/eslint-plugin-smarthr/rules/a11y-input-has-name-attribute` } ] },
59
+ { code: '<select name="hoge[fuga][0][あいうえお]" />', errors: [ { message: `select のname属性の値(hoge[fuga][0][あいうえお])はブラウザの自動補完が適切に行えない可能性があるため"/^[a-zA-Z0-9_\\[\\]]+$/"にmatchするフォーマットで命名してください
60
+ - 詳細: https://github.com/kufu/tamatebako/tree/master/packages/eslint-plugin-smarthr/rules/a11y-input-has-name-attribute` } ] },
48
61
  { code: '<Input {...hoge} />', errors: [ { message: `Input にname属性を指定してください
49
62
  - ブラウザの自動補完が有効化されるなどのメリットがあります
50
- - より多くのブラウザが自動補完を行える可能性を上げるため、\"/^[a-zA-Z0-9_\\[\\]]+$/\"にmatchするフォーマットで命名してください` } ] },
63
+ - より多くのブラウザが自動補完を行える可能性を上げるため、\"/^[a-zA-Z0-9_\\[\\]]+$/\"にmatchするフォーマットで命名してください
64
+ - 詳細: https://github.com/kufu/tamatebako/tree/master/packages/eslint-plugin-smarthr/rules/a11y-input-has-name-attribute` } ] },
51
65
  { code: '<Input {...hoge} hoge="fuga" />', options: [{ checkType: 'always' }], errors: [ { message: `Input にname属性を指定してください
52
66
  - ブラウザの自動補完が有効化されるなどのメリットがあります
53
- - より多くのブラウザが自動補完を行える可能性を上げるため、\"/^[a-zA-Z0-9_\\[\\]]+$/\"にmatchするフォーマットで命名してください` } ] },
67
+ - より多くのブラウザが自動補完を行える可能性を上げるため、\"/^[a-zA-Z0-9_\\[\\]]+$/\"にmatchするフォーマットで命名してください
68
+ - 詳細: https://github.com/kufu/tamatebako/tree/master/packages/eslint-plugin-smarthr/rules/a11y-input-has-name-attribute` } ] },
54
69
  ],
55
70
  });
@@ -11,26 +11,33 @@ const ruleTester = new RuleTester({
11
11
  },
12
12
  })
13
13
  const noLabeledInput = (name) => `${name} を、smarthr-ui/FormControl もしくはそれを拡張したコンポーネントが囲むようマークアップを変更してください。
14
+ - 詳細: https://github.com/kufu/tamatebako/tree/master/packages/eslint-plugin-smarthr/rules/a11y-input-in-form-control
14
15
  - FormControlで入力要素を囲むことでラベルと入力要素が適切に紐づき、操作性が高まります
15
16
  - 画面上に表示するラベルが存在しない場合でも、必ずその入力要素は何であるか、どんな値を入力すればいいのか?を伝えるため、ラベルの設定は必須です。
16
17
  - この場合、FormControlのdangerouslyTitleHidden属性をtrueにして、ラベルを非表示にしてください(https://smarthr.design/products/components/form-control/)
17
18
  - ${name}が入力要素とラベル・タイトル・説明など含む概念を表示するコンポーネントの場合、コンポーネント名を/(Form(Control|Group)|(F|^f)ieldset)$/とマッチするように修正してください
18
19
  - ${name}が入力要素自体を表現するコンポーネントの一部である場合、ルートとなるコンポーネントの名称を/(RadioButton(Panel)?(s)?|Check(B|b)ox(es|s)?|(Search)?(I|^i)nput(File)?|(T|^t)extarea|(S|^s)elect|Combo(B|b)ox|(Date|Wareki|Time)Picker)$/とマッチするように修正してください`
19
20
  const noLabeledSelect = (name) => `${name} を、smarthr-ui/FormControl もしくはそれを拡張したコンポーネントが囲むようマークアップを変更してください。
21
+ - 詳細: https://github.com/kufu/tamatebako/tree/master/packages/eslint-plugin-smarthr/rules/a11y-input-in-form-control
20
22
  - FormControlで入力要素を囲むことでラベルと入力要素が適切に紐づき、操作性が高まります
21
23
  - 画面上に表示するラベルが存在しない場合でも、必ずその入力要素は何であるか、どんな値を入力すればいいのか?を伝えるため、ラベルの設定は必須です。
22
24
  - この場合、FormControlのdangerouslyTitleHidden属性をtrueにして、ラベルを非表示にしてください(https://smarthr.design/products/components/form-control/)
23
25
  - ${name}が入力要素とラベル・タイトル・説明など含む概念を表示するコンポーネントの場合、コンポーネント名を/(Form(Control|Group)|(F|^f)ieldset)$/とマッチするように修正してください
24
26
  - ${name}が入力要素自体を表現するコンポーネントの一部である場合、ルートとなるコンポーネントの名称を/(RadioButton(Panel)?(s)?|Check(B|b)ox(es|s)?|(Search)?(I|^i)nput(File)?|(T|^t)extarea|(S|^s)elect|Combo(B|b)ox|(Date|Wareki|Time)Picker)$/とマッチするように修正してください`
25
27
  const invalidPureCheckboxInFormControl = (name) => `HogeFormControl が ${name} を含んでいます。smarthr-ui/FormControl を smarthr-ui/Fieldset に変更し、正しくグルーピングされるように修正してください。
28
+ - 詳細: https://github.com/kufu/tamatebako/tree/master/packages/eslint-plugin-smarthr/rules/a11y-input-in-form-control
26
29
  - 可能なら${name}はsmarthr-ui/Checkboxへの変更を検討してください。難しい場合は ${name} と結びつくlabel要素が必ず存在するよう、マークアップする必要があることに注意してください。`
27
- const invalidCheckboxInFormControl = (name) => `HogeFormControl が ${name} を含んでいます。smarthr-ui/FormControl を smarthr-ui/Fieldset に変更し、正しくグルーピングされるように修正してください。`
30
+ const invalidCheckboxInFormControl = (name) => `HogeFormControl が ${name} を含んでいます。smarthr-ui/FormControl を smarthr-ui/Fieldset に変更し、正しくグルーピングされるように修正してください。
31
+ - 詳細: https://github.com/kufu/tamatebako/tree/master/packages/eslint-plugin-smarthr/rules/a11y-input-in-form-control`
28
32
  const invalidPureRadioInFormControl = (name) => `HogeFormControl が ${name} を含んでいます。smarthr-ui/FormControl を smarthr-ui/Fieldset に変更し、正しくグルーピングされるように修正してください。
33
+ - 詳細: https://github.com/kufu/tamatebako/tree/master/packages/eslint-plugin-smarthr/rules/a11y-input-in-form-control
29
34
  - Fieldsetで同じname属性のラジオボタン全てを囲むことで正しくグループ化され、適切なタイトル・説明を追加出来ます
30
35
  - 可能なら${name}はsmarthr-ui/RadioButton、smarthr-ui/RadioButtonPanelへの変更を検討してください。難しい場合は ${name} と結びつくlabel要素が必ず存在するよう、マークアップする必要があることに注意してください。`
31
36
  const invalidRadioInFormControl = (name) => `HogeFormControl が ${name} を含んでいます。smarthr-ui/FormControl を smarthr-ui/Fieldset に変更し、正しくグルーピングされるように修正してください。
37
+ - 詳細: https://github.com/kufu/tamatebako/tree/master/packages/eslint-plugin-smarthr/rules/a11y-input-in-form-control
32
38
  - Fieldsetで同じname属性のラジオボタン全てを囲むことで正しくグループ化され、適切なタイトル・説明を追加出来ます`
33
39
  const invalidMultiInputsInFormControl = () => `HogeFormControl が複数の入力要素を含んでいます。ラベルと入力要素の紐づけが正しく行われない可能性があるため、以下の方法のいずれかで修正してください。
40
+ - 詳細: https://github.com/kufu/tamatebako/tree/master/packages/eslint-plugin-smarthr/rules/a11y-input-in-form-control
34
41
  - 方法1: 郵便番号や電話番号など、本来一つの概念の入力要素を分割して複数の入力要素にしている場合、一つの入力要素にまとめることを検討してください
35
42
  - コピーアンドペーストがしやすくなる、ブラウザの自動補完などがより適切に反映されるなど多大なメリットがあります
36
43
  - 方法2: HogeFormControlをsmarthr-ui/Fieldset、もしくはそれを拡張したコンポーネントに変更した上で、入力要素を一つずつsmarthr-ui/FormControlで囲むようにマークアップを変更してください
@@ -38,6 +45,7 @@ const invalidMultiInputsInFormControl = () => `HogeFormControl が複数の入
38
45
  - この場合、FormControlのdangerouslyTitleHidden属性をtrueにして、ラベルを非表示にしてください(https://smarthr.design/products/components/form-control/)
39
46
  - 方法3: HogeFormControl が smarthr-ui/FormControl、もしくはそれを拡張しているコンポーネントではない場合、名称を /(Form(Control|Group)|(F|^f)ieldset)$/ にマッチしないものに変更してください`
40
47
  const noLabeledInputInFieldset = (name) => `HogeFieldset が ラベルを持たない入力要素(${name})を含んでいます。入力要素が何であるかを正しく伝えるため、以下の方法のいずれかで修正してください。
48
+ - 詳細: https://github.com/kufu/tamatebako/tree/master/packages/eslint-plugin-smarthr/rules/a11y-input-in-form-control
41
49
  - 方法1: HogeFieldset を smarthr-ui/FormControl、もしくはそれを拡張したコンポーネントに変更してください
42
50
  - 画面上に表示するラベルが存在しない場合でも、必ずその入力要素は何であるか、どんな値を入力すればいいのか?を伝えるため、ラベルの設定は必須です。
43
51
  - この場合、FormControlのdangerouslyTitleHidden属性をtrueにして、ラベルを非表示にしてください(https://smarthr.design/products/components/form-control/)
@@ -48,6 +56,7 @@ const noLabeledInputInFieldset = (name) => `HogeFieldset が ラベルを持た
48
56
  - 方法4: HogeFieldset が smarthr-ui/Fieldset、もしくはそれを拡張しているコンポーネントではない場合、名称を /Fieldset$/ にマッチしないものに変更してください
49
57
  - 方法5: 別途label要素が存在し、それらと紐づけたい場合はlabel要素のhtmlFor属性、${name}のid属性に同じ文字列を指定してください。この文字列はhtml内で一意である必要があります`
50
58
  const noLabeledInputInFieldsetWithSelect = (name) => `HogeFieldset が ラベルを持たない入力要素(${name})を含んでいます。入力要素が何であるかを正しく伝えるため、以下の方法のいずれかで修正してください。
59
+ - 詳細: https://github.com/kufu/tamatebako/tree/master/packages/eslint-plugin-smarthr/rules/a11y-input-in-form-control
51
60
  - 方法1: HogeFieldset を smarthr-ui/FormControl、もしくはそれを拡張したコンポーネントに変更してください
52
61
  - 画面上に表示するラベルが存在しない場合でも、必ずその入力要素は何であるか、どんな値を入力すればいいのか?を伝えるため、ラベルの設定は必須です。
53
62
  - この場合、FormControlのdangerouslyTitleHidden属性をtrueにして、ラベルを非表示にしてください(https://smarthr.design/products/components/form-control/)
@@ -58,6 +67,7 @@ const noLabeledInputInFieldsetWithSelect = (name) => `HogeFieldset が ラベル
58
67
  - 方法4: HogeFieldset が smarthr-ui/Fieldset、もしくはそれを拡張しているコンポーネントではない場合、名称を /Fieldset$/ にマッチしないものに変更してください
59
68
  - 方法5: 別途label要素が存在し、それらと紐づけたい場合はlabel要素のhtmlFor属性、${name}のid属性に同じ文字列を指定してください。この文字列はhtml内で一意である必要があります`
60
69
  const useFormControlInsteadOfSection = (name, section) => `${name}は${section}より先に、smarthr-ui/FormControlが入力要素を囲むようマークアップを以下のいずれかの方法で変更してください。
70
+ - 詳細: https://github.com/kufu/tamatebako/tree/master/packages/eslint-plugin-smarthr/rules/a11y-input-in-form-control
61
71
  - 方法1: ${section} をFormControl、もしくはそれを拡張したコンポーネントに変更してください
62
72
  - ${section} 内のHeading要素はFormControlのtitle属性に変更してください
63
73
  - 方法2: ${section} と ${name} の間に FormControl が存在するようにマークアップを変更してください
@@ -65,18 +75,22 @@ const useFormControlInsteadOfSection = (name, section) => `${name}は${section}
65
75
  - この場合、FormControlのdangerouslyTitleHidden属性をtrueにして、ラベルを非表示にしてください(https://smarthr.design/products/components/form-control/)
66
76
  - 方法3: 別途label要素が存在し、それらと紐づけたい場合はlabel要素のhtmlFor属性、${name}のid属性に同じ文字列を指定してください。この文字列はhtml内で一意である必要があります`
67
77
  const useFormControlInsteadOfSectionInRadio = (name, section) => `${name}は${section}より先に、smarthr-ui/Fieldsetが入力要素を囲むようマークアップを以下のいずれかの方法で変更してください。
78
+ - 詳細: https://github.com/kufu/tamatebako/tree/master/packages/eslint-plugin-smarthr/rules/a11y-input-in-form-control
68
79
  - 方法1: ${section} をFieldset、もしくはそれを拡張したコンポーネントに変更してください
69
80
  - ${section} 内のHeading要素はFieldsetのtitle属性に変更してください
70
81
  - 方法2: ${section} と ${name} の間に Fieldset が存在するようにマークアップを変更してください
71
82
  - 画面上に表示するラベルが存在しない場合でも、必ずその入力要素は何であるか、どんな値を入力すればいいのか?を伝えるため、ラベルの設定は必須です。
72
83
  - この場合、FieldsetのdangerouslyTitleHidden属性をtrueにして、ラベルを非表示にしてください(https://smarthr.design/products/components/form-control/)`
73
84
  const invalidFieldsetHasRoleGroup = (fieldset, base) => `${fieldset}に 'role="group" が設定されています。${base} をつかってマークアップする場合、'role="group"' は不要です
85
+ - 詳細: https://github.com/kufu/tamatebako/tree/master/packages/eslint-plugin-smarthr/rules/a11y-input-in-form-control
74
86
  - ${fieldset} が ${base}、もしくはそれを拡張しているコンポーネントではない場合、名称を /(Form(Control|Group)|(F|^f)ieldset)$/ にマッチしないものに変更してください`
75
87
  const invalidChildreninFormControl = (children) => `FormControl が、${children} を子要素として持っており、マークアップとして正しくない状態になっています。以下のいずれかの方法で修正を試みてください。
88
+ - 詳細: https://github.com/kufu/tamatebako/tree/master/packages/eslint-plugin-smarthr/rules/a11y-input-in-form-control
76
89
  - 方法1: 親要素であるFormControlをsmarthr-ui/FormControl、もしくはそれを拡張していないコンポーネントでマークアップしてください
77
90
  - FormControlではなく、smarthr-ui/Fieldset、もしくはsmarthr-ui/Section + smarthr-ui/Heading などでのマークアップを検討してください
78
91
  - 方法2: 親要素であるFormControlがsmarthr-ui/FormControlを拡張したコンポーネントではない場合、コンポーネント名を/(Form(Control|Group))$/と一致しない名称に変更してください`
79
92
  const requireMultiInputInFormControlWithRoleGroup = () => `HogeFormControl内に入力要素が2個以上存在しないため、'role=\"group\"'を削除してください。'role=\"group\"'は複数の入力要素を一つのグループとして扱うための属性です。
93
+ - 詳細: https://github.com/kufu/tamatebako/tree/master/packages/eslint-plugin-smarthr/rules/a11y-input-in-form-control
80
94
  - HogeFormControl内に2つ以上の入力要素が存在する場合、入力要素を含むコンポーネント名全てを/(RadioButton(Panel)?(s)?|Check(B|b)ox(es|s)?|(Search)?(I|^i)nput(File)?|(T|^t)extarea|(S|^s)elect|Combo(B|b)ox|(Date|Wareki|Time)Picker)$/、もしくは/(Form(Control|Group)|(F|^f)ieldset)$/にマッチする名称に変更してください`
81
95
 
82
96
  ruleTester.run('a11y-input-in-form-control', rule, {