Skip to content

Commit b9a89e2

Browse files
committed
update playground
1 parent 0aa4e19 commit b9a89e2

File tree

6 files changed

+167
-24
lines changed

6 files changed

+167
-24
lines changed

README.md

Lines changed: 4 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,6 @@
11
# Introduction
22

3-
`@ota-meshi/eslint-plugin-svelte` is ESLint plugin for Svelte.
3+
`@ota-meshi/eslint-plugin-svelte` is [ESLint] plugin for [Svelte].
44
It provides many unique check rules by using the template AST.
55
You can check on the [Online DEMO](https://ota-meshi.github.io/eslint-plugin-svelte/playground/).
66

@@ -19,12 +19,12 @@ You can check on the [Online DEMO](https://ota-meshi.github.io/eslint-plugin-sve
1919

2020
## :name_badge: What is this plugin?
2121

22-
ESLint plugin for Svelte.
22+
[ESLint] plugin for [Svelte].
2323
It provides many unique check rules using the AST generated by [svelte-eslint-parser].
2424

2525
### ❓ Why?
2626

27-
[Svelte] has the official ESLint plugin the [eslint-plugin-svelte3]. The [eslint-plugin-svelte3] works well enough to check scripts. However, it does not handle the AST of the template, which makes it very difficult for third parties to create their own the [ESLint] rules for the [Svelte].
27+
[Svelte] has the official [ESLint] plugin the [eslint-plugin-svelte3]. The [eslint-plugin-svelte3] works well enough to check scripts. However, it does not handle the AST of the template, which makes it very difficult for third parties to create their own the [ESLint] rules for the [Svelte].
2828

2929
The [svelte-eslint-parser] aims to make it easy to create your own rules for the [Svelte] by allowing the template AST to be used in the rules.
3030

@@ -34,7 +34,6 @@ The [svelte-eslint-parser] and the `@ota-meshi/eslint-plugin-svelte` can not be
3434

3535
[svelte-eslint-parser]: https://github.com/ota-meshi/svelte-eslint-parser
3636
[eslint-plugin-svelte3]: https://github.com/sveltejs/eslint-plugin-svelte3
37-
[eslint]: https://eslint.org/
3837

3938
<!--DOCS_IGNORE_START-->
4039

@@ -332,3 +331,4 @@ This plugin uses [svelte-eslint-parser](https://github.com/ota-meshi/svelte-esli
332331
See the [LICENSE](LICENSE) file for license rights and limitations (MIT).
333332

334333
[svelte]: https://svelte.dev/
334+
[eslint]: https://eslint.org/

docs-svelte-kit/src/lib/components/ESLintPlayground.svelte

Lines changed: 31 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -4,7 +4,7 @@
44
import { deserializeState, serializeState } from "../eslint/scripts/state"
55
import {
66
DEFAULT_RULES_CONFIG,
7-
getURL,
7+
getRule,
88
createLinter,
99
preprocess,
1010
postprocess,
@@ -128,7 +128,7 @@
128128
<span style="margin-left: 16px">{time}</span>
129129
</div>
130130
<div class="playground-content">
131-
<RulesSettings bind:rules class="rules-settings" />
131+
<RulesSettings bind:rules />
132132
<div class="editor-content">
133133
<ESLintEditor
134134
{linter}
@@ -146,17 +146,20 @@
146146
},
147147
}}
148148
{options}
149-
class="eslint-playground"
150149
on:result={onLintedResult}
151150
/>
152151
<div class="messages">
153152
<ol>
154153
{#each messages as msg, i (`${msg.line}:${msg.column}:${msg.ruleId}@${i}`)}
155154
<li class="message">
156155
[{msg.line}:{msg.column}]:
157-
{msg.message} (<a href={getURL(msg.ruleId)} target="_blank">
158-
{msg.ruleId}
159-
</a>)
156+
{msg.message}
157+
<a
158+
class="rule-link {getRule(msg.ruleId)?.classes}"
159+
class:is-rule-error={msg.ruleId}
160+
href={getRule(msg.ruleId)?.url}
161+
target="_blank">({msg.ruleId})</a
162+
>
160163
</li>
161164
{/each}
162165
</ol>
@@ -179,7 +182,7 @@
179182
height: calc(100% - 16px);
180183
border: 1px solid #cfd4db;
181184
background-color: #282c34;
182-
color: #f8c555;
185+
color: #fff;
183186
}
184187
185188
.playground-content > .editor-content {
@@ -200,4 +203,25 @@
200203
padding: 8px;
201204
font-size: 12px;
202205
}
206+
.playground-content
207+
> .editor-content
208+
> .messages
209+
.rule-link:not(.is-rule-error) {
210+
display: none;
211+
}
212+
.rule-link {
213+
transition: color 0.2s linear;
214+
}
215+
.rule-link.svelte-rule {
216+
color: #40b3ff80;
217+
}
218+
.rule-link.svelte-rule:hover {
219+
color: #40b3ff;
220+
}
221+
.rule-link.core-rule {
222+
color: #8080f280;
223+
}
224+
.rule-link.core-rule:hover {
225+
color: #8080f2;
226+
}
203227
</style>

docs-svelte-kit/src/lib/eslint/RulesSettings.svelte

Lines changed: 99 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -2,6 +2,25 @@
22
import { categories } from "./scripts/linter.js"
33
44
export let rules = {}
5+
6+
let filterValue = ""
7+
let filteredCategories = categories
8+
$: {
9+
filteredCategories = []
10+
for (const category of categories) {
11+
let filteredRules = category.rules
12+
if (filterValue) {
13+
// eslint-disable-next-line no-loop-func -- ignore
14+
filteredRules = filteredRules.filter((r) =>
15+
r.ruleId.includes(filterValue),
16+
)
17+
}
18+
filteredCategories.push({
19+
...category,
20+
rules: filteredRules,
21+
})
22+
}
23+
}
524
let categoryState = Object.fromEntries(
625
categories.map((c) => {
726
return [
@@ -12,10 +31,12 @@
1231
]
1332
}),
1433
)
15-
function onAllClick(category, e) {
34+
35+
function onCategoryClick(category, e) {
36+
const checked = e.target.checked
1637
const newRules = Object.assign({}, rules)
1738
for (const rule of category.rules) {
18-
if (e.target.checked) {
39+
if (checked) {
1940
newRules[rule.ruleId] = "error"
2041
} else {
2142
delete newRules[rule.ruleId]
@@ -24,8 +45,9 @@
2445
rules = newRules
2546
}
2647
function onClick(ruleId, e) {
48+
const checked = e.target.checked
2749
const newRules = Object.assign({}, rules)
28-
if (e.target.checked) {
50+
if (checked) {
2951
newRules[ruleId] = "error"
3052
} else {
3153
delete newRules[ruleId]
@@ -35,13 +57,55 @@
3557
function isErrorState(rules, ruleId) {
3658
return rules[ruleId] === "error" || rules[ruleId] === 2
3759
}
60+
61+
function onAllClick(e) {
62+
const checked = e.target.checked
63+
const newRules = Object.assign({}, rules)
64+
for (const category of filteredCategories) {
65+
for (const rule of category.rules) {
66+
if (checked) {
67+
newRules[rule.ruleId] = "error"
68+
} else {
69+
delete newRules[rule.ruleId]
70+
}
71+
}
72+
}
73+
rules = newRules
74+
}
3875
</script>
3976

4077
<div class="rules-settings">
78+
<div class="tools">
79+
<label class="tool">
80+
<span class="tool-label">Filter:</span>
81+
<input
82+
type="search"
83+
placeholder="Rule Filter"
84+
class="tool-form"
85+
bind:value={filterValue}
86+
/>
87+
</label>
88+
<label class="tool">
89+
<input
90+
type="checkbox"
91+
on:click={onAllClick}
92+
checked={filteredCategories.every((category) =>
93+
category.rules.every((rule) => isErrorState(rules, rule.ruleId)),
94+
)}
95+
indeterminate={filteredCategories.some((category) =>
96+
category.rules.some((rule) => isErrorState(rules, rule.ruleId)),
97+
) &&
98+
filteredCategories.some((category) =>
99+
category.rules.some((rule) => !isErrorState(rules, rule.ruleId)),
100+
)}
101+
/>
102+
<span>All Rules</span>
103+
</label>
104+
</div>
41105
<ul class="categories">
42-
{#each categories as category (category.title)}
106+
{#each filteredCategories as category (category.title)}
43107
{#if category.rules.length}
44-
<li class="category">
108+
<li class="category {category.classes}">
45109
<button
46110
class="category-button"
47111
class:category-button--close={categoryState[category.title].close}
@@ -81,7 +145,7 @@
81145
!category.rules.every(
82146
(rule) => !isErrorState(rules, rule.ruleId),
83147
)}
84-
on:input={(e) => onAllClick(category, e)}
148+
on:input={(e) => onCategoryClick(category, e)}
85149
/>
86150
{category.title}
87151
</label>
@@ -186,7 +250,36 @@
186250
text-decoration: none;
187251
}
188252
253+
.tools {
254+
background-color: #676778;
255+
}
256+
.tool {
257+
padding: 4px;
258+
display: flex;
259+
align-items: center;
260+
}
261+
.tool-label {
262+
width: 3.5rem;
263+
flex-shrink: 0;
264+
}
265+
.tool-form {
266+
width: 100%;
267+
}
268+
189269
.category {
190270
color: #fff;
191271
}
272+
273+
.svelte-category .category-title {
274+
color: #40b3ff;
275+
}
276+
.svelte-category a > svg {
277+
color: #40b3ff;
278+
}
279+
.core-category .category-title {
280+
color: #8080f2;
281+
}
282+
.core-category a > svg {
283+
color: #8080f2;
284+
}
192285
</style>

docs-svelte-kit/src/lib/eslint/scripts/linter.js

Lines changed: 22 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -10,41 +10,50 @@ const linter = new Linter()
1010
export const categories = [
1111
{
1212
title: "Possible Errors",
13+
classes: "svelte-category",
1314
rules: [],
1415
},
1516
{
1617
title: "Security Vulnerability",
18+
classes: "svelte-category",
1719
rules: [],
1820
},
1921
{
2022
title: "Best Practices",
23+
classes: "svelte-category",
2124
rules: [],
2225
},
2326
{
2427
title: "Stylistic Issues",
28+
classes: "svelte-category",
2529
rules: [],
2630
},
2731
{
2832
title: "Extension Rules",
33+
classes: "svelte-category",
2934
rules: [],
3035
},
3136
{
3237
title: "System",
38+
classes: "svelte-category",
3339
rules: [],
3440
},
3541
{
3642
type: "problem",
3743
title: "Possible Errors (CORE)",
44+
classes: "core-category",
3845
rules: [],
3946
},
4047
{
4148
type: "suggestion",
4249
title: "Suggestions (CORE)",
50+
classes: "core-category",
4351
rules: [],
4452
},
4553
{
4654
type: "layout",
4755
title: "Layout & Formatting (CORE)",
56+
classes: "core-category",
4857
rules: [],
4958
},
5059
]
@@ -58,6 +67,7 @@ for (const rule of pluginRules) {
5867
const data = {
5968
ruleId: rule.meta.docs.ruleId,
6069
rule,
70+
classes: "svelte-rule",
6171
url: rule.meta.docs.url,
6272
}
6373
rules.push(data)
@@ -76,6 +86,7 @@ for (const [ruleId, rule] of linter.getRules()) {
7686
const data = {
7787
ruleId,
7888
rule,
89+
classes: "core-rule",
7990
url: rule.meta.docs.url,
8091
}
8192
rules.push(data)
@@ -86,9 +97,17 @@ for (const [ruleId, rule] of linter.getRules()) {
8697
DEFAULT_RULES_CONFIG[ruleId] = "error"
8798
}
8899
}
89-
/** get url */
90-
export function getURL(ruleId) {
91-
return linter.getRules().get(ruleId)?.meta.docs.url ?? ""
100+
101+
/** Get rule data */
102+
export function getRule(ruleId) {
103+
for (const cat of categories) {
104+
for (const rule of cat.rules) {
105+
if (rule.ruleId === ruleId) {
106+
return rule
107+
}
108+
}
109+
}
110+
return ""
92111
}
93112

94113
export function createLinter() {

docs-svelte-kit/src/lib/sidemenu/UlMenu.svelte

Lines changed: 7 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -84,4 +84,11 @@
8484
border: var(--size) solid transparent;
8585
border-right: var(--size) solid var(--accent-color);
8686
}
87+
88+
a.sidebar-menu-item-title:not(.active) {
89+
transition: color 0.2s linear;
90+
}
91+
a.sidebar-menu-item-title:not(.active):hover {
92+
color: #40b3ff;
93+
}
8794
</style>

0 commit comments

Comments
 (0)