Catalogs

You can get values from catalogs and paste them into forms using the getCatalog method. For example, you can calculate table values or filter a catalog with values taken from another one.

interface form {
  getCatalog(
    catalogName: string | number,
    filters?: CatalogItemFilter[]
  ): Promise<CatalogItem[]>;
}

interface CatalogItem {
  item_id: number;
  columns: {
    [name: string]: string;
  };
}

interface CatalogItemFilter {
  columnName: string;
  value: string;
  useWildcard: boolean;
}

The getCatalog method takes the catalog name (a string) or ID (a number) as its first argument and returns a Promise with an array of catalog items. Each item is an object with the following fields:

  • item_id — the unique ID of the catalog item;
  • columns — an object whose keys are catalog column names and whose values are the column values.

Server-side filtering

Use the optional second parameter, filters, to get only the catalog items you need. Specify a column and the value to match. If you pass several conditions, an item must match all of them.

Each filter contains columnName — the column name, value — the value to look for (an empty string finds empty values), and useWildcard — whether to use pattern matching. With useWildcard: false, the value must match exactly; with true, * stands for any number of characters and ? for a single character.

Keep in mind that these are two separate steps: getCatalog returns the filtered catalog items, but it doesn't change the options available in the form field by itself. To limit those options, use setFilterAsync and pass it the list of values, as shown in the example below. For more on filtering catalog and form fields, see Filtering options.

For example, to get the cities of Texas:

const cities = await form.getCatalog('USA states and cities', [
  { columnName: 'State', value: 'Texas', useWildcard: false }
]);

If the catalog is large, filter it on the server like this instead of loading all of its items.

Example: filtering cities by state

Suppose a user selected a state in the State field and we only want cities from the selected state to be available in the City field.

In our example, the State field corresponds with the States catalog while the City field corresponds to the Cities catalog. There is also a States and cities catalog that lists cities by region.

To filter the list of cities by selected state, add the following script to the form:

form.onChange(["State"]).setFilterAsync("City", async state => {
  const [region] = state.changes;

  if (!region?.columns)
    return null;

  const regionCol = region.columns["State"];

  // Get only the cities of the selected state
  const catalogItems = await form.getCatalog("USA states and cities", [
    { columnName: "State", value: regionCol, useWildcard: false }
  ]);
  const filtered = catalogItems.map(item => item.columns["City"]);

  return { values: filtered }
});

The getCatalog method returns only the cities of the selected state, and setFilterAsync leaves only these values available in the City field. If there are no matches, the script returns { values: [] } — an empty list of allowed values. In this example, null is returned only when no state is selected.

Pay attention: you can filter catalogs not only by their name, but also by ID number. In this case, the code in the script will look like this:

const catalogPromise = form.getCatalog(123);

Was this article helpful?