← back to Nationalrealestate

src/ingest/brokers/tx_trec.ts

45 lines

/**
 * TX — TREC "Broker and Sales Agent License Holder Information" on the state
 * Socrata portal (data.texas.gov s7ft-44qi, refreshed daily; ~322k rows probed
 * 2026-07-21: 18,945 Broker Company / 42,417 Broker Individual / 260,426 Sales Agent).
 * Firm linkage: related_license_* on each sponsored licensee = the sponsoring
 * broker/company. No city column in this dataset (county only) — city stays null.
 */
import { download } from '../run.ts';
import { parseCsvObjects } from './csv.ts';
import type { BrokerRow, FetchedFile, StateAdapter } from './types.ts';

const URL = 'https://data.texas.gov/api/views/s7ft-44qi/rows.csv?accessType=DOWNLOAD';

export const txTrec: StateAdapter = {
  state: 'TX',
  source: 'tx_trec',
  url: URL,
  async fetch() {
    return [await download(URL, 'tx_trec_license_holders.csv')];
  },
  *parse(files: FetchedFile[]): Generator<BrokerRow> {
    for (const o of parseCsvObjects(files[0].path)) {
      const type = o.license_type;
      const name = o.full_name || o.key_name;
      if (!name || !o.license_number) continue;
      if (type === 'Broker Company') {
        yield {
          kind: 'firm', name, license_no: o.license_number,
          license_type: type, license_status: o.status || null, state_code: 'TX',
        };
      } else {
        const rel = o.related_license_type || '';
        const sponsored = rel.startsWith('Broker') && !!o.related_license_full_name;
        yield {
          kind: 'broker', name, license_no: o.license_number,
          license_type: type, license_status: o.status || null,
          firm_name: sponsored ? o.related_license_full_name : null,
          firm_license_no: sponsored ? o.related_license_number || null : null,
          state_code: 'TX',
        };
      }
    }
  },
};