Para agentes de IA: um índice de documentação está disponível em https://www.mongodb.com/pt-br/docs/llms.txt — as versões de markdown de todas as páginas estão disponíveis anexando .md a qualquer caminho de URL.
Menu Docs

Relacionamentos incorporados e referências manuais

Neste guia, você pode aprender a usar o MongoDB Entity Framework Core Provider para modelar relacionamentos entre documentos em seu banco de dados MongoDB. O EF Core Provider suporta os seguintes tipos de relacionamento:

  • Relacionamentos incorporados: subdocumentos incorporados diretamente em um documento pai. Essa é a abordagem recomendada para relacionamentos um-para-um e um-para-muitos no MongoDB.

  • Referências manuais: um documento que referencia outro documento armazenando seu ID em um campo, em vez de incorporar o documento como um subdocumento. Essa abordagem funciona bem para modelar relacionamentos muitos para muitos ou quando você precisa acessar os documentos de forma independente.

Dica

Crie seu esquema para padrões de query

Ao modelar dados para o MongoDB, primeiro determine as operações que seu aplicativo executa com mais frequência. Em seguida, escolha uma estrutura de documento que suporte essas operações com eficiência. O esquema mais eficiente no MongoDB pode não corresponder ao esquema que você usaria para um banco de dados relacional. Em vez disso, considere quais dados são recuperados juntos com frequência, quais valores mudam com frequência e quais relacionamentos de dados mudam ao longo do tempo.

Para saber mais sobre modelagem de dados e migração de um banco de dados relacional para o MongoDB Server, consulte o gráfico de mapeamento de SQL para MongoDB e a modelagem de dados no MongoDB na documentação do MongoDB Server.

Para incorporar um subdocumento em um documento pai, especifique o modelo para o documento incorporado como uma entidade de propriedade. Os relacionamentos incorporados são a maneira nativa do MongoDB de modelar relacionamentos e oferecem melhor desempenho para documentos que você acessa com frequência.

Use documento incorporado quando os dados relacionados forem geralmente visualizados no contexto de seu pai e quando os dados incorporados permanecerem razoavelmente limitados em tamanho. Isso inclui pequenos conjuntos de valores filho, como endereços, configurações ou uma lista limitada de itens recentes. Quando você incorpora documentos incorporados, o MongoDB Server pode melhorar o desempenho recuperando dados relacionados em uma única operação de banco de dados e atualizando dados relacionados atomicamente em um único documento.

Considere o embedding de dados nos seguintes casos:

  • Seu aplicativo geralmente lê dados pai e filho juntos. Buscar tudo em uma query é mais eficiente do que fazer chamadas separadas.

  • Os dados relacionados não crescem sem um limite superior claro. Os dados limitados não farão com que os documentos cresçam indefinidamente ou atinjam o limite de tamanho de documento de 16MB do MongoDB.

  • Os dados relacionados não mudam com frequência e independentemente do pai. Isso incorre em menos sobrecarga da reescrita do documento pai.

Observação

Hierarquias aninhadas

Quando você atualiza qualquer propriedade de uma entidade aninhada, o provedor EF Core reescreve todo o documento raiz. Para hierarquias de entidades com três ou mais níveis de aninhamento, esse custo de gravação se agrava, pois uma pequena alteração profunda na árvore aciona uma reescrita completa do documento pai. Se o seu modelo usar aninhamento profundo e seu aplicativo executar gravações frequentes, considere nivelar a hierarquia ou substituir entidades internas por referências manuais.

Para saber mais, consulte Dados incorporados na documentação do MongoDB Server.

Você pode designar uma entidade própria das seguintes maneiras:

  • [Propriedade] Atributo: aplicar o atributo de anotação de dados [Owned] à classe de modelo para o subdocumento. Essa abordagem é declarativa e concisa, mas também menos flexível, porque se aplica globalmente a todos os usos do tipo de propriedade.

  • API fluente: chame os métodos OwnsOne() ou OwnsMany() em sua configuração DbContext. Essa abordagem oferece mais controle e flexibilidade, permitindo que você configure o relacionamento de forma diferente para entidades específicas sem modificar a classe de modelo.

As seções a seguir fornecem exemplos dessas abordagens para modelagem de entidades únicas e múltiplas.

Para incorporar um único documento em um documento pai, chame o método OwnsOne() em sua configuração DbContext ou aplique o atributo [Owned] à classe incorporada.

O exemplo a seguir mostra uma entidade Customer que contém um documento Address incorporado. Selecione a aba [Owned] Attribute ou Fluent API para ver a sintaxe correspondente:

[Owned]
public class Address
{
public string Street { get; set; } = null!;
public string City { get; set; } = null!;
public string Country { get; set; } = null!;
}
public class Customer
{
public ObjectId Id { get; set; }
public string Name { get; set; } = null!;
public Address Address { get; set; } = null!;
}
public class CustomerDbContext : DbContext
{
public DbSet<Customer> Customers { get; set; } = null!;
public CustomerDbContext(DbContextOptions options) : base(options) { }
protected override void OnModelCreating(ModelBuilder modelBuilder)
{
base.OnModelCreating(modelBuilder);
modelBuilder.Entity<Customer>(c =>
{
c.OwnsOne(c => c.Address);
c.ToCollection("customers");
});
}
}

Ao salvar uma entidade Customer, o MongoDB armazena o Address como um documento incorporado no documento Customer. O JSON a seguir mostra como esse relacionamento aparece no MongoDB:

{
"_id": ObjectId("..."),
"Name": "John Doe",
"Address": {
"Street": "123 Main St",
"City": "New York",
"Country": "USA"
}
}

Para incorporar vários documentos em um documento pai, chame o método OwnsMany() ou aplique o atributo [Owned] à classe incorporada e defina uma propriedade de coleção.

O exemplo a seguir mostra uma entidade Customer que contém vários documentos Order incorporados. Selecione a aba [Owned] Attribute ou Fluent API para ver a sintaxe correspondente:

[Owned]
public class Order
{
public string Product { get; set; } = null!;
public int Quantity { get; set; }
}
public class CustomerWithOrders
{
public ObjectId Id { get; set; }
public string Name { get; set; } = null!;
public List<Order> Orders { get; set; } = new();
}
public class OrderDbContext : DbContext
{
public DbSet<CustomerWithOrders> Customers { get; set; } = null!;
public OrderDbContext(DbContextOptions options) : base(options) { }
protected override void OnModelCreating(ModelBuilder modelBuilder)
{
base.OnModelCreating(modelBuilder);
modelBuilder.Entity<CustomerWithOrders>(c =>
{
c.OwnsMany(c => c.Orders);
c.ToCollection("customers");
});
}
}

Ao salvar uma entidade CustomerWithOrders, o MongoDB armazena o Orders como um array de documentos incorporados, conforme mostrado no JSON a seguir:

{
"_id": ObjectId("..."),
"Name": "Jane Smith",
"Orders": [
{ "Product": "Laptop", "Quantity": 1 },
{ "Product": "Mouse", "Quantity": 2 }
]
}

Para modelar relacionamentos entre entidades que não estão incorporadas, você pode armazenar referências manualmente salvando o ID de um documento em um campo de outro documento. Essa abordagem exige que você gerencie o relacionamento no código do aplicativo.

Use referências quando você query regularmente os dados relacionados independentemente de seu pai, quando o conjunto filho pode crescer muito ou quando os dados relacionados mudam com frequência.

Considere usar referências nos seguintes casos:

  • Os dados relacionados crescem sem um limite superior claro. Arrays ilimitados podem causar problemas de desempenho e podem atingir o limite de tamanho de documento de 16MB do MongoDB.

  • Você precisa query a entidade relacionada por conta própria. Você pode query e indexar a coleção filho diretamente sem digitalizar documentos pai.

  • Os dados relacionados mudam com frequência e independentemente do pai. As atualizações frequentes de dados incorporados exigem a reescrita de todo o documento pai a cada vez, o que é ineficiente.

  • O aplicativo geralmente não lê dados pai e filho juntos. Ao usar referências, você evita buscar dados filho de que não precisa.

  • O relacionamento é muitos para muitos ou complexo.

  • A duplicação dos dados criaria muita sobrecarga de atualização.

Para **aprender** mais, consulte Dados de referência na documentação do MongoDB Server.

O exemplo a seguir mostra como armazenar uma referência a uma entidade relacionada:

public class Author
{
public ObjectId Id { get; set; }
public string Name { get; set; } = null!;
}
public class Book
{
public ObjectId Id { get; set; }
public string Title { get; set; } = null!;
// Store reference to Author by storing the Author's Id
public ObjectId AuthorId { get; set; }
}

Para recuperar a entidade relacionada, você deve query a coleção referenciada separadamente, conforme mostrado no exemplo a seguir:

// Query a book and its author
var book = db.Books.FirstOrDefault(b => b.Title == "My Book");
var author = db.Authors.FirstOrDefault(a => a.Id == book!.AuthorId);

Se um documento pai contiver um array grande, mas seu aplicativo geralmente usar apenas os itens mais recentes ou mais acessados, considere o padrão de subconjunto.

No padrão de subconjunto, você mantém os itens acessados com mais frequência no documento principal e move o restante para uma coleção separada. Essa abordagem pode reduzir o tamanho do documento e manter mais do seu conjunto de trabalho na RAM, o que pode melhorar o desempenho da query.

Esse padrão é útil quando você deseja os benefícios de desempenho do embedding, mas um histórico completo incorporado faria com que os documentos se tornassem muito grandes ou muito caros para carregar.

Para saber mais sobre as melhores práticas para projeto de esquema no MongoDB, consulte Melhores práticas para modelagem de dados no MongoDB e Projetando seu esquema na documentação do MongoDB Server.

Para aprender mais sobre modelagem de dados no MongoDB, consulte Modelagem de dados na documentação do MongoDB Server.

Para aprender mais sobre tipos de entidade de propriedade no Entity Framework Core, consulte Owned Entity Types na documentação do Microsoft Entity Framework Core.

Para saber mais sobre os métodos e tipos discutidos neste guia, consulte a seguinte documentação da API da Microsoft: