sass-imobiliaria/.specify/features/003-property-listing/spec.md

108 lines
3.9 KiB
Markdown
Raw Permalink Blame History

This file contains ambiguous Unicode characters

This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

# Feature Specification: Listagem de Imóveis com Filtros
**Feature Branch**: `003-property-listing`
**Created**: 2026-04-13
**Status**: Approved
## Contexto
Página pública `/imoveis` onde visitantes navegam e filtram o catálogo completo de imóveis. Os filtros utilizam dados dinâmicos cadastrados pela área administrativa (tipos, características, lazer, condomínio, segurança).
## User Stories
### US1 — Visitante navega no catálogo (P1)
**Given** o visitante acessa `/imoveis`, **When** a página carrega, **Then** vê a grade de imóveis ativos com paginação, foto, preço, tipo, dormitórios, banheiros, área e vagas.
### US2 — Visitante filtra por tipo de imóvel (P1)
**Given** o painel de filtros está visível, **When** seleciona categoria "Residencial" e subtipo "Apartamento", **Then** a lista atualiza mostrando apenas apartamentos residenciais.
### US3 — Visitante filtra por preço (P1)
**Given** o filtro de preço está disponível, **When** define min R$ 500.000 e max R$ 1.500.000, **Then** apenas imóveis nesse intervalo aparecem. Com a opção "incluir condomínio" marcada, o backend soma `price + condo_fee` antes de comparar.
### US4 — Visitante filtra por quartos/banheiros/vagas (P1)
**Given** os sliders numéricos estão disponíveis, **When** define mínimo 2 quartos, **Then** apenas imóveis com ≥ 2 quartos aparecem.
### US5 — Visitante filtra por área (P1)
**Given** o filtro de área em m² está disponível, **When** define 50150 m², **Then** apenas imóveis nesse intervalo aparecem.
### US6 — Visitante filtra por características (P2)
**Given** a lista de características está visível (Aceita animais, Ar-condicionado, etc.), **When** seleciona múltiplas, **Then** apenas imóveis que possuem TODAS as características selecionadas aparecem.
### US7 — Visitante filtra lazer, condomínio e segurança (P2)
Mesmo comportamento do US6 para os grupos adicionais.
## API Contract
### Endpoints necessários
**GET /api/v1/property-types** → lista hierárquica de categorias e subtipos
```json
[
{
"id": 1, "name": "Residencial", "slug": "residencial",
"subtypes": [{"id": 10, "name": "Apartamento", "slug": "apartamento"}, ...]
}
]
```
**GET /api/v1/amenities** → lista agrupada de amenidades
```json
[
{"id": 1, "name": "Aceita animais", "group": "caracteristica", "count": 37},
...
]
```
**GET /api/v1/properties** (atualizar) — aceitar query params:
| Param | Tipo | Descrição |
|---|---|---|
| `subtype_id` | int | ID do subtipo |
| `listing_type` | venda\|aluguel | tipo da transação |
| `price_min` | number | preço mínimo |
| `price_max` | number | preço máximo |
| `include_condo` | bool | somar condomínio ao preço |
| `bedrooms_min` | int | quartos mínimo |
| `bedrooms_max` | int | quartos máximo |
| `bathrooms_min` | int | banheiros mínimo |
| `bathrooms_max` | int | banheiros máximo |
| `parking_min` | int | vagas mínimo |
| `parking_max` | int | vagas máximo |
| `area_min` | int | área m² mínimo |
| `area_max` | int | área m² máximo |
| `amenity_ids` | int[] (CSV) | IDs de amenidades (AND) |
| `page` | int | página (default 1) |
| `per_page` | int | itens por página (default 24, max 48) |
| `featured` | bool | retorna destaques (comportamento existente) |
Resposta paginada:
```json
{
"items": [...],
"total": 120,
"page": 1,
"per_page": 24,
"pages": 5
}
```
## Modelos necessários
### PropertyType (novo)
- `id`, `name`, `slug`, `parent_id` (nullable → hierarquia)
### Amenity (novo)
- `id`, `name`, `slug`, `group` (enum: caracteristica | lazer | condominio | seguranca), `count` (denormalizado)
### PropertyAmenity (nova tabela N:N)
- `property_id`, `amenity_id`
### Atualizar Property (novo campo)
- `subtype_id` FK → PropertyType
- `parking_spots` INT
- `condo_fee` NUMERIC(10,2) nullable
## Out of Scope
- Detalhe do imóvel (feature 004)
- Mapa/geolocalização
- Ordenação customizada (entregue com default created_at desc)
- Favoritos / comparador