mirror of
https://github.com/tuna/mirror-web.git
synced 2025-12-25 20:32:46 +00:00
split out mirrorlist fetching
This commit is contained in:
parent
5855a7e573
commit
28da3dced1
|
|
@ -1,48 +1,37 @@
|
|||
<script setup>
|
||||
import { ref, onUpdated, computed, onMounted, nextTick } from "vue";
|
||||
import { TUNASYNC_JSON_PATH } from "../lib/consts";
|
||||
import { ref, computed } from "vue";
|
||||
import { options as globalOptions } from "virtual:jekyll-data";
|
||||
import HelpPages from "virtual:tuna-help-pages";
|
||||
import { format as TimeAgoFormat } from "timeago.js";
|
||||
import BootStrapPopover from "bootstrap/js/dist/popover";
|
||||
import SearchBox from "./SearchBox.vue";
|
||||
import { useMirrorList } from "../lib/mirrorList";
|
||||
|
||||
const label_map = globalOptions.label_map;
|
||||
const new_mirrors = Object.fromEntries(
|
||||
globalOptions.new_mirrors.map((x) => [x, true]),
|
||||
);
|
||||
const unlisted = globalOptions.unlisted_mirrors;
|
||||
const options = Object.fromEntries(
|
||||
globalOptions.force_redirect_help_mirrors.map((m) => [
|
||||
m,
|
||||
{ url: "/help/" + m + "/" },
|
||||
]),
|
||||
const forceHelp = Object.fromEntries(
|
||||
globalOptions.force_redirect_help_mirrors.map((m) => [m, true]),
|
||||
);
|
||||
const descriptions = Object.fromEntries(
|
||||
globalOptions.mirror_desc.map((m) => [m.name, m.desc]),
|
||||
);
|
||||
|
||||
const stringifyTime = (ts) => {
|
||||
const date = new Date(ts * 1000);
|
||||
let str = "";
|
||||
let ago = "";
|
||||
if (date.getFullYear() > 2000) {
|
||||
str =
|
||||
`${("000" + date.getFullYear()).slice(-4)}-${("0" + (date.getMonth() + 1)).slice(-2)}-${("0" + date.getDate()).slice(-2)}` +
|
||||
` ${("0" + date.getHours()).slice(-2)}:${("0" + date.getMinutes()).slice(-2)}`;
|
||||
ago = TimeAgoFormat(date);
|
||||
} else {
|
||||
str = "0000-00-00 00:00";
|
||||
ago = "Never";
|
||||
}
|
||||
return [str, ago];
|
||||
};
|
||||
const rawMirrorList = useMirrorList(unlisted);
|
||||
|
||||
const dateTooltip = localStorage.getItem("DateTooltip") !== "false";
|
||||
|
||||
const mirrorList = ref([]);
|
||||
const mirrorList = computed(() => {
|
||||
return rawMirrorList.value
|
||||
.filter((d) => !(d.status == "disabled"))
|
||||
.map((d) => ({
|
||||
...d,
|
||||
url: forceHelp[d.name] ? HelpPages[d.name] : d.url,
|
||||
help_url: HelpPages[d.name],
|
||||
is_new: Boolean(new_mirrors[d.name]),
|
||||
description: descriptions[d.name],
|
||||
github_release: d.url && d.url.startsWith("/github-release/"),
|
||||
}));
|
||||
});
|
||||
const filter = ref("");
|
||||
const rawMirrorList = ref([]);
|
||||
|
||||
const getURL = (mir) => {
|
||||
if (mir.url !== undefined) {
|
||||
|
|
@ -51,8 +40,6 @@ const getURL = (mir) => {
|
|||
return `/${mir.name}/`;
|
||||
};
|
||||
|
||||
var refreshTimer = null;
|
||||
|
||||
const filteredMirrorList = computed(() => {
|
||||
var filterText = filter.value.toLowerCase();
|
||||
return mirrorList.value.filter((m) => {
|
||||
|
|
@ -60,44 +47,6 @@ const filteredMirrorList = computed(() => {
|
|||
});
|
||||
});
|
||||
|
||||
const refreshMirrorList = async () => {
|
||||
if (document.hidden === true) {
|
||||
return;
|
||||
}
|
||||
try{
|
||||
const res = await fetch(TUNASYNC_JSON_PATH);
|
||||
let status_data = await res.json();
|
||||
const unlisted_mir = unlisted.map((d) => processMirrorItem(d));
|
||||
status_data = status_data.map((d) => processMirrorItem(d));
|
||||
let mir_data = unlisted_mir.concat(status_data);
|
||||
mir_data = processLinkItem(mir_data);
|
||||
status_data = sortAndUniqMirrors(status_data);
|
||||
mir_data = sortAndUniqMirrors(mir_data).filter(
|
||||
(d) => !(d.status == "disabled"),
|
||||
);
|
||||
mirrorList.value = mir_data;
|
||||
rawMirrorList.value = status_data;
|
||||
}catch(e){
|
||||
throw e;
|
||||
}finally{
|
||||
refreshTimer = setTimeout(refreshMirrorList, 10000);
|
||||
}
|
||||
};
|
||||
|
||||
nextTick().then(() => refreshMirrorList());
|
||||
|
||||
onMounted(() => {
|
||||
window.addEventListener("visibilitychange", () => {
|
||||
if (refreshTimer) {
|
||||
clearTimeout(refreshTimer);
|
||||
refreshTimer = null;
|
||||
}
|
||||
if (document.visibilityState === "visible") {
|
||||
refreshMirrorList().then();
|
||||
}
|
||||
});
|
||||
});
|
||||
|
||||
const vWithPopover = {
|
||||
mounted: (el) => {
|
||||
BootStrapPopover.getOrCreateInstance(el);
|
||||
|
|
@ -106,81 +55,6 @@ const vWithPopover = {
|
|||
BootStrapPopover.getInstance(el)?.dispose();
|
||||
},
|
||||
};
|
||||
|
||||
const sortAndUniqMirrors = (mirs) => {
|
||||
mirs.sort((a, b) => {
|
||||
return a.name < b.name ? -1 : 1;
|
||||
});
|
||||
return mirs.reduce((acc, cur) => {
|
||||
if (acc.length > 1 && acc[acc.length - 1].name == cur.name) {
|
||||
if (acc[acc.length - 1].last_update_ts && cur.last_update_ts) {
|
||||
if (acc[acc.length - 1].last_update_ts < cur.last_update_ts) {
|
||||
acc[acc.length - 1] = cur;
|
||||
}
|
||||
} else if (cur.last_update_ts) {
|
||||
acc[acc.length - 1] = cur;
|
||||
}
|
||||
} else {
|
||||
acc.push(cur);
|
||||
}
|
||||
return acc;
|
||||
}, []);
|
||||
};
|
||||
|
||||
const processLinkItem = (mirrors) => {
|
||||
var processed = [];
|
||||
for (let d of mirrors) {
|
||||
if (d.link_to === undefined) {
|
||||
processed.push(d);
|
||||
continue;
|
||||
}
|
||||
for (const target of mirrors) {
|
||||
if (d.link_to === target.name) {
|
||||
d.status = target.status;
|
||||
d.label = target.label;
|
||||
d.upstream = target.upstream;
|
||||
d.show_status = target.show_status;
|
||||
d.last_update = target.last_update;
|
||||
d.last_update_ago = target.last_update_ago;
|
||||
d.last_ended = target.last_ended;
|
||||
d.last_ended_ago = target.last_ended_ago;
|
||||
d.last_schedule = target.last_schedule;
|
||||
d.last_schedule_ago = target.last_schedule_ago;
|
||||
processed.push(d);
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
return processed;
|
||||
};
|
||||
|
||||
const processMirrorItem = (d) => {
|
||||
if (options[d.name] != undefined) {
|
||||
for (const key of Object.keys(d)) {
|
||||
if (options[d.name].hasOwnProperty(key)) {
|
||||
d[key] = options[d.name][key];
|
||||
}
|
||||
}
|
||||
}
|
||||
d.help_url = HelpPages[d.name];
|
||||
d.is_new = Boolean(new_mirrors[d.name]);
|
||||
d.description = descriptions[d.name];
|
||||
d.github_release = d.url && d.url.startsWith("/github-release/");
|
||||
if (d.is_master === undefined) {
|
||||
d.is_master = true;
|
||||
}
|
||||
if (d.link_to !== undefined) {
|
||||
return d;
|
||||
}
|
||||
d.label = label_map[d.status];
|
||||
d.show_status = d.status != "success";
|
||||
// Strip the second component of last_update
|
||||
[d.last_update, d.last_update_ago] = stringifyTime(d.last_update_ts);
|
||||
[d.last_ended, d.last_ended_ago] = stringifyTime(d.last_ended_ts);
|
||||
[d.last_started, d.last_started_ago] = stringifyTime(d.last_started_ts);
|
||||
[d.next_schedule, d.next_schedule_ago] = stringifyTime(d.next_schedule_ts);
|
||||
return d;
|
||||
};
|
||||
</script>
|
||||
<template src="./main-mirror-list.html" lang="liquid"></template>
|
||||
|
||||
|
|
|
|||
|
|
@ -0,0 +1,125 @@
|
|||
import { TUNASYNC_JSON_PATH } from "../lib/consts";
|
||||
import { options as globalOptions } from "virtual:jekyll-data";
|
||||
import { ref, onMounted, nextTick } from "vue";
|
||||
import { format as TimeAgoFormat } from "timeago.js";
|
||||
|
||||
const label_map = globalOptions.label_map;
|
||||
|
||||
export const useMirrorList = (additional = []) => {
|
||||
const mirrorList = ref([]);
|
||||
let refreshTimer = null;
|
||||
|
||||
const refreshMirrorList = async () => {
|
||||
if (document.hidden === true) {
|
||||
return;
|
||||
}
|
||||
try {
|
||||
const res = await fetch(TUNASYNC_JSON_PATH);
|
||||
const status_data = await res.json();
|
||||
const processed = status_data
|
||||
.concat(additional)
|
||||
.map((d) => processMirrorItem(d));
|
||||
mirrorList.value = sortAndUniqMirrors(processLinkItem(processed));
|
||||
} catch (e) {
|
||||
throw e;
|
||||
} finally {
|
||||
refreshTimer = setTimeout(refreshMirrorList, 10000);
|
||||
}
|
||||
};
|
||||
|
||||
nextTick().then(() => refreshMirrorList());
|
||||
|
||||
onMounted(() => {
|
||||
window.addEventListener("visibilitychange", () => {
|
||||
if (refreshTimer) {
|
||||
clearTimeout(refreshTimer);
|
||||
refreshTimer = null;
|
||||
}
|
||||
if (document.visibilityState === "visible") {
|
||||
refreshMirrorList().then();
|
||||
}
|
||||
});
|
||||
});
|
||||
|
||||
return mirrorList;
|
||||
};
|
||||
|
||||
const processLinkItem = (mirrors) => {
|
||||
var processed = [];
|
||||
for (let d of mirrors) {
|
||||
if (d.link_to === undefined) {
|
||||
processed.push(d);
|
||||
continue;
|
||||
}
|
||||
for (const target of mirrors) {
|
||||
if (d.link_to === target.name) {
|
||||
d.status = target.status;
|
||||
d.label = target.label;
|
||||
d.upstream = target.upstream;
|
||||
d.show_status = target.show_status;
|
||||
d.last_update = target.last_update;
|
||||
d.last_update_ago = target.last_update_ago;
|
||||
d.last_ended = target.last_ended;
|
||||
d.last_ended_ago = target.last_ended_ago;
|
||||
d.last_schedule = target.last_schedule;
|
||||
d.last_schedule_ago = target.last_schedule_ago;
|
||||
processed.push(d);
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
return processed;
|
||||
};
|
||||
|
||||
const stringifyTime = (ts) => {
|
||||
const date = new Date(ts * 1000);
|
||||
let str = "";
|
||||
let ago = "";
|
||||
if (date.getFullYear() > 2000) {
|
||||
str =
|
||||
`${("000" + date.getFullYear()).slice(-4)}-${("0" + (date.getMonth() + 1)).slice(-2)}-${("0" + date.getDate()).slice(-2)}` +
|
||||
` ${("0" + date.getHours()).slice(-2)}:${("0" + date.getMinutes()).slice(-2)}`;
|
||||
ago = TimeAgoFormat(date);
|
||||
} else {
|
||||
str = "0000-00-00 00:00";
|
||||
ago = "Never";
|
||||
}
|
||||
return [str, ago];
|
||||
};
|
||||
|
||||
const processMirrorItem = (d) => {
|
||||
if (d.is_master === undefined) {
|
||||
d.is_master = true;
|
||||
}
|
||||
if (d.link_to !== undefined) {
|
||||
return d;
|
||||
}
|
||||
d.label = label_map[d.status];
|
||||
d.show_status = d.status != "success";
|
||||
// Strip the second component of last_update
|
||||
[d.last_update, d.last_update_ago] = stringifyTime(d.last_update_ts);
|
||||
[d.last_ended, d.last_ended_ago] = stringifyTime(d.last_ended_ts);
|
||||
[d.last_started, d.last_started_ago] = stringifyTime(d.last_started_ts);
|
||||
[d.next_schedule, d.next_schedule_ago] = stringifyTime(d.next_schedule_ts);
|
||||
return d;
|
||||
};
|
||||
|
||||
const sortAndUniqMirrors = (mirs) => {
|
||||
mirs.sort((a, b) => {
|
||||
return a.name < b.name ? -1 : 1;
|
||||
});
|
||||
return mirs.reduce((acc, cur) => {
|
||||
if (acc.length > 1 && acc[acc.length - 1].name == cur.name) {
|
||||
if (acc[acc.length - 1].last_update_ts && cur.last_update_ts) {
|
||||
if (acc[acc.length - 1].last_update_ts < cur.last_update_ts) {
|
||||
acc[acc.length - 1] = cur;
|
||||
}
|
||||
} else if (cur.last_update_ts) {
|
||||
acc[acc.length - 1] = cur;
|
||||
}
|
||||
} else {
|
||||
acc.push(cur);
|
||||
}
|
||||
return acc;
|
||||
}, []);
|
||||
};
|
||||
Loading…
Reference in New Issue