import * as cheerio from "cheerio";
import { Property } from "../types/property";
import { PlaywrightBaseScraper } from "./playwrightBaseScraper";

/**
 * Scraper para RE/MAX España (franquicia inmobiliaria global)
 * La página es un WordPress SPA que carga los resultados vía AJAX en #reResults.
 * Playwright espera hasta 45s a que el selector #reResults .item aparezca.
 */
export class RemaxScraper extends PlaywrightBaseScraper {
    // Los resultados se inyectan en #reResults vía AJAX; usamos .item como indicador
    protected waitForSelector = '#reResults .item, #reResults .listingSmallImage';
    protected pageTimeoutMs = 45000;

    constructor() { super("https://www.remax.es", "REMAX España"); }

    async scrape(): Promise<Property[]> {
        const zones = await this.getActiveZones();
        const slugs = zones.length > 0 ? zones.map(z => z.slug) : ["lliria"];

        const properties: Property[] = [];
        const seenUrls = new Set<string>();

        for (const slug of slugs) {
            const url = `${this.baseUrl}/buscador-de-inmuebles/venta/piso/valencia-valencia/${slug}/`;
            const html = await this.fetchHtmlPlaywright(url, '#reResults .item, #reResults .listingSmallImage');
            if (!html) continue;
            const $ = cheerio.load(html);

            // Los resultados se cargan dentro de #reResults
            const container = $('#reResults');
            const items = container.find('.item');
            items.each((_i, el) => {
                try {
                    // Título: primer enlace prominente dentro del item
                    const title = this.sanitizeText(
                        $(el).find('h2 a, h3 a, .fnTitle a, .titulo a, a[title]').first().text() ||
                        $(el).find('h2, h3, .fnTitle, .titulo').first().text() ||
                        "Propiedad REMAX"
                    );

                    // Precio: clase .listprice, .precio, o clase con price/Price
                    const priceRaw = this.sanitizeText(
                        $(el).find('.listprice, .precio, [class*="price"], [class*="Price"]').first().text()
                    );
                    const price = this.parsePrice(priceRaw);

                    // URL: primer href en el item
                    const href =
                        $(el).find('h2 a, h3 a, .fnTitle a').first().attr('href') ||
                        $(el).find('a[href*="/inmueble/"]').first().attr('href') ||
                        $(el).find('a[href]').first().attr('href') || '';
                    const absUrl = href.startsWith('http') ? href : `${this.baseUrl}${href}`;

                    // Localización: .addr, .city, .location, o texto cerca del precio
                    const location = this.sanitizeText(
                        $(el).find('.addr, .city, .location, [class*="location"], [class*="address"]').first().text() ||
                        slug
                    );

                    // Habitaciones y superficie
                    let rooms = 0, size_m2 = 0;
                    $(el).find('*').each((_j, e) => {
                        const txt = $(e).text();
                        const rMatch = txt.match(/^(\d+)\s*(?:hab|dorm)/i);
                        if (rMatch) rooms = parseInt(rMatch[1]);
                        const sMatch = txt.match(/^(\d+)\s*m[²2]/i);
                        if (sMatch) size_m2 = parseInt(sMatch[1]);
                    });

                    // Imagen
                    const image_url =
                        $(el).find('img').first().attr('src') ||
                        $(el).find('img').first().attr('data-src') || '';

                    if (price > 0 && href && !seenUrls.has(absUrl)) {
                        seenUrls.add(absUrl);
                        properties.push({
                            title, price, location,
                            municipality: this.detectMunicipality(location + ' ' + slug, zones),
                            property_type: this.normalizeType(title),
                            rooms, size_m2, url: absUrl,
                            source: this.sourceName, image_url,
                        });
                    }
                } catch { /* skip */ }
            });
        }
        return this.validateResults(properties);
    }
}
