TypeScript 61.9%
HTML 37.2%
SQL 0.7%
1import { describe, expect, it } from 'vitest';2import type { NormalizedRecord } from '@rareindex/shared';3import { ConnectorMetaSchema } from '@rareindex/connectors';4import { listFixtures, loadFixture, runFixtureSuite } from '@rareindex/connectors/testing';5import metaJson from './meta.json' with { type: 'json' };6import createConnector from './index.js';7import { parseDrouotCatalogue } from '../_g8-auctions-eu-apac-lib/drouot-platform.js';89const meta = ConnectorMetaSchema.parse(metaJson);10const connector = createConnector(meta);11const attrsOf = (r: NormalizedRecord) => {12 if (!('attributes' in r)) throw new Error(`record kind ${r.kind} has no attributes`);13 return r.attributes;14};15const HOUSE = { base: 'https://www.osenat.com', currency: 'EUR' as const };1617const CATALOGUE = `<h1 class="nom_vente"> Montres de poche </h1> <div class="date_vente"> mercredi 15 juillet 2026 14:00 </div> <div class="lieu_vente"> Paris </div>18<div class="nbre_lot_haut"> Lots 1 à 50 sur 50 </div>19<div class="ordre_false product clearfix vente174356" id="lot1 lotId34285207"> <div class="product-image"> <a href="/lot/174356/34285207-valentin-dalleizette-montre-de-gousset-vers-1780-boitier"> <img src="https://cdn.drouot.com/d/image/lot?size=phare&path=67/174356/6957" class="lot_visu" alt="x"></a> <div class="sale-flash"> Résultat : <nobr>2 245 EUR</nobr> </div></div> <div class="product-desc"> <div class="num_lot"> <span class='lotnum'>1 </span> </div> <div class="product-title"> <h2> <a href="/lot/174356/34285207-x"> VALENTIN DALLEIZETTE </a> </h2> </div> <div class="product-description"> <a href="/lot/174356/34285207-x"> <h2 id="lotDesc-34285207">VALENTIN DALLEIZETTE Montre de gousset. Vers 1780. Boîtier en or</h2> </a> </div> <div class="product-price"> <div class="estimAff4"> 1500 - 2500 EUR </div> <div class="sale-flash2"> Résultat <nobr>2 245 EUR</nobr> </div> <div class="explicationResultats"> Résultats sans frais </div> </div> </div> </div>`;2021describe('osenat', () => {22 runFixtureSuite(connector, it, expect);2324 it('fixtures: EUR hammer results (Osenat = sans frais)', async () => {25 let sales = 0;26 for (const name of listFixtures('osenat')) {27 for (const r of await connector.normalize(loadFixture('osenat', name).raw)) {28 if (!('attributes' in r)) continue;29 expect(r.attributes.identifiers.osenat_lot).toMatch(/^\d+\/\S+$/);30 expect(r.sourceUrl).toMatch(/^https:\/\/www\.osenat\.com\//);31 if (r.kind === 'sale') {32 sales++;33 expect(r.currency).toBe('EUR');34 expect(r.buyerPremiumIncluded).toBe(false);35 expect(r.auctionHouse).toBe('Osenat');36 }37 }38 }39 expect(sales).toBeGreaterThan(10);40 });4142 it('reads "Résultats sans frais" as hammer and French dates/prices', async () => {43 const sale = { id: '174356', title: 'Montres de poche', url: 'https://www.osenat.com/catalogue/174356-montres-de-poche', date: null, location: null, extra: {} };44 const p = parseDrouotCatalogue(CATALOGUE, sale, HOUSE)!;45 expect(p.hasMore).toBe(false);46 expect(p.totalLots).toBe(50);47 expect(p.lots[0]).toMatchObject({ lotNo: '1', price: 2245, currency: 'EUR', premiumIncluded: false, estimateLow: 1500, estimateHigh: 2500, sold: true });48 expect(p.sale).toMatchObject({ date: '2026-07-15T00:00:00.000Z', location: 'Paris', title: 'Montres de poche' });49 Object.assign(sale, p.sale, { extra: p.sale!.extra });50 const out = await connector.normalize({ url: sale.url, kind: 'sale', engine: 'api', fetchedAt: new Date(), payload: { kind: 'sale_results', url: sale.url, sale, page: 1, totalLots: 50, lots: p.lots } });51 expect(out).toHaveLength(1);52 expect(out[0]!.kind).toBe('sale');53 expect(attrsOf(out[0]!).categorySlug).toBe('other_watches');54 expect(attrsOf(out[0]!).year).toBe(1780);55 if (out[0]!.kind === 'sale') expect(out[0]!.location).toBe('Paris');56 expect(connector.salePageUrl(sale, 3)).toBe('https://www.osenat.com/catalogue/174356?lang=fr&search=&offset=100&max=50');57 });58});59