Docs / Build Workflow

Filtro — select

Cuándo usar select

Usa select cuando el usuario tiene que elegir un valor de un set conocido: un status, una región, una marca, una categoría. El dropdown refleja o bien una lista de opciones estáticas declarada en YAML o una lista dinámica resuelta corriendo una query Malloy en page load.

Recurre a uno de los filtros de fecha en su lugar cuando el input es una fecha o un date range. Recurre a cross-filtering cuando se espera que el usuario drillee clickeando un chart en vez de elegir de un dropdown.

Campos requeridos

  • type: select

O options u options_query tiene que estar presente (y solo uno de los dos).

Campos opcionales

  • id — identifier interno; también el nombre de parámetro default cuando param no está seteado.
  • label — display label arriba del dropdown.
  • param — el nombre del parámetro Malloy al que bindear el valor seleccionado. Default a id.
  • default — valor seleccionado inicial. Tiene que matchear el id de una de las opciones.
  • options — array de objetos {id, label}. Usalo para una lista de opciones estática.
  • options_query — string en formato models/<file>.malloy::<view_name> (el mismo shape que una referencia query de una viz). Looky corre esta query en page load y convierte las filas en opciones.

Opciones estáticas

Declara la lista inline. Mejor para enumeraciones chicas y estables — statuses, toggles on/off, periodicidades.

filters:
  - type: select
    id: status
    label: Status
    param: status
    default: all
    options:
      - { id: all,        label: All }
      - { id: active,     label: Active }
      - { id: cancelled,  label: Cancelled }
      - { id: refunded,   label: Refunded }

Cada opción tiene que tener un id (el valor mandado a la query) y un label (el texto mostrado en el dropdown). El id es lo que tu model Malloy recibe — diseña el parámetro del model para aceptar el mismo shape.

Opciones dinámicas (options_query)

Usalo cuando la lista de opciones viene de datos — marcas, clientes, países, cualquier cosa que cambia con el tiempo. El options_query corre al cargar la página, así que mantenlo como una agregación liviana (un group_by sobre la dimension), o cachealo con un sidecar para que el dropdown abra al instante.

filters:
  - type: select
    id: brand
    label: Brand
    param: brand
    options_query: "models/ec_revenue.malloy::brand_options"
    default: all

La query brand_options tiene que devolver filas con columnas id y label (una columna opcional sort_order controla el ordenamiento). Un model de opciones completo:

##! experimental.parameters

# models/ec_brand_options.malloy — feeds the Brand dropdown.
source: ec_brand_options() is ecommerce.table('bigquery-public-data.thelook_ecommerce.products') extend {
  view: brand_options is {
    group_by:
      id is brand
      label is brand
    order_by: brand asc
  }
}

Para incluir un sentinel "all" en una lista dinámica (recomendado como default), construye la lista en un source de SQL crudo y une la fila sentinel con un union — la columna sort_order la fija arriba:

##! experimental.parameters

source: ec_brand_options() is ecommerce.sql("""
  SELECT 'all' AS id, 'All brands' AS label, 0 AS sort_order
  UNION ALL
  SELECT brand AS id, brand AS label, 1 AS sort_order
  FROM `bigquery-public-data.thelook_ecommerce.products`
  WHERE brand IS NOT NULL
  GROUP BY 1, 2
""") extend {
  view: brand_options is {
    select: id, label, sort_order
    order_by: sort_order asc, label asc
  }
}

Cada fila de la query se vuelve una opción. Looky normaliza cada fila a un {id, label}:

  • id — la columna id (los aliases legacy indicator_code / group_code también se reconocen).
  • label — la columna label (aliases indicator_label / group_label). Cae al id cuando está vacía.
  • sort key — si una fila tiene sort_order (aliases indicator_order / group_order), las opciones se ordenan numéricamente por ese campo; si no, se ordenan alfabéticamente por label.

Las filas a las que les faltan tanto un id como un label se dropean.

Valor default

Si default está seteado, es el valor del parámetro cuando carga la página. El botón de reset restaura este valor. Si no se setea default, el parámetro queda unset hasta que el usuario elija un valor, y la query subyacente tiene que aceptar la ausencia del parámetro (típicamente declarando su propio default).

Para listas de opciones dinámicas, declarar una opción sentinel "all" y usarla como default es un patrón común — tu model Malloy trata "all" como "sin filtro". Incluye el sentinel en la lista de opciones — agregalo al resultado de la query, o declaralo en options junto a options_query.

Cómo llega el valor a la query Malloy

El id de la opción elegida se manda como el parámetro con nombre — por default con el nombre del id del filtro, o param si lo seteas. El model Malloy declara un parámetro con el nombre matcheante (después de strippear el prefix p_ — mira Soporte de Malloy) y lo usa en la query. El match es exacto, incluyendo mayúsculas — cuando la data viene con case mixto, normaliza los dos lados en el model (lower(status) = lower(p_status)).

# in the Malloy model
##! experimental.parameters

source: ec_orders(
  p_status::string is "all"
) is ecommerce.table('bigquery-public-data.thelook_ecommerce.order_items') extend {
  view: detail is {
    where:
      p_status = "all" or status = p_status
    select:
      *
  }
}

Diferencias entre adapters

Los valores de select son típicamente strings o identifiers cortos; los tres adapters los bindean idéntico. El único edge case es cuando el parámetro del lado del model se declara como date o timestamp — ese patrón sigue las reglas de Diferencias entre adapters de source.

Ejemplos trabajados

Enumeración estática con un sentinel "all":

filters:
  - type: select
    id: status
    label: Status
    param: status
    default: all
    options:
      - { id: all,        label: All }
      - { id: active,     label: Active }
      - { id: cancelled,  label: Cancelled }

Dinámica desde una query, con binding de parámetro custom — el id del filtro es libre, y param nombra el nombre externo del parámetro del model (brand se bindea a p_brand en la signature del source):

filters:
  - type: select
    id: brand_filter
    label: Brand
    param: brand
    options_query: "models/ec_brand_options.malloy::brand_options"
    default: all

Múltiples selects en el mismo dashboard, cada uno filtrando una dimension distinta:

filters:
  - type: select
    id: country
    label: Country
    options_query: "models/ec_revenue.malloy::country_options"
    default: all
  - type: select
    id: channel
    label: Channel
    options:
      - { id: all,      label: All channels }
      - { id: organic,  label: Organic }
      - { id: paid,     label: Paid }
      - { id: direct,   label: Direct }
    default: all