Projects and Milestones filters in issue/PR lists if they are empty.",
- "screenshot": "https://github-production-user-asset-6210df.s3.amazonaws.com/83146190/262557246-4ef1c702-eece-4701-9000-0aad21c54c1b.png"
+ "description": "Hides Projects filter in issue/PR lists if it is empty.",
+ "screenshot": "https://github.com/user-attachments/assets/b690405f-b138-413d-9779-9467c160e802"
},
{
"id": "clean-conversation-headers",
- "description": "Removes duplicate information in the header of issues and PRs (\"User wants to merge X commits from Y into Z\")",
+ "description": "Removes duplicate information in the header of PRs (\"User wants to merge X commits from Y into Z\")",
"css": true,
"screenshot": "https://user-images.githubusercontent.com/44045911/112314137-a34b0680-8ce3-11eb-9e0e-8afd6c8235c2.png"
},
@@ -142,6 +148,11 @@
"description": "Adds links to browse the repository and linked files at the time of each comment.",
"screenshot": "https://github-production-user-asset-6210df.s3.amazonaws.com/83146190/252749373-9313f1d9-3d92-44a2-a1d1-2b49a29e6a5c.png"
},
+ {
+ "id": "confirm-release",
+ "description": "Adds a confirmation dialog when publishing a release, preventing accidental submissions.",
+ "screenshot": "https://github.com/user-attachments/assets/6cff805d-3825-43c4-ac20-38c76decd858"
+ },
{
"id": "conflict-marker",
"description": "Shows which PRs have conflicts in PR lists.",
@@ -170,11 +181,6 @@
"description": "Adds a link to the issues and pulls on the user profile repository tab and global search.",
"screenshot": "https://user-images.githubusercontent.com/16872793/78712349-82c54900-78e6-11ea-8328-3c2d39a78862.png"
},
- {
- "id": "convert-pr-to-draft-improvements",
- "description": "Moves the \"Convert PR to Draft\" button to the mergeability box and adds visual feedback to its confirm button.",
- "screenshot": "https://user-images.githubusercontent.com/1402241/95644892-885f3f80-0a7f-11eb-8428-8e0fb0c8dfa5.gif"
- },
{
"id": "convert-release-to-draft",
"description": "Adds a button to convert a release to draft.",
@@ -309,11 +315,6 @@
"description": "Hides inactive deployments in PRs.",
"screenshot": null
},
- {
- "id": "hide-issue-list-autocomplete",
- "description": "Removes the autocomplete on search fields.",
- "screenshot": "https://user-images.githubusercontent.com/1402241/42991841-1f057e4e-8c07-11e8-909c-b051db7a2a03.png"
- },
{
"id": "hide-low-quality-comments",
"description": "Hides reaction comments (\"+1\", \"👍\", …) (except the maintainers’) but they can still be shown.",
@@ -350,6 +351,7 @@
{
"id": "improve-shortcut-help",
"description": "Shows all of Refined GitHub’s new keyboard shortcuts in the help modal (? hotkey).",
+ "css": true,
"screenshot": "https://user-images.githubusercontent.com/29176678/36999174-9f07d33e-20bf-11e8-83e3-b3a9908a4b5f.png"
},
{
@@ -360,11 +362,12 @@
{
"id": "jump-to-conversation-close-event",
"description": "Adds a link to jump to the latest close event of a issue/PR.",
+ "css": true,
"screenshot": "https://user-images.githubusercontent.com/16872793/177792713-64219754-f8df-4629-a9ec-33259307cfe7.gif"
},
{
"id": "keyboard-navigation",
- "description": "Adds shortcuts to issues, PRs conversations, and PR file lists: j focuses the comment/file below; k focuses the comment/file above.",
+ "description": "Adds shortcuts to issues, PRs conversations, and PR file lists: j focuses the comment/file below; k focuses the comment/file above; x marks the file as viewed/unviewed.",
"screenshot": "https://user-images.githubusercontent.com/1402241/86573176-48665900-bf74-11ea-8996-a5c46cb7bdfd.gif"
},
{
@@ -418,14 +421,10 @@
"description": "Makes certain text clickable, like issue references in the issue title and discussion sidebar.",
"screenshot": "https://github.com/user-attachments/assets/1d31f695-c198-477e-a3ae-cc0687417a90"
},
- {
- "id": "linkify-user-edit-history-popup",
- "description": "Linkifies the username in the edit history popup.",
- "screenshot": "https://user-images.githubusercontent.com/1402241/88917988-9ebb7480-d260-11ea-8690-0a3440f1ebbc.png"
- },
{
"id": "linkify-user-labels",
- "description": "Links the \"Contributor\" and \"Member\" labels on comments to the author’s commits on the repo.",
+ "description": "Links the \"Contributor\", \"Member\" and \"Collaborator\" labels on comments to the author’s commits on the repo.",
+ "css": true,
"screenshot": "https://user-images.githubusercontent.com/1402241/177033344-4d4eea63-e075-4096-b2d4-f4b879f1df31.png"
},
{
@@ -466,11 +465,6 @@
"css": true,
"screenshot": "https://user-images.githubusercontent.com/1402241/245446231-28f44b59-0151-4986-8cb9-05b5645592d8.png"
},
- {
- "id": "more-conversation-filters",
- "description": "Adds Everything you’re involved in and Everything you subscribed to filters in the search box dropdown.",
- "screenshot": "https://github-production-user-asset-6210df.s3.amazonaws.com/83146190/253043952-cfb99cea-1c7b-43ad-9144-9d84bda8206f.png"
- },
{
"id": "more-dropdown-links",
"description": "Adds useful links to the repository navigation dropdown",
@@ -487,6 +481,11 @@
"description": "Adds unobtrusive netiquette reminders (old closed issues, highly-active issues, draft PRs, …).",
"screenshot": "https://github.com/user-attachments/assets/8646d663-7458-4e6d-888a-68d38110fcda"
},
+ {
+ "id": "new-milestone-button",
+ "description": "Adds a 'New Milestone' button to the milestone page.",
+ "screenshot": "https://github.com/user-attachments/assets/1fceb336-6d32-4733-afe0-9971989b1987"
+ },
{
"id": "new-or-deleted-file",
"description": "Indicates with an icon whether files in commits and PRs are being added or removed.",
@@ -507,6 +506,11 @@
"description": "Disable modals that reduce user-experience instead of enhancing it.",
"screenshot": "https://github.com/user-attachments/assets/7b63c7db-ae31-4ee8-8510-3b9db0c11f3e"
},
+ {
+ "id": "no-self-reference",
+ "description": "Warns against self-reference links, helping you avoid mistakes.",
+ "screenshot": "https://github.com/user-attachments/assets/f5f7a3da-513e-4eff-9571-1cdb72fac2bd"
+ },
{
"id": "no-unnecessary-split-diff-view",
"description": "Always uses unified diffs on files where split diffs aren’t useful.",
@@ -550,11 +554,6 @@
"description": "Makes the \"comment\" icon in issue lists link to the latest comment of the issue.",
"screenshot": "https://github-production-user-asset-6210df.s3.amazonaws.com/83146190/261159396-0610574b-ab1f-42fb-813f-ee7310a1e5b6.png"
},
- {
- "id": "pagination-hotkey",
- "description": "Adds shortcuts to navigate through pages with pagination: ← and →.",
- "screenshot": null
- },
{
"id": "parse-backticks",
"description": "GitHub renders ` text in backticks ` in some places but not others; this features fills in where forgotten.",
@@ -627,11 +626,6 @@
"description": "Suggests fixing links that are wrongly shortened by GitHub.",
"screenshot": "https://github-production-user-asset-6210df.s3.amazonaws.com/83146190/260087535-a0f19995-5f4a-44e9-87d8-cf742b9bfeed.gif"
},
- {
- "id": "prevent-pr-merge-panel-opening",
- "description": "Prevents the merge panel from automatically opening on every page load after it’s been opened once.",
- "screenshot": null
- },
{
"id": "preview-hidden-comments",
"description": "Previews hidden comments inline.",
@@ -709,7 +703,7 @@
{
"id": "quick-review-comment-deletion",
"description": "Adds a button to delete review comments in one click when editing them.",
- "screenshot": "https://user-images.githubusercontent.com/46634000/115445792-9fdd6900-a216-11eb-9ba3-6dab4d2f9d32.png"
+ "screenshot": "https://github.com/user-attachments/assets/4e56a9d8-5f6f-48f7-921a-8288c0eb5435"
},
{
"id": "reactions-avatars",
@@ -730,7 +724,7 @@
},
{
"id": "releases-dropdown",
- "description": "Adds a tags dropdown/search on tag/release pages.",
+ "description": "Adds a tags dropdown/search on release pages.",
"screenshot": "https://user-images.githubusercontent.com/1402241/231678527-f0a96112-9c30-4b49-8205-efa472bd880e.png"
},
{
@@ -764,9 +758,9 @@
"screenshot": null
},
{
- "id": "resolve-conflicts",
- "description": "Adds one-click merge conflict fixers.",
- "screenshot": "https://user-images.githubusercontent.com/1402241/54978791-45906080-4fdc-11e9-8fe1-45374f8ff636.png"
+ "id": "rerun-workflow",
+ "description": "Unwraps the \"Re-run jobs\" dropdown into individual buttons and adds a keyboard shortcut to re-run failed jobs: r f.",
+ "screenshot": "https://github.com/user-attachments/assets/67331112-f5b2-4a2b-af43-800d46bd6bf7"
},
{
"id": "restore-file",
@@ -856,6 +850,12 @@
"description": "Lets you subscribe to opening/closing events of issues in one click.",
"screenshot": "https://github-production-user-asset-6210df.s3.amazonaws.com/1402241/238186901-cbc98b51-d173-40c6-b21e-5f0bae3d800c.png"
},
+ {
+ "id": "sticky-comment-header",
+ "description": "Makes the comment header sticky when scrolling through long comments. Requires show-names to be enabled.",
+ "css": true,
+ "screenshot": "https://github.com/user-attachments/assets/0d6deca0-0f49-4aa3-ab23-0cfbde4fa4e8"
+ },
{
"id": "sticky-conversation-list-toolbar",
"description": "Makes the issue/PR list’s filters toolbar sticky.",
@@ -922,6 +922,12 @@
"description": "Adds a shortcut to toggle all similar items (minimized comments, deferred diffs, etc) at once: alt click on each button or checkbox.",
"screenshot": "https://github-production-user-asset-6210df.s3.amazonaws.com/83146190/253063446-6f556e7d-2ac5-439d-92f0-0c6d719fc86f.gif"
},
+ {
+ "id": "unclip-checks",
+ "description": "Automatically shows all checks without scrolling when expanding the checks panel.",
+ "css": true,
+ "screenshot": "https://github.com/user-attachments/assets/785fffab-43e8-4f79-8170-7c264111df9f"
+ },
{
"id": "unfinished-comments",
"description": "Notifies the user of unfinished comments in hidden tabs.",
@@ -952,12 +958,6 @@
"description": "Adds possible related pages and alternatives on 404 pages.",
"screenshot": "https://user-images.githubusercontent.com/1402241/46402857-7bdada80-c733-11e8-91a1-856573078ff5.png"
},
- {
- "id": "user-local-time",
- "description": "Shows the user local time in their hovercard (based on their last commit).",
- "css": true,
- "screenshot": "https://github-production-user-asset-6210df.s3.amazonaws.com/140871606/257039621-132bd789-e213-4a89-83ff-e1266215c60d.png"
- },
{
"id": "user-profile-follower-badge",
"description": "On profiles, it shows whether the user follows you.",
diff --git a/build/__snapshots__/imported-features.json b/build/__snapshots__/imported-features.json
index a9e143ba9136..3e264d9fca9e 100644
--- a/build/__snapshots__/imported-features.json
+++ b/build/__snapshots__/imported-features.json
@@ -2,6 +2,7 @@
"action-pr-link",
"action-used-by-link",
"actionable-pr-view-file",
+ "actions-run-removal",
"align-issue-labels",
"archive-forks-link",
"avoid-accidental-submissions",
@@ -26,12 +27,12 @@
"command-palette-navigation-shortcuts",
"comment-excess",
"comments-time-machine-links",
+ "confirm-release",
"conflict-marker",
"conventional-commits",
"conversation-activity-filter",
"conversation-authors",
"conversation-links-on-repo-lists",
- "convert-pr-to-draft-improvements",
"convert-release-to-draft",
"copy-on-y",
"create-release-shortcut",
@@ -57,7 +58,6 @@
"hidden-review-comments-indicator",
"hide-diff-signs",
"hide-inactive-deployments",
- "hide-issue-list-autocomplete",
"hide-low-quality-comments",
"hide-navigation-hover-highlight",
"hide-user-forks",
@@ -78,7 +78,6 @@
"linkify-line-numbers",
"linkify-symbolic-links",
"linkify-text",
- "linkify-user-edit-history-popup",
"linkify-user-labels",
"linkify-user-location",
"list-prs-for-branch",
@@ -86,14 +85,15 @@
"locked-issue",
"mark-merge-commits-in-list",
"mark-private-orgs",
- "more-conversation-filters",
"more-dropdown-links",
"more-file-links",
"netiquette",
+ "new-milestone-button",
"new-or-deleted-file",
"new-repo-disable-projects-and-wikis",
"no-duplicate-list-update-time",
"no-modals",
+ "no-self-reference",
"no-unnecessary-split-diff-view",
"one-click-diff-options",
"one-click-pr-or-gist",
@@ -102,7 +102,6 @@
"open-all-conversations",
"open-all-notifications",
"open-issue-to-latest-comment",
- "pagination-hotkey",
"parse-backticks",
"patch-diff-links",
"pinned-issues-update-time",
@@ -116,7 +115,6 @@
"prevent-comment-loss",
"prevent-duplicate-pr-submission",
"prevent-link-loss",
- "prevent-pr-merge-panel-opening",
"preview-hidden-comments",
"previous-next-commit-buttons",
"previous-version",
@@ -141,7 +139,7 @@
"repo-avatars",
"repo-header-info",
"repo-wide-file-finder",
- "resolve-conflicts",
+ "rerun-workflow",
"restore-file",
"rgh-deduplicator",
"rgh-dim-commits",
@@ -169,6 +167,7 @@
"small-user-avatars",
"sort-conversations-by-update-time",
"status-subscription",
+ "sticky-comment-header",
"sticky-sidebar",
"stop-redirecting-in-notification-bar",
"suggest-commit-title-limit",
@@ -179,13 +178,13 @@
"tag-changes-link",
"tags-on-commits-list",
"toggle-everything-with-alt",
+ "unclip-checks",
"unfinished-comments",
"unread-anywhere",
"unreleased-commits",
"unwrap-unnecessary-dropdowns",
"update-pr-from-base-branch",
"useful-not-found-page",
- "user-local-time",
"user-profile-follower-badge",
"vertical-front-matter",
"view-last-pr-deployment",
diff --git a/build/features.test.ts b/build/features.test.ts
index a4442ce77bf4..a0d7d5847e7c 100755
--- a/build/features.test.ts
+++ b/build/features.test.ts
@@ -18,14 +18,13 @@ const isGitIgnored = fastIgnore(readFileSync('.gitignore', 'utf8'));
const noScreenshotExceptions = new Set([
// Only add feature here if it's a shortcut only and/or extremely clear by name or description
'sort-conversations-by-update-time',
- 'prevent-pr-merge-panel-opening',
'command-palette-navigation-shortcuts',
'copy-on-y',
'create-release-shortcut',
- 'pagination-hotkey',
'profile-hotkey',
'repo-wide-file-finder',
'select-all-notifications-shortcut',
+ 'rerun-workflow',
'selection-in-new-tab',
'click-outside-modal',
'same-page-links',
@@ -52,10 +51,12 @@ const userAttachmentsRegex = /user-attachments[/]assets[/]/;
const screenshotRegex = regexJoinWithSeparator('|', [imageRegex, rghUploadsRegex, userAttachmentsRegex]);
class FeatureFile {
- readonly id: FeatureID;
+ readonly id: FeatureId;
readonly path: string;
- constructor(readonly name: string) {
- this.id = path.parse(name).name as FeatureID;
+ readonly name: string;
+ constructor(name: string) {
+ this.name = name;
+ this.id = path.parse(name).name as FeatureId;
this.path = path.join('source/features', name);
}
@@ -63,7 +64,7 @@ class FeatureFile {
return existsSync(this.path);
}
- // eslint-disable-next-line node/prefer-global/buffer, ts/no-restricted-types -- Just passing it
+ // eslint-disable-next-line @typescript-eslint/no-restricted-types, n/prefer-global/buffer -- Just passing it
contents(): Buffer {
return readFileSync(this.path);
}
@@ -129,7 +130,7 @@ function validateGql(file: FeatureFile): void {
);
}
-function validateReadme(featureId: FeatureID): void {
+function validateReadme(featureId: FeatureId): void {
const [featureMeta, duplicate] = featuresInReadme.filter(feature => feature.id === featureId);
assert(featureMeta, 'Should be described in the readme');
@@ -161,6 +162,7 @@ function validateTsx(file: FeatureFile): void {
`${file.id} uses the v4 API, so it should include \`await expectToken()\` in its init function or, if the token is optional, \`hasToken\` anywhere`,
);
}
+
if (file.contents().includes('.addCssFeature')) {
assert(
file.css.exists(),
diff --git a/build/readme-parser.ts b/build/readme-parser.ts
index 5e81d93f2893..b9282f682098 100644
--- a/build/readme-parser.ts
+++ b/build/readme-parser.ts
@@ -23,7 +23,7 @@ function extractDataFromMatch(match: RegExpMatchArray): FeatureMeta {
} = match.groups!;
if (highlightedId) {
return {
- id: highlightedId as FeatureID,
+ id: highlightedId as FeatureId,
description: parseMarkdown(highlightedDescripion + '.'),
screenshot: highlightedImage,
};
@@ -37,11 +37,11 @@ function extractDataFromMatch(match: RegExpMatchArray): FeatureMeta {
const linkLessMarkdownDescription = simpleDescription.replaceAll(/\[(.+?)\]\((.+?)\)/g, urlExtracter);
return {
- id: simpleId as FeatureID,
+ id: simpleId as FeatureId,
description: parseMarkdown(linkLessMarkdownDescription),
// `undefined` hides the key when CSS is missing
css: existsSync(`source/features/${simpleId}.css`) || undefined,
- // eslint-disable-next-line unicorn/no-null -- `null` makes the keys visible in the JSON file
+ // `null` makes the keys visible in the JSON file
screenshot: urls.find(url => screenshotRegex.test(url)) ?? null,
};
}
@@ -50,12 +50,12 @@ export function getFeaturesMeta(): FeatureMeta[] {
const readmeContent = readFileSync('readme.md', 'utf8');
return [...readmeContent.matchAll(featureRegex)]
.map(match => extractDataFromMatch(match))
- .sort((firstFeature, secondFeature) => firstFeature.id.localeCompare(secondFeature.id));
+ .toSorted((firstFeature, secondFeature) => firstFeature.id.localeCompare(secondFeature.id));
}
-export function getImportedFeatures(): FeatureID[] {
+export function getImportedFeatures(): FeatureId[] {
const contents = readFileSync('source/refined-github.ts', 'utf8');
return [...contents.matchAll(/^import '\.\/features\/([^.]+)\.js';/gm)]
- .map(match => match[1] as FeatureID)
- .sort();
+ .map(match => match[1] as FeatureId)
+ .toSorted();
}
diff --git a/eslint.config.js b/eslint.config.js
index 3841d1400877..70726d6ec77a 100644
--- a/eslint.config.js
+++ b/eslint.config.js
@@ -1,239 +1,290 @@
-import antfu from '@antfu/eslint-config';
+import xo from 'xo';
+import sveltePlugin from 'eslint-plugin-svelte';
+import svelteParser from 'svelte-eslint-parser';
+import {includeIgnoreFile} from '@eslint/compat';
+import {fileURLToPath} from 'node:url';
-export default antfu(
- {
- react: true,
- svelte: true,
- stylistic: {
- indent: 'tab',
- },
- unicorn: {
- allRecommended: true,
- },
- globals: [
- 'browser',
- ],
- typescript: {
- overrides: {
- 'ts/method-signature-style': 'off', // Disagree and it breaks types https://github.com/typescript-eslint/typescript-eslint/issues/1991
- 'ts/consistent-type-definitions': 'off', // Review later
- 'ts/consistent-type-imports': [
+const gitignorePath = fileURLToPath(new URL('.gitignore', import.meta.url));
+
+export default [
+ includeIgnoreFile(gitignorePath, 'Imported .gitignore patterns'),
+ ...xo.xoToEslintConfig([
+ {
+ semicolon: true,
+ prettier: false,
+ languageOptions: {
+ globals: {
+ browser: 'readonly',
+ },
+ },
+ rules: {
+ 'no-irregular-whitespace': 'off', // We do want to use non-breaking spaces
+
+ // Disable some unicorn rules
+ 'unicorn/expiring-todo-comments': 'off', // We just got too many, too much noise
+ 'unicorn/no-nested-ternary': 'off',
+ 'unicorn/better-regex': 'off',
+ 'unicorn/prefer-top-level-await': 'off',
+ 'unicorn/prefer-dom-node-dataset': 'off',
+ 'unicorn/prefer-ternary': 'off', // Unreadable https://github.com/sindresorhus/eslint-plugin-unicorn/issues/1633
+ 'unicorn/prevent-abbreviations': [
'error',
{
- // Preferred style
- fixStyle: 'inline-type-imports',
+ replacements: {
+ utils: false,
+ props: false,
+ ref: false,
+ nav: false,
+ },
},
],
- 'ts/explicit-function-return-type': [
+
+ // Restore errors
+ 'no-await-in-loop': 'error',
+ 'new-cap': [
'error',
{
- allowExpressions: true,
+ newIsCap: true,
+ capIsNew: true,
},
],
- },
- },
- rules: {
- 'react-refresh/only-export-components': 'off', // N/A
- 'react/no-missing-key': 'off', // N/A
- 'no-irregular-whitespace': 'off', // We do want to use non-breaking spaces
- 'jsdoc/check-alignment': 'off', // Not enough to be useful
+ 'no-console': 'off',
+ '@stylistic/jsx-quotes': 'off', // Keep existing quote style in JSX
+ '@stylistic/function-paren-newline': 'off', // Allow JSX on separate lines from parens
+ 'promise/prefer-await-to-then': ['error', {strict: false}], // Allows `await x.catch()`
- // Antfu style disagreements
- 'regexp/no-useless-character-class': 'off', // [/] is more readable than \/
- 'style/object-curly-spacing': ['error', 'never'], // Unnecessary change for now
- 'style/block-spacing': ['error', 'never'], // Same
- 'jsonc/array-bracket-spacing': 'off', // Same
- 'style/brace-style': ['error', '1tbs'], // Naw, man
- 'style/semi': ['error', 'always'],
- 'style/member-delimiter-style': ['error', {
- multiline: {
- delimiter: 'semi',
- },
- }],
- 'style/arrow-parens': ['error', 'as-needed'],
- 'prefer-template': 'off', // When there's a single `+` templates are less readable
- 'style/jsx-one-expression-per-line': 'off', // Terrible for inline elements, e.g. text
+ // Allow unassigned imports for CSS and feature files
+ 'import-x/no-unassigned-import': ['error', {
+ allow: [
+ '**/*.css',
+ '**/*.scss',
+ '**/*.sass',
+ '**/*.less',
+ '**/features/**',
+ '**/github-helpers/**',
+ 'webext-bugs/*',
+ 'vite/client',
+ 'webext-dynamic-content-scripts',
+ ],
+ }],
- // Disable some unicorn rules
- 'unicorn/expiring-todo-comments': 'off', // We just got too many, too much noise
- 'unicorn/no-nested-ternary': 'off',
- 'unicorn/better-regex': 'off',
- 'unicorn/prefer-top-level-await': 'off',
- 'unicorn/prefer-dom-node-dataset': 'off',
- 'unicorn/prefer-ternary': 'off', // Unreadable https://github.com/sindresorhus/eslint-plugin-unicorn/issues/1633
- 'unicorn/prevent-abbreviations': [
- 'error',
- {
- replacements: {
- props: false,
- ref: false,
- nav: false,
+ 'no-restricted-imports': [
+ 'error',
+ {
+ paths: [
+ {
+ name: 'select-dom',
+ importNames: ['$', 'expectElement'],
+ message: 'Import $ or $optional from `select-dom/strict.js` instead',
+ },
+ ],
},
- },
- ],
- // Restore errors
- 'no-await-in-loop': 'error',
- 'new-cap': [
- 'error',
- {
- newIsCap: true,
- capIsNew: true,
- },
- ],
+ ],
+ 'no-restricted-syntax': [
+ 'error',
+ {
+ selector:
+ ':matches([callee.name=delegate], [callee.name=$], [callee.name=$$], [callee.name=$optional], [callee.name=observe], [callee.property.name=querySelector], [callee.property.name=querySelectorAll], [callee.property.name=closest])[arguments.0.value=/,/][arguments.0.value.length>=20]:not([arguments.0.value=/:has|:is/])',
+ message: 'Instead of a single string, pass an array of selectors and add comments to each selector',
+ },
+ {
+ selector:
+ ':matches([callee.name=delegate], [callee.name=$], [callee.name=$$], [callee.name=$optional], [callee.name=observe], [callee.property.name=querySelector], [callee.property.name=querySelectorAll], [callee.property.name=closest])[arguments.0.type=ArrayExpression][arguments.0.elements.length=1]:not([arguments.0.value=/:has|:is/])',
+ message: 'If it\'s a single selector, use a single string instead of an array',
+ },
+ {
+ selector: 'TSNonNullExpression > CallExpression > [name=$optional]',
+ message: 'Use `$()` instead of non-null `$optional()`. Use it as `import {expectElement as $}`',
+ },
+ {
+ selector: 'TSNonNullExpression > CallExpression > [name=$]',
+ message: 'Unused null expression: !',
+ },
+ {
+ selector: 'MemberExpression[optional=true][object.callee.name=$]',
+ message: 'Either use $optional() with `?.` or $() without. $() will throw when the element is not found.',
+ },
+ {
+ message: 'Init functions wrapped with onetime() must have a name ending with "Once"',
+ selector: 'ObjectExpression > Property[key.name=init] > CallExpression[callee.name=onetime]:not([arguments.0.name=/Once$/])',
+ },
+ {
+ message: 'Init functions that run once, cannot accept a signal: https://github.com/refined-github/refined-github/pull/8072',
+ selector: 'FunctionDeclaration[id.name=/Once$/] > Identifier[name=signal]',
+ },
+ {
+ message: 'Elements with data-hotkey must have a title or aria-label in the format "Hotkey: Makes whitespace characters visible
Adds one-click merge conflict fixers -
+
Tells you whether you're looking at the latest version of a repository, or if there are any unreleased commits +
Shows how far behind a PR head branch is + tells you its base commit
@@ -105,11 +105,12 @@ https://github.com/refined-github/refined-github/wiki/Contributing#metadata-guid
- [](# "repo-avatars") [Adds the profile picture to the header of public repositories.](https://github-production-user-asset-6210df.s3.amazonaws.com/1402241/255323568-aee4d90e-844e-41e8-880a-ce466826516c.png)
- [](# "quick-new-issue") [Adds a link to create issues from anywhere in a repository.](https://github-production-user-asset-6210df.s3.amazonaws.com/1402241/274816033-820ec518-049d-4248-9f8a-27b9423e350b.png)
- [](# "small-user-avatars") [Shows a small avatar next to the username in issue/PR lists and mentions.](https://github-production-user-asset-6210df.s3.amazonaws.com/1402241/271184107-24ec471e-54d1-434a-a5f2-615902d2cad9.png)
-- [](# "unreleased-commits") 🔥 [Tells you whether you're looking at the latest version of a repository, or if there are any unreleased commits.](https://github-production-user-asset-6210df.s3.amazonaws.com/1402241/267236196-8564c193-a3c7-4248-9735-54749c1990c7.png)
- [](# "action-pr-link") 🔥 [Adds a link back to the PR that ran the workflow.](https://github-production-user-asset-6210df.s3.amazonaws.com/50487467/241645264-076a0137-36a2-4fd0-a66e-735ef3b3a563.png)
- [](# "mobile-tabs") [Makes the tabs more compact on mobile so more of them can be seen.](https://user-images.githubusercontent.com/1402241/245446231-28f44b59-0151-4986-8cb9-05b5645592d8.png)
- [](# "repo-header-info") [Shows whether a repo is a fork and adds the number of stars to its header.](https://github-production-user-asset-6210df.s3.amazonaws.com/1402241/267216946-404d79ab-46d7-4bc8-ba88-ae8f8029150d.png)
- [](# "visit-tag") [When navigating a repo's file on a specific tag, it adds a link to see the release/tag itself.](https://github-production-user-asset-6210df.s3.amazonaws.com/1402241/285123739-e5f4fa0a-3f48-49ef-9b87-2fd6f183c923.png)
+- [](# "actions-run-removal") [Lets you cancel or delete workflow runs faster from the workflow list.](https://github.com/user-attachments/assets/a054f9b4-9d56-40c0-9aac-09a8b07bbb3b)
+- [](# "rerun-workflow") [Unwraps the "Re-run jobs" dropdown into individual buttons and adds a keyboard shortcut to re-run failed jobs: r f](https://github.com/user-attachments/assets/67331112-f5b2-4a2b-af43-800d46bd6bf7).
- {title}
+ {title} v{version}