Menu Docs
Página inicial do Docs
/ / /
Kotlin Coroutine
/ /

Construtores de projeções

Nesta página

  • Visão geral
  • Amostras de documentos e exemplos
  • Operações de Projeção
  • Inclusão
  • Exclusion
  • Combinando projeções
  • Exclusão de _id
  • Projetar uma correspondência de elemento da array
  • Projetar uma divisão da array
  • Projetar uma Pontuação de Texto

Neste guia, você pode aprender como especificar projeções utilizandoconstrutores do no driver MongoDB Kotlin .

O MongoDB oferece projeção de campo, especificando quais campos incluir e excluir ao gerar resultados de uma query. A projeção no MongoDB segue algumas regras básicas:

  • O campo _id está sempre incluído, a menos que esteja explicitamente excluído

  • A especificação de um campo para inclusão exclui implicitamente todos os outros campos exceto o campo _id

  • Especificar um campo para exclusão remove apenas esse campo em um resultado de consulta

Encontre mais informações sobre mecânica de projeção no guia Campos de projeto para retornar da query na documentação do MongoDB Server .

A classe Projections fornece métodos de fábrica estáticos para todos os operadores de projeção do MongoDB. Cada método retorna uma instância do tipo BSON que você pode passar para qualquer método que espera uma projeção.

Dica

Por questões de brevidade, você pode optar por importar os métodos das Projeções classe:

import com.mongodb.client.model.Projections.*

As seguintes seções apresentam exemplos que executam operações de query e projeção em uma collection de amostra denominada projection_builders. Cada seção usa uma variável chamada collection para fazer referência à instância MongoCollection da coleção projection_builders.

O acervo contém os seguintes documentos, representando as temperaturas médias mensais em Celsius para os anos de 2018 e 2019:

{
"year" : 2018,
"type" : "even number but not a leap year",
"temperatures" : [
{ "month" : "January", "avg" : 9.765 },
{ "month" : "February", "avg" : 9.675 },
{ "month" : "March", "avg" : 10.004 },
{ "month" : "April", "avg" : 9.983 },
{ "month" : "May", "avg" : 9.747 },
{ "month" : "June", "avg" : 9.65 },
{ "month" : "July", "avg" : 9.786 },
{ "month" : "August", "avg" : 9.617 },
{ "month" : "September", "avg" : 9.51 },
{ "month" : "October", "avg" : 10.042 },
{ "month" : "November", "avg" : 9.452 },
{ "month" : "December", "avg" : 9.86 }
]
},
{
"year" : 2019,
"type" : "odd number, can't be a leap year",
"temperatures" : [
{ "month" : "January", "avg" : 10.023 },
{ "month" : "February", "avg" : 9.808 },
{ "month" : "March", "avg" : 10.43 },
{ "month" : "April", "avg" : 10.175 },
{ "month" : "May", "avg" : 9.648 },
{ "month" : "June", "avg" : 9.686 },
{ "month" : "July", "avg" : 9.794 },
{ "month" : "August", "avg" : 9.741 },
{ "month" : "September", "avg" : 9.84 },
{ "month" : "October", "avg" : 10.15 },
{ "month" : "November", "avg" : 9.84 },
{ "month" : "December", "avg" : 10.366 }
]
}

A seguinte classe de dados é usada para representar o documento na collection:

data class YearlyTemperature(
@BsonId val id: ObjectId,
val year: Int,
val type: String,
val temperatures: List<MonthlyTemperature>
) {
data class MonthlyTemperature(
val month: String,
val avg: Double
)
}

As seções seguintes contêm informações sobre as operações de projeção disponíveis e como construí-las utilizando a classe Projections.

Utilize o método include() para especificar a inclusão de um ou mais campos.

O exemplo seguinte inclui o campo year e implicitamente o campo _id :

data class Results(@BsonId val id: ObjectId, val year: Int)
val filter = Filters.empty()
val projection = Projections.include(YearlyTemperature::year.name)
val resultsFlow = collection.find<Results>(filter).projection(projection)
resultsFlow.collect { println(it) }
Results(id=6467808db5003e6354a1ee22, year=2018)
Results(id=6467808db5003e6354a1ee23, year=2019)

O exemplo seguinte inclui os type e year o _id :

data class Results(@BsonId val id: ObjectId, val year: Int, val type: String)
val filter = Filters.empty()
val projection = Projections.include(YearlyTemperature::year.name, YearlyTemperature::type.name)
val resultsFlow = collection.find<Results>(filter).projection(projection)
resultsFlow.collect { println(it) }
Results(id=646780e3311323724f69a907, year=2018, type=even number but not a leap year)
Results(id=646780e3311323724f69a908, year=2019, type=odd number, can't be a leap year)

Utilize o método exclude() para especificar a exclusão de um ou mais campos.

O exemplo seguinte exclui o campo temperatures:

data class Results(@BsonId val id: ObjectId, val year: Int, val type: String)
val filter = Filters.empty()
val projection = Projections.exclude(YearlyTemperature::temperatures.name)
val resultsFlow = collection.find<Results>(filter).projection(projection)
resultsFlow.collect { println(it) }
Results(id=6462976102c85b29a7bfc9d5, year=2018, type=even number but not a leap year)
Results(id=6462976102c85b29a7bfc9d6, year=2019, type=odd number, can't be a leap year)

O exemplo seguinte exclui os campos temperatures e type:

data class Results(@BsonId val id: ObjectId, val year: Int)
val filter = Filters.empty()
val projection = Projections.exclude(YearlyTemperature::temperatures.name, YearlyTemperature::type.name)
val resultsFlow = collection.find<Results>(filter).projection(projection)
resultsFlow.collect { println(it) }
Results(id=64629783d7760d2365215147, year=2018)
Results(id=64629783d7760d2365215148, year=2019)

Utilize o método fields() para combinar múltiplas projeções.

O exemplo seguinte inclui os campos year e type e exclui o campo _id:

data class Results(val year: Int, val type: String)
val filter = Filters.empty()
val projection = Projections.fields(
Projections.include(YearlyTemperature::year.name, YearlyTemperature::type.name),
Projections.excludeId()
)
val resultsFlow = collection.find<Results>(filter).projection(projection)
resultsFlow.collect { println(it) }
Results(year=2018, type=even number but not a leap year)
Results(year=2019, type=odd number, can't be a leap year)

Utilize o método de conveniência excludeId() para especificar a exclusão do campo _id:

data class Results(val year: Int, val type: String, val temperatures: List<YearlyTemperature.MonthlyTemperature>)
val filter = Filters.empty()
val projection = Projections.excludeId()
val resultsFlow = collection.find<Results>(filter).projection(projection)
resultsFlow.collect { println(it) }
Results(year=2018, type=even number but not a leap year, temperatures=[MonthlyTemperature(month=January, avg=9.765), MonthlyTemperature(month=February, avg=9.675), MonthlyTemperature(month=March, avg=10.004), MonthlyTemperature(month=April, avg=9.983), MonthlyTemperature(month=May, avg=9.747), MonthlyTemperature(month=June, avg=9.65), MonthlyTemperature(month=July, avg=9.786), MonthlyTemperature(month=August, avg=9.617), MonthlyTemperature(month=September, avg=9.51), MonthlyTemperature(month=October, avg=10.042), MonthlyTemperature(month=November, avg=9.452), MonthlyTemperature(month=December, avg=9.86)])
Results(year=2019, type=odd number, can't be a leap year, temperatures=[MonthlyTemperature(month=January, avg=10.023), MonthlyTemperature(month=February, avg=9.808), MonthlyTemperature(month=March, avg=10.43), MonthlyTemperature(month=April, avg=10.175), MonthlyTemperature(month=May, avg=9.648), MonthlyTemperature(month=June, avg=9.686), MonthlyTemperature(month=July, avg=9.794), MonthlyTemperature(month=August, avg=9.741), MonthlyTemperature(month=September, avg=9.84), MonthlyTemperature(month=October, avg=10.15), MonthlyTemperature(month=November, avg=9.84), MonthlyTemperature(month=December, avg=10.366)])

Use a variante do método elemMatch(String, Bson) para especificar uma projeção de array que incluirá o primeiro elemento de uma array que corresponda a um filtro de queries fornecido. Essa filtragem ocorre depois que todos os documentos correspondentes ao filtro de queries (se fornecidos) são recuperados.

Observação

Somente o primeiro elemento que corresponde ao filtro de consulta especificado será incluído, independentemente de quantas correspondências possam haver.

O exemplo seguinte projeta o primeiro elemento da array temperatures onde o campo avg é maior que 10.1:

data class Results(
val year: Int,
val temperatures: List<YearlyTemperature.MonthlyTemperature>?
)
val filter = Filters.empty()
val projection = Projections.fields(
Projections.include(YearlyTemperature::year.name),
Projections.elemMatch(
YearlyTemperature::temperatures.name,
Filters.gt(YearlyTemperature.MonthlyTemperature::avg.name, 10.1)
)
)
val resultsFlow = collection.find<Results>(filter).projection(projection)
resultsFlow.collect { println(it) }
Results(year=2018, temperatures=null)
Results(year=2019, temperatures=[MonthlyTemperature(month=March, avg=10.43)])

Depois de especificar critérios de correspondência na parte de query da sua operação, use a variante do método elemMatch(String) para especificar uma projeção posicional para incluir o primeiro elemento de uma array. Somente documentos que correspondam ao filtro de queries serão recuperados.

Importante

Na versão 4.4 e anteriores do MongoDB, o campo de array especificado deve aparecer no filtro de query. Iniciando no MongoDB 4.4, você pode usar um projeto posicional em um campo de array que não aparece no filtro de query.

O exemplo abaixo projeta o primeiro elemento da array temperatures:

data class Results(
val year: Int,
val temperatures: List<YearlyTemperature.MonthlyTemperature>
)
val filter = Filters.gt(
"${YearlyTemperature::temperatures.name}.${YearlyTemperature.MonthlyTemperature::avg.name}",
10.1
)
val projection = Projections.fields(
Projections.include(YearlyTemperature::year.name),
Projections.elemMatch(YearlyTemperature::temperatures.name)
)
val resultsFlow = collection.find<Results>(filter).projection(projection)
resultsFlow.collect { println(it) }
Results(year=2019, temperatures=[MonthlyTemperature(month=March, avg=10.43)])

Use o método slice() para projetar uma fatia de uma matriz.

O exemplo abaixo projeta os primeiros 6 elementos da array temperatures :

data class Results(val temperatures: List<YearlyTemperature.MonthlyTemperature>)
val filter = Filters.empty()
// First half of the year
val projection = Projections.fields(
Projections.slice(YearlyTemperature::temperatures.name, 6),
Projections.excludeId()
)
val resultsFlow = collection.find<Results>(filter)
.projection(projection)
resultsFlow.collect { println(it) }
Results(temperatures=[MonthlyTemperature(month=January, avg=9.765), MonthlyTemperature(month=February, avg=9.675), MonthlyTemperature(month=March, avg=10.004), MonthlyTemperature(month=April, avg=9.983), MonthlyTemperature(month=May, avg=9.747), MonthlyTemperature(month=June, avg=9.65)])
Results(temperatures=[MonthlyTemperature(month=January, avg=10.023), MonthlyTemperature(month=February, avg=9.808), MonthlyTemperature(month=March, avg=10.43), MonthlyTemperature(month=April, avg=10.175), MonthlyTemperature(month=May, avg=9.648), MonthlyTemperature(month=June, avg=9.686)])

O exemplo a seguir pula os primeiros 6 elementos da array temperatures e projeta os próximos 6:

data class Results(val temperatures: List<YearlyTemperature.MonthlyTemperature>)
val filter = Filters.empty()
// Second half of the year
val projection = Projections.fields(
Projections.slice(YearlyTemperature::temperatures.name, 6, 6),
Projections.excludeId()
)
val resultsFlow = collection.find<Results>(filter)
.projection(projection)
resultsFlow.collect { println(it) }
Results(temperatures=[MonthlyTemperature(month=July, avg=9.786), MonthlyTemperature(month=August, avg=9.617), MonthlyTemperature(month=September, avg=9.51), MonthlyTemperature(month=October, avg=10.042), MonthlyTemperature(month=November, avg=9.452), MonthlyTemperature(month=December, avg=9.86)])
Results(temperatures=[MonthlyTemperature(month=July, avg=9.794), MonthlyTemperature(month=August, avg=9.741), MonthlyTemperature(month=September, avg=9.84), MonthlyTemperature(month=October, avg=10.15), MonthlyTemperature(month=November, avg=9.84), MonthlyTemperature(month=December, avg=10.366)])

Utilize o método metaTextScore() para especificar uma projeção da pontuação de uma query de texto.

O exemplo seguinte projeta a pontuação de texto como o valor do campo score:

data class Results(val year: Int, val score: Double)
val filter = Filters.text("even number")
val projection = Projections.fields(
Projections.include(YearlyTemperature::year.name),
Projections.metaTextScore("score")
)
val resultsFlow = collection.find<Results>(filter).projection(projection)
resultsFlow.collect { println(it) }
Results(year=2018, score=1.25)
Results(year=2019, score=0.625)

Voltar

Construtores de índices