98 lines
4.9 KiB
JavaScript
98 lines
4.9 KiB
JavaScript
javascript:(async function() {
|
|
function getProperty() {
|
|
try {
|
|
const el = document.querySelector('.acct-level-menu-address-single .exclude-translation');
|
|
const text = el ? el.innerText : document.body.innerText;
|
|
if (text.includes("23511")) return "23511 E 2nd";
|
|
if (text.includes("23513")) return "23513 E 2nd";
|
|
if (text.includes("Myrtlewood")) return "Myrtlewood";
|
|
if (text.includes("E Upriver")) return "Brookstone";
|
|
if (text.includes("W 2nd")) return "Ascott";
|
|
if (text.includes("E 36th") || text.includes("E 37th")) return "Commons";
|
|
return "Unknown";
|
|
} catch(e) { return "Unknown"; }
|
|
}
|
|
const propertyName = getProperty();
|
|
const limitInput = prompt("Detected Property: " + propertyName + "\n\nLimit downloads to how many?\n(Leave blank for ALL, click Cancel to stop script)");
|
|
if (limitInput === null) return;
|
|
let maxDownloads = Infinity;
|
|
if (limitInput.trim() !== "") {
|
|
const parsed = parseInt(limitInput, 10);
|
|
if (!isNaN(parsed)) maxDownloads = parsed;
|
|
}
|
|
const processedUrls = new Set();
|
|
let totalDownloaded = 0;
|
|
const wait = (ms) => new Promise(resolve => setTimeout(resolve, ms));
|
|
alert("Starting process.\nTarget: " + (maxDownloads === Infinity ? "ALL" : maxDownloads) + " files.\n\nPlease keep this tab open.");
|
|
async function scanAndDownload() {
|
|
const rows = document.querySelectorAll('tr[ng-repeat="entry in pageData.Entries"]');
|
|
const currentTotalRows = rows.length;
|
|
for (const row of rows) {
|
|
if (totalDownloaded >= maxDownloads) return { count: currentTotalRows, lastText: "", stop: true };
|
|
const dateCell = row.querySelector('td[data-heading-label="Date"]');
|
|
const pdfCell = row.querySelector('td[data-heading-label="View Bill PDF"]');
|
|
if (!dateCell || !pdfCell || pdfCell.classList.contains('ng-hide')) continue;
|
|
const linkElement = pdfCell.querySelector('a');
|
|
if (!linkElement || !linkElement.href) continue;
|
|
if (processedUrls.has(linkElement.href)) continue;
|
|
processedUrls.add(linkElement.href);
|
|
const rawDate = dateCell.innerText.trim();
|
|
const parts = rawDate.split('/');
|
|
const cleanDate = parts[2] + "-" + parts[0].padStart(2, '0') + "-" + parts[1].padStart(2, '0');
|
|
const safeProp = propertyName.replace(/[^a-z0-9\s-_]/gi, '').trim();
|
|
const filename = "Avista - " + safeProp + " - " + cleanDate + ".pdf";
|
|
try {
|
|
const response = await fetch(linkElement.href);
|
|
const blob = await response.blob();
|
|
const blobUrl = window.URL.createObjectURL(blob);
|
|
const a = document.createElement('a');
|
|
a.style.display = 'none';
|
|
a.href = blobUrl;
|
|
a.download = filename;
|
|
document.body.appendChild(a);
|
|
a.click();
|
|
window.URL.revokeObjectURL(blobUrl);
|
|
document.body.removeChild(a);
|
|
totalDownloaded++;
|
|
await wait(800);
|
|
} catch (err) { console.error("Download failed", err); }
|
|
}
|
|
const lastRowText = rows.length > 0 ? rows[rows.length - 1].innerText : "";
|
|
if (totalDownloaded >= maxDownloads) return { count: currentTotalRows, lastText: lastRowText, stop: true };
|
|
return { count: currentTotalRows, lastText: lastRowText, stop: false };
|
|
}
|
|
async function waitForNewRows(previousState) {
|
|
let attempts = 0;
|
|
while (attempts < 30) {
|
|
const rows = document.querySelectorAll('tr[ng-repeat="entry in pageData.Entries"]');
|
|
const currentCount = rows.length;
|
|
const currentLastText = rows.length > 0 ? rows[rows.length - 1].innerText : "";
|
|
if (currentCount > previousState.count || currentLastText !== previousState.lastText) {
|
|
return true;
|
|
}
|
|
await wait(500);
|
|
attempts++;
|
|
}
|
|
return false;
|
|
}
|
|
let keepGoing = true;
|
|
let currentState = await scanAndDownload();
|
|
if (currentState.stop) keepGoing = false;
|
|
while (keepGoing) {
|
|
const allSpans = Array.from(document.querySelectorAll('span.btn-secondary'));
|
|
const moreButton = allSpans.find(s => s.innerText && s.innerText.toLowerCase().includes('load more') && s.offsetParent !== null);
|
|
const navWrapper = document.querySelector('.nav-pagination-mobile');
|
|
const isHidden = navWrapper && navWrapper.classList.contains('ng-hide');
|
|
if (moreButton && !isHidden) {
|
|
moreButton.click();
|
|
await waitForNewRows(currentState);
|
|
currentState = await scanAndDownload();
|
|
if (currentState.stop) keepGoing = false;
|
|
} else {
|
|
keepGoing = false;
|
|
}
|
|
}
|
|
alert("Job Done!\n\nTotal bills downloaded: " + totalDownloaded);
|
|
})();
|
|
|