Skip to content

Commit

Permalink
Merge branch 'SashaXser-dev' into dev
Browse files Browse the repository at this point in the history
  • Loading branch information
ilyhalight committed Jan 26, 2025
2 parents 55f294f + d6b763a commit 50d0f12
Show file tree
Hide file tree
Showing 5 changed files with 171 additions and 206 deletions.
12 changes: 6 additions & 6 deletions dist/vot-min.user.js

Large diffs are not rendered by default.

195 changes: 87 additions & 108 deletions dist/vot.user.js
Original file line number Diff line number Diff line change
Expand Up @@ -4810,7 +4810,7 @@ const votStorage = new (class {

const userlang = navigator.language || navigator.userLanguage;
const MAX_SECS_FRACTION = 0.66;
const lang = userlang?.substr(0, 2)?.toLowerCase() ?? "en";
const lang = userlang?.substring(0, 2).toLowerCase() || "en";

function secsToStrTime(secs) {
let minutes = Math.floor(secs / 60);
Expand Down Expand Up @@ -4861,34 +4861,24 @@ function initHls() {
: undefined;
}

const deletefilter = [
/(?:https?|ftp):\/\/\S+/g,
/https?:\/\/\S+|www\.\S+/gm,
/\b\S+\.\S+/gm,
/#[^\s#]+/g,
/Auto-generated by YouTube/g,
/Provided to YouTube by/g,
/Released on/g,
/0x[a-fA-F0-9]{40}/g,
/[13][a-km-zA-HJ-NP-Z1-9]{25,34}/g,
/4[0-9AB][1-9A-HJ-NP-Za-km-z]{93}/g,
/Paypal/g,
];
const textFilters = (() => {
const patterns = [
/(?:https?|www|\bhttp\s+)[^\s/]*?(?:\.\s*[a-z]{2,}|\/)[^\s]*/gi,
/#[^\s#]+|Auto-generated\s+by\s+YouTube|Provided\s+to\s+YouTube\s+by|Released\s+on|PayPal?/gi,
/0x[\da-f]{40}|[13][a-km-zA-HJ-NP-Z1-9]{25,34}|4[0-9AB][1-9A-HJ-NP-Za-km-z]{93}/g,
];

const combinedRegex = new RegExp(
deletefilter.map((regex) => regex.source).join("|"),
);
return new RegExp(patterns.map((p) => p.source).join("|"), "gi");
})();

function cleanText(title, description) {
const cleanedDescription = description
? description
.split("\n")
.filter((line) => !combinedRegex.test(line))
.join(" ")
: "";

const fullText = `${title} ${cleanedDescription}`.slice(0, 450);
return fullText.replace(/[^\p{L}\s]+|\s+/gu, " ").trim();
return (title + " " + (description || ""))
.replace(textFilters, "")
.replace(/(?:[\s\u200B]+|\.{2,})/g, " ")
.replace(/[^\p{L}\s]/gu, "")
.replace(/\s+/g, " ")
.substring(0, 450)
.trim();
}
/**
* Download binary file with entered filename
Expand Down Expand Up @@ -9196,21 +9186,11 @@ class SubtitlesProcessor {
};
}

static async fetchWithTimeout(url, timeout = 5000) {
try {
const response = await GM_fetch(url, { timeout });
return response;
} catch (error) {
console.error("[VOT] Fetch failed:", error);
throw error;
}
}

static async fetchSubtitles(subtitlesObject) {
const { source, isAutoGenerated, format, url } = subtitlesObject;

try {
const response = await this.fetchWithTimeout(url);
const response = await GM_fetch(url, { timeout: 7000 });
let subtitles;

if (["vtt", "srt"].includes(format)) {
Expand Down Expand Up @@ -10836,7 +10816,7 @@ class VideoHandler {
*/
audioPlayer;

videoTranslations = []; // list of video translations
videoTranslations = new Map(); // map of video translations
videoTranslationTTL = 7200; // 2 hours
cachedTranslation; // cached video translation

Expand Down Expand Up @@ -10943,11 +10923,6 @@ class VideoHandler {
}

return new Promise((resolve) => {
const timeoutDuration = this.subtitlesList.some(
(item) => item.source === "yandex",
)
? 20_000
: 30_000;
this.autoRetry = setTimeout(async () => {
const res = await this.translateVideoImpl(
videoData,
Expand All @@ -10958,7 +10933,7 @@ class VideoHandler {
if (!res || (res.translated && res.remainingTime < 1)) {
resolve(res);
}
}, timeoutDuration);
}, 20_000);
});
}

Expand Down Expand Up @@ -11728,7 +11703,7 @@ class VideoHandler {
this.data.translateProxyEnabled,
);
this.initVOTClient();
this.videoTranslations = [];
this.videoTranslations.clear();
},
labelElement: UI.createVOTSelectLabel(
localizationProvider.get("VOTTranslateProxyStatus"),
Expand Down Expand Up @@ -12039,46 +12014,55 @@ class VideoHandler {
// VOT Menu
{
this.votDownloadButton.addEventListener("click", async () => {
if (!this.downloadTranslationUrl) {
return;
}
if (!this.downloadTranslationUrl) return;

if (!this.data.downloadWithName) {
return window.open(this.downloadTranslationUrl, "_blank").focus();
}
try {
if (!this.data.downloadWithName) {
window.open(this.downloadTranslationUrl, "_blank").focus();
return;
}

const votLoader = document.querySelector("#vot-loader-download");
const primaryColor = getComputedStyle(
this.votMenu.container,
).getPropertyValue("--vot-primary-rgb");
const updateAnimation = UI.animateLoader(votLoader, primaryColor);
this.votLoader = document.querySelector("#vot-loader-download");
const primaryColor = getComputedStyle(
this.votMenu.container,
).getPropertyValue("--vot-primary-rgb");
const updateAnimation = UI.animateLoader(
this.votLoader,
primaryColor,
);

const res = await GM_fetch(this.downloadTranslationUrl);
const reader = res.body.getReader();
const contentLength = +res.headers.get("Content-Length");
const res = await GM_fetch(this.downloadTranslationUrl);

let receivedLength = 0;
const chunks = [];
while (true) {
const { done, value } = await reader.read();
if (!res.ok) throw new Error(`HTTP ${res.status}`);

if (done) {
break;
}
const contentLength = +res.headers.get("Content-Length");
const reader = res.body.getReader();
const chunksBuffer = new Uint8Array(contentLength);
let offset = 0;

chunks.push(value);
receivedLength += value.length;
updateAnimation(Math.round((receivedLength / contentLength) * 100));
}
while (true) {
const { done, value } = await reader.read();
if (done) break;

UI.afterAnimateLoader(votLoader, primaryColor);
const blob = new Blob(chunks);
const filename = clearFileName(this.videoData.downloadTitle);
const arrayBuffer = await blob.arrayBuffer();
const writer = new o(arrayBuffer);
writer.setFrame("TIT2", filename);
writer.addTag();
downloadBlob(writer.getBlob(), `${filename}.mp3`);
chunksBuffer.set(value, offset);
offset += value.length;

updateAnimation(Math.round((offset / contentLength) * 100));
}
UI.afterAnimateLoader(this.votLoader, primaryColor);
const filename = clearFileName(this.videoData.downloadTitle);
const writer = new o(chunksBuffer.buffer);
writer.setFrame("TIT2", filename);
writer.addTag();

downloadBlob(writer.getBlob(), `${filename}.mp3`);
} catch (err) {
console.error("Download failed:", err);
this.transformBtn(
"error",
localizationProvider.get("downloadFailed"),
);
}
});

this.votDownloadSubtitlesButton.addEventListener("click", async () => {
Expand Down Expand Up @@ -13287,24 +13271,24 @@ class VideoHandler {
method: "HEAD",
});
utils_debug.log("Test audio response", response);
if (response.status !== 404) {
if (response.ok) {
utils_debug.log("Valid audioUrl", audioUrl);
return audioUrl;
} else {
utils_debug.log("Yandex returned not valid audio, trying to fix...");
let translateRes = await this.translateVideoImpl(
this.videoData,
(this.videoData.detectedLanguage = "auto"),
this.videoData.responseLanguage,
this.videoData.translationHelp,
);
this.setSelectMenuValues(
this.videoData.detectedLanguage,
this.videoData.responseLanguage,
);
audioUrl = translateRes.url;
utils_debug.log("Fixed audio audioUrl", audioUrl);
}

utils_debug.log("Yandex returned not valid audio, trying to fix...");
let translateRes = await this.translateVideoImpl(
this.videoData,
(this.videoData.detectedLanguage = "auto"),
this.videoData.responseLanguage,
this.videoData.translationHelp,
);
this.setSelectMenuValues(
this.videoData.detectedLanguage,
this.videoData.responseLanguage,
);
audioUrl = translateRes.url;
utils_debug.log("Fixed audio audioUrl", audioUrl);
} catch (err) {
utils_debug.log("Test audio error:", err);
}
Expand Down Expand Up @@ -13409,16 +13393,14 @@ class VideoHandler {
return this.afterUpdateTranslation(streamURL);
}

this.cachedTranslation = this.videoTranslations.find(
(t) =>
t.videoId === VIDEO_ID &&
t.expires > utils_getTimestamp() &&
t.from === requestLang &&
t.to === responseLang &&
t.useNewModel === this.data.useNewModel,
);
const cacheKey = `${VIDEO_ID}_${requestLang}_${responseLang}_${this.data.useNewModel}`;
this.cachedTranslation = this.videoTranslations.get(cacheKey);

if (this.cachedTranslation) {
const currentTimestamp = utils_getTimestamp();
if (
this.cachedTranslation &&
this.cachedTranslation.expires > currentTimestamp
) {
await this.updateTranslation(this.cachedTranslation.url);
utils_debug.log("[translateFunc] Cached translation was received");
return;
Expand Down Expand Up @@ -13447,19 +13429,16 @@ class VideoHandler {
item.language === this.videoData.responseLanguage,
)
) {
this.subtitlesList = await SubtitlesProcessor.getSubtitles(
this.votClient,
this.videoData,
);
await this.loadSubtitles();
await this.updateSubtitlesLangSelect();
}

this.videoTranslations.push({
this.videoTranslations.set(cacheKey, {
videoId: VIDEO_ID,
from: requestLang,
to: responseLang,
url: this.downloadTranslationUrl,
expires: utils_getTimestamp() + this.videoTranslationTTL,
expires: currentTimestamp + this.videoTranslationTTL,
useNewModel: this.data?.useNewModel,
});
}
Expand Down
Loading

0 comments on commit 50d0f12

Please sign in to comment.