Utilisez Shifter avec Apify
Intégrez les proxies résidentiels et ISP de Shifter dans n'importe quel acteur Apify -- Crawlee gère la file d'attente et les tentatives répétées, Shifter gère les IP résidentielles. ProxyConfiguration accepte nativement les URL Shifter.
Démarrage rapide
Installer
npm install apify crawlee Utilisation de base
// main.js (an Apify Actor)
import { Actor } from "apify";
import { CheerioCrawler, ProxyConfiguration } from "crawlee";
await Actor.init();
const proxyConfiguration = new ProxyConfiguration({
proxyUrls: [
"customer-USERNAME-country-us-sid-123ABC:PASSWORD@p.shifter.io:443",
],
});
const crawler = new CheerioCrawler({
proxyConfiguration,
async requestHandler({ request, $, log }) {
log.info(`${request.url} -> ${$("h1").text().trim()}`);
},
});
await crawler.run(["https://example.com"]);
await Actor.exit(); Fonctionnalités
Exemples
Crawlee + Rotation par session
Crawlee gère automatiquement les blocages et l'expiration des sessions. Utilisez newUrlFunction pour générer une nouvelle URL Shifter par session — lorsque Crawlee retire une session en raison d'un blocage, la suivante obtient une nouvelle IP résidentielle.
import { Actor } from "apify";
import { CheerioCrawler, ProxyConfiguration } from "crawlee";
await Actor.init();
const proxyConfiguration = new ProxyConfiguration({
// Each session asks for a fresh URL — and Crawlee bumps the session
// on bans, so stale IPs get cycled out automatically.
newUrlFunction: () => {
const sid = Math.random().toString(36).slice(2, 10);
return `customer-USERNAME-country-uk-sid-${sid}-ttl-300:PASSWORD@p.shifter.io:443`;
},
});
const crawler = new CheerioCrawler({
proxyConfiguration,
useSessionPool: true,
persistCookiesPerSession: true,
maxConcurrency: 8,
async requestHandler({ request, $, enqueueLinks, log, session }) {
log.info(`Session ${session.id} -> ${request.url}`);
$(".product-card").each((_, el) => {
// Push to dataset (auto-persisted by Apify)
Actor.pushData({
url: request.url,
title: $(el).find("h2").text().trim(),
price: $(el).find(".price").text().trim(),
});
});
await enqueueLinks({ selector: "a.next-page", strategy: "same-domain" });
},
failedRequestHandler({ request, log }) {
log.error(`Failed after retries: ${request.url}`);
},
});
await crawler.run(["https://example.co.uk/products"]);
await Actor.exit(); PuppeteerCrawler (cibles à fort contenu JS)
Lorsque la cible nécessite un vrai navigateur, remplacez CheerioCrawler par PuppeteerCrawler. La même ProxyConfiguration s'intègre — Crawlee transmet l'URL Shifter dans les arguments de lancement de Puppeteer.
import { Actor } from "apify";
import { PuppeteerCrawler, ProxyConfiguration } from "crawlee";
await Actor.init();
const proxyConfiguration = new ProxyConfiguration({
newUrlFunction: () => {
const sid = Math.random().toString(36).slice(2, 10);
return `customer-USERNAME-country-de-city-berlin-sid-${sid}:PASSWORD@p.shifter.io:443`;
},
});
const crawler = new PuppeteerCrawler({
proxyConfiguration,
useSessionPool: true,
launchContext: {
launchOptions: { headless: "new" },
},
maxConcurrency: 4,
async requestHandler({ request, page, log }) {
log.info(`Visiting ${request.url}`);
await page.waitForSelector(".product");
const products = await page.$$eval(".product", (els) =>
els.map((el) => ({
title: el.querySelector("h2")?.textContent?.trim(),
price: el.querySelector(".price")?.textContent?.trim(),
})),
);
await Actor.pushData(products);
},
});
await crawler.run(["https://example.de/categories/electronics"]);
await Actor.exit(); Actor par pays avec schéma d'entrée
Exposez le pays en tant qu'entrée d'Actor Apify. L'Actor le lit au démarrage et configure Shifter pour le pool résidentiel correspondant. Le même code d'Actor fonctionne pour chaque région.
// .actor/input_schema.json
{
"title": "Localized Scraper Input",
"type": "object",
"schemaVersion": 1,
"properties": {
"startUrl": { "type": "string", "title": "Start URL", "default": "https://example.com" },
"country": { "type": "string", "title": "Country", "enum": ["us","uk","de","jp","fr","br"], "default": "us" },
"maxPages": { "type": "integer", "title": "Max Pages", "default": 100, "minimum": 1, "maximum": 5000 }
},
"required": ["startUrl", "country"]
}
// main.js
import { Actor } from "apify";
import { CheerioCrawler, ProxyConfiguration } from "crawlee";
await Actor.init();
const { startUrl, country, maxPages } = await Actor.getInput();
const proxyConfiguration = new ProxyConfiguration({
newUrlFunction: () => {
const sid = Math.random().toString(36).slice(2, 10);
return `customer-USERNAME-country-${country}-sid-${sid}-ttl-300:PASSWORD@p.shifter.io:443`;
},
});
const crawler = new CheerioCrawler({
proxyConfiguration,
maxRequestsPerCrawl: maxPages,
useSessionPool: true,
async requestHandler({ request, $, enqueueLinks }) {
await Actor.pushData({
country,
url: request.url,
title: $("title").text().trim(),
h1: $("h1").first().text().trim(),
});
await enqueueLinks({ strategy: "same-domain" });
},
});
await crawler.run([startUrl]);
await Actor.exit(); SDK Apify hors de Crawlee (logique personnalisée)
Si Crawlee ne correspond pas à votre cas d'usage, vous pouvez tout de même récupérer une URL de proxy Shifter depuis ProxyConfiguration et l'utiliser avec n'importe quel client HTTP. Les sessions, les nouvelles tentatives et la persistance fonctionnent toujours.
import { Actor } from "apify";
import { ProxyConfiguration } from "crawlee";
import { gotScraping } from "got-scraping";
await Actor.init();
const proxyConfiguration = new ProxyConfiguration({
newUrlFunction: () => {
const sid = Math.random().toString(36).slice(2, 10);
return `customer-USERNAME-country-fr-sid-${sid}:PASSWORD@p.shifter.io:443`;
},
});
// Pull a fresh proxy URL per logical task
async function fetchTarget(url) {
const proxyUrl = await proxyConfiguration.newUrl();
const html = await gotScraping({
url,
proxyUrl,
headerGeneratorOptions: {
browsers: [{ name: "chrome", minVersion: 120 }],
locales: ["en-US"],
},
}).text();
return html;
}
const urls = [
"https://example.fr/api/v1/products?page=1",
"https://example.fr/api/v1/products?page=2",
// ...
];
for (const url of urls) {
try {
const html = await fetchTarget(url);
await Actor.pushData({ url, length: html.length });
} catch (err) {
console.error(`Failed ${url}: ${err.message}`);
}
}
await Actor.exit(); Questions fréquentes Questions FAQ
Questions fréquentes sur l'utilisation de Shifter avec Apify.
Utilisez la classe ProxyConfiguration de Crawlee avec soit un tableau `proxyUrls` (une ou plusieurs URLs Shifter), soit une `newUrlFunction` qui retourne une nouvelle URL Shifter par session. Passez la configuration à votre crawler — chaque requête est automatiquement acheminée via Shifter.
Commencer à utiliser Shifter avec Apify
Exécutez des Actors Apify via les proxies résidentiels et ISP 205M+ de Shifter. Configuration native Crawlee ProxyConfiguration, IPs persistantes par session, et prise en charge complète des crawlers Cheerio / Puppeteer / Playwright.