FSM Search Result Processing

Note:

This topic is intended for administrators and developers who configure sorting, summaries, and other search result processing.

Sorting, summary operations, and duplicate merging have different purposes.

This topic includes the following sections:

Sorting

Use < or > on a mapped search column to request ascending or descending order:

            {
  "id": "internalid",
  "label": "<title"
} 

          

This mapping orders the search by task title. Sorting doesn't increase the number of retrieved results.

For an article record model, article.sortby sorts the retrieved, mapped articles in ascending text order by a top-level property. For example, the standard History resource uses "sortby": "date" to order articles combined from its named sources. This sorting happens after retrieval and combination. It doesn't determine which rows NetSuite retrieves first. It is separate from the sort property used to order a resolved combined array and from any sorting applied by the FSM Mobile interface. Numbers are compared as text, so use a search-column sort where numeric ordering is required.

Summary Searches

Use ^ for a grouped column and a summary flag for each aggregated column. For example:

            {
  "record": "task",
  "filters": ["case.internalid", "noneof", "@NONE@"],
  "all": true,
  "map": {
    "caseId": "^case.internalid",
    "taskCount": "?internalid"
  }
} 

          

This search produces a count of matching tasks for each linked case. Its returned objects describe groups, rather than editable task records. Use compatible grouped or aggregated columns throughout a summary map. NetSuite determines which summary operations are valid for each column.

Use } for a maximum value and { for a minimum value. The ^ flag groups values. It doesn't select their maximum.

Merging Duplicate Rows

A joined search can return more than one row for a record. The * flag merges mapped objects with the same key after their search rows are read. For example, standard transaction maps use a merge key to collect lines into one transaction object.

Place the merge-key mapping first in the object and ensure that every row to keep has a populated key. Arrays are concatenated during merging. Existing populated individual values are retained, and missing values can be supplied by later rows. Duplicate merging is not a summary search and doesn't automatically remove duplicate entries from a merged array.

Use grouping and aggregation to calculate totals across search rows. Use duplicate merging when the result needs an object assembled from those rows.

Articles Built from Multiple Searches

An article definition without a direct record property can contain named source definitions. Each source has its own record, filters, and map. Supported search options such as all apply to that source. The standard History resource uses this structure to combine completed CRM Tasks and Project Tasks with related transaction and file data.

The standard record model combines those results by their mapped id. Sources describing the same article must use the same ID. Records that should remain separate must use distinct IDs. If a source map omits id, the model supplies an ID in the form <record type>-<internal ID>.

If two sources return the same article ID, properties from the second source replace matching properties from the first source. An array property is also replaced, rather than concatenated. Avoid relying on source order to resolve conflicting values across several sources. Give each combined property one source where possible. This combination differs from the * duplicate-row merge within an individual search. For information about the array: true option-list combination, see Combining Search Results. The article.sortby property can order the combined articles afterward.

Nested Searches

A search can supply values used by another search's filters. FSM resolves the inner search before executing the outer search. The inner map should return the value shape expected by the outer filter, such as an array of internal IDs.

The following example retrieves the case linked to the current CRM Task:

            {
  "record": "supportcase",
  "filters": [
    "internalid",
    "anyof",
    {
      "array": true,
      "default": "0",
      "linkedCaseIds": {
        "record": "task",
        "filters": [
          ["internalid", "anyof", "${event.internalid}"],
          "and",
          ["case.internalid", "noneof", "@NONE@"]
        ],
        "map": "case.internalid"
      }
    }
  ],
  "map": {
    "id": "internalid",
    "label": "casenumber"
  }
} 

          

The array: true object combines its supplied values into one array. The string "0" ensures that the filter value is not an empty array when no linked case is found. When the inner search returns a case ID, the combined array still includes "0" as well as that ID.

In this pattern, default is a name for an included value. It is not a conditional fallback: the value is included whether the inner search finds records. The name linkedCaseIds labels the inner search and is not a NetSuite field ID.

Choose an included placeholder appropriate to the filter. Don't substitute "@NONE@" for "0" without considering the operator and field: the empty-value marker can change which records match. An empty inner search doesn't otherwise supply a filter value automatically.

Where either search can return more than 1,000 rows, give that search its own all: true in a supported location. Setting all on the outer search doesn't enable it for the inner search.

Combining Search Results

An array: true object can combine several option searches. Each search should return the same option shape.

            {
  "array": true,
  "sort": "label",
  "serviceItems": {
    "record": "item",
    "filters": [
      ["isinactive", "is", "F"],
      "and",
      ["type", "anyof", "Service"]
    ],
    "all": true,
    "map": {
      "id": "internalid",
      "label": "itemid"
    }
  },
  "nonInventoryItems": {
    "record": "item",
    "filters": [
      ["isinactive", "is", "F"],
      "and",
      ["type", "anyof", "NonInvtPart"]
    ],
    "all": true,
    "map": {
      "id": "internalid",
      "label": "itemid"
    }
  }
} 

          

Use this object as an element's options definition. It combines the two lists and sorts their string labels without regard to letter case. Set sort to the name of the option property to sort by. Every included option must supply a suitable string value for that property.

Combining arrays doesn't deduplicate options. If the searches overlap, adjust their filters or otherwise ensure that duplicate choices are not returned.

For a list used on several tabs, define the search one time in a loaded supporting resource and reference its options. For the complete Inventory placement and loading relationship for the user resource, see Sharing Data Between Resources in FSM Configuration. That subsection also includes an example of a Select that uses the shared options. Referencing the loaded list doesn't run a separate search each time it is used.

Additional Information

Related Topics

General Notices