Inspiration

I hate real estate search websites. Searching is tedious - you filter by bedrooms, price, location separately. Recommendations are terrible, they just match keywords. Photos are subjective when you want to search by features, not aesthetics. Just decided to check if it's really hard to build (spoiler - it is!)

What it does

Frenta understands natural language queries and searches apartments by meaning, with hybrid structured query support

Type "2BR with hardwood floors near subway in Brooklyn under $4000" and it:

  • Breaks your query into atomic requirements
  • Searches for all requirement (we call it claim) across 3 domains in parallel: neighborhoods, apartments, rooms
  • Filters results that satisfy ALL domains (no apartments without qualifying kitchens slip through)
  • Verifies location claims with Google Maps ("near subway" -> "529m to Bedford Ave L station")
  • Ranks by coverage - apartments matching more of your requirements rank higher

The system indexes apartments by extracting claims from text AND images. Gemini vision describes photos, LLM extracts structured facts, claim-based embeddings enable semantic matching.

How we built it

Backend:

  • Claim extraction: Gemini 2.5 Pro breaks descriptions into atomic facts with domain labels (neighborhood/apartment/room)
  • Multi-modal indexing: Process text + images together, deduplicate claims across sources
  • Hierarchical search: Elasticsearch kNN across 3 indices simultaneously, filter by hierarchy
  • Location grounding: Google Maps verifies location claims with real coordinates and distances
  • Scoring: Weighted domain scores + coverage-first ranking prioritizes apartments satisfying more requirements

Frontend:

  • Next.js with TypeScript
  • Real-time search with debouncing

Stack:

  • Gemini 2.5 Pro + Flash (claim aggregation, quantifier extraction)
  • Gemini embedding-001 (768-dim vectors)
  • Elasticsearch 8.11 (kNN with HNSW)
  • Google Maps Grounding API
  • FastAPI + uvicorn
  • Next.js 15 + shadcn/ui

Challenges we ran into

Recursive domain searches are kinda hard. You need to query rooms, apartments, and neighborhoods separately, then merge results while maintaining hierarchy. I used elastic parallel queries, then filtered apartments by set intersection - only apartments with matching rooms AND in matching neighborhoods.

Quantifier extraction and negations are tricky. "Kitchen >10m^2" needs semantic embedding ("kitchen area VAR_1") separate from numeric filtering (area >= 10). LLMs misparse units, and units need normalization:) Negations are handled for queries like "not in city center". You can't possible predict such a claim on index, but you can search for "city center", remember matches, and filter them out. This one is obvious, but there are a few tricks.

Claim deduplication across text and images also need to be handled. Images often redundantly describe what's already in text, LLM halutinates sometimes and contradictions appear. Gotta sort them all out

Partially solved so far is semantically similar terms that should be different for our domain (like "electric oven" vs "gas oven" - very /similar semantically/ but not for our case). Solved it so far by straightly double-checking (asking small LLMs to judge for us), but seriously should be solved with finetuned embeddings.

Accomplishments that we're proud of

I love that search capabilities are quite rich, and I like the design drafted. Not sure, but I'd probably be able to sell it to some real estate co already. Never was my intention, but overall, I think it's a good work.

Built With

Share this project:

Updates