Modelos de objetos - .NET SDK
Nesta página
- Criar um modelo de objeto
- Esquema de objetos
- Anotações da propriedade
- Chave primária
- Indexes
- Índices de pesquisa de texto completo
- Valores de campo padrão
- Ignorar uma propriedade
- Renomear uma propriedade
- Renomear uma turma
- Setters personalizados
- Definir dados não estruturados
- Omitir classes do seu esquema de domínio
- Propriedades obrigatórias e opcionais
- Ignorando nulidade
Criar um modelo de objeto
As classes Realm são classes C# regulares que definem o esquema Realm.
Importante
Herança
Todos os objetos do Realm herdam a partir da interface IRealmObject, IEmbeddedObject ou IAsymmetricObject e devem ser declarados partial
classes.
Em versões do .NET SDK anteriores a 10.18.0, objetos derivam das classes de base RealmObject, EmbeddedObject ou AsymmetricObject . Essa abordagem para a definição do modelo Realm ainda é suportada, mas não inclui novos recursos, como as anotações de nulidade. Em uma futura versão do SDK, as classes básicas se tornarão obsoletas. Você deve usar as interfaces para quaisquer novas classes que escrever e deve considerar a migração das suas classes existentes.
Observação
Os nomes das classes têm um limite máximo de 57 caracteres UTF-8.
Esquema de objetos
Um esquema de objeto é um objeto de configuração que define as propriedades e relacionamentos de um objeto de Realm. Os aplicativos cliente de realm definem esquemas de objeto com a implementação de classe nativa em sua respectiva linguagem usando o Esquema de Objeto.
Os esquemas de objeto especificam restrições nas propriedades do objeto, como o tipo de dados de cada propriedade e se uma propriedade é necessária ou não. Os esquemas também podem definir relações entre tipos de objeto em um realm.
Cada aplicação tem um Esquema App Services composto por uma lista de esquemas de objetos para cada tipo de objeto que os realms desse aplicativo podem conter. O Realm garante que todos os objetos em um realm estejam em conformidade com o esquema do seu tipo de objeto e valida os objetos sempre que eles são criados, modificados ou excluídos.
Anotações da propriedade
As propriedades do esquema são propriedades C# padrão em um RealmObject
. Há várias anotações de propriedade que você pode usar para definir com mais precisão como um Realm lida com uma propriedade específica.
Chave primária
Uma chave primária é uma propriedade que identifica exclusivamente um objeto. Você pode criar uma chave primária com qualquer um dos seguintes tipos (ou suas contrapartes anuláveis):
ObjectId
UUID
string
char
byte
short
int
long
Você pode definir uma chave primária em uma propriedade única para um tipo de objeto como parte do esquema de objetos. O Realm indexa automaticamente as propriedades de chave primária, o que lhe permite ler e modificar objetos com eficiência com base em sua chave primária.
Se um tipo de objeto tiver uma chave primária, todos os objetos desse tipo deverão incluir a propriedade da chave primária com um valor exclusivo entre objetos do mesmo tipo em um domínio.
Observação
Depois de atribuir uma propriedade como chave primária, não é possível alterá-la.
O exemplo a seguir demonstra como designar uma chave primária em um esquema de objeto:
public partial class Dog : IRealmObject { [ ] public string Name { get; set; } public int Age { get; set; } public Person? Owner { get; set; } }
Indexes
Índices melhoram significativamente os tempos de query em um Realm. Sem índices, o Realm verifica todos os documentos de uma coleção para selecionar os documentos que correspondem à query fornecida. No entanto, se um índice aplicável existir para uma query, o Realm usará o índice para limitar o número de documentos que ele deve inspecionar.
Você pode indexar propriedades com os seguintes tipos:
bool
byte
short
int
long
DateTimeOffset
char
string
ObjectId
UUID
Observação
A adição de um índice acelera as queries ao custo de tempos de gravação um pouco mais lentos e sobrecarga adicional de armazenamento e memória. Os índices requerem espaço em seu arquivo de reino, portanto, adicionar um índice a uma propriedade aumenta o espaço em disco consumido pelo arquivo de reino. Toda entrada do índice tem um mínimo de 12 bytes.
Para indexar uma propriedade, use o atributo Indexado . Com o atributo Indexed
, você pode especificar o tipo de índice na propriedade usando o enum IndexType . No exemplo seguinte, temos um índice padrão ("Geral") na propriedade Name
:
public partial class Person : IRealmObject { [ ] public string Name { get; set; } [ ] public string Biography { get; set; } }
Observação
Quando cria um índice, está a criá-lo no domínio local e não numa colecção Atlas. Se você precisar executar query de uma coleção do Atlas diretamente e desejar melhorar o desempenho, consulte Criar, Visualizar, Soltar e Ocultar Índices.
Índices de pesquisa de texto completo
Além dos índices padrão, o Realm também suporta índices de Pesquisa de Texto Completo (FTS) em propriedades do string
. Embora você possa executar uma query de um campo de string com ou sem um índice padrão, um índice FTS permite pesquisar várias palavras e frases e excluir outras.
Para obter mais informações sobre a consulta de índices de texto completo, consulte Full Text Search (LINQ) e Full Text Search (RQL).
Para indexar uma propriedade FTS, use o atributo Indexado com o enum IndexType.FullText . No exemplo seguinte, temos um índice FullText
na propriedade Biography
:
public partial class Person : IRealmObject { [ ] public string Name { get; set; } [ ] public string Biography { get; set; } }
Valores de campo padrão
Você pode utilizar as feições de idioma embutidas para atribuir um valor padrão para uma propriedade. Em C#, você pode atribuir um valor padrão em primitivos na declaração de propriedade. Você não pode definir um valor padrão em uma coleção, exceto para defini-lo para null!
. Mesmo que você defina uma coleção como null!
, as collections são sempre inicializadas no primeiro acesso, portanto, nunca serão nulas.
public partial class Person : IRealmObject { public string Name { get; set; } = "foo"; public IList<PhoneNumber> PhoneNumbers { get; } = null!; }
Observação
Valores padrão e anulabilidade
Embora os valores padrão garantam que um objeto recém-criado não possa conter um valor de null
(a menos que você especifique um valor padrão de null
), eles não afetam a nulidade de uma propriedade. Para tornar uma propriedade não nula, consulte Propriedades obrigatórias.
Ignorar uma propriedade
Se não quiser salvar uma propriedade em seu modelo em um domínio, você poderá ignorar esta propriedade. Uma propriedade é ignorada por padrão se não for autoimplementada ou não tiver um setter.
Ignore uma propriedade de um modelo de objeto Realm com o atributo Ignorado :
// Rather than store an Image in Realm, // store the path to the Image... public string ThumbnailPath { get; set; } // ...and the Image itself can be // in-memory when the app is running: [ ]public Image? Thumbnail { get; set; }
Renomear uma propriedade
Por padrão, o Realm utiliza o nome definido na classe do modelo para representar propriedades internamente. Em alguns casos, talvez você queira alterar esse comportamento:
Para facilitar o trabalho em todas as plataformas, uma vez que as convenções de nomenclatura são diferentes.
Para alterar um nome de propriedade no .NET sem forçar uma migração.
Escolher um nome interno diferente do nome usado nas classes de modelo tem as seguintes implicações:
As migrações devem usar o nome interno ao criar classes e propriedades.
Erros de esquema relatados usarão o nome interno.
Use o atributo [MapTo] para renomear uma propriedade:
public partial class Person : IRealmObject { [ ] public string Name { get; set; } }
Renomear uma turma
Por padrão, o Realm utiliza o nome definido na classe de modelo para representar classes internamente. Em alguns casos, você pode querer alterar esse comportamento:
Para oferecer suporte a várias classes de modelo com o mesmo nome simples em diferentes namespaces.
Para facilitar o trabalho em todas as plataformas, uma vez que as convenções de nomenclatura são diferentes.
Para usar um nome de classe maior que o limite de 57 caracteres imposto pelo Realm.
Para alterar o nome de classe no .NET sem forçar uma migração.
Use o atributo [MapTo] para renomear uma classe:
[ ]public partial class Person : IRealmObject { public string Name { get; set; } }
Setters personalizados
O Realm não armazenará uma propriedade com uma preparação personalizada. Para usar uma preparação personalizada, armazene o valor da propriedade em uma propriedade privada e, em seguida, mapeie esse valor para uma propriedade pública com a preparação personalizada. O Realm irá armazenar a propriedade privada, enquanto modifica o seu valor através da propriedade pública. No código a seguir, a propriedade privada email
é armazenada no realm, mas a propriedade pública Email
, que fornece validação não é persistida:
// This property will be stored in the Realm private string email { get; set; } // Custom validation of the email property. // This property is *not* stored in Realm. public string Email { get { return email; } set { if (!value.Contains("@")) throw new Exception("Invalid email address"); email = value; } }
Definir dados não estruturados
Novidades na versão 12.2.0.
A partir da versão 12.2.0 do SDK, você pode armazenar collections de dados mistos dentro de uma propriedade RealmValue
. Você pode usar esse recurso para modelar estruturas de dados complexas, como documentos JSON ou MongoDB , sem precisar definir um modelo de dados rigoroso.
Dados não estruturados são dados que não estão em conformidade com facilmente um esquema esperado, tornando difícil ou impraticável modelar classes de dados individuais. Por exemplo, seu aplicativo pode ter dados altamente variáveis ou dados dinâmicos cuja estrutura é desconhecida no tempo de execução.
O armazenamento de coleções em uma propriedade mista oferece flexibilidade sem sacrificar a funcionalidade, incluindo sincronização de desempenho ao usar o Device Sync. E você pode trabalhar com eles da mesma forma que faria com uma collection não mista:
Você pode aninhar collections mistas em até 100 níveis.
Você pode consultar e React a alterações em coleções mistas.
Você pode localizar e atualizar elementos individuais de coleção mista.
No entanto, armazenar dados em coleções mistas é menos eficiente do que usar um esquema estruturado ou serializar blobs JSON em uma única propriedade de string.
Para modelar dados não estruturados em seu aplicativo, defina as propriedades apropriadas em seu esquema como tipos de RealmValue . Você pode então definir essas propriedades RealmValue
como uma lista ou um dicionário de RealmValue
elementos. Observe que RealmValue
não pode representar um conjunto ou um objeto incorporado.
Dica
Use um mapa de tipos de dados mistos quando o tipo for desconhecido, mas cada valor terá um identificador exclusivo.
Use uma lista de tipos de dados mistos quando o tipo for desconhecido, mas a ordem dos objetos for significativa.
Omitir classes do seu esquema de domínio
Por padrão, o Realm Schema do seu aplicativo inclui todas as classes que implementam IRealmObject
ou IEmbeddedObject
. Se você quiser incluir apenas um subconjunto dessas classes no Realm Schema, poderá atualizar a configuração para incluir as classes específicas desejadas:
// Declare your schema partial class LoneClass : IRealmObject { public string Name { get; set; } } class AnotherClass { private void SetUpMyRealmConfig() { // Define your config with a single class var config = new RealmConfiguration("RealmWithOneClass.realm"); config.Schema = new[] { typeof(LoneClass) }; // Or, specify multiple classes to use in the Realm config.Schema = new[] { typeof(Dog), typeof(Cat) }; } }
Propriedades obrigatórias e opcionais
No C#, os tipos de valor, como int
e bool
, são implicitamente não anuláveis. No entanto, eles podem tornar-se opcionais usando a?
notação de pontode interrogação ( ).
A partir do C# 8.0, foram introduzidos tipos de referência anuláveis. Se o seu projeto estiver utilizando C# 8.0 ou posterior, você também poderá declarar tipos de referência, como string
e byte[]
, como anuláveis com ?
.
Observação
Começando com o .NET 6.0, o contexto anulável é habilitado por padrão para novos projetos. Para projetos mais antigos, você pode habilitá-lo manualmente. Para mais informações, consulte https://learn.microsoft.com/en-us/dotnet/csharp/language-reference/builtin-types/nullable-reference-types#setting-the-nullable-context.
O Realm .NET SDK oferece suporte total ao contexto com reconhecimento de nulidade e usa a nulidade para determinar se uma propriedade é obrigatória ou opcional. O SDK tem as seguintes regras:
O Realm pressupõe que as propriedades de valor e de tipo de referência sejam necessárias se você não as designar como anuláveis. Se você as designar como anuláveis usando
?
, o Realm as considerará opcionais.Você deve declarar propriedades que são tipos de objeto de Realm como anuláveis.
Você não pode declarar collections (lista, conjuntos, backlinks e dicionários) como anuláveis, mas seus parâmetros podem ser anuláveis de acordo com as seguintes regras:
Para todos os tipos de collections, se os parâmetros forem primitivos (tipos de valor ou referência), eles podem ser obrigatórios ou anuláveis.
Para listas, conjuntos e backlinks, se os parâmetros forem objetos de Realm, eles não podem ser anuláveis.
Para dicionários com um tipo de valor de objeto de Realm, você deve declarar o parâmetro de tipo de valor como anulável.
O seguinte trecho de código demonstra estas regras:
public partial class Person : IRealmObject { /* Reference Types */ public string NonNullableName { get; set; } public string? NullableName { get; set; } public byte[] NonNullableArray { get; set; } public byte[]? NullableArray { get; set; } /* Value Types */ public int NonNullableInt { get; set; } public int? NullableInt { get; set; } /* Realm Objects */ public Dog? NullableDog { get; set; } // public Dog NonNullableDog { get; set; } // Compile-time error /* Collections of Primitives */ public IList<int> IntListWithNonNullableValues { get; } public IList<int?> IntListWithNullableValues { get; } // public IList<int>? NullableListOfInts { get; } // Compile-time error /* Collections of Realm Objects */ public IList<Dog> ListOfNonNullableObjects { get; } // public IList<Dog>? NullableListOfObjects { get; } // Compile-time error // public IList<Dog?> ListOfNullableObjects { get; } // Compile-time error public ISet<Dog> SetOfNonNullableObjects { get; } // public ISet<Dog>? NullableSetOfObjects { get; } // Compile-time error // public ISet<Dog?> SetOfNullableObjects { get; } // Compile-time error public IDictionary<string, Dog?> DictionaryOfNullableObjects { get; } // public IDictionary<string, Dog> DictionaryOfNonNullableObjects { get; } // Compile-time error // public IDictionary<string, Dog>? NullableDictionaryOfObjects { get; } // Compile-time error [ ] public IQueryable<Dog> MyDogs { get; } // [Backlink(nameof(Dog.People))] // public IQueryable<Dog?> MyDogs { get; } // Compile-time error }
Observação
Se estiver usando a definição de tipo de esquema mais antiga (suas classes derivam da classe base RealmObject
) ou se não tiver a capacidade de anulação ativada, será necessário usar o atributo [Required] para qualquer string
e byte[]
necessários propriedade.
Ignorando nulidade
Você pode preferir ter mais flexibilidade na definição da nulidade das propriedades em seus objetos de Realm. Você pode fazer isso definindo realm.ignore_objects_nullability = true
em um arquivo de configuração global.
Se você habilitar realm.ignore_objects_nullability
, as anotações de nulidade serão ignoradas nas propriedades do objeto Realm, incluindo coleções de Objetos de Realm.