Seleccionar

Descripción

Genera documentos nuevos, ya sea haciendo referencia a un subconjunto de campos existentes o asignando un campo al resultado de una expresión determinada.

Sintaxis

Node.js

const names = await db.pipeline()
  .collection("/cities")
  .select(stringConcat(field("name"), ", ", field("location.country")).as("name"), "population")
  .execute();

Ejemplos de clientes

Web

const result = await execute(db.pipeline()
  .collection("books")
  .select(field("soldBooks").multiply(field("price")).round().as("partialRevenue"))
  .aggregate(field("partialRevenue").sum().as("totalRevenue"))
  );
Swift
let result = try await db.pipeline()
  .collection("books")
  .select([Field("soldBooks").multiply(Field("price")).round().as("partialRevenue")])
  .aggregate([Field("partialRevenue").sum().as("totalRevenue")])
  .execute()

Kotlin

val result = db.pipeline()
    .collection("books")
    .select(Expression.multiply(field("soldBooks"), field("price")).round().alias("partialRevenue"))
    .aggregate(AggregateFunction.sum("partialRevenue").alias("totalRevenue"))
    .execute()

Java

Task<Pipeline.Snapshot> result = db.pipeline()
    .collection("books")
    .select(Expression.multiply(field("soldBooks"), field("price")).round().alias("partialRevenue"))
    .aggregate(AggregateFunction.sum("partialRevenue").alias("totalRevenue"))
    .execute();
Python
from google.cloud.firestore_v1.pipeline_expressions import Field

result = (
    client.pipeline()
    .collection("books")
    .select(
        Field.of("soldBooks")
        .multiply(Field.of("price"))
        .round()
        .as_("partialRevenue")
    )
    .aggregate(Field.of("partialRevenue").sum().as_("totalRevenue"))
    .execute()
)
Java
Pipeline.Snapshot result =
    firestore
        .pipeline()
        .collection("books")
        .select(round(multiply(field("soldBooks"), field("price"))).as("partialRevenue"))
        .aggregate(sum("partialRevenue").as("totalRevenue"))
        .execute()
        .get();

Comportamiento

Posición de una etapa de selección

No hay restricciones sobre cuándo se puede usar una etapa de selección, pero los campos que no se incluyan en una etapa de selección no estarán disponibles para las etapas posteriores de una canalización.

Por ejemplo, para seleccionar solo los campos name y location de todas las ciudades de Canadá del siguiente conjunto de datos:

Node.js

await db.collection('cities').doc('SF').set({name: 'San Francisco', population: 800000, location: {country: 'USA', state: 'California'}});
await db.collection('cities').doc('TO').set({name: 'Toronto', population: 3000000, location: {country: 'Canada', province: 'Ontario'}});

Se puede usar la siguiente canalización:

Node.js

const names = await db.pipeline()
  .collection("/cities")
  .where(equal(field("location.country"), "Canada"))
  .select(stringConcat(field("name"), ", ", field("location.country")).as("name"), "population")
  .execute();

Esto produce los siguientes documentos:

{name: 'Toronto, Canada', population: 3000000},

Sin embargo, si la etapa select se coloca antes de la etapa where, como se muestra a continuación:

Node.js

const names = await db.pipeline()
  .collection("/cities")
  .select(stringConcat(field("name"), ",", field("location.country")).as("name"), "population")
  .where(equal(field("location.country"), "Canada"))
  .execute();

No se producirá ningún documento, ya que location.country se quitó del documento antes de la ejecución de la etapa where.

Selecciona campos anidados

La etapa de selección se puede usar para seleccionar campos anidados de mapas y arrays.

Por ejemplo, para seleccionar el campo country anidado y la primera entrada del array landmarks de los siguientes documentos:

Node.js

await db.collection('cities').doc('SF').set({name: 'San Francisco', population: 800000, location: {country: 'USA', state: 'California'}, landmarks: ['Golden Gate Bridge', 'Alcatraz']});
await db.collection('cities').doc('TO').set({name: 'Toronto', population:  3000000, province: 'ON', location: {country: 'Canada', province: 'Ontario'}, landmarks: ['CN Tower', 'Casa Loma']});
await db.collection('cities').doc('AT').set({name: 'Atlantis', population: null});

Se puede usar la siguiente canalización:

Node.js

const locations = await db.pipeline()
  .collection("/cities")
  .select(field("name").as("city"), field("location.country").as("country"), field("landmarks").arrayGet(0).as("topLandmark"))
  .execute();

Esto produce los siguientes documentos:

{city: 'San Francisco', country: 'USA', topLandmark: 'Golden Gate Bridge'},
{city: 'Toronto', country: 'Canada', topLandmark: 'CN Tower'},
{city: 'Atlantis'}

Si no existe un valor de mapa o de array anidado, no se incluye en el documento resultante. El acceso a arrays y mapas en la etapa de selección se comporta de manera idéntica a las funciones array_get y map_get, respectivamente.