import type { JSONSupport } from "../core/JSONSupport.js";

export interface ElementExpressionInfoProperties extends Partial<Pick<ElementExpressionInfo, "expression" | "title">> {}

/**
 * Defines an [Arcade](https://developers.arcgis.com/javascript/latest/arcade/) expression used to create an [ExpressionContent](https://developers.arcgis.com/javascript/latest/references/core/popup/content/ExpressionContent/)
 * element in a [PopupTemplate](https://developers.arcgis.com/javascript/latest/references/core/PopupTemplate/). The expression must evaluate to a [dictionary](https://developers.arcgis.com/arcade/guide/types/#dictionary), representing a
 * [TextContent](https://developers.arcgis.com/javascript/latest/references/core/popup/content/TextContent/),
 * [FieldsContent](https://developers.arcgis.com/javascript/latest/references/core/popup/content/FieldsContent/), or
 * [MediaContent](https://developers.arcgis.com/javascript/latest/references/core/popup/content/MediaContent/) popup element as
 * defined in the [Popup Element web map specification](https://developers.arcgis.com/web-map-specification/objects/popupElement/).
 *
 * This expression may access data values from the feature, its layer, or other layers
 * in the map or datastore with the `$feature`, `$layer`, `$map`, and `$datastore` profile variables.
 * See the [Popup Element Arcade Profile](https://developers.arcgis.com/javascript/latest/arcade/#popup-element) specification
 * for more information and examples of valid return dictionaries.
 *
 * @since 4.22
 * @see [PopupTemplate](https://developers.arcgis.com/javascript/latest/references/core/PopupTemplate/)
 * @see [Popup Element Web Map Specification](https://developers.arcgis.com/web-map-specification/objects/popupElement/)
 * @see [Popup Element Profile](https://developers.arcgis.com/javascript/latest/arcade/#popup-element)
 * @see [Arcade Profiles: Popup Element Specification](https://developers.arcgis.com/arcade/profiles/popup-element/)
 * @see [Sample - Create popup charts from Arcade expressions](https://developers.arcgis.com/javascript/latest/sample-code/popuptemplate-arcade-expression-content)
 * @see [Sample - Popup charts for point clusters](https://developers.arcgis.com/javascript/latest/sample-code/featurereduction-cluster-popup-chart)
 * @example
 * // Creates an ordered list in a cluster's popup
 * // listing the type of fuel used to generate power in the cluster
 * // ordered by the total number of power plants for each fuel type.
 * layer.featureReduction = {
 *   type: "cluster",
 *   popupTemplate: {
 *     title: "Power plant summary",
 *     content: [{
 *       type: "expression",
 *       expressionInfo: {
 *         expression: `
 *           // Specify which fields are required by the expression
 *           Expects($aggregatedFeatures, "fuel1", "capacity_mw")
 *
 *           // Query stats for each fuel type
 *           var statsFS = GroupBy($aggregatedFeatures,
 *             [
 *               { name: 'Type', expression: 'fuel1'},
 *             ],
 *             [  // statistics to return for each unique category
 *               { name: 'capacity_total', expression: 'capacity_mw', statistic: 'SUM' },
 *               { name: 'capacity_max', expression: 'capacity_mw', statistic: 'MAX' },
 *               { name: 'num_features', expression: '1', statistic: 'COUNT' }
 *             ]
 *           );
 *           // create an list in descending order based
 *           // on the number of plants for each fuel type.
 *           var ordered = OrderBy(statsFs, 'num_features DESC');
 *
 *           var list = "<ol>";
 *
 *           for (var group in ordered){
 *             list += \`<li>\${group.Type} (\${Text(group.num_features, "#,###")})</li>\`
 *           }
 *           list += "</ol>";
 *
 *           // The return dictionary must return a text, fields, or media
 *           // popup element as defined in the web map specification
 *           return {
 *             type: "text",
 *             text: list
 *           }
 *         `,
 *         title: "List of fuel types"
 *       }
 *     }]
 *   }
 * };
 */
export default class ElementExpressionInfo extends JSONSupport {
  constructor(properties?: ElementExpressionInfoProperties);
  /**
   * The [Arcade](https://developers.arcgis.com/javascript/latest/arcade/) expression evaluating to
   * a dictionary. The dictionary must represent either a
   * [TextContent](https://developers.arcgis.com/javascript/latest/references/core/popup/content/TextContent/),
   * [FieldsContent](https://developers.arcgis.com/javascript/latest/references/core/popup/content/FieldsContent/), or a
   * [MediaContent](https://developers.arcgis.com/javascript/latest/references/core/popup/content/MediaContent/) popup content element as
   * defined in the [Popup Element web map specification](https://developers.arcgis.com/web-map-specification/objects/popupElement/).
   *
   * This expression may access data values from the feature, its layer, or other layers
   * in the map or datastore with the `$feature`, `$layer`, `$map`, and `$datastore` profile variables.
   * See the [Popup Element Arcade Profile](https://developers.arcgis.com/javascript/latest/arcade/#popup-element) specification
   * for more information and examples of valid return dictionaries.
   *
   * @see [Popup Element web map specification](https://developers.arcgis.com/web-map-specification/objects/popupElement/)
   * @see [Popup Element Profile](https://developers.arcgis.com/javascript/latest/arcade/#popup-element)
   * @see [Arcade Profiles: Popup Element Specification](https://developers.arcgis.com/arcade/profiles/popup-element/)
   * @see [Sample - Create popup charts from Arcade expressions](https://developers.arcgis.com/javascript/latest/sample-code/popuptemplate-arcade-expression-content)
   * @see [Sample - Popup charts for point clusters](https://developers.arcgis.com/javascript/latest/sample-code/featurereduction-cluster-popup-chart)
   * @example
   * // Creates an column chart where each category/value
   * // is an aggregate of two or more fields
   * layer.popupTemplate = {
   *   title: "Educational Attainment",
   *   content: [{
   *     type: "expression",
   *     expressionInfo: {
   *       expression: `
   *         // Create a dictionary of attributes representing the values
   *         // to display in the table
   *         var attributes = {
   *           "No School": $feature.no_school + $feature.some_primary,
   *           "Primary": $feature.primary_complete + $feature.some_secondary,
   *           "Secondary": $feature.secondary_complete + $feature.some_highSchool,
   *           "High School": $feature.highSchool_diploma + $feature.highSchool_ged + $feature.some_college,
   *           "College/University": $feature.associates + $feature.bachelors + $feature.masters + $feature.doctorate + $feature.professional;
   *         };
   *
   *         var fieldInfos = [];
   *
   *         // Create an array representing the attribute names (or keys)
   *         // to include in the chart
   *         for (var k in attributes){
   *           Push(fieldInfos, {
   *             fieldName: k
   *           });
   *         }
   *
   *         // Returns a dictionary providing the information
   *         // required by the popup to render a table of key value pairs
   *         return {
   *           type: "media",
   *           attributes: attributes,
   *           // The list of attribute names (keys) to include in the table
   *           fieldInfos: fieldInfos
   *         };
   *       `,
   *       title: "Educational Attainment"
   *     }
   *   }]
   * };
   */
  accessor expression: string;
  /** The return type of the expression. Content element expressions always return dictionaries. */
  get returnType(): "dictionary";
  /** The title used to describe the popup element returned by the expression. */
  accessor title: string | null | undefined;
  /**
   * Creates a deep clone of the ElementExpressionInfo instance.
   *
   * @returns A deep clone of the ElementExpressionInfo instance.
   */
  clone(): ElementExpressionInfo;
}