Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Use fetch helpers instead of fetch #27026

Merged
merged 15 commits into from
Sep 19, 2023
Merged
5 changes: 4 additions & 1 deletion .eslintrc.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -46,6 +46,9 @@ overrides:
- files: ["*.config.*"]
rules:
import/no-unused-modules: [0]
- files: ["web_src/js/modules/fetch.js", "web_src/js/standalone/**/*"]
rules:
no-restricted-syntax: [2, WithStatement, ForInStatement, LabeledStatement, SequenceExpression]

rules:
"@eslint-community/eslint-comments/disable-enable-pair": [2]
Expand Down Expand Up @@ -420,7 +423,7 @@ rules:
no-restricted-exports: [0]
no-restricted-globals: [2, addEventListener, blur, close, closed, confirm, defaultStatus, defaultstatus, error, event, external, find, focus, frameElement, frames, history, innerHeight, innerWidth, isFinite, isNaN, length, location, locationbar, menubar, moveBy, moveTo, name, onblur, onerror, onfocus, onload, onresize, onunload, open, opener, opera, outerHeight, outerWidth, pageXOffset, pageYOffset, parent, print, removeEventListener, resizeBy, resizeTo, screen, screenLeft, screenTop, screenX, screenY, scroll, scrollbars, scrollBy, scrollTo, scrollX, scrollY, self, status, statusbar, stop, toolbar, top, __dirname, __filename]
no-restricted-imports: [0]
no-restricted-syntax: [2, WithStatement, ForInStatement, LabeledStatement, SequenceExpression]
no-restricted-syntax: [2, WithStatement, ForInStatement, LabeledStatement, SequenceExpression, {selector: "CallExpression[callee.name='fetch']", message: "use modules/fetch.js instead"}]
no-return-assign: [0]
no-script-url: [2]
no-self-assign: [2, {props: true}]
Expand Down
2 changes: 1 addition & 1 deletion docs/content/contributing/guidelines-frontend.en-us.md
Original file line number Diff line number Diff line change
Expand Up @@ -95,7 +95,7 @@ Some lint rules and IDEs also have warnings if the returned Promise is not handl
### Fetching data

To fetch data, use the wrapper functions `GET`, `POST` etc. from `modules/fetch.js`. They
accept a `data` option for the content, will automatically set CSFR token and return a
accept a `data` option for the content, will automatically set CSRF token and return a
Promise for a [Response](https://developer.mozilla.org/en-US/docs/Web/API/Response).

### HTML Attributes and `dataset`
Expand Down
5 changes: 3 additions & 2 deletions web_src/js/components/DashboardRepoList.vue
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,7 @@
import {createApp, nextTick} from 'vue';
import $ from 'jquery';
import {SvgIcon} from '../svg.js';
import {GET} from '../modules/fetch.js';

const {appSubUrl, assetUrlPrefix, pageData} = window.config;

Expand Down Expand Up @@ -233,11 +234,11 @@ const sfc = {
try {
if (!this.reposTotalCount) {
const totalCountSearchURL = `${this.subUrl}/repo/search?count_only=1&uid=${this.uid}&team_id=${this.teamId}&q=&page=1&mode=`;
response = await fetch(totalCountSearchURL);
response = await GET(totalCountSearchURL);
this.reposTotalCount = response.headers.get('X-Total-Count');
}

response = await fetch(searchedURL);
response = await GET(searchedURL);
json = await response.json();
} catch {
if (searchedURL === this.searchURL) {
Expand Down
3 changes: 2 additions & 1 deletion web_src/js/components/DiffCommitSelector.vue
Original file line number Diff line number Diff line change
@@ -1,5 +1,6 @@
<script>
import {SvgIcon} from '../svg.js';
import {GET} from '../modules/fetch.js';

export default {
components: {SvgIcon},
Expand Down Expand Up @@ -123,7 +124,7 @@ export default {
},
/** Load the commits to show in this dropdown */
async fetchCommits() {
const resp = await fetch(`${this.issueLink}/commits/list`);
const resp = await GET(`${this.issueLink}/commits/list`);
const results = await resp.json();
this.commits.push(...results.commits.map((x) => {
x.hovered = false;
Expand Down
4 changes: 2 additions & 2 deletions web_src/js/components/RepoBranchTagSelector.vue
Original file line number Diff line number Diff line change
Expand Up @@ -4,6 +4,7 @@ import $ from 'jquery';
import {SvgIcon} from '../svg.js';
import {pathEscapeSegments} from '../utils/url.js';
import {showErrorToast} from '../modules/toast.js';
import {GET} from '../modules/fetch.js';

const sfc = {
components: {SvgIcon},
Expand Down Expand Up @@ -190,8 +191,7 @@ const sfc = {
}
this.isLoading = true;
try {
const reqUrl = `${this.repoLink}/${this.mode}/list`;
const resp = await fetch(reqUrl);
const resp = await GET(`${this.repoLink}/${this.mode}/list`);
const {results} = await resp.json();
for (const result of results) {
let selected = false;
Expand Down
7 changes: 4 additions & 3 deletions web_src/js/features/common-global.js
Original file line number Diff line number Diff line change
Expand Up @@ -11,6 +11,7 @@ import {htmlEscape} from 'escape-goat';
import {showTemporaryTooltip} from '../modules/tippy.js';
import {confirmModal} from './comp/ConfirmModal.js';
import {showErrorToast} from '../modules/toast.js';
import {request} from '../modules/fetch.js';

const {appUrl, appSubUrl, csrfToken, i18n} = window.config;

Expand Down Expand Up @@ -81,7 +82,7 @@ function fetchActionDoRedirect(redirect) {

async function fetchActionDoRequest(actionElem, url, opt) {
try {
const resp = await fetch(url, opt);
const resp = await request(url, opt);
if (resp.status === 200) {
let {redirect} = await resp.json();
redirect = redirect || actionElem.getAttribute('data-redirect');
Expand Down Expand Up @@ -127,7 +128,7 @@ async function formFetchAction(e) {
}

let reqUrl = formActionUrl;
const reqOpt = {method: formMethod.toUpperCase(), headers: {'X-Csrf-Token': csrfToken}};
const reqOpt = {method: formMethod.toUpperCase()};
if (formMethod.toLowerCase() === 'get') {
const params = new URLSearchParams();
for (const [key, value] of formData) {
Expand Down Expand Up @@ -264,7 +265,7 @@ async function linkAction(e) {
const url = el.getAttribute('data-url');
const doRequest = async () => {
el.disabled = true;
await fetchActionDoRequest(el, url, {method: 'POST', headers: {'X-Csrf-Token': csrfToken}});
await fetchActionDoRequest(el, url, {method: 'POST'});
el.disabled = false;
};

Expand Down
5 changes: 3 additions & 2 deletions web_src/js/features/common-issue-list.js
Original file line number Diff line number Diff line change
@@ -1,7 +1,8 @@
import $ from 'jquery';
import {isElemHidden, onInputDebounce, toggleElem} from '../utils/dom.js';
const {appSubUrl} = window.config;
import {GET} from '../modules/fetch.js';

const {appSubUrl} = window.config;
const reIssueIndex = /^(\d+)$/; // eg: "123"
const reIssueSharpIndex = /^#(\d+)$/; // eg: "#123"
const reIssueOwnerRepoIndex = /^([-.\w]+)\/([-.\w]+)#(\d+)$/; // eg: "{owner}/{repo}#{index}"
Expand Down Expand Up @@ -54,7 +55,7 @@ export function initCommonIssueListQuickGoto() {
// try to check whether the parsed goto link is valid
let targetUrl = parseIssueListQuickGotoLink(repoLink, searchText);
if (targetUrl) {
const res = await fetch(`${targetUrl}/info`);
const res = await GET(`${targetUrl}/info`);
if (res.status !== 200) targetUrl = '';
}

Expand Down
9 changes: 2 additions & 7 deletions web_src/js/features/comp/ImagePaste.js
Original file line number Diff line number Diff line change
@@ -1,16 +1,11 @@
import $ from 'jquery';

const {csrfToken} = window.config;
import {POST} from '../../modules/fetch.js';

async function uploadFile(file, uploadUrl) {
const formData = new FormData();
formData.append('file', file, file.name);

const res = await fetch(uploadUrl, {
method: 'POST',
headers: {'X-Csrf-Token': csrfToken},
body: formData,
});
const res = await POST(uploadUrl, {data: formData});
return await res.json();
}

Expand Down
14 changes: 3 additions & 11 deletions web_src/js/features/comp/ReactionSelector.js
Original file line number Diff line number Diff line change
@@ -1,6 +1,5 @@
import $ from 'jquery';

const {csrfToken} = window.config;
import {POST} from '../../modules/fetch.js';

export function initCompReactionSelector($parent) {
$parent.find(`.select-reaction .item.reaction, .comment-reaction-button`).on('click', async function (e) {
Expand All @@ -12,15 +11,8 @@ export function initCompReactionSelector($parent) {
const reactionContent = $(this).attr('data-reaction-content');
const hasReacted = $(this).closest('.ui.segment.reactions').find(`a[data-reaction-content="${reactionContent}"]`).attr('data-has-reacted') === 'true';

const res = await fetch(`${actionUrl}/${hasReacted ? 'unreact' : 'react'}`, {
method: 'POST',
headers: {
'content-type': 'application/x-www-form-urlencoded',
},
body: new URLSearchParams({
_csrf: csrfToken,
content: reactionContent,
}),
const res = await POST(`${actionUrl}/${hasReacted ? 'unreact' : 'react'}`, {
data: new URLSearchParams({content: reactionContent}),
});

const data = await res.json();
Expand Down
3 changes: 2 additions & 1 deletion web_src/js/features/copycontent.js
Original file line number Diff line number Diff line change
@@ -1,6 +1,7 @@
import {clippie} from 'clippie';
import {showTemporaryTooltip} from '../modules/tippy.js';
import {convertImage} from '../utils.js';
import {GET} from '../modules/fetch.js';

const {i18n} = window.config;

Expand All @@ -20,7 +21,7 @@ export function initCopyContent() {
if (link) {
btn.classList.add('is-loading', 'small-loading-icon');
try {
const res = await fetch(link, {credentials: 'include', redirect: 'follow'});
const res = await GET(link, {credentials: 'include', redirect: 'follow'});
const contentType = res.headers.get('content-type');

if (contentType.startsWith('image/') && !contentType.startsWith('image/svg')) {
Expand Down
3 changes: 2 additions & 1 deletion web_src/js/features/install.js
Original file line number Diff line number Diff line change
@@ -1,5 +1,6 @@
import $ from 'jquery';
import {hideElem, showElem} from '../utils/dom.js';
import {GET} from '../modules/fetch.js';

export function initInstall() {
const $page = $('.page-content.install');
Expand Down Expand Up @@ -111,7 +112,7 @@ function initPostInstall() {
const targetUrl = el.getAttribute('href');
let tid = setInterval(async () => {
try {
const resp = await fetch(targetUrl);
const resp = await GET(targetUrl);
if (tid && resp.status === 200) {
clearInterval(tid);
tid = null;
Expand Down
9 changes: 3 additions & 6 deletions web_src/js/features/pull-view-file.js
Original file line number Diff line number Diff line change
@@ -1,7 +1,8 @@
import {diffTreeStore} from '../modules/stores.js';
import {setFileFolding} from './file-fold.js';
import {POST} from '../modules/fetch.js';

const {csrfToken, pageData} = window.config;
const {pageData} = window.config;
const prReview = pageData.prReview || {};
const viewedStyleClass = 'viewed-file-checked-form';
const viewedCheckboxSelector = '.viewed-file-form'; // Selector under which all "Viewed" checkbox forms can be found
Expand Down Expand Up @@ -68,11 +69,7 @@ export function initViewedCheckboxListenerFor() {
const data = {files};
const headCommitSHA = form.getAttribute('data-headcommit');
if (headCommitSHA) data.headCommitSHA = headCommitSHA;
fetch(form.getAttribute('data-link'), {
method: 'POST',
headers: {'X-Csrf-Token': csrfToken},
body: JSON.stringify(data),
});
POST(form.getAttribute('data-link'), {data});
silverwind marked this conversation as resolved.
Show resolved Hide resolved

// Fold the file accordingly
const parentBox = form.closest('.diff-file-header');
Expand Down
3 changes: 2 additions & 1 deletion web_src/js/features/repo-diff-commit.js
Original file line number Diff line number Diff line change
@@ -1,9 +1,10 @@
import {hideElem, showElem, toggleElem} from '../utils/dom.js';
import {GET} from '../modules/fetch.js';

async function loadBranchesAndTags(area, loadingButton) {
loadingButton.classList.add('disabled');
try {
const res = await fetch(loadingButton.getAttribute('data-fetch-url'));
const res = await GET(loadingButton.getAttribute('data-fetch-url'));
const data = await res.json();
hideElem(loadingButton);
addTags(area, data.tags);
Expand Down
18 changes: 3 additions & 15 deletions web_src/js/features/repo-issue-list.js
Original file line number Diff line number Diff line change
Expand Up @@ -5,6 +5,7 @@ import {htmlEscape} from 'escape-goat';
import {confirmModal} from './comp/ConfirmModal.js';
import {showErrorToast} from '../modules/toast.js';
import {createSortable} from '../modules/sortable.js';
import {DELETE, POST} from '../modules/fetch.js';

function initRepoIssueListCheckboxes() {
const $issueSelectAll = $('.issue-checkbox-all');
Expand Down Expand Up @@ -146,13 +147,7 @@ function initPinRemoveButton() {
const id = Number(el.getAttribute('data-issue-id'));

// Send the unpin request
const response = await fetch(el.getAttribute('data-unpin-url'), {
method: 'delete',
headers: {
'X-Csrf-Token': window.config.csrfToken,
'Content-Type': 'application/json',
},
});
const response = await DELETE(el.getAttribute('data-unpin-url'));
if (response.ok) {
// Delete the tooltip
el._tippy.destroy();
Expand All @@ -166,14 +161,7 @@ function initPinRemoveButton() {
async function pinMoveEnd(e) {
const url = e.item.getAttribute('data-move-url');
const id = Number(e.item.getAttribute('data-issue-id'));
await fetch(url, {
method: 'post',
body: JSON.stringify({id, position: e.newIndex + 1}),
headers: {
'X-Csrf-Token': window.config.csrfToken,
'Content-Type': 'application/json',
},
});
await POST(url, {data: {id, position: e.newIndex + 1}});
}

async function initIssuePinSort() {
Expand Down
13 changes: 4 additions & 9 deletions web_src/js/features/repo-migrate.js
Original file line number Diff line number Diff line change
@@ -1,7 +1,8 @@
import $ from 'jquery';
import {hideElem, showElem} from '../utils/dom.js';
import {GET, POST} from '../modules/fetch.js';

const {appSubUrl, csrfToken} = window.config;
const {appSubUrl} = window.config;

export function initRepoMigrationStatusChecker() {
const $repoMigrating = $('#repo_migrating');
Expand All @@ -13,7 +14,7 @@ export function initRepoMigrationStatusChecker() {

// returns true if the refresh still need to be called after a while
const refresh = async () => {
const res = await fetch(`${appSubUrl}/user/task/${task}`);
const res = await GET(`${appSubUrl}/user/task/${task}`);
if (res.status !== 200) return true; // continue to refresh if network error occurs

const data = await res.json();
Expand Down Expand Up @@ -58,12 +59,6 @@ export function initRepoMigrationStatusChecker() {
}

async function doMigrationRetry(e) {
await fetch($(e.target).attr('data-migrating-task-retry-url'), {
method: 'post',
headers: {
'X-Csrf-Token': csrfToken,
'Content-Type': 'application/json',
},
});
await POST($(e.target).attr('data-migrating-task-retry-url'));
window.location.reload();
}
Loading