diff --git a/.eslintrc.yaml b/.eslintrc.yaml index f84cb39a41..5f291f13e7 100644 --- a/.eslintrc.yaml +++ b/.eslintrc.yaml @@ -487,7 +487,7 @@ rules: no-jquery/no-visibility: [2] no-jquery/no-when: [2] no-jquery/no-wrap: [2] - no-jquery/variable-pattern: [0] + no-jquery/variable-pattern: [2] no-label-var: [2] no-labels: [0] # handled by no-restricted-syntax no-lone-blocks: [2] diff --git a/web_src/js/components/RepoBranchTagSelector.vue b/web_src/js/components/RepoBranchTagSelector.vue index 70ce9bd6a0..83289c8852 100644 --- a/web_src/js/components/RepoBranchTagSelector.vue +++ b/web_src/js/components/RepoBranchTagSelector.vue @@ -123,7 +123,7 @@ const sfc = { return -1; }, scrollToActive() { - let el = this.$refs[`listItem${this.active}`]; + let el = this.$refs[`listItem${this.active}`]; // eslint-disable-line no-jquery/variable-pattern if (!el || !el.length) return; if (Array.isArray(el)) { el = el[0]; diff --git a/web_src/js/features/common-global.js b/web_src/js/features/common-global.js index ee4ade1f04..d99f606c8a 100644 --- a/web_src/js/features/common-global.js +++ b/web_src/js/features/common-global.js @@ -231,8 +231,8 @@ export function initDropzone(el) { init() { this.on('success', (file, data) => { file.uuid = data.uuid; - const input = $(``).val(data.uuid); - $dropzone.find('.files').append(input); + const $input = $(``).val(data.uuid); + $dropzone.find('.files').append($input); // Create a "Copy Link" element, to conveniently copy the image // or file link as Markdown to the clipboard const copyLinkElement = document.createElement('div'); @@ -305,15 +305,15 @@ export function initGlobalLinkActions() { filter += `#${$this.attr('data-modal-id')}`; } - const dialog = $(`.delete.modal${filter}`); - dialog.find('.name').text($this.data('name')); + const $dialog = $(`.delete.modal${filter}`); + $dialog.find('.name').text($this.data('name')); for (const [key, value] of Object.entries(dataArray)) { if (key && key.startsWith('data')) { - dialog.find(`.${key}`).text(value); + $dialog.find(`.${key}`).text(value); } } - dialog.modal({ + $dialog.modal({ closable: false, onApprove: async () => { if ($this.data('type') === 'form') { @@ -380,8 +380,8 @@ function initGlobalShowModal() { $attrTarget.text(attrib.value); // FIXME: it should be more strict here, only handle div/span/p } } - const colorPickers = $modal.find('.color-picker'); - if (colorPickers.length > 0) { + const $colorPickers = $modal.find('.color-picker'); + if ($colorPickers.length > 0) { initCompColorPicker(); // FIXME: this might cause duplicate init } $modal.modal('setting', { diff --git a/web_src/js/features/comp/LabelEdit.js b/web_src/js/features/comp/LabelEdit.js index 2a22190e10..2e7e1df669 100644 --- a/web_src/js/features/comp/LabelEdit.js +++ b/web_src/js/features/comp/LabelEdit.js @@ -6,23 +6,23 @@ function isExclusiveScopeName(name) { } function updateExclusiveLabelEdit(form) { - const nameInput = $(`${form} .label-name-input`); - const exclusiveField = $(`${form} .label-exclusive-input-field`); - const exclusiveCheckbox = $(`${form} .label-exclusive-input`); - const exclusiveWarning = $(`${form} .label-exclusive-warning`); + const $nameInput = $(`${form} .label-name-input`); + const $exclusiveField = $(`${form} .label-exclusive-input-field`); + const $exclusiveCheckbox = $(`${form} .label-exclusive-input`); + const $exclusiveWarning = $(`${form} .label-exclusive-warning`); - if (isExclusiveScopeName(nameInput.val())) { - exclusiveField.removeClass('muted'); - exclusiveField.removeAttr('aria-disabled'); - if (exclusiveCheckbox.prop('checked') && exclusiveCheckbox.data('exclusive-warn')) { - exclusiveWarning.removeClass('gt-hidden'); + if (isExclusiveScopeName($nameInput.val())) { + $exclusiveField.removeClass('muted'); + $exclusiveField.removeAttr('aria-disabled'); + if ($exclusiveCheckbox.prop('checked') && $exclusiveCheckbox.data('exclusive-warn')) { + $exclusiveWarning.removeClass('gt-hidden'); } else { - exclusiveWarning.addClass('gt-hidden'); + $exclusiveWarning.addClass('gt-hidden'); } } else { - exclusiveField.addClass('muted'); - exclusiveField.attr('aria-disabled', 'true'); - exclusiveWarning.addClass('gt-hidden'); + $exclusiveField.addClass('muted'); + $exclusiveField.attr('aria-disabled', 'true'); + $exclusiveWarning.addClass('gt-hidden'); } } @@ -46,18 +46,18 @@ export function initCompLabelEdit(selector) { $('.edit-label .color-picker').minicolors('value', $(this).data('color')); $('#label-modal-id').val($(this).data('id')); - const nameInput = $('.edit-label .label-name-input'); - nameInput.val($(this).data('title')); + const $nameInput = $('.edit-label .label-name-input'); + $nameInput.val($(this).data('title')); - const isArchivedCheckbox = $('.edit-label .label-is-archived-input'); - isArchivedCheckbox.prop('checked', this.hasAttribute('data-is-archived')); + const $isArchivedCheckbox = $('.edit-label .label-is-archived-input'); + $isArchivedCheckbox.prop('checked', this.hasAttribute('data-is-archived')); - const exclusiveCheckbox = $('.edit-label .label-exclusive-input'); - exclusiveCheckbox.prop('checked', this.hasAttribute('data-exclusive')); + const $exclusiveCheckbox = $('.edit-label .label-exclusive-input'); + $exclusiveCheckbox.prop('checked', this.hasAttribute('data-exclusive')); // Warn when label was previously not exclusive and used in issues - exclusiveCheckbox.data('exclusive-warn', + $exclusiveCheckbox.data('exclusive-warn', $(this).data('num-issues') > 0 && - (!this.hasAttribute('data-exclusive') || !isExclusiveScopeName(nameInput.val()))); + (!this.hasAttribute('data-exclusive') || !isExclusiveScopeName($nameInput.val()))); updateExclusiveLabelEdit('.edit-label'); $('.edit-label .label-desc-input').val($(this).data('description')); diff --git a/web_src/js/features/comp/ReactionSelector.js b/web_src/js/features/comp/ReactionSelector.js index 76834f8844..6df4bde069 100644 --- a/web_src/js/features/comp/ReactionSelector.js +++ b/web_src/js/features/comp/ReactionSelector.js @@ -17,21 +17,21 @@ export function initCompReactionSelector($parent) { const data = await res.json(); if (data && (data.html || data.empty)) { - const content = $(this).closest('.content'); - let react = content.find('.segment.reactions'); - if ((!data.empty || data.html === '') && react.length > 0) { - react.remove(); + const $content = $(this).closest('.content'); + let $react = $content.find('.segment.reactions'); + if ((!data.empty || data.html === '') && $react.length > 0) { + $react.remove(); } if (!data.empty) { - const attachments = content.find('.segment.bottom:first'); - react = $(data.html); - if (attachments.length > 0) { - react.insertBefore(attachments); + const $attachments = $content.find('.segment.bottom:first'); + $react = $(data.html); + if ($attachments.length > 0) { + $react.insertBefore($attachments); } else { - react.appendTo(content); + $react.appendTo($content); } - react.find('.dropdown').dropdown(); - initCompReactionSelector(react); + $react.find('.dropdown').dropdown(); + initCompReactionSelector($react); } } }); diff --git a/web_src/js/features/notification.js b/web_src/js/features/notification.js index 1c95804e4c..b04ee0bf52 100644 --- a/web_src/js/features/notification.js +++ b/web_src/js/features/notification.js @@ -45,9 +45,9 @@ async function receiveUpdateCount(event) { } export function initNotificationCount() { - const notificationCount = $('.notification_count'); + const $notificationCount = $('.notification_count'); - if (!notificationCount.length) { + if (!$notificationCount.length) { return; } @@ -55,7 +55,7 @@ export function initNotificationCount() { const startPeriodicPoller = (timeout, lastCount) => { if (timeout <= 0 || !Number.isFinite(timeout)) return; usingPeriodicPoller = true; - lastCount = lastCount ?? notificationCount.text(); + lastCount = lastCount ?? $notificationCount.text(); setTimeout(async () => { await updateNotificationCountWithCallback(startPeriodicPoller, timeout, lastCount); }, timeout); @@ -143,8 +143,8 @@ async function updateNotificationCountWithCallback(callback, timeout, lastCount) } async function updateNotificationTable() { - const notificationDiv = $('#notification_div'); - if (notificationDiv.length > 0) { + const $notificationDiv = $('#notification_div'); + if ($notificationDiv.length > 0) { try { const params = new URLSearchParams(window.location.search); params.set('div-only', true); @@ -158,7 +158,7 @@ async function updateNotificationTable() { const data = await response.text(); if ($(data).data('sequence-number') === notificationSequenceNumber) { - notificationDiv.replaceWith(data); + $notificationDiv.replaceWith(data); initNotificationsTable(); } } catch (error) { @@ -177,14 +177,14 @@ async function updateNotificationCount() { const data = await response.json(); - const notificationCount = $('.notification_count'); + const $notificationCount = $('.notification_count'); if (data.new === 0) { - notificationCount.addClass('gt-hidden'); + $notificationCount.addClass('gt-hidden'); } else { - notificationCount.removeClass('gt-hidden'); + $notificationCount.removeClass('gt-hidden'); } - notificationCount.text(`${data.new}`); + $notificationCount.text(`${data.new}`); return `${data.new}`; } catch (error) { diff --git a/web_src/js/features/repo-diff.js b/web_src/js/features/repo-diff.js index 7c7c238b1a..ffe3fada85 100644 --- a/web_src/js/features/repo-diff.js +++ b/web_src/js/features/repo-diff.js @@ -99,10 +99,10 @@ function initRepoDiffConversationForm() { const data = await response.text(); if ($(this).closest('.conversation-holder').length) { - const conversation = $(data); - $(this).closest('.conversation-holder').replaceWith(conversation); - conversation.find('.dropdown').dropdown(); - initCompReactionSelector(conversation); + const $conversation = $(data); + $(this).closest('.conversation-holder').replaceWith($conversation); + $conversation.find('.dropdown').dropdown(); + initCompReactionSelector($conversation); } else { window.location.reload(); } @@ -211,8 +211,8 @@ function initRepoDiffShowMore() { export function initRepoDiffView() { initRepoDiffConversationForm(); - const diffFileList = $('#diff-file-list'); - if (diffFileList.length === 0) return; + const $diffFileList = $('#diff-file-list'); + if ($diffFileList.length === 0) return; initDiffFileTree(); initDiffCommitSelect(); initRepoDiffShowMore(); diff --git a/web_src/js/features/repo-editor.js b/web_src/js/features/repo-editor.js index 4fe7ed8a4d..fea98e2df8 100644 --- a/web_src/js/features/repo-editor.js +++ b/web_src/js/features/repo-editor.js @@ -15,9 +15,9 @@ function initEditPreviewTab($form) { const $this = $(this); let context = `${$this.data('context')}/`; const mode = $this.data('markup-mode') || 'comment'; - const treePathEl = $form.find('input#tree_path'); - if (treePathEl.length > 0) { - context += treePathEl.val(); + const $treePathEl = $form.find('input#tree_path'); + if ($treePathEl.length > 0) { + context += $treePathEl.val(); } context = context.substring(0, context.lastIndexOf('/')); @@ -25,7 +25,7 @@ function initEditPreviewTab($form) { formData.append('mode', mode); formData.append('context', context); formData.append('text', $form.find(`.tab[data-tab="${$tabMenu.data('write')}"] textarea`).val()); - formData.append('file_path', treePathEl.val()); + formData.append('file_path', $treePathEl.val()); try { const response = await POST($this.data('url'), {data: formData}); const data = await response.text(); @@ -78,11 +78,11 @@ export function initRepoEditor() { const joinTreePath = ($fileNameEl) => { const parts = []; $('.breadcrumb span.section').each(function () { - const element = $(this); - if (element.find('a').length) { - parts.push(element.find('a').text()); + const $element = $(this); + if ($element.find('a').length) { + parts.push($element.find('a').text()); } else { - parts.push(element.text()); + parts.push($element.text()); } }); if ($fileNameEl.val()) parts.push($fileNameEl.val()); @@ -181,6 +181,6 @@ export function renderPreviewPanelContent($panelPreviewer, data) { $panelPreviewer.html(data); initMarkupContent(); - const refIssues = $panelPreviewer.find('p .ref-issue'); - attachRefIssueContextPopup(refIssues); + const $refIssues = $panelPreviewer.find('p .ref-issue'); + attachRefIssueContextPopup($refIssues); } diff --git a/web_src/js/features/repo-graph.js b/web_src/js/features/repo-graph.js index c83f448b76..4fbf95b9d5 100644 --- a/web_src/js/features/repo-graph.js +++ b/web_src/js/features/repo-graph.js @@ -63,10 +63,10 @@ export function initRepoGraphGit() { (async () => { const response = await GET(String(ajaxUrl)); const html = await response.text(); - const div = $(html); - $('#pagination').html(div.find('#pagination').html()); - $('#rel-container').html(div.find('#rel-container').html()); - $('#rev-container').html(div.find('#rev-container').html()); + const $div = $(html); + $('#pagination').html($div.find('#pagination').html()); + $('#rel-container').html($div.find('#rel-container').html()); + $('#rev-container').html($div.find('#rev-container').html()); $('#loading-indicator').addClass('gt-hidden'); $('#rel-container').removeClass('gt-hidden'); $('#rev-container').removeClass('gt-hidden'); diff --git a/web_src/js/features/repo-home.js b/web_src/js/features/repo-home.js index bbba7b103e..50f324d788 100644 --- a/web_src/js/features/repo-home.js +++ b/web_src/js/features/repo-home.js @@ -6,55 +6,55 @@ import {POST} from '../modules/fetch.js'; const {appSubUrl} = window.config; export function initRepoTopicBar() { - const mgrBtn = $('#manage_topic'); - if (!mgrBtn.length) return; - const editDiv = $('#topic_edit'); - const viewDiv = $('#repo-topics'); - const saveBtn = $('#save_topic'); - const topicDropdown = $('#topic_edit .dropdown'); - const topicForm = editDiv; // the old logic, editDiv is topicForm - const topicDropdownSearch = topicDropdown.find('input.search'); + const $mgrBtn = $('#manage_topic'); + if (!$mgrBtn.length) return; + const $editDiv = $('#topic_edit'); + const $viewDiv = $('#repo-topics'); + const $saveBtn = $('#save_topic'); + const $topicDropdown = $('#topic_edit .dropdown'); + const $topicForm = $editDiv; // the old logic, $editDiv is topicForm + const $topicDropdownSearch = $topicDropdown.find('input.search'); const topicPrompts = { - countPrompt: topicDropdown.attr('data-text-count-prompt'), - formatPrompt: topicDropdown.attr('data-text-format-prompt'), + countPrompt: $topicDropdown.attr('data-text-count-prompt'), + formatPrompt: $topicDropdown.attr('data-text-format-prompt'), }; - mgrBtn.on('click', () => { - hideElem(viewDiv); - showElem(editDiv); - topicDropdownSearch.focus(); + $mgrBtn.on('click', () => { + hideElem($viewDiv); + showElem($editDiv); + $topicDropdownSearch.trigger('focus'); }); $('#cancel_topic_edit').on('click', () => { - hideElem(editDiv); - showElem(viewDiv); - mgrBtn.focus(); + hideElem($editDiv); + showElem($viewDiv); + $mgrBtn.trigger('focus'); }); - saveBtn.on('click', async () => { + $saveBtn.on('click', async () => { const topics = $('input[name=topics]').val(); const data = new FormData(); data.append('topics', topics); - const response = await POST(saveBtn.attr('data-link'), {data}); + const response = await POST($saveBtn.attr('data-link'), {data}); if (response.ok) { const responseData = await response.json(); if (responseData.status === 'ok') { - viewDiv.children('.topic').remove(); + $viewDiv.children('.topic').remove(); if (topics.length) { const topicArray = topics.split(','); topicArray.sort(); for (const topic of topicArray) { - const link = $(''); - link.attr('href', `${appSubUrl}/explore/repos?q=${encodeURIComponent(topic)}&topic=1`); - link.text(topic); - link.insertBefore(mgrBtn); // insert all new topics before manage button + const $link = $(''); + $link.attr('href', `${appSubUrl}/explore/repos?q=${encodeURIComponent(topic)}&topic=1`); + $link.text(topic); + $link.insertBefore($mgrBtn); // insert all new topics before manage button } } - hideElem(editDiv); - showElem(viewDiv); + hideElem($editDiv); + showElem($viewDiv); } } else if (response.status === 422) { const responseData = await response.json(); @@ -62,10 +62,10 @@ export function initRepoTopicBar() { topicPrompts.formatPrompt = responseData.message; const {invalidTopics} = responseData; - const topicLabels = topicDropdown.children('a.ui.label'); + const $topicLabels = $topicDropdown.children('a.ui.label'); for (const [index, value] of topics.split(',').entries()) { if (invalidTopics.includes(value)) { - topicLabels.eq(index).removeClass('green').addClass('red'); + $topicLabels.eq(index).removeClass('green').addClass('red'); } } } else { @@ -74,10 +74,10 @@ export function initRepoTopicBar() { } // Always validate the form - topicForm.form('validate form'); + $topicForm.form('validate form'); }); - topicDropdown.dropdown({ + $topicDropdown.dropdown({ allowAdditions: true, forceSelection: false, fullTextSearch: 'exact', @@ -100,7 +100,7 @@ export function initRepoTopicBar() { const query = stripTags(this.urlData.query.trim()); let found_query = false; const current_topics = []; - topicDropdown.find('a.label.visible').each((_, el) => { + $topicDropdown.find('a.label.visible').each((_, el) => { current_topics.push(el.getAttribute('data-value')); }); @@ -150,15 +150,15 @@ export function initRepoTopicBar() { }); $.fn.form.settings.rules.validateTopic = function (_values, regExp) { - const topics = topicDropdown.children('a.ui.label'); - const status = topics.length === 0 || topics.last().attr('data-value').match(regExp); + const $topics = $topicDropdown.children('a.ui.label'); + const status = $topics.length === 0 || $topics.last().attr('data-value').match(regExp); if (!status) { - topics.last().removeClass('green').addClass('red'); + $topics.last().removeClass('green').addClass('red'); } - return status && topicDropdown.children('a.ui.label.red').length === 0; + return status && $topicDropdown.children('a.ui.label.red').length === 0; }; - topicForm.form({ + $topicForm.form({ on: 'change', inline: true, fields: { diff --git a/web_src/js/features/repo-issue.js b/web_src/js/features/repo-issue.js index 01c30a9e53..bca062bcc7 100644 --- a/web_src/js/features/repo-issue.js +++ b/web_src/js/features/repo-issue.js @@ -144,9 +144,9 @@ export function initRepoIssueSidebarList() { $('.menu .ui.dropdown.label-filter').on('keydown', (e) => { if (e.altKey && e.keyCode === 13) { - const selectedItems = $('.menu .ui.dropdown.label-filter .menu .item.selected'); - if (selectedItems.length > 0) { - excludeLabel($(selectedItems[0])); + const $selectedItems = $('.menu .ui.dropdown.label-filter .menu .item.selected'); + if ($selectedItems.length > 0) { + excludeLabel($($selectedItems[0])); } } }); @@ -214,12 +214,12 @@ export function initRepoIssueDependencyDelete() { export function initRepoIssueCodeCommentCancel() { // Cancel inline code comment $(document).on('click', '.cancel-code-comment', (e) => { - const form = $(e.currentTarget).closest('form'); - if (form.length > 0 && form.hasClass('comment-form')) { - form.addClass('gt-hidden'); - showElem(form.closest('.comment-code-cloud').find('button.comment-form-reply')); + const $form = $(e.currentTarget).closest('form'); + if ($form.length > 0 && $form.hasClass('comment-form')) { + $form.addClass('gt-hidden'); + showElem($form.closest('.comment-code-cloud').find('button.comment-form-reply')); } else { - form.closest('.comment-code-cloud').remove(); + $form.closest('.comment-code-cloud').remove(); } }); } @@ -370,10 +370,10 @@ export function initRepoIssueComments() { }); $(document).on('click', (event) => { - const urlTarget = $(':target'); - if (urlTarget.length === 0) return; + const $urlTarget = $(':target'); + if ($urlTarget.length === 0) return; - const urlTargetId = urlTarget.attr('id'); + const urlTargetId = $urlTarget.attr('id'); if (!urlTargetId) return; if (!/^(issue|pull)(comment)?-\d+$/.test(urlTargetId)) return; @@ -390,18 +390,18 @@ export function initRepoIssueComments() { export async function handleReply($el) { hideElem($el); - const form = $el.closest('.comment-code-cloud').find('.comment-form'); - form.removeClass('gt-hidden'); + const $form = $el.closest('.comment-code-cloud').find('.comment-form'); + $form.removeClass('gt-hidden'); - const $textarea = form.find('textarea'); + const $textarea = $form.find('textarea'); let editor = getComboMarkdownEditor($textarea); if (!editor) { // FIXME: the initialization of the dropzone is not consistent. // When the page is loaded, the dropzone is initialized by initGlobalDropzone, but the editor is not initialized. // When the form is submitted and partially reload, none of them is initialized. - const dropzone = form.find('.dropzone')[0]; + const dropzone = $form.find('.dropzone')[0]; if (!dropzone.dropzone) initDropzone(dropzone); - editor = await initComboMarkdownEditor(form.find('.combo-markdown-editor')); + editor = await initComboMarkdownEditor($form.find('.combo-markdown-editor')); } editor.focus(); return editor; @@ -413,30 +413,30 @@ export function initRepoPullRequestReview() { if (window.history.scrollRestoration !== 'manual') { window.history.scrollRestoration = 'manual'; } - const commentDiv = $(window.location.hash); - if (commentDiv) { + const $commentDiv = $(window.location.hash); + if ($commentDiv) { // get the name of the parent id - const groupID = commentDiv.closest('div[id^="code-comments-"]').attr('id'); + const groupID = $commentDiv.closest('div[id^="code-comments-"]').attr('id'); if (groupID && groupID.startsWith('code-comments-')) { const id = groupID.slice(14); - const ancestorDiffBox = commentDiv.closest('.diff-file-box'); + const $ancestorDiffBox = $commentDiv.closest('.diff-file-box'); // on pages like conversation, there is no diff header - const diffHeader = ancestorDiffBox.find('.diff-file-header'); + const $diffHeader = $ancestorDiffBox.find('.diff-file-header'); // offset is for scrolling let offset = 30; - if (diffHeader[0]) { - offset += $('.diff-detail-box').outerHeight() + diffHeader.outerHeight(); + if ($diffHeader[0]) { + offset += $('.diff-detail-box').outerHeight() + $diffHeader.outerHeight(); } $(`#show-outdated-${id}`).addClass('gt-hidden'); $(`#code-comments-${id}`).removeClass('gt-hidden'); $(`#code-preview-${id}`).removeClass('gt-hidden'); $(`#hide-outdated-${id}`).removeClass('gt-hidden'); // if the comment box is folded, expand it - if (ancestorDiffBox.attr('data-folded') && ancestorDiffBox.attr('data-folded') === 'true') { - setFileFolding(ancestorDiffBox[0], ancestorDiffBox.find('.fold-file')[0], false); + if ($ancestorDiffBox.attr('data-folded') && $ancestorDiffBox.attr('data-folded') === 'true') { + setFileFolding($ancestorDiffBox[0], $ancestorDiffBox.find('.fold-file')[0], false); } window.scrollTo({ - top: commentDiv.offset().top - offset, + top: $commentDiv.offset().top - offset, behavior: 'instant' }); } @@ -504,12 +504,12 @@ export function initRepoPullRequestReview() { const side = $(this).data('side'); const idx = $(this).data('idx'); const path = $(this).closest('[data-path]').data('path'); - const tr = $(this).closest('tr'); - const lineType = tr.data('line-type'); + const $tr = $(this).closest('tr'); + const lineType = $tr.data('line-type'); - let ntr = tr.next(); - if (!ntr.hasClass('add-comment')) { - ntr = $(` + let $ntr = $tr.next(); + if (!$ntr.hasClass('add-comment')) { + $ntr = $(`