Skip to main content

Coveo

Integrating Real-World Data into Coveo Search Using the Generic REST API Source Connector

Istock 1419229965

This blog will guide you through indexing content from API endpoints into Coveo using the Generic REST API source. This tool allows the indexing of data from any web service exposing a REST API, such as Content Management Systems (CMS), databases, or third-party platforms. While the demo API here is for illustration, the steps can be adapted for real-world scenarios, like integrating Adobe Experience Manager (AEM) data or fetching structured content, such as user profiles or metadata, from various repositories.

By the end of this guide, you’ll be able to index and display structured data in Coveo, enhancing search relevance and user experience.

Why Use Coveo’s Generic REST API Source?

The Generic REST API source in Coveo is designed to pull data from an API and make it available for search and analytics. It’s highly versatile and enables you to:

  • Index data from any API without a dedicated connector.
  • Customize indexing with JSON configurations for API calls and responses.
  • Access content from various web applications using REST APIs. And handle content from diverse repositories efficiently.
  • Simplifies data retrieval and management through structured API calls.

What You Need

  • API Access: The API should expose the data you want to index. For this blog, we’re using a sample API.
  • Coveo Admin Console Access: You’ll need admin rights to configure sources.
  • Optional Tool: Use Postman or a similar API client to inspect API responses before configuration.

Step-by-Step Implementation

Step 1: Explore the API Output

Before integrating with Coveo, examine the API response to understand the data structure. For this blog, I’m using Free fake and reliable API for testing and prototyping.

Test with Postman or cURL:

curl --location --request GET 'https://jsonplaceholder.typicode.com/users'

API Call:

GET https://jsonplaceholder.typicode.com/users

Accept: application/json
Authorization: Bearer **********-****-****-****-************

Sample API Response:

[
  {
    "id": 1,
    "name": "Leanne Graham",
    "username": "Bret",
    "email": "Sincere@april.biz",
    "address": {
      "street": "Kulas Light",
      "suite": "Apt. 556",
      "city": "Gwenborough",
      "zipcode": "92998-3874"
    },
    "phone": "1-770-736-8031 x56442",
    "website": "hildegard.org"
  }
]

JSON Configuration Structure

Before crawling data from the API, define a clear structure for the JSON configuration. This structure determines how Coveo retrieves and organizes data from the API.
Ds Genapi

  • API (Root Node): The interaction entry point, representing the external data source (any RESTful API).
  • Service: The layer that processes requests to the API and supports various data sources or services.
  • Endpoints: Defined paths the API exposes (e.g., /users, /comments, /albums).
  • Data Mapping: Each endpoint retrieves specific data (e.g., user profiles from /users, comments from /comments, albums from /albums).

Identify Fields for Indexing

From the response, fields like id, name, email, and address can be mapped for indexing.

Step 2: Create the Generic REST API Source Connector in coveo

  • Log In to Coveo Admin Console: Navigate to Content > Sources and click Add Source.
  • Select Source Type: Choose REST API from the options.
  • Configure Basic Details, Source Name: Use something descriptive like user profiles etc.
  • Don’t build it; just save it for now.

Note:

  • REST API URL: https://jsonplaceholder.typicode.com/users
  • Authentication: Skip if the API is public. If authentication is required, configure it under the Authentication Tab.

Add Source1

Add Source2

Step 3: Configure JSON Settings

  • After saving the source, click Edit JSON Configuration from the source menu.
  • Replace the default JSON with the following configuration:
{
  "services": [
    {
      "url": "https://jsonplaceholder.typicode.com",
      "paging": {
        "pageSize": 20,
        "offsetStart": 10,
        "offsetType": "item",
        "parameters": {
          "limit": "limit",
          "offset": "offset"
        }
      },
      "endpoints": [
        {
          "path": "/users",
          "method": "GET",
          "itemType": "userprofile",
          "uri": "%[coveo_url]/users/%[id]",
          "clickableUri": "%[coveo_url]/users/%[id]",
          "title": "%[name]",
          "metadata": {
            "id": "%[id]",
            "username": "%[username]",
            "email": "%[email]",
            "address": "%[address]",
            "phone": "%[phone]",
            "website": "%[website]",
            "company": "%[company]"
          }
        }
      ]
    }
  ]
}

Json Config For Rest Api Spurce

Step 4: Save and Rebuild the Source

  • Click Save to apply changes.
  • Go back to the source page and click Save and Rebuild.
  • Monitor logs to ensure successful indexing using the log browser.

The screenshot below shows the rebuild process or logs confirming successful indexingLogsforuser Profile Sourc

Mapping and Displaying Data

Step 5: Map API Fields to Coveo Fields and then associate it with the rest-api source

  • Navigate to Fields in the Admin Console.
  • As shown below, create new fields for attributes such as id, name, email, address, and others. The field for ‘name’ has already been created; follow the same process for the other fields.Add Field
  • Map these fields in the Mappings tab of the source configuration.
    Field Mapping

For more detailed information on Coveo fields and mappings, refer to the following blogs:

To view a more detailed field mapping configuration for your source, see the steps below:  Edit Mappin Json1 Edit Mappin Json2See the below Mapping JSON:

[
  {
    "content": "%[filename]",
    "extractionMethod": "METADATA",
    "fieldName": "filename",
    "id": "ashwinitestorg6zfn7o3t-wktezkeyf53ibe2gryghnjsk6y-qaut7yluelbrwf5b3x23ea2iji",
    "kind": "COMMON",
    "rules": [
      "%[filename]"
    ]
  },
  {
    "content": "%[clickableuri]",
    "extractionMethod": "METADATA",
    "fieldName": "clickableuri",
    "id": "ashwinitestorg6zfn7o3t-wktezkeyf53ibe2gryghnjsk6y-qidgh3yqtqgxpt2zarqg5y2fki",
    "kind": "COMMON",
    "rules": [
      "%[clickableuri]"
    ]
  },
  {
    "content": "%[email]",
    "extractionMethod": "METADATA",
    "fieldName": "up_email",
    "id": "ashwinitestorg6zfn7o3t-wktezkeyf53ibe2gryghnjsk6y-q66t3o5osh6wqdzc4rlwrlsc3m",
    "kind": "COMMON",
    "rules": [
      "%[email]"
    ]
  },
  {
    "content": "%[phone]",
    "extractionMethod": "METADATA",
    "fieldName": "up_phone",
    "id": "ashwinitestorg6zfn7o3t-wktezkeyf53ibe2gryghnjsk6y-qr7g25pyvh3rl42wtyheppcopy",
    "kind": "COMMON",
    "rules": [
      "%[phone]"
    ]
  },
  {
    "content": "%[username]",
    "extractionMethod": "METADATA",
    "fieldName": "up_username",
    "id": "ashwinitestorg6zfn7o3t-wktezkeyf53ibe2gryghnjsk6y-sfqu5sxfgk32iarhiaes22chhm",
    "kind": "COMMON",
    "rules": [
      "%[username]"
    ]
  },
  {
    "content": "%[website]",
    "extractionMethod": "METADATA",
    "fieldName": "up_website",
    "id": "ashwinitestorg6zfn7o3t-wktezkeyf53ibe2gryghnjsk6y-qrti6wae2lzbq4iy7vd5zhkatq",
    "kind": "COMMON",
    "rules": [
      "%[website]"
    ]
  },
  {
    "content": "%[company]",
    "extractionMethod": "METADATA",
    "fieldName": "up_company",
    "id": "ashwinitestorg6zfn7o3t-wktezkeyf53ibe2gryghnjsk6y-sxfkfclwtarbh3fvrjvtfr2iwe",
    "kind": "COMMON",
    "rules": [
      "%[company]"
    ]
  },
  {
    "content": "%[address]",
    "extractionMethod": "METADATA",
    "fieldName": "up_address",
    "id": "ashwinitestorg6zfn7o3t-wktezkeyf53ibe2gryghnjsk6y-u6ajgmpuoedwigbmeuzhszkpvy",
    "kind": "COMMON",
    "rules": [
      "%[address]"
    ]
  },
  {
    "content": "%[id]",
    "extractionMethod": "METADATA",
    "fieldName": "up_id",
    "id": "ashwinitestorg6zfn7o3t-wktezkeyf53ibe2gryghnjsk6y-udpex4lvcj5g7jaynzkwsc2fie",
    "kind": "COMMON",
    "rules": [
      "%[id]"
    ]
  },
  {
    "content": "%[month]",
    "extractionMethod": "METADATA",
    "fieldName": "month",
    "id": "ashwinitestorg6zfn7o3t-wktezkeyf53ibe2gryghnjsk6y-qrz336tyq4qbvj2qizlqpwkaky",
    "kind": "COMMON",
    "rules": [
      "%[month]"
    ]
  },
  {
    "content": "%[title:crawler]",
    "extractionMethod": "METADATA",
    "fieldName": "title",
    "id": "ashwinitestorg6zfn7o3t-wktezkeyf53ibe2gryghnjsk6y-r3agbznnaduqkgul7b7hudsarq",
    "kind": "COMMON",
    "rules": [
      "%[title:crawler]"
    ]
  },
  {
    "content": "%[year]",
    "extractionMethod": "METADATA",
    "fieldName": "year",
    "id": "ashwinitestorg6zfn7o3t-wktezkeyf53ibe2gryghnjsk6y-rbfbf2soa6rzlgai7eygpfkgoq",
    "kind": "COMMON",
    "rules": [
      "%[year]"
    ]
  },
  {
    "content": "%[mobile]",
    "extractionMethod": "METADATA",
    "fieldName": "mobilephone",
    "id": "ashwinitestorg6zfn7o3t-wktezkeyf53ibe2gryghnjsk6y-rdhx4wtyfy5znb6txno4qvcpba",
    "kind": "COMMON",
    "rules": [
      "%[mobile]"
    ]
  },
  {
    "content": "%[company]",
    "extractionMethod": "METADATA",
    "fieldName": "company",
    "id": "ashwinitestorg6zfn7o3t-wktezkeyf53ibe2gryghnjsk6y-rdjy3kkqcxbs66phsdmcfdcpou",
    "kind": "COMMON",
    "rules": [
      "%[company]"
    ]
  },
  {
    "content": "%[permanentid]",
    "extractionMethod": "METADATA",
    "fieldName": "permanentid",
    "id": "ashwinitestorg6zfn7o3t-wktezkeyf53ibe2gryghnjsk6y-rirzsjru43xswhpfwc4c7bkb4m",
    "kind": "COMMON",
    "rules": [
      "%[permanentid]"
    ]
  },
  {
    "content": "%[coveo_externalurl]",
    "extractionMethod": "METADATA",
    "fieldName": "relatedlink",
    "id": "ashwinitestorg6zfn7o3t-wktezkeyf53ibe2gryghnjsk6y-rjuqiqtvi6fe5kbrwwvbc2sanu",
    "kind": "COMMON",
    "rules": [
      "%[coveo_externalurl]"
    ]
  },
  {
    "content": "%[office]",
    "extractionMethod": "METADATA",
    "fieldName": "office",
    "id": "ashwinitestorg6zfn7o3t-wktezkeyf53ibe2gryghnjsk6y-xsbc254qtlebiqu4dcqt6rcmn4",
    "kind": "COMMON",
    "rules": [
      "%[office]"
    ]
  }
]

To view the indexed documents with their mapped properties, go to Content > Content Browser in the Coveo Admin Console.

Click the properties option in the top-right corner to view metadata, as shown below.
Content Browser 1
Here are the properties, as shown below
Content Browser Metadat 1

Step 6: Configure Search Interface

Display the indexed data on the Coveo search page. Use Coveo JSUI Framework components to show the details:

<script id="Default" class="result-template" type="text/html" data-layout="list">
    <div class="coveo-result-frame">
        <div class="coveo-result-cell" style="vertical-align:top;text-align:center;width:32px;"> <span class="CoveoIcon" data-small="true" data-with-label="false"></span>
            <div class="CoveoQuickview"></div>
        </div>
        <div class="coveo-result-cell" style="vertical-align: top;padding-left: 16px;">
            <div class="coveo-result-row" style="margin-top:0;">
                <div class="coveo-result-cell" style="vertical-align:top;font-size:16px;" role="heading" aria-level="2">
                    <a class="CoveoResultLink"></a>
                </div>
                <div class="coveo-result-cell" style="width:120px;text-align:right;font-size:12px">
                    <div class="coveo-result-row"> <span class="CoveoFieldValue" data-field="@date" data-helper="date"></span> </div>
                </div>
            </div>
            <div class="coveo-result-row" style="margin-top:10px;">
                <div class="coveo-result-cell"> <span class="CoveoExcerpt"></span> </div>
            </div>
            <div class="coveo-result-row" style="margin-top:10px;">
                <div class="coveo-result-cell"> <span class="CoveoFieldValue" data-field="@up_id" data-text-caption="Id:" style="margin-right:30px;"></span> </div>
            </div>
            <div class="coveo-result-row" style="margin-top:10px;">
                <div class="coveo-result-cell"> <span class="CoveoFieldValue" data-field="@up_email" data-text-caption="Email" style="margin-right:30px;"></span> </div>
            </div>
            <div class="coveo-result-row" style="margin-top:10px;">
                <div class="coveo-result-cell"> <span class="CoveoFieldValue" data-field="@up_username" data-text-caption="Username" style="margin-right:30px;"></span> </div>
            </div>
            <div class="coveo-result-row" style="margin-top:10px;">
                <div class="coveo-result-cell"> <span class="CoveoFieldValue" data-field="@up_address" data-text-caption="Address" style="margin-right:30px;"></span> </div>
            </div>
            <div class="coveo-result-row" style="margin-top:10px;">
                <div class="coveo-result-cell"> <span class="CoveoFieldValue" data-field="@up_phone" data-text-caption="Phone" style="margin-right:30px;"></span> </div>
            </div>
            <div class="coveo-result-row" style="margin-top:10px;">
                <div class="coveo-result-cell"> <span class="CoveoFieldValue" data-field="@up_company" data-text-caption="Company" style="margin-right:30px;"></span> </div>
            </div>
            <div class="coveo-result-row" style="margin-top:10px;">
                <div class="coveo-result-cell"> <span class="CoveoFieldValue" data-field="@up_website" data-text-caption="Website" style="margin-right:30px;"></span> </div>
            </div>
            <div class="coveo-result-row" style="margin-top:10px;">
                <div class="coveo-result-cell"> <span class="CoveoFieldValue" data-field="@filetype" data-text-caption="File Type" style="margin-right:30px;"></span> </div>
            </div>
            <div class="coveo-result-row" style="margin-top:10px;">
                <div class="coveo-result-cell"> <span class="CoveoFieldValue" data-field="@source" data-text-caption="Source" style="margin-right:30px;"></span> </div>
            </div>
            <div class="coveo-result-row" style="margin-top:10px;">
                <div class="coveo-result-cell">
                    <div class="CoveoPrintableUri"></div>
                </div>
            </div>
            <div class="coveo-result-row">
                <div class="coveo-result-cell">
                    <div class="CoveoMissingTerms"></div>
                </div>
            </div>
        </div>
    </div>
</script>

Search interface displaying the mapped fields.
Displaying Result

Conclusion

Indexing data from APIs like AEM into Coveo using the Generic REST API source is straightforward. Following this guide, you can set up a robust pipeline to fetch, map, and display API data in your Coveo search interface. With the flexibility of JSON configurations and Coveo’s search components, it can deliver powerful, enriched search experiences.

Useful Links

Add a REST API source | Coveo Platform

Use the Log Browser to review indexing logs | Coveo Platform

Inspect items with the Content Browser | Coveo Platform

Part 1: Building the Source and Corresponding Mappings in Coveo Enterprise Search / Blogs / Perficient

Part 2: Building the Source and Corresponding Mappings in Coveo Enterprise Search / Blogs / Perficient

Leave a Reply

Your email address will not be published. Required fields are marked *

This site uses Akismet to reduce spam. Learn how your comment data is processed.

Ashwini Bhave

Ashwini works at Perficient as a Technical Consultant. She is familiar with various technologies and frameworks, including Coveo enterprise search and AI-powered relevance. She holds a Coveo developer certification. Learning about cutting-edge technology interests her she is also motivated to share her knowledge through her blogs.

More from this Author

Follow Us