# Admin Ad Index — Filters Reference

**Endpoint:** `GET /dashboard/ads`

All parameters are optional (`sometimes`). Category-specific filters only apply when `category_id` matches the corresponding category.

---

## Search

| Parameter | Type | Notes |
|---|---|---|
| `keyword` | string (max:255) | Searches across **ad name** and **ad number** using a partial match (`LIKE %value%`). Works on all ad types regardless of category. |

---

## Global Filters (all ad types)

| Parameter | Type | Allowed Values | Notes |
|---|---|---|---|
| `keyword` | string | max:255 | See Search section above |
| `category_id` | integer | exists in `categories` | Scopes to a category; enables category-specific filters below |
| `status` | string | `pending`, `active`, `sold`, `closed`, `paid` |
| `ad_type` | string | `sell`, `exchange`, `partner` | |
| `region_id` | integer | exists in `regions` | Admin-only |
| `city_id` | integer | exists in `cities` | |
| `district_id` | integer | exists in `districts` | |
| `is_promoted` | boolean | `true`, `false` | |
| `min_price` | numeric | 0 – 9,999,999,999 | Checks sell price, exchange difference, or partner required amount |
| `max_price` | numeric | 0 – 9,999,999,999 | Same as above |
| `sort` | string | `latest` *(default)*, `oldest`, `most_viewed`, `least_viewed` | |
| `per_page` | integer | 1 – 100 | Default: 15 |

---

## Cars (`category_id` → cars)

| Parameter | Type | Allowed Values |
|---|---|---|
| `brand_id` | integer | exists in `brands` |
| `model_id` | integer | exists in `models` |
| `manufacture_year` | integer | 1900 – next year |
| `car_status` | string | `new`, `used` |
| `transmission` | string | `manual`, `automatic` |
| `body_condition` | string | `agency`, `cosmetic_paint`, `accident_paint`, `damaged` |
| `engine_condition` | string | `excellent`, `good`, `needs_maintenance`, `needs_restoration` |
| `fuel_type` | string | `petrol`, `diesel`, `hybrid`, `electric` |
| `min_kilometers` | numeric | 0 – 9,999,999 |
| `max_kilometers` | numeric | 0 – 9,999,999 |

---

## Plates (`category_id` → plates)

| Parameter | Type | Allowed Values |
|---|---|---|
| `plate_type` | string | `private`, `private_transport`, `public_transport`, `motorcycle` |
| `plate_distinction_id` | integer | exists in `plate_distinctions` |
| `arabic_numbers` | string | max:10 |
| `english_numbers` | string | max:10 |
| `ready_for_transfer_ownership` | boolean | `true`, `false` |

---

## Real Estate (`category_id` → real_estate)

### General

| Parameter | Type | Allowed Values |
|---|---|---|
| `property_type` | string | `building`, `land` *(from PropertyTypeEnum)* |
| `building_type_id` | integer | exists in `building_types` |
| `advertiser_role` | string | `owner`, `broker`, `real_estate_company` |
| `purpose` | string | `residential`, `commercial`, `residential_commercial` |
| `facade` | string | `north`, `south`, `east`, `west`, `multiple` |
| `has_mortgage` | boolean | `true`, `false` |
| `has_legal_dispute` | boolean | `true`, `false` |
| `vacancy_readiness` | string | `immediate`, `bank_mortgage`, `has_heirs` |

### Building-specific

| Parameter | Type | Allowed Values |
|---|---|---|
| `rooms` | integer | 0 – 999 |
| `bathrooms` | integer | 0 – 999 |
| `property_age` | integer | 0 – 999 |
| `min_area` | numeric | 0 – 99,999,999 (m²) |
| `max_area` | numeric | 0 – 99,999,999 (m²) |

### Land-specific

| Parameter | Type | Allowed Values |
|---|---|---|
| `land_facade` | string | `north`, `south`, `east`, `west`, `multiple` |
| `streets_count` | integer | 0 – 99 |
| `min_street_width` | numeric | 0 – 9,999 |
| `max_street_width` | numeric | 0 – 9,999 |
| `min_land_facade_length` | numeric | 0 – 99,999 |
| `max_land_facade_length` | numeric | 0 – 99,999 |

---

## Business (`category_id` → business)

| Parameter | Type | Allowed Values |
|---|---|---|
| `business_activity_type_id` | integer | exists in `business_activity_types` |
| `ownership_nature` | string | `rent`, `owned`, `equipment_liquidation` |
| `operation_status` | string | `active`, `under_establishment`, `struggling` |
| `brand_included` | string | `included`, `not_included` |
| `licenses_status` | string | `valid`, `expired`, `needs_transfer` |

---

## Notes

- **Category-specific filters are only applied when `category_id` is provided** and resolves to the matching category key (`cars`, `plates`, `real_estate`, `business`). Sending e.g. `brand_id` without the cars `category_id` has no effect.
- **`status`** omits `rejected` and `expired` — rejected ads are hard-deleted immediately upon rejection and will never appear in the index.
- **Price filtering** (`min_price` / `max_price`) is cross-category and checks across `sell_details.final_price`, `exchange_details.final_price`, and `partner_details.required_amount`.
- **`keyword`** searches both `name` and `ad_number` using a partial (`LIKE`) match.
- **`region_id`** is admin-only; the client endpoint filters by `city_id`/`district_id` instead.
