> ## Knowledge Base Index
> Fetch the complete knowledge base index at: https://help.repliers.com/sitemap.xml
> Use this file to discover available pages before exploring further.
> Pure-Markdown content can be obtained by appending a '.md' suffix to the content URLs listed in the sitemap (without the trailing slash).

# Building an Autocomplete Search Feature with Repliers APIs

A comprehensive guide to implementing a unified search experience that combines MLS® listings with cities and neighborhoods using the Repliers API.

## Overview

This recipe demonstrates how to build a powerful autocomplete search feature that allows users to search for both MLS® listings and locations simultaneously. The results are presented categorically, giving users a seamless search experience whether they're looking for a specific property address, MLS® number, or exploring different areas.

## Example

![An example of an autocomplete search using Repliers](https://storage.crisp.chat/users/helpdesk/website/-/9/5/7/a/957a8eb8f0b80800/screenshot-2025-06-05-at-90225_4e0upj.png =400x311)


## Implementation Steps

### Step 1: Search MLS® Listings

The first step involves searching through MLS® listings using the `/listings` endpoint. This allows users to find properties by address components or MLS® numbers.

#### API Request

```
GET https://api.repliers.io/listings?search={user_input}&searchFields=address.streetNumber,address.streetName,mlsNumber,address.city&fields=address.*,mlsNumber,listPrice
```

#### Request Parameters Breakdown

| Parameter | Description | Example |
| ---- |
| `search` | The user's input from the search field | `123` |
| `searchFields` | Comma-separated list of fields to search within | `address.streetNumber,address.streetName,mlsNumber,address.city` |
| `fields` | Fields to include in the response (for performance optimization) | `address.*,mlsNumber,listPrice` |
#### 
Why These Search Fields?

* **`address.streetNumber`** - Allows finding properties by house number
* **`address.streetName`** - Enables searching by street names
* **`mlsNumber`** - Lets users search by listing ID/MLS® number
* **`address.city`** - Enables city-based property searches

#### Field Selection Best Practices

Only request the fields you need to display in your autocomplete results. This improves API performance significantly. Learn more about field optimization in our [Fields Parameter Guide](https://help.repliers.com/en/article/optimizing-api-requests-with-the-fields-parameter-lq416x/).

#### Example Response

```json
{
    "apiVersion": "1",
    "page": 1,
    "numPages": 3,
    "pageSize": 100,
    "count": 293,
    "statistics": {
        "listPrice": {
            "min": 1,
            "max": 14585000
        }
    },
    "listings": [
        {
            "mlsNumber": "X12151945",
            "listPrice": "1250000.00",
            "address": {
                "area": "Peterborough",
                "city": "Trent Lakes",
                "country": "Canada",
                "district": null,
                "majorIntersection": "Hwy 36 & Bessie Ave",
                "neighborhood": "Trent Lakes",
                "streetDirection": null,
                "streetName": "Fire Route 123",
                "streetNumber": "13",
                "streetSuffix": "N/A",
                "unitNumber": null,
                "zip": "K0M 1A0",
                "state": "Ontario",
                "communityCode": null,
                "streetDirectionPrefix": null
            }
        },
        {
            "mlsNumber": "X12196167",
            "listPrice": "1895000.00",
            "address": {
                "area": "Grey County",
                "city": "Grey Highlands",
                "country": "Canada",
                "district": null,
                "majorIntersection": "Lakeview Rd off of Rd 63",
                "neighborhood": "Grey Highlands",
                "streetDirection": null,
                "streetName": "Lakeview",
                "streetNumber": "123",
                "streetSuffix": "Rd",
                "unitNumber": null,
                "zip": "N0C 1M0",
                "state": "Ontario",
                "communityCode": null,
                "streetDirectionPrefix": null
            }
        }
    ]
}
```

**Note:** Results are returned in order of relevance based on our proprietary algorithm, refined over years of optimization.

### Step 2: Search Locations (Asynchronous)

Simultaneously search for matching locations using the `/locations/autocomplete` endpoint. This provides cities, neighborhoods, and areas from MLS® data.

#### API Request

```
GET https://api.repliers.io/locations/autocomplete?search={user_input}
```

#### Filtering by Location Type

You can limit results to specific location types if needed:

```
GET https://api.repliers.io/locations/autocomplete?search=tor&type=city&type=neighborhood
```

This example excludes areas (counties/regions) and only returns cities and neighborhoods.

#### Example Response

```json
{
    "page": 1,
    "numPages": 2,
    "pageSize": 10,
    "count": 20,
    "locations": [
        {
            "resource": "Property:2381",
            "locationId": "CAONCIREWPFEEZ",
            "name": "Toronto",
            "type": "city",
            "map": {
                "latitude": "43.653226",
                "longitude": "-79.3831843"
            },
            "address": {
                "state": "ON",
                "country": "CA",
                "city": "Toronto",
                "area": "Toronto",
                "neighborhood": ""
            }
        },
        {
            "resource": "Property:2381",
            "locationId": "CAONNBZFGYQLJV",
            "name": "Toronto Gore Rural Estate",
            "type": "neighborhood",
            "map": {
                "latitude": "43.8003876",
                "longitude": "-79.7014332"
            },
            "address": {
                "state": "ON",
                "country": "CA",
                "city": "Brampton",
                "area": "Peel",
                "neighborhood": "Toronto Gore Rural Estate"
            }
        }
    ]
}
```

### Step 3: Combine and Present Results

Concatenate the listings and locations results, then present them to users in organized categories (e.g., "Properties", "Cities", "Neighborhoods").

## Implementation Best Practices

### Performance Optimization

**Debounce User Input** Implement a debounce mechanism to prevent API calls on every keystroke. Recommended delay: 300-500ms after the user stops typing.

```js
// Example debounce implementation
const debounce = (func, delay) => {
  let timeoutId;
  return (...args) => {
    clearTimeout(timeoutId);
    timeoutId = setTimeout(() => func.apply(null, args), delay);
  };
};

const debouncedSearch = debounce(performSearch, 300);
```

**Field Selection** Only request the fields you need in your `fields` parameter. This significantly improves response times and reduces bandwidth usage.
**Concurrent Requests** Execute both API calls (listings and locations) simultaneously using Promise.all() or similar concurrent execution patterns.

### User Experience Considerations

**Categorized Results** Present results in clear categories:

* **Properties** (from listings endpoint)
* **Cities** (from locations endpoint)
* **Neighborhoods** (from locations endpoint)
* **Areas** (from locations endpoint, if included)

**Visual Hierarchy** Use clear visual distinctions between categories and include relevant details like:

* Property addresses and prices
* Location types (city, neighborhood, area)
* Geographic context when helpful

**Loading States** Implement appropriate loading indicators while API requests are in progress.

## Code Example

```js
async function performAutocompleteSearch(query) {
  if (query.length < 2) return; // Don't search for very short queries
  
  try {
    // Execute both searches concurrently
    const [listingsResponse, locationsResponse] = await Promise.all([
      fetch(`https://api.repliers.io/listings?search=${encodeURIComponent(query)}&searchFields=address.streetNumber,address.streetName,mlsNumber,address.city&fields=address.*,mlsNumber,listPrice`),
      fetch(`https://api.repliers.io/locations/autocomplete?search=${encodeURIComponent(query)}`)
    ]);
    
    const listings = await listingsResponse.json();
    const locations = await locationsResponse.json();
    
    // Combine and categorize results
    const results = {
      properties: listings.listings || [],
      cities: locations.locations?.filter(loc => loc.type === 'city') || [],
      neighborhoods: locations.locations?.filter(loc => loc.type === 'neighborhood') || [],
      areas: locations.locations?.filter(loc => loc.type === 'area') || []
    };
    
    displayResults(results);
    
  } catch (error) {
    console.error('Search failed:', error);
    // Handle error appropriately
  }
}

// Apply debouncing
const debouncedSearch = debounce(performAutocompleteSearch, 300);

// Attach to search input
document.getElementById('search-input').addEventListener('input', (e) => {
  debouncedSearch(e.target.value);
});
```

## Alternative Approaches

### Hybrid Location Services

For markets where MLS® location data doesn't align with local terminology, consider combining:

**Option 1: Google Places Integration**

```js
// Use Google Places for locations, Repliers for listings
const [listingsResponse, placesResponse] = await Promise.all([
  searchReplierListings(query),
  searchGooglePlaces(query)
]);
```

**Option 2: Mapbox Integration**

```js
// Use Mapbox for locations, Repliers for listings
const [listingsResponse, mapboxResponse] = await Promise.all([
  searchReplierListings(query),
  searchMapboxPlaces(query)
]);
```

This hybrid approach provides the comprehensive MLS® listing data from Repliers while leveraging the superior location recognition capabilities of specialized mapping services.

## Conclusion

This autocomplete implementation provides users with a comprehensive search experience that bridges the gap between specific property searches and general location exploration. By combining both endpoints and following the optimization practices outlined above, you can create a fast, intuitive search interface that helps users find exactly what they're looking for.

# What questions does this article answer?

* How do I build an autocomplete search experience that returns both listings and locations?  
* How do I structure results so that MLS® listings, cities, and neighborhoods appear in separate categories?  
* Which endpoints should I combine (Listings, Locations, possibly NLP) for a unified autocomplete?  
* What does a complete implementation flow look like from keystroke to API requests and response handling?  
* How can I design a UX similar to Repliers’ autocomplete demo?  
