Advanced Search

Overview

The Advanced CIS REST Web API supports the ability to perform advanced searches against customer/account and related data in order to retrieve matching records in a single function. The functionality and results exactly mimic the search features in the CIS AccountView form. Indeed, the same API is used for both, ensuring the search behavior and results are consistent across all interfaces.

There are two APIs related to searching. The legacy end point at /data/customeraccount/search which supports searching for customer/accounts only, and the new search API at /data/customeraccount/$search which is more generic and powerful. The newer $search API is also available at additional end points at /data/customer and /data/account to search for those items, and may be expanded to other end points in the future.

 

Refer to the specific section below describing the specific search API you are interested in.


CIS Search API V2

This is the newer and preferred search mechanism if you are implemented new functionality. It will be supported and enhanced on an ongoing basis.

This functionality is implemented as two related end points: a $searchconfig end point to retrieve configuration details that itemize every alias, target, table, and field supported by that search; and a $search end point that submits the actual search and returns details about the search results. These end points are general, and will be added to more contexts as needed, but they are currently available on the /data/customer, /data/customeraccount, and /data/account end points.

GET /data/customeraccount/$searchconfig

Retrieve a list of tables, fields, aliases supported by the context (customeraccount in this case). Used to validate input and offer help, code completion, and intellisense to search providers using this end point. It is not required to use this search; it is an aid for reflection/discovery purposes related to this search context. See the REST Swagger details for this end point to review the details of the returned data.

GET /data/customeraccount/$search?query=&matchtype=&fields=&maximum=&loadcount=

Invoke a search on the context (customeraccount in this case) using the given query string. Refer to the details below for an explanation of the query string contents and possibilities. The return data can include the found context business object, and/or a formatted result line with selected content taken from the result object and its children and match conditions, and/or also any child or related items of the result object by using the optional standard fields= directive. See the Swagger documentation for this end point for details on the result data format. The order of the results is done in match weight order. Items with a higher match weight are sorted higher in the result list. Match weights are set in the CIS application dictionary and are highest for fields in the target table and lower for related tables.

Query String

Description

query= 

 The general format for a search query string is:

     [target:] terms [ AND|OR [target:] terms …]

 

The target: is optional and can be used to specifically target a field, table, or special alias; the terms are any combination of the following and can be combined using AND, OR, and NOT operators:

  • Keyword term: any number of words, by default space between words is translated to AND operator

  • Exact term: any combination of words in quotes, exact terms are searched as is and space is not translated to AND operator.

  • Group term: any combination of words in round brackets. Group queries can be used in advanced search queries to format complex search criteria

  • Range term: is defined using square brackets and is used to search for a range of values. The general format is [from:to] with "from" or "to" being optional: [from:] or [:to]

Wildcards can be used in any search query: * or % for any number of characters, ? or _ for a single character, and ^ or / to determine the starting or ending character. Search queries require minimum of 3 characters, unless it is an exact term search or name or address search as explained later.

Specific NULL keyword can be used to search for null values in a field, while EMPTY keyword or "" can be used to search for empty strings or null values in a field. NULL or EMPTY keywords are case-insensitive and can be used in combination with other keywords or operators.

Examples:

    firstname: john AND (birthday: [1980-01-01:2000-01-01] OR age: [20:40])

    firstname: john lastname: NOT (smith OR nazeri)

    firstname: "john" lastname: "smith"

    firstname: jo??

    firstname: jo%

    firstname: ^jo

    firstname: hn^

    firstname: NULL

    firstname: EMPTY

    customer.firstname: NOT EMPTY AND customer.nametype: C

 

Date, Date/Time, Boolean format:

  • Date: the standardized date format for the API is YYYY-MM-DD is preferred, but if the Content-Language header is passed with a supported locale, then dates in the format supported by that locale are also recognized.

  • Date/Time: the standardized date/time format is YYYY-MM-DDThh:mm:ss is preferred, but if the Content-Language header is passed with a supported locale, then date/times in the format supported by that locale are also recognized.

  • Boolean: logical or flag values will recognize false, f, .F., 0, no, n (case-insensitive) as false, and anything else as true.

Contexts

A search is performed in a Context. A Search-Context is combination of a main table and its related tables. If a match if found, the record from the main table is returned. For each search-context, the search is performed in all Searchable fields of corresponding tables. Searchable fields are defined in AppDict. For example, the “CustomerAccount” search-context, performs search in BIF003 and all its related tables including Customer (BIF001), Account (BIF002), Address (BIF006), … but the result of this search always returns a context item, e.g. CustomerAccount. So far only the following search-contexts are implemented:

  • Customer

  • Account

  • CustomerAccount

The result of a search query is the list of primary keys of a main table of a search-context together with table/field names of its related tables where data matches were found.

The detail of a search result is the underlying business object associated to the main table of the search-context and a Description Text object explaining the content of the search result.

 

General features of the CisSearch:

  • Wildcards can be used in any search query: * or % for everything, ? or _ for a single character, and ^ or / to determine the starting or ending character.

  • When wildcards are not used, by default search will find all records that "contain" the input query. Using contains is equivalent to surrounding any string search words with "*" or "%" wildcards (e.g. *findme* )
    To perform "starts-with" or "ends-with" searches, use the "^" or "/" wildcards at the beginning or end of the search term (e.g. ^findme or findme^ )

  • The search result’s Detail Text object uses a Text ID defined in Resources and supports all the properties of the underlying business object.

  • The text format can be changed dynamically to reflect customer's need. All properties of the underlying business object are accessible in the Text object.

  • Search fields support aliases. This can be configured by the user to target a searchable field in a table with one or more aliases.

  • Search tables support aliases. This can be configured by the user to target all searchable fields in a table with one alias.

  • Table or business object name in each search-context can be targeted using aliases. In that case all the fields in the table are being used, disregarding the Searchable flag in AppDict:

    • The syntax is [table name]: query or [business type name]: query

    • The user’s custom aliases cannot be the same as the business name or table name as they are reserved aliases.

  • Field or property name of a business object in each search-context can be targeted using aliases.

    • The syntax is [table name].[field name]: query for table/field names and [business type name].[property name]: query for business/property names

 

Special Aliases feature of the CisSearch:

Along with the standard table and business name targets, there are several special alias targets implemented. These targets implement special meaning and handling of the search terms applied to them. Special target aliases begin with a “.” To indicate they are special targets and to avoid name overlaps with table names or business names. The currently implemented special alias targets are .name, .address, and .serviceaddress.

Customer name search using .name:

The combined fields representing a name in the Customer (BIF001) table can be targeted for intelligent searches using the alias .name:

  • .name: alias is greedy, meaning everything following the alias is considered part of the name, until we reach another alias, a group query, a range query, an exact query, or operators such as AND, OR, NOT

  • When searching for names, single character queries are also accepted.

  • When query is only one word, it is being used to search in first, middle, or last names, with priorities of 2, 3, 1 respectively.

  • When query contains a comma “,” the meaning is swapped. The word before the comma is used to search in the last name, the word after comma is used to search in the first name or the middle name.

  • When query is two words, the following queries are executed:

    • Word 1 + word 2 (as entered) in last name (priority: 1) OR

    • Word 1 in first name and word 2 in last name (priority: 2) OR

    • Word 1 in middle name and word 2 in last name (priority: 3)

  • When query is three words, the following queries are executed:

    • Word 1 + word 2 + word 3 (as entered) in last name (priority: 1) OR

    • Word 1 in first name, word 2 in middle name, word 3 in last name (priority: 2) OR

    • Word 1 in first name and word 2 + word 3 in last name (priority: 3) OR

    • Word 1 in middle name and word 2 + word 3 in last name (priority: 4)

  • When query is more than three words, every combination of the words is used against every searchable field in Customer (BIF001).

Examples:

    .name: john smith

    .name: smith, john

    .name: auto repair

 

Customer address search using .address:

Customer/Account address search is performed by an alias .address:

  • .address: alias is greedy, meaning everything following the alias is considered part of the address, until we reach another alias, a group query, a range query, an exact query, or operators such as AND, OR, NOT

  • When the query contains a pattern matching US zip-code or Canadian postal-code, that part of the query is extracted and is used to search in PostalCode field automatically.

  • When the query ends with a comma followed by another term the part after the comma is considered the town name and is used to search in the Town field automatically.

  • The CIS AddressParser is used to parse the remainder of the text and each property of the result is used to search in its corresponding field.

  • Address search targets Account (BIF002) and Address (BIF006) tables.

Service address search using .serviceaddress:

  • Service Address search is performed by the alias .serviceaddress: and it targets the Account (BIF002) table only. This means only service addresses are searched.

  • It parses and recognizes address parts exactly like the .address: special alias above.

Examples:

    .serviceaddress: 123 main

    .address: main st, smallville 90210

    .address: apt 12 main st

 

Payment search using .payment:

  • Payment search is performed by the alias .payment: and it targets reconstructed payments which may not be available in original form any more. Payment amounts can be searched for, and optionally within a date range and with optional reference number or receipt number.

  • Format is .payment: $amount [ref# | check# | receipt#] [startdate]-[enddate]

Examples:

    .payment: $201.55

    .payment: 201.55 456

    .payment: 201.55 1/1/2021

    .payment: 201.55 1/1/2021-12/31/2021

    .payment: 201.55 -06/15/2022 ref444

 

Meter search using .meter:

  • Meter search is performed by the alias .meter: and it targets installed meter numbers which exist in the AccountMeter (BIF005) table. Because meter numbers may be overlapping for different services, you can optionally specify the service as well.

  • Format is .meter: meter# [service] where the meter# is a partial (starts-with) match, and the optional service is also a partial (starts-with) match.

Active Meter search using .ameter:

  • Performs the same search in the same format as the .meter: search, except this variation only matches currently active meters.

  • Format is .ameter: meter# [service] where the meter# is a partial (starts-with) match, and the optional service is also a partial (starts-with) match.

Examples:

    .meter: 5612345

    .ameter: E554367 electric

    .meter: KL665431 wa

 

Service Order search using .so:

  • Service orders matching a number or range of numbers can be found, with optional filtering for service order type.

  • Format is .so: from#[-to#] [type] where the from# and to# represent a number or a range and the type is an optional partial match (starts-with) of the service order type description or code. The SO# range can be from-less (-to#) or to-less (from#-).

Examples:

    .so: 101145

    .so: 10555-10590 turn off

    .so: 560000- LALO

 

fields= 

Optional data shaping directive; include or exclude fields by using a comma separated list of fields or elements; prefix field with '-' to exclude item.

 The optional embedded child items 'Account', 'Customer', 'CustomerAccount', 'Address', and 'ContactInformation' are also available via this query string. These items will be returned as standard embedded objects in the _embedded container of each result item. Children of these children are also supported using the standard fields= syntax for selecting them.

  • E.g. *, *.*, fielda, .child1.field2, .child2.*, .child3.subchild1.*

  • Exclude items by prefixing with “-”, e.g. “-field1,-field2,-.child1.*,-.child2.field5”.

  • The default for the list and resource level GET is “*”, which selects all properties on each returned object.

  • Child items are returned using the standard HATEOAS HAL _embedded container.

The default is '*'

maximum= 

Optional maximum number of search results to limit the response to.

The default value is 100.

loadcount=

Optional parameter to indicate whether you want the total match count returned. This is an optimization parameter meant to suppress the match count from being returned in order to return the results more quickly. This is typically used in combination with the maximum= directive to e.g. quickly return the top e.g. 10 matches for a given search. Suppressing the match count improves performance because the search does not have to do extra work to quantify the result set when the total match is not needed and only a limited number of items are requested.

The default is true.

 

 

 


CIS Search API V1

This search is a legacy implementation. There are no plans to remove it, but it will not be expanded or enhanced. Refer to the $search form of the search API for the best search experience available via the CIS API.

The search function is invoked via a HTTP GET against /data/customeraccount/search

The full URL signature is:

         GET: /data/customeraccount/search?where=&fields=&maximum=&order=

 

Query String

Description

where= 

Search condition(s) to be used. Multiple conditions must be AND connected. Field names to search are formatted as ‘class.property’ or ‘table.field’. Only 'eq' and 'like' expressions are currently supported. Note that an OR connector will be accepted but is treated like an AND - all expressions are additive irrespective of connector type.

Table / class prefixes to be used in the expressions can come from the subset of tables/classes:

  • BIF001 / customer

  • BIF002 / account

  • BIF003 / customeraccount

  • BIF004 / accountservicegroup, accountservice

  • BIF005 / accountmeter, accountmeterreadtype

  • BIF006 / address

  • BIF010 / contactinformation

  • BIF023 / serviceorder

  • BIF012 / supplierenrollment

Additionally, there are a few special prefixes with interesting functionality:

  • name - Causes a name match to be found from the primary customer as well as any related customers. Use 'customer' / 'BIF001' if you only want to match on the primary name for a customer/account.

  • address - Causes any address associated with the search to match. This includes service address as well as any additional addresses. If you want to target specifically the additional addresses and not the service address, then you must use 'BIF006' as the prefix.

 

Examples:

    where=name.lastname like 'SMI*' and name.firstname like 'JO*'

    where=account.streetname like 'MAIN*' and account.town eq 'TORONTO

    where=bif001.c_nametype eq 'C' and bif001.c_lastname like '*CORP*' and address.c_town eq 'MYVILLE'

    where=serviceorder.serviceordertype eq 'FIX1' AND accountmeter.meter like '1234*' AND accountservice.service eq '10'

    where=name.lastname like 'ACME *' and address.streetname eq 'MAIN'

fields= 

Optional data shaping directive; include or exclude fields by using a comma separated list of fields or elements; prefix field with '-' to exclude item.

 The optional embedded child items 'Account', 'Customer', 'CustomerAccount', 'Address', and 'ContactInformation' are also available via this query string. These items will be returned as standard embedded objects in the _embedded container of each result item. Children of these children are also supported using the standard fields= syntax for selecting them.

  • E.g. *, *.*, fielda, .child1.field2, .child2.*, .child3.subchild1.*

  • Exclude items by prefixing with “-”, e.g. “-field1,-field2,-.child1.*,-.child2.field5”.

  • The default for the list and resource level GET is “*”, which selects all properties on each returned object.

  • Child items are returned using the standard HATEOAS HAL _embedded container.

maximum= 

Optional maximum number of search results to limit the response to. The default and maximum value allowed is 500. Any value outside the range 1-500 will cause 500 to be used. The total number of matches will always be returned in the result TotalItems property no matter the limit applied; this allows you to know how many matches really occurred even though you did not retrieve details for all of them.

order= 

Optional comma separated list of result fields to use to sort the result list. Prefix fields with “-“ to sort descending. The sort field names should be taken from the available fields in the CustomerAccountSearchResulItemtModel return results.  Only basic search result fields can be used to sort on - not _embedded data.

 

Return Results

The basic result data includes formatted names and formatted addresses for all matching records.

The result set is meant to select a BIF003/customeraccount record, so searching on e.g. name will return multiple records for the same person if that person has multiple customer/account items, or is in the process of moving (in which case the outgoing and the incoming items are returned).  The results include BIF001PK, BIF002PK, and BIF003PK, so it is easy to dedupe the results cased on service address or customer if that’s all you need, but typically the resulting selection would be used to select the applicable BIF003/customeraccount, so deduping might not be advisable.

Refer to the fields= query string for details on including additional child object data for each result item. Doing this may save you additional calls if the data you require is available in one of the available children.

Refer to the detailed definitions of the CustomerAccountSearchResultModel and CustomerAccountSearchResultItemModel for names and descriptions of the returned result properties.