WebUI: prefer range based for loop

Using `entries()` can also save the work of manually handling the index variable.

PR #23182.
This commit is contained in:
Chocobo1
2025-08-31 21:54:48 +08:00
committed by GitHub
parent b851caa6b9
commit dffd27a879
14 changed files with 61 additions and 82 deletions

View File

@@ -71,6 +71,7 @@ export default [
"Stylistic/semi": "error", "Stylistic/semi": "error",
"Stylistic/spaced-comment": ["error", "always", { exceptions: ["*"] }], "Stylistic/spaced-comment": ["error", "always", { exceptions: ["*"] }],
"Unicorn/no-array-for-each": "error", "Unicorn/no-array-for-each": "error",
"Unicorn/no-for-loop": "error",
"Unicorn/no-zero-fractions": "error", "Unicorn/no-zero-fractions": "error",
"Unicorn/prefer-number-properties": "error", "Unicorn/prefer-number-properties": "error",
"Unicorn/switch-case-braces": ["error", "avoid"] "Unicorn/switch-case-braces": ["error", "avoid"]

View File

@@ -167,8 +167,7 @@
span.textContent = ""; span.textContent = "";
// Update renamed column for matched rows // Update renamed column for matched rows
for (let i = 0; i < matchedRows.length; ++i) { for (const row of matchedRows) {
const row = matchedRows[i];
const element = document.getElementById(`filesTablefileRenamed${row.rowId}`); const element = document.getElementById(`filesTablefileRenamed${row.rowId}`);
if (element === null) if (element === null)
continue; continue;

View File

@@ -175,8 +175,7 @@ window.qBittorrent.Client ??= (() => {
const uploadTorrentFiles = (files) => { const uploadTorrentFiles = (files) => {
const fileNames = []; const fileNames = [];
const formData = new FormData(); const formData = new FormData();
for (let i = 0; i < files.length; ++i) { for (const [i, file] of files.entries()) {
const file = files[i];
fileNames.push(file.name); fileNames.push(file.name);
// send dummy file name as file name won't be used and may not be encoded properly // send dummy file name as file name won't be used and may not be encoded properly
formData.append("file", file, i); formData.append("file", file, i);
@@ -193,8 +192,7 @@ window.qBittorrent.Client ??= (() => {
} }
const json = await response.json(); const json = await response.json();
for (let i = 0; i < json.length; ++i) { for (const [i, metadata] of json.entries()) {
const metadata = json[i];
const title = metadata.name || fileNames[i]; const title = metadata.name || fileNames[i];
const hash = metadata.infohash_v2 || metadata.infohash_v1; const hash = metadata.infohash_v2 || metadata.infohash_v1;
createAddTorrentWindow(title, hash, metadata); createAddTorrentWindow(title, hash, metadata);

View File

@@ -106,8 +106,7 @@ window.qBittorrent.ContextMenu ??= (() => {
// position the sub-menu // position the sub-menu
const uls = this.menu.getElementsByTagName("ul"); const uls = this.menu.getElementsByTagName("ul");
for (let i = 0; i < uls.length; ++i) { for (const ul of uls) {
const ul = uls[i];
if (ul.classList.contains("scrollableMenu")) if (ul.classList.contains("scrollableMenu"))
ul.style.maxHeight = `${scrollableMenuMaxHeight}px`; ul.style.maxHeight = `${scrollableMenuMaxHeight}px`;
const rectParent = ul.parentNode.getBoundingClientRect(); const rectParent = ul.parentNode.getBoundingClientRect();
@@ -536,9 +535,7 @@ window.qBittorrent.ContextMenu ??= (() => {
const sortedTags = [...tags.keys()]; const sortedTags = [...tags.keys()];
sortedTags.sort(window.qBittorrent.Misc.naturalSortCollator.compare); sortedTags.sort(window.qBittorrent.Misc.naturalSortCollator.compare);
for (let i = 0; i < sortedTags.length; ++i) { for (const [i, tagName] of sortedTags.entries()) {
const tagName = sortedTags[i];
const input = document.createElement("input"); const input = document.createElement("input");
input.type = "checkbox"; input.type = "checkbox";
input.addEventListener("click", (event) => { input.addEventListener("click", (event) => {

View File

@@ -634,8 +634,7 @@ window.qBittorrent.DynamicTable ??= (() => {
updateHeader(header) { updateHeader(header) {
const ths = this.getRowCells(header); const ths = this.getRowCells(header);
for (let i = 0; i < ths.length; ++i) { for (const [i, th] of ths.entries()) {
const th = ths[i];
if (th.columnName !== this.columns[i].name) { if (th.columnName !== this.columns[i].name) {
th.title = this.columns[i].caption; th.title = this.columns[i].caption;
th.textContent = this.columns[i].caption; th.textContent = this.columns[i].caption;
@@ -865,14 +864,14 @@ window.qBittorrent.DynamicTable ??= (() => {
const trs = [...this.getTrs()]; const trs = [...this.getTrs()];
const trMap = new Map(trs.map(tr => [tr.rowId, tr])); const trMap = new Map(trs.map(tr => [tr.rowId, tr]));
for (let rowPos = 0; rowPos < rows.length; ++rowPos) { for (const row of rows) {
const rowId = rows[rowPos].rowId; const rowId = row.rowId;
const existingTr = trMap.get(rowId); const existingTr = trMap.get(rowId);
if (existingTr !== undefined) { if (existingTr !== undefined) {
this.updateRow(existingTr, fullUpdate); this.updateRow(existingTr, fullUpdate);
} }
else { else {
const tr = this.createRowElement(rows[rowPos]); const tr = this.createRowElement(row);
// TODO look into using DocumentFragment or appending all trs at once for add'l performance gains // TODO look into using DocumentFragment or appending all trs at once for add'l performance gains
// add to end of table - we'll move into the proper order later // add to end of table - we'll move into the proper order later
@@ -885,8 +884,7 @@ window.qBittorrent.DynamicTable ??= (() => {
// reorder table rows // reorder table rows
let prevTr = null; let prevTr = null;
for (let rowPos = 0; rowPos < rows.length; ++rowPos) { for (const [rowPos, { rowId }] of rows.entries()) {
const { rowId } = rows[rowPos];
const tr = trMap.get(rowId); const tr = trMap.get(rowId);
trMap.delete(rowId); trMap.delete(rowId);
@@ -1061,8 +1059,7 @@ window.qBittorrent.DynamicTable ??= (() => {
const selectedRowId = this.getSelectedRowId(); const selectedRowId = this.getSelectedRowId();
let selectedIndex = -1; let selectedIndex = -1;
for (let i = 0; i < visibleRows.length; ++i) { for (const [i, row] of visibleRows.entries()) {
const row = visibleRows[i];
if (row.getAttribute("data-row-id") === selectedRowId) { if (row.getAttribute("data-row-id") === selectedRowId) {
selectedIndex = i; selectedIndex = i;
break; break;
@@ -1083,8 +1080,7 @@ window.qBittorrent.DynamicTable ??= (() => {
const selectedRowId = this.getSelectedRowId(); const selectedRowId = this.getSelectedRowId();
let selectedIndex = -1; let selectedIndex = -1;
for (let i = 0; i < visibleRows.length; ++i) { for (const [i, row] of visibleRows.entries()) {
const row = visibleRows[i];
if (row.getAttribute("data-row-id") === selectedRowId) { if (row.getAttribute("data-row-id") === selectedRowId) {
selectedIndex = i; selectedIndex = i;
break; break;

View File

@@ -383,8 +383,7 @@ const initializeWindows = () => {
let torrentsHaveSameShareRatio = true; let torrentsHaveSameShareRatio = true;
// check if all selected torrents have same share ratio // check if all selected torrents have same share ratio
for (let i = 0; i < hashes.length; ++i) { for (const hash of hashes) {
const hash = hashes[i];
const row = torrentsTable.getRow(hash).full_data; const row = torrentsTable.getRow(hash).full_data;
const origValues = `${row.ratio_limit}|${row.seeding_time_limit}|${row.inactive_seeding_time_limit}|${row.max_ratio}` const origValues = `${row.ratio_limit}|${row.seeding_time_limit}|${row.inactive_seeding_time_limit}|${row.max_ratio}`
+ `|${row.max_seeding_time}|${row.max_inactive_seeding_time}|${row.share_limit_action}`; + `|${row.max_seeding_time}|${row.max_inactive_seeding_time}|${row.share_limit_action}`;
@@ -1160,10 +1159,8 @@ const initializeWindows = () => {
const names = []; const names = [];
if (selectedRows.length > 0) { if (selectedRows.length > 0) {
const rows = torrentsTable.getFilteredAndSortedRows(); const rows = torrentsTable.getFilteredAndSortedRows();
for (let i = 0; i < selectedRows.length; ++i) { for (const hash of selectedRows)
const hash = selectedRows[i];
names.push(rows[hash].full_data.name); names.push(rows[hash].full_data.name);
}
} }
return names.join("\n"); return names.join("\n");
}; };
@@ -1198,10 +1195,8 @@ const initializeWindows = () => {
const magnets = []; const magnets = [];
if (selectedRows.length > 0) { if (selectedRows.length > 0) {
const rows = torrentsTable.getFilteredAndSortedRows(); const rows = torrentsTable.getFilteredAndSortedRows();
for (let i = 0; i < selectedRows.length; ++i) { for (const hash of selectedRows)
const hash = selectedRows[i];
magnets.push(rows[hash].full_data.magnet_uri); magnets.push(rows[hash].full_data.magnet_uri);
}
} }
return magnets.join("\n"); return magnets.join("\n");
}; };
@@ -1215,8 +1210,7 @@ const initializeWindows = () => {
const comments = []; const comments = [];
if (selectedRows.length > 0) { if (selectedRows.length > 0) {
const rows = torrentsTable.getFilteredAndSortedRows(); const rows = torrentsTable.getFilteredAndSortedRows();
for (let i = 0; i < selectedRows.length; ++i) { for (const hash of selectedRows) {
const hash = selectedRows[i];
const comment = rows[hash].full_data.comment; const comment = rows[hash].full_data.comment;
if (comment && (comment !== "")) if (comment && (comment !== ""))
comments.push(comment); comments.push(comment);

View File

@@ -187,8 +187,7 @@ window.qBittorrent.MultiRename ??= (() => {
const match = matches[i]; const match = matches[i];
let replacement = this.#inner_replacement; let replacement = this.#inner_replacement;
// Replace numerical groups // Replace numerical groups
for (let g = 0; g < match.length; ++g) { for (const [g, group] of match.entries()) {
const group = match[g];
if (!group) if (!group)
continue; continue;
replacement = replaceGroup(replacement, `$${g}`, group, "\\", false); replacement = replaceGroup(replacement, `$${g}`, group, "\\", false);

View File

@@ -772,9 +772,9 @@ window.qBittorrent.Search ??= (() => {
}; };
const getPlugin = (name) => { const getPlugin = (name) => {
for (let i = 0; i < searchPlugins.length; ++i) { for (const searchPlugin of searchPlugins) {
if (searchPlugins[i].name === name) if (searchPlugin.name === name)
return searchPlugins[i]; return searchPlugin;
} }
return null; return null;
@@ -877,8 +877,7 @@ window.qBittorrent.Search ??= (() => {
if (responseJSON.results) { if (responseJSON.results) {
const results = responseJSON.results; const results = responseJSON.results;
for (let i = 0; i < results.length; ++i) { for (const result of results) {
const result = results[i];
const row = { const row = {
rowId: state.rowId, rowId: state.rowId,
descrLink: result.descrLink, descrLink: result.descrLink,

View File

@@ -200,8 +200,7 @@ window.qBittorrent.TorrentContent ??= (() => {
const selectComboboxPriority = (combobox, priority) => { const selectComboboxPriority = (combobox, priority) => {
const options = combobox.options; const options = combobox.options;
for (let i = 0; i < options.length; ++i) { for (const option of options) {
const option = options[i];
if (normalizePriority(option.value) === priority) if (normalizePriority(option.value) === priority)
option.selected = true; option.selected = true;
else else
@@ -404,8 +403,8 @@ window.qBittorrent.TorrentContent ??= (() => {
const uniqueRowIds = new Set(); const uniqueRowIds = new Set();
const uniqueFileIds = new Set(); const uniqueFileIds = new Set();
for (let i = 0; i < rowIds.length; ++i) { for (const [i, rowId] of rowIds.entries()) {
const rows = getAllChildren(rowIds[i], fileIds[i]); const rows = getAllChildren(rowId, fileIds[i]);
for (const rowId of rows.rowIds) for (const rowId of rows.rowIds)
uniqueRowIds.add(rowId); uniqueRowIds.add(rowId);
for (const fileId of rows.fileIds) for (const fileId of rows.fileIds)

View File

@@ -127,8 +127,7 @@
const getSelectedRadioValue = (name) => { const getSelectedRadioValue = (name) => {
const radios = document.getElementsByName(name); const radios = document.getElementsByName(name);
for (let i = 0; i < radios.length; ++i) { for (const radio of radios) {
const radio = radios[i];
if (radio.checked) if (radio.checked)
return radio.value; return radio.value;
} }
@@ -137,8 +136,7 @@
const setSelectedRadioValue = (name, value) => { const setSelectedRadioValue = (name, value) => {
const radios = document.getElementsByName(name); const radios = document.getElementsByName(name);
for (let i = 0; i < radios.length; ++i) { for (const radio of radios) {
const radio = radios[i];
if (radio.value === value) if (radio.value === value)
radio.checked = true; radio.checked = true;
} }

View File

@@ -387,27 +387,27 @@
clearTimeout(logFilterTimer); clearTimeout(logFilterTimer);
logFilterTimer = -1; logFilterTimer = -1;
for (let i = 0; i < responseJSON.length; ++i) { for (const logEntry of responseJSON) {
let row; let row;
if (curTab === "main") { if (curTab === "main") {
row = { row = {
rowId: responseJSON[i].id, rowId: logEntry.id,
message: responseJSON[i].message, message: logEntry.message,
timestamp: responseJSON[i].timestamp, timestamp: logEntry.timestamp,
type: responseJSON[i].type, type: logEntry.type,
}; };
} }
else { else {
row = { row = {
rowId: responseJSON[i].id, rowId: logEntry.id,
ip: responseJSON[i].ip, ip: logEntry.ip,
timestamp: responseJSON[i].timestamp, timestamp: logEntry.timestamp,
blocked: responseJSON[i].blocked, blocked: logEntry.blocked,
reason: responseJSON[i].reason, reason: logEntry.reason,
}; };
} }
tableInfo[curTab].instance.updateRowData(row); tableInfo[curTab].instance.updateRowData(row);
tableInfo[curTab].last_id = Math.max(Number(responseJSON[i].id), tableInfo[curTab].last_id); tableInfo[curTab].last_id = Math.max(Number(logEntry.id), tableInfo[curTab].last_id);
} }
tableInfo[curTab].instance.updateTable(); tableInfo[curTab].instance.updateTable();

View File

@@ -558,8 +558,7 @@
// subtract 'unread' row // subtract 'unread' row
if ((rssFeedRows.length - 1) === flattenedResp.length) { if ((rssFeedRows.length - 1) === flattenedResp.length) {
match = true; match = true;
for (let i = 0; i < flattenedResp.length; ++i) { for (const [i, newData] of flattenedResp.entries()) {
const newData = flattenedResp[i];
const existingData = rssFeedRows[i + 1].full_data; const existingData = rssFeedRows[i + 1].full_data;
if (newData.fullName !== existingData.dataPath) { if (newData.fullName !== existingData.dataPath) {
@@ -578,14 +577,14 @@
// partial refresh // partial refresh
// update status // update status
let statusDiffers = false; let statusDiffers = false;
for (let i = 0; i < flattenedResp.length; ++i) { for (const [i, item] of flattenedResp.entries()) {
const oldStatus = rssFeedRows[i + 1].full_data.status; const oldStatus = rssFeedRows[i + 1].full_data.status;
let status = "default"; let status = "default";
if (flattenedResp[i].hasError) if (item.hasError)
status = "hasError"; status = "hasError";
if (flattenedResp[i].isLoading) if (item.isLoading)
status = "isLoading"; status = "isLoading";
if (flattenedResp[i].isFolder) if (item.isFolder)
status = "isFolder"; status = "isFolder";
if (oldStatus !== status) { if (oldStatus !== status) {

View File

@@ -178,16 +178,16 @@
const updateTable = () => { const updateTable = () => {
const oldPlugins = [...searchPluginsTable.getRowIds()]; const oldPlugins = [...searchPluginsTable.getRowIds()];
// remove old rows from the table // remove old rows from the table
for (let i = 0; i < oldPlugins.length; ++i) { for (const oldPlugin of oldPlugins) {
let found = false; let found = false;
for (let j = 0; j < window.qBittorrent.Search.searchPlugins.length; ++j) { for (let j = 0; j < window.qBittorrent.Search.searchPlugins.length; ++j) {
if (window.qBittorrent.Search.searchPlugins[j].name === oldPlugins[i]) { if (window.qBittorrent.Search.searchPlugins[j].name === oldPlugin) {
found = true; found = true;
break; break;
} }
} }
if (!found) if (!found)
searchPluginsTable.removeRow(oldPlugins[i]); searchPluginsTable.removeRow(oldPlugin);
} }
for (let i = 0; i < window.qBittorrent.Search.searchPlugins.length; ++i) { for (let i = 0; i < window.qBittorrent.Search.searchPlugins.length; ++i) {

View File

@@ -242,23 +242,23 @@
table.clear(); table.clear();
if (responseJSON.length > 0) { if (responseJSON.length > 0) {
for (let i = 0; i < responseJSON.length; ++i) { for (const entry of responseJSON) {
const status = responseJSON[i].status; const status = entry.status;
const row = { const row = {
rowId: responseJSON[i].taskID, rowId: entry.taskID,
source_path: responseJSON[i].sourcePath, source_path: entry.sourcePath,
progress: status === "Finished" ? 100 : responseJSON[i].progress, progress: status === "Finished" ? 100 : entry.progress,
status: status, status: status,
torrent_format: responseJSON[i].format, torrent_format: entry.format,
piece_size: responseJSON[i].pieceSize, piece_size: entry.pieceSize,
private: responseJSON[i].private, private: entry.private,
added_on: responseJSON[i].timeAdded, added_on: entry.timeAdded,
start_on: responseJSON[i].timeStarted, start_on: entry.timeStarted,
completion_on: responseJSON[i].timeFinished, completion_on: entry.timeFinished,
trackers: responseJSON[i].trackers, trackers: entry.trackers,
comment: responseJSON[i].comment, comment: entry.comment,
source: responseJSON[i].source, source: entry.source,
error_message: responseJSON[i].errorMessage, error_message: entry.errorMessage,
}; };
table.updateRowData(row); table.updateRowData(row);