// Data contracts for the contractor-first "Set up your agency" onboarding.
//
// THE SEAM: the frontend (onboarding-agency.tsx) is built fully against these
// types + mock data (onboarding-agency-mock.ts). The cheaper model implements
// the endpoints below to these exact shapes — no shared write scope.
//
// Endpoints to implement (all scoped to the signed-in consultant's workspace):
//   GET  /api/agency/cities?q=<query>
//        -> CityRef[]                    (Places API (New) Autocomplete → Place Details for the
//                                         locality's region/country/latlng — GLOBAL, 200M+ places)
//   POST /api/agency/analyze-expertise         { text: string }
//        -> { tools: string[] }          (LLM extracts canonical tool-category labels from
//                                         the consultant's free-text expertise)
//   POST /api/agency/targets                   { city: CityRef, tools: string[] }
//        -> TerritoryOpportunity[]       (SMB types whose softwareNeeds ∩ tools; per-city
//                                         counts via Places Aggregate API × gap × saturation)
//   POST /api/agency                           AgencyOnboardingResult
//        -> { workspaceSlug: string; prospectId: string }
//
// DATA ALIGNMENT (see market_data_assets/):
//  - Cities are GLOBAL via Places API (New) Autocomplete + Place Details — not a fixed list.
//  - Niches are Google Business Profile categories keyed by `gcid` (e.g. "gcid:dentist");
//    the gcid suffix maps to a Places `type` for the Aggregate query. Canonical list in
//    gbp_categories.json / canada.md / us.md.
//  - Per-city business counts come from the Places Aggregate API (computeInsights),
//    filtered by place type within the city's area — works anywhere.
//    dfs_categories_raw.json / camp_market_sizes.csv are country-level benchmarks for
//    reference only; CityRef.countryCode joins to them where coverage exists (CA/US today).
//  - TOOLS the consultant builds are software categories; the targeting step
//    intersects them with each SMB type's `softwareNeeds`
//    (smb_to_software_mapping_final.json) to recommend local businesses to target.
//
// "Illustrative" economics: until the metering ledger is live, cost/price numbers
// are platform estimates and MUST be labeled as such in the UI.

/**
 * A geocoded place. Sourced from Places Autocomplete at runtime; `countryCode`
 * is the join key into our country-split market data (camp_market_sizes.csv etc.).
 */
export interface CityRef {
  /** Stable id — a Places id, or a `${name}-${region}` slug for seed data. */
  id: string;
  /** "Victoria" */
  name: string;
  /** Province / state code — "BC", "WA". */
  region: string;
  /** "Canada" / "United States". */
  country: string;
  /** ISO 3166-1 alpha-2 ("CA", "US", "GB"…). From Place Details; benchmark join key. */
  countryCode: string;
  lat?: number;
  lng?: number;
}

export interface AgencyProfile {
  /** Agency / studio name the consultant chooses. */
  name: string;
  /** Optional one-line positioning. */
  tagline?: string;
  /** Optional uploaded logo. */
  logoUrl?: string;
  /** Home city — seeds the targeting step. */
  city?: CityRef;
  /** Online presence the consultant already has (else Vibn can set them up). */
  hasWebsite?: boolean;
  websiteUrl?: string;
  hasSocials?: boolean;
  hasBlog?: boolean;
  hasCustomDomain?: boolean;
  hasExistingClients?: boolean;
}

/**
 * A category of custom tool the consultant builds. `label` matches the
 * softwareNeeds strings in the SMB mapping so targeting can intersect on it.
 */
export interface ToolCategory {
  id: string;
  /** Canonical software-category label (matches smb_to_software_mapping). */
  label: string;
  /** Short human label for the card. */
  short: string;
  /** Icon key resolved by the UI. */
  icon: string;
}

export type TerritoryStatus = "open" | "contested" | "claimed";

export interface TerritoryOpportunity {
  id: string;
  /** Google Business Profile category key, e.g. "gcid:dentist". Joins to market data. */
  gcid: string;
  /** Display label, e.g. "Dentists" (GBP displayName). */
  niche: string;
  city: string;
  /** Total local businesses in this niche (TAM). */
  businessCount: number;
  /** How many have a weak / missing website or Google profile (the gap). */
  weakWebsiteCount: number;
  /** How many are already served by a Vibn consultant (saturation). */
  vibnClaimedCount: number;
  /** 0..100 — demand × gap × low-saturation, biased by tool-fit. Higher = more open. */
  opportunityScore: number;
  status: TerritoryStatus;
  /** Which of the consultant's tools this SMB needs (the intersection). */
  matchedTools?: string[];
  /** Secondary matching niches discovered for this business */
  alternativeCategories?: Array<{
    gcid: string;
    typeLabel: string;
    presetTools: string[];
    description: string;
  }>;
}

/** Final payload posted to create the agency workspace; then route to the dashboard. */
export interface AgencyOnboardingResult {
  profile: AgencyProfile;
  /** The consultant's free-text expertise ("what I love helping people build"). */
  expertise: string;
  /** Tool-category labels the AI extracted from `expertise` (match the mapping). */
  tools: string[];
}
