Collect URLs from koharu.to artist pages and store them in GM_storage
当前为
// ==UserScript==
// @name Koharu Artist URL Collector
// @namespace https://koharu.to/
// @version 1.7.1
// @description Collect URLs from koharu.to artist pages and store them in GM_storage
// @license MIT
// @author viatana35
// @match https://koharu.to/?s=artist*
// @match https://koharu.to/?s=circle*
// @grant GM_getValue
// @grant GM_setValue
// @grant GM_deleteValue
// @grant GM_download
// ==/UserScript==
(function () {
'use strict';
const urlKey = 'koharuUrls';
const continueKey = 'continue_treatment';
const artistsLibKey = 'artists_lib';
let urlList = GM_getValue(urlKey, []);
let continueTreatment = GM_getValue(continueKey, false);
let artistsLib = GM_getValue(artistsLibKey, []);
// Function to process the current page and store English articles
function processPage() {
const articles = document.querySelectorAll('article');
articles.forEach(article => {
const isEnglish = article.querySelector('a > header > h3 > span > svg[id="flag-icons-gb"]');
if (isEnglish) {
const articleUrl = article.querySelector('a').href;
if (!urlList.includes(articleUrl)) {
urlList.push(articleUrl);
}
}
});
// Save the updated URL list
GM_setValue(urlKey, urlList);
}
// Function to navigate to the next page
function goToNextPage() {
const paginationList = document.querySelector('footer nav.pagination ul');
if (paginationList) {
const paginationItems = paginationList.children;
const lastItem = paginationItems[paginationItems.length - 1]; // On prend le dernier élément de la liste
const nextPageLink = lastItem.querySelector('a');
if (nextPageLink) {
const currentPageNumber = parseInt(new URL(window.location.href).searchParams.get('page') || '1', 10);
const nextPageNumber = parseInt(new URL(nextPageLink.href).searchParams.get('page'), 10);
if (nextPageNumber === currentPageNumber + 1) {
console.log(currentPageNumber, "->", nextPageNumber);
GM_setValue(continueKey, true);
window.location.href = nextPageLink.href;
} else {
console.log("end of treatment 1");
saveArtistData();
GM_setValue(continueKey, false); // Pas de page suivante
}
} else {
saveArtistData();
GM_setValue(continueKey, false); // Pas de lien pour la page suivante
}
}
else
{
console.log("end of treatment 2");
saveArtistData();
GM_setValue(continueKey, false); // Pas de page suivante
}
}
function treatArtist() {
// If there is no pagination list, check if the URL contains "&page"
const urlParams = new URLSearchParams(window.location.search);
if (urlParams.has('page')) {
showPopup("please go to page one to treat artist");
} else {
console.log("beginning of the treatment");
processPage();
goToNextPage();
}
}
// Function to get the artist's name
function getArtistName() {
const urlParams = new URLSearchParams(window.location.search);
let artistName = null;
// Check for 's' parameter
if (urlParams.has('s')) {
const searchQuery = urlParams.get('s');
// Extract the artist or circle name from the search query
const match = searchQuery.match(/(artist|circle):\^(.+)\$$/);
if (match && match[2]) {
artistName = match[2];
}
}
return artistName;
}
function showPopup(message) {
const popup = document.createElement('div');
popup.id = 'popup';
popup.style.position = 'fixed';
popup.style.top = '50%';
popup.style.left = '50%';
popup.style.transform = 'translate(-50%, -50%)';
popup.style.backgroundColor = '#f1f1f1';
popup.style.padding = '20px';
popup.style.border = '1px solid #ccc';
popup.style.boxShadow = '0 2px 4px rgba(0, 0, 0, 0.1)';
popup.style.zIndex = '1001';
popup.style.textAlign = 'center';
popup.style.opacity = '0';
popup.style.transition = 'opacity 0.3s ease-in-out';
popup.textContent = message;
document.body.appendChild(popup);
// Fade in the popup
setTimeout(() => {
popup.style.opacity = '1';
}, 10);
// Fade out and remove the popup after 5 seconds
setTimeout(() => {
popup.style.opacity = '0';
setTimeout(() => {
document.body.removeChild(popup);
}, 300);
}, 5000);
}
// Function to save the current artist's data
function saveArtistData() {
const artistName = getArtistName();
console.log(artistName);
if (artistName && urlList.length > 0) {
const artistData = {
artist: artistName,
lst_dl: urlList
};
// Add the artist data to the artistsLib
artistsLib.push(artistData);
// Save the updated artistsLib
GM_setValue(artistsLibKey, artistsLib);
// Clear the URL list for the next artist
GM_setValue(urlKey, []);
urlList = [];
showPopup(`Artist ${artistName} has been processed.`);
clearButton.disabled = false;
}
}
// Function to handle automatic processing if continue_treatment is true
function handleAutoProcessing() {
console.log(continueTreatment);
if (continueTreatment) {
processPage();
goToNextPage();
}
}
// Function to download the artists_lib as a JSON file
function downloadArtistsLib() {
const artistsLibData = GM_getValue(artistsLibKey, []);
const jsonContent = JSON.stringify(artistsLibData, null, 2); // Pretty print JSON with indentation
const blob = new Blob([jsonContent], { type: 'application/json' });
const url = URL.createObjectURL(blob);
const a = document.createElement('a');
a.href = url;
a.download = 'artists_lib.json';
a.click();
URL.revokeObjectURL(url); // Clean up the URL object
}
// Create a container for the buttons
const buttonContainer = document.createElement('div');
buttonContainer.style.position = 'sticky';
buttonContainer.style.top = '0';
buttonContainer.style.backgroundColor = '#f1f1f1';
buttonContainer.style.padding = '10px';
buttonContainer.style.zIndex = 1000;
buttonContainer.style.display = 'flex';
buttonContainer.style.justifyContent = 'center';
buttonContainer.style.alignItems = 'center';
document.body.prepend(buttonContainer);
// Create a button to process the artist's pages
const processButton = document.createElement('button');
processButton.textContent = 'Traiter l\'artiste';
processButton.style.margin = '0 10px';
processButton.style.padding = '10px';
processButton.style.backgroundColor = '#4CAF50';
processButton.style.color = 'white';
processButton.style.border = 'none';
processButton.style.cursor = 'pointer';
processButton.onclick = () => {
GM_setValue(continueKey, true);
treatArtist();
};
buttonContainer.appendChild(processButton);
// Create a button to clear the list and artists_lib
const clearButton = document.createElement('button');
clearButton.textContent = 'Clear list';
clearButton.style.margin = '0 10px';
clearButton.style.padding = '10px';
clearButton.style.backgroundColor = '#f44336';
clearButton.style.color = 'white';
clearButton.style.border = 'none';
clearButton.style.cursor = 'pointer';
clearButton.disabled = artistsLib.length === 0;
clearButton.onclick = () => {
if (confirm('Do you really want to clear the list ?')) {
GM_deleteValue(urlKey);
GM_deleteValue(artistsLibKey);
urlList = [];
artistsLib = [];
clearButton.disabled = true;
showPopup("list cleared");
}
};
buttonContainer.appendChild(clearButton);
// Create a button to download the artists_lib JSON
const downloadButton = document.createElement('button');
downloadButton.textContent = 'Download the lsit';
downloadButton.style.margin = '0 10px';
downloadButton.style.padding = '10px';
downloadButton.style.backgroundColor = '#2196F3';
downloadButton.style.color = 'white';
downloadButton.style.border = 'none';
downloadButton.style.cursor = 'pointer';
downloadButton.onclick = downloadArtistsLib;
buttonContainer.appendChild(downloadButton);
// Enable the clear button if the list contains elements
if (artistsLib.length > 0) {
clearButton.disabled = false;
}
// Wait for DOM to fully load before executing handleAutoProcessing
window.onload = () => {
handleAutoProcessing();
};
})();