initial commit
This commit is contained in:
164
src/index.ts
Normal file
164
src/index.ts
Normal file
@ -0,0 +1,164 @@
|
||||
/**
|
||||
* Selenium WebDriver script to visit TripAdvisor pages for random cities
|
||||
* & 'C:\Program Files\Google\Chrome\Application\chrome.exe' --remote-debugging-port=9222
|
||||
*/
|
||||
|
||||
import { Builder, By, until, WebDriver } from 'selenium-webdriver';
|
||||
import * as chromedriver from 'chromedriver';
|
||||
import chrome, { ServiceBuilder } from 'selenium-webdriver/chrome';
|
||||
import * as fs from 'fs';
|
||||
import * as path from 'path';
|
||||
import { getCities } from './lib/cities';
|
||||
import { WebDriverUtils, saveContactInfoToCSV } from './lib/utils';
|
||||
import * as UIActions from './lib/UIActions';
|
||||
import { randomUUID } from 'crypto';
|
||||
|
||||
|
||||
/**
|
||||
* Function to visit TripAdvisor pages for each city
|
||||
*/
|
||||
async function visitCityPages(): Promise<void> {
|
||||
|
||||
const cities = getCities(path.join(__dirname, 'cities.csv'));
|
||||
|
||||
console.log('Connecting to existing Chrome browser...');
|
||||
|
||||
// Connect to an existing Chrome browser running in debug mode on port 9222
|
||||
const options = new chrome.Options();
|
||||
|
||||
// Set the debugger address to connect to the existing Chrome instance
|
||||
options.debuggerAddress('localhost:9222');
|
||||
|
||||
// Create WebDriver instance that connects to the existing browser
|
||||
const driver: WebDriver = await new Builder()
|
||||
.forBrowser('chrome')
|
||||
.setChromeOptions(options)
|
||||
.build();
|
||||
|
||||
// Visit each city's TripAdvisor page
|
||||
for (let i = 0; i < cities.length; i++) {
|
||||
const city = cities[i];
|
||||
console.log(`[${i + 1}/${cities.length}] Visiting TripAdvisor page for ${city}...`);
|
||||
let originalWindow;
|
||||
let cityTopWindow;
|
||||
let attactionsWindow;
|
||||
let museumWindow;
|
||||
|
||||
try {
|
||||
|
||||
const originalWindow = await driver.getWindowHandle();
|
||||
|
||||
console.log("Logo click")
|
||||
if (!await UIActions.gotoHome(driver)) throw `${city} failed`;
|
||||
await WebDriverUtils.wait(5);
|
||||
|
||||
console.log("Exec Search")
|
||||
if (!await UIActions.execSearch(driver, city)) throw `${city} failed`;
|
||||
await WebDriverUtils.wait(5);
|
||||
|
||||
console.log("Click See all")
|
||||
if (!await UIActions.clickSeeAll(driver)) {
|
||||
if (!await UIActions.clickTourismLink(driver)) throw `${city} failed`;
|
||||
if (!await UIActions.clickSeeAll(driver)) throw `${city} failed`;
|
||||
}
|
||||
await WebDriverUtils.wait(5);
|
||||
|
||||
console.log("Switch tab")
|
||||
let windows = await driver.getAllWindowHandles();
|
||||
// Switch to the newly opened window/tab
|
||||
for (const handle of windows) {
|
||||
if (handle !== originalWindow) {
|
||||
cityTopWindow = handle;
|
||||
await driver.switchTo().window(handle);
|
||||
}
|
||||
}
|
||||
|
||||
console.log("Click See all attractions")
|
||||
if (!await UIActions.clickSeeAllAttractions(driver)) throw `${city} failed`;
|
||||
await WebDriverUtils.wait(5);
|
||||
|
||||
console.log("Switch tab to Attraction")
|
||||
windows = await driver.getAllWindowHandles();
|
||||
// Switch to the newly opened window/tab
|
||||
for (const handle of windows) {
|
||||
if (handle !== originalWindow && handle !== cityTopWindow) {
|
||||
attactionsWindow = handle;
|
||||
await driver.switchTo().window(attactionsWindow);
|
||||
}
|
||||
}
|
||||
|
||||
// click museum
|
||||
console.log("Click Museum link");
|
||||
if (!await UIActions.clickMuseumsLink(driver)) throw `${city} failed`;
|
||||
await WebDriverUtils.wait(5);
|
||||
|
||||
let page = 1;
|
||||
while (1) {
|
||||
|
||||
// get list of museums
|
||||
console.log("Get list of museums");
|
||||
const museumElms = await UIActions.getMusiums(driver);
|
||||
await WebDriverUtils.wait(1);
|
||||
|
||||
for (const listItem of museumElms) {
|
||||
|
||||
await listItem.click();
|
||||
await WebDriverUtils.wait(3);
|
||||
|
||||
windows = await driver.getAllWindowHandles();
|
||||
for (const handle of windows) {
|
||||
if (handle !== originalWindow && handle !== cityTopWindow && handle !== attactionsWindow) {
|
||||
museumWindow = handle;
|
||||
await driver.switchTo().window(museumWindow);
|
||||
}
|
||||
}
|
||||
|
||||
const { websiteUrl, email } = await UIActions.getWebsiteAndEmail(driver);
|
||||
|
||||
console.log(`${websiteUrl} / ${email}`);
|
||||
saveContactInfoToCSV(city, { websiteUrl: websiteUrl, email: email }, path.join(__dirname, 'contact_info.csv'));
|
||||
|
||||
museumWindow && await driver.switchTo().window(museumWindow);
|
||||
await driver.close();
|
||||
await WebDriverUtils.wait(1);
|
||||
|
||||
attactionsWindow && await driver.switchTo().window(attactionsWindow);
|
||||
await WebDriverUtils.wait(1);
|
||||
|
||||
}
|
||||
|
||||
page++;
|
||||
|
||||
if (page > 10) break;
|
||||
|
||||
UIActions.clickPagination(driver, page);
|
||||
await WebDriverUtils.wait(5);
|
||||
|
||||
}
|
||||
|
||||
|
||||
await UIActions.closeAllTabsExceptFirst(driver);
|
||||
|
||||
|
||||
if (i < cities.length - 1) {
|
||||
console.log(`Waiting for 5000 seconds before next city...`);
|
||||
await WebDriverUtils.wait(5); // Wait 5000 seconds before next city
|
||||
}
|
||||
} catch (error) {
|
||||
|
||||
await UIActions.closeAllTabsExceptFirst(driver);
|
||||
|
||||
// If the button is not found within the timeout, log and continue to the next city
|
||||
console.log(`No Museums button found for ${city}. Moving to next city after 5 seconds...`);
|
||||
await WebDriverUtils.wait(5); // Wait 5 seconds before next city
|
||||
}
|
||||
}
|
||||
|
||||
console.log('Finished visiting all cities!');
|
||||
|
||||
}
|
||||
|
||||
// Run the function
|
||||
visitCityPages().catch(error => {
|
||||
console.error('Error in main function:', error);
|
||||
});
|
||||
Reference in New Issue
Block a user