Weiter geht es mit den Videodaten; ich habe auch die relevanten Abschnitte des HTML-Dokuments hervorgehoben. Hier müssen wir eine Liste von Elementen extrahieren, also schauen wir uns zuerst die übergeordneten Container an und durchlaufen dann jeden einzelnen davon.
Wir verfolgen denselben Ansatz wie im vorherigen Abschnitt: Wir wählen einige eindeutige CSS-Selektoren aus, um die benötigten Daten zu finden, wobei wir uns auf deren IDs konzentrieren. Der Code sollte in etwa so aussehen:
const videos = await page.evaluate(() => {
const videosEls = Array.from(document.querySelectorAll('div#dismissible'))
return videosEls.map(video => {
const titleEl = video.querySelector('yt-formatted-string#video-title');
const viewsEl = video.querySelector('div#metadata-line > span');
const thumbnailEl = video.querySelector('yt-image.ytd-thumbnail > img');
const locationEl = video.querySelector('a#thumbnail');
return {
title: titleEl ? titleEl.textContent : null,
views: viewsEl ? viewsEl.textContent : null,
thumbnail: thumbnailEl ? thumbnailEl.getAttribute('src') : null,
location: locationEl ? locationEl.getAttribute('href') : null
}
})
})
console.log(videos)
Wenn du den Code ausführst, sollte die Ausgabe eine Liste von JavaScript-Objekten sein. Jedes davon sollte den Titel, die Anzahl der Aufrufe, das Vorschaubild und die Position jedes Videoelements auf der Seite enthalten.
Sie werden jedoch feststellen, dass Ihre Liste ab einem bestimmten Punkt wie folgt aussieht:
{
title: 'GitLab CI/CD Full Course released - CI/CD with Docker | K8s | Microservices!',
views: '114K views',
thumbnail: null,
location: '/watch?v=F7WMRXLUQRM'
},
{
title: 'Kubernetes Security Best Practices you need to know | THE Guide for securing your K8s cluster!',
views: '103K views',
thumbnail: null,
location: '/watch?v=oBf5lrmquYI'
},
{
title: 'How I learn new technologies as a DevOps Engineer (without being overwhelmed)',
views: '366K views',
thumbnail: null,
location: '/watch?v=Cthla7KqU04'
},
{
title: 'Automate your Multi-Stage Continuous Delivery and Operations | with Keptn',
views: '59K views',
thumbnail: null,
location: '/watch?v=3EEZmSwMXp8'
},
Obwohl die Videoelemente weiterhin ein Miniaturbild haben und sich der CSS-Selektor nicht geändert hat, ist der extrahierte Wert null. Dies geschieht in der Regel, wenn eine Website Lazy Loading implementiert, was bedeutet, dass der Rest der Liste geladen wird, während Sie zum Ende der Seite scrollen.
Um dieses Problem zu lösen, müssen wir unser Skript einfach anweisen, auf der Kanalseite nach unten zu scrollen.
async function autoScroll(page: any, scroll_number: number): Promise<any> {
await page.evaluate(async (scroll_number: number) => {
await new Promise((resolve) => {
let totalHeight = 0;
const timer = setInterval(() => {
const scrollHeight = window.innerHeight * scroll_number;
window.scrollBy(0, window.innerHeight);
totalHeight += window.innerHeight;
if (totalHeight > scrollHeight) {
clearInterval(timer);
resolve(true);
}
}, 1000);
});
}, scroll_number);
}
Diese Funktion nimmt als Parameter unsere geöffnete Seite und eine Anzahl von Scrollbewegungen entgegen. Anschließend versucht sie, die Entfernung, die der Fensterhöhe entspricht, so oft zu scrollen, wie es der Parameter scroll_number vorgibt. Diese Bewegungen werden alle 1 Sekunde ausgeführt.
Rufe nun einfach die Funktion vor dem Code-Schnipsel auf, der die Liste der Videos extrahiert.
await autoScroll(page, 10)
await page.waitForTimeout(2 * 1000)
Ich habe eine zusätzliche Wartezeit von 2 Sekunden hinzugefügt, damit die Website Zeit hat, die letzten Elemente der Liste vollständig zu laden. Wenn du das Skript erneut ausführst, wirst du zunächst sehen, wie die Scrollbewegungen ablaufen, und dann, dass alle Elemente in der Liste einen Thumbnail-Wert haben.