Query functions

This is for:

Developer

A query function is a mathematical expression evaluated against each item returned by a query, and whose output is stored in a dynamic, temporary field generated at query time. Query function expressions are defined using the C++ Mathematical Expression Toolkit Library (ExprTk), but they do not support control and loop structures (for example, if-then-else, while loop, etc.).

This article describes the members of the structure that defines a single query function. You can specify an array of query functions in a query using the queryFunctions top-level query parameter.

Note

You can use a field generated by a query function almost anywhere you would use a normal numeric field. One notable exception is automatic range generation in Group By operations (see the generateAutomaticRanges Group By parameter). If you need to create ranges for a field generated by a query function, you must specify those ranges explicitly using the rangeValues Group By parameter, because the index can’t determine them automatically.

This implies that in a JavaScript Search Framework interface, if you want to render a FacetRange component based on a field generated by a query function, you must use the ranges option to specify the desired ranges.

Examples
  1. You want to compute the file size in kilobytes for each item at query time and store the results in a dynamically generated field called @sizekb.

    POST https://platform.cloud.coveo.com/rest/search/v2 HTTP/1.1
    
    Content-Type: application/json
    Accept: application/json
    Authorization: Bearer **********-****-****-****-************

    Payload

    {
      "queryFunctions": [
        {
          "fieldName": "@sizekb",
          "function" : "@size/1024"
        }
      ]
    }
    Tip

    200 OK response body (excerpt)

    {
      ...
      "results": [
        ...
        {
          "raw": {
            ...
            "size": 1767763,
            "sizekb": 1726.3310546875,
            ...
          },
          ...
        },
        ...
      ],
      ...
    }
  2. You want to compute the distance between two coordinates in miles for each item at query time and store the results in a dynamically generated field called @distanceinmiles.

    POST https://platform.cloud.coveo.com/rest/search/v2 HTTP/1.1
    
    Content-Type: application/json
    Accept: application/json
    Authorization: Bearer **********-****-****-****-************

    Payload

    {
      "queryFunctions": [
        {
          "fieldName": "@distance",
          "function" : "dist(@latitude, @longitude, 46.8167, -71.167)"
        },
        {
          "fieldName": "@distanceinmiles",
          "function": "@distance*0.000621371"
        }
      ]
    }
    Tip

    200 OK response body (excerpt)

    {
      ...
      "results": [
        ...
        {
          "raw": {
            ...
            "distance": 235762,
            "distanceinmiles": 146.495669702,
            ...
          },
          ...
        },
        ...
      ],
      ...
    }
  3. You have a @price field on your items. You need a @discountedprice field that contains the price with a 10% discount.

    POST https://platform.cloud.coveo.com/rest/search/v2 HTTP/1.1
    
    Content-Type: application/json
    Accept: application/json
    Authorization: Bearer **********-****-****-****-************

    Payload

    {
      "queryFunctions": [
        {
          "fieldName": "discountPrice",
          "function" : "@price*0.9"
        }
      ]
    }
    Tip

    200 OK response body (excerpt)

    {
      ...
      "results": [
        ...
        {
          "raw": {
            ...
            "price": 10,
            "discountPrice": 9,
            ...
          },
          ...
        },
        ...
      ],
      ...
    }

Performance issues

To prevent performance issues, every computed field referenced in the function must be stored in memory. Not doing so may lead to serious performance issues, with queries that might take over a second, depending on your number of items.

This is because query functions are executed on all accessible items. If the computed field isn’t stored in memory, it might have to be loaded from the disk, which can significantly slow the query.

Solve the issue in the Coveo Administration Console

For Coveo for Sitecore, follow these steps:

  1. Access the Coveo Administration Console.

  2. Under Content, select Fields.

  3. Search for the field you want to store in cache.

  4. Select your desired field, and click Edit.

  5. In the Edit a Field window, select Advanced Settings.

  6. Select Use cache for numeric queries.

Important

If your numerical field is stored as a string, you may need to change its Type, for example to Long.

  1. Select Save Field to save your changes.

Exceptions

A few query exceptions can be returned when using Query Functions:

  • InvalidQueryFunction, Value: 40, Using the '@' character without any field name.

  • InvalidQueryFunctionField, Value: 41, Using a field that doesn’t exist in the index, nor in any prior query function.

  • InvalidQueryFunctionFieldType: Value: 42, Using a field that’s not a numerical field.

  • InvalidQueryFunctionSyntax: Value: 43, Syntax error in the expression.