Skip to content

Commit

Permalink
Support hierarchical partition keys in Cosmos provider (#33536)
Browse files Browse the repository at this point in the history
* Support hierarchical partition keys in Cosmos provider

Fixes #28186
Fixes #28265
Fixes #33535

Also:
- Allow non-string partition key values
- Warn if no partition key has been defined
- Use a value converter if needed for values passed to WithPartitionKey (This is probably a bug, but should be docced as a breaking change anyway.)

Updated based on review feedback

* Added test for type that cannot be a partition key
  • Loading branch information
ajcvickers authored May 2, 2024
1 parent 21d64d3 commit a970d4f
Show file tree
Hide file tree
Showing 154 changed files with 16,060 additions and 10,345 deletions.
23 changes: 22 additions & 1 deletion src/EFCore.Cosmos/Diagnostics/CosmosEventId.cs
Original file line number Diff line number Diff line change
Expand Up @@ -34,7 +34,11 @@ private enum Id
ExecutedReadItem,
ExecutedCreateItem,
ExecutedReplaceItem,
ExecutedDeleteItem
ExecutedDeleteItem,

// Model validation events
NoPartitionKeyDefined = CoreEventId.ProviderBaseId + 600,

}

private static readonly string DatabasePrefix = DbLoggerCategory.Database.Name + ".";
Expand Down Expand Up @@ -149,4 +153,21 @@ public static readonly EventId ExecutedReplaceItem
/// </remarks>
public static readonly EventId ExecutedDeleteItem
= new((int)Id.ExecutedDeleteItem, CommandPrefix + Id.ExecutedDeleteItem);

private static EventId MakeValidationId(Id id)
=> new((int)id, DbLoggerCategory.Model.Validation.Name + "." + id);

/// <summary>
/// No partition key has been configured for an entity type. It is highly recommended that an appropriate partition key be defined.
/// See https://aka.ms/efdocs-cosmos-partition-keys for more information.
/// </summary>
/// <remarks>
/// <para>
/// This event is in the <see cref="DbLoggerCategory.Model.Validation" /> category.
/// </para>
/// <para>
/// This event uses the <see cref="EntityTypeEventData" /> payload when used with a <see cref="DiagnosticSource" />.
/// </para>
/// </remarks>
public static readonly EventId NoPartitionKeyDefined = MakeValidationId(Id.NoPartitionKeyDefined);
}
Original file line number Diff line number Diff line change
Expand Up @@ -21,7 +21,7 @@ public class CosmosItemCommandExecutedEventData : EventData
/// <param name="activityId">The activity ID.</param>
/// <param name="resourceId">The ID of the resource being read.</param>
/// <param name="containerId">The ID of the Cosmos container being queried.</param>
/// <param name="partitionKey">The key of the Cosmos partition that the query is using.</param>
/// <param name="partitionKeyValue">The key of the Cosmos partition that the query is using.</param>
/// <param name="logSensitiveData">Indicates whether the application allows logging of sensitive data.</param>
public CosmosItemCommandExecutedEventData(
EventDefinitionBase eventDefinition,
Expand All @@ -31,7 +31,7 @@ public CosmosItemCommandExecutedEventData(
string activityId,
string containerId,
string resourceId,
string? partitionKey,
PartitionKey partitionKeyValue,
bool logSensitiveData)
: base(eventDefinition, messageGenerator)
{
Expand All @@ -40,7 +40,7 @@ public CosmosItemCommandExecutedEventData(
ActivityId = activityId;
ContainerId = containerId;
ResourceId = resourceId;
PartitionKey = partitionKey;
PartitionKeyValue = partitionKeyValue;
LogSensitiveData = logSensitiveData;
}

Expand Down Expand Up @@ -72,7 +72,7 @@ public CosmosItemCommandExecutedEventData(
/// <summary>
/// The key of the Cosmos partition that the query is using.
/// </summary>
public virtual string? PartitionKey { get; }
public virtual PartitionKey PartitionKeyValue { get; }

/// <summary>
/// Indicates whether the application allows logging of sensitive data.
Expand Down
8 changes: 4 additions & 4 deletions src/EFCore.Cosmos/Diagnostics/CosmosQueryEventData.cs
Original file line number Diff line number Diff line change
Expand Up @@ -17,22 +17,22 @@ public class CosmosQueryEventData : EventData
/// <param name="eventDefinition">The event definition.</param>
/// <param name="messageGenerator">A delegate that generates a log message for this event.</param>
/// <param name="containerId">The ID of the Cosmos container being queried.</param>
/// <param name="partitionKey">The key of the Cosmos partition that the query is using.</param>
/// <param name="partitionKeyValue">The key value of the Cosmos partition that the query is using.</param>
/// <param name="parameters">Name/values for each parameter in the Cosmos Query.</param>
/// <param name="querySql">The SQL representing the query.</param>
/// <param name="logSensitiveData">Indicates whether the application allows logging of sensitive data.</param>
public CosmosQueryEventData(
EventDefinitionBase eventDefinition,
Func<EventDefinitionBase, EventData, string> messageGenerator,
string containerId,
string? partitionKey,
PartitionKey partitionKeyValue,
IReadOnlyList<(string Name, object? Value)> parameters,
string querySql,
bool logSensitiveData)
: base(eventDefinition, messageGenerator)
{
ContainerId = containerId;
PartitionKey = partitionKey;
PartitionKeyValue = partitionKeyValue;
Parameters = parameters;
QuerySql = querySql;
LogSensitiveData = logSensitiveData;
Expand All @@ -46,7 +46,7 @@ public CosmosQueryEventData(
/// <summary>
/// The key of the Cosmos partition that the query is using.
/// </summary>
public virtual string? PartitionKey { get; }
public virtual PartitionKey PartitionKeyValue { get; }

/// <summary>
/// Name/values for each parameter in the Cosmos Query.
Expand Down
8 changes: 4 additions & 4 deletions src/EFCore.Cosmos/Diagnostics/CosmosQueryExecutedEventData.cs
Original file line number Diff line number Diff line change
Expand Up @@ -20,7 +20,7 @@ public class CosmosQueryExecutedEventData : EventData
/// <param name="requestCharge">The request charge in RU.</param>
/// <param name="activityId">The activity ID.</param>
/// <param name="containerId">The ID of the Cosmos container being queried.</param>
/// <param name="partitionKey">The key of the Cosmos partition that the query is using.</param>
/// <param name="partitionKeyValue">The key value of the Cosmos partition that the query is using.</param>
/// <param name="parameters">Name/values for each parameter in the Cosmos Query.</param>
/// <param name="querySql">The SQL representing the query.</param>
/// <param name="logSensitiveData">Indicates whether the application allows logging of sensitive data.</param>
Expand All @@ -31,7 +31,7 @@ public CosmosQueryExecutedEventData(
double requestCharge,
string activityId,
string containerId,
string? partitionKey,
PartitionKey partitionKeyValue,
IReadOnlyList<(string Name, object? Value)> parameters,
string querySql,
bool logSensitiveData)
Expand All @@ -41,7 +41,7 @@ public CosmosQueryExecutedEventData(
RequestCharge = requestCharge;
ActivityId = activityId;
ContainerId = containerId;
PartitionKey = partitionKey;
PartitionKeyValue = partitionKeyValue;
Parameters = parameters;
QuerySql = querySql;
LogSensitiveData = logSensitiveData;
Expand Down Expand Up @@ -70,7 +70,7 @@ public CosmosQueryExecutedEventData(
/// <summary>
/// The key of the Cosmos partition that the query is using.
/// </summary>
public virtual string? PartitionKey { get; }
public virtual PartitionKey PartitionKeyValue { get; }

/// <summary>
/// Name/values for each parameter in the Cosmos Query.
Expand Down
8 changes: 4 additions & 4 deletions src/EFCore.Cosmos/Diagnostics/CosmosReadItemEventData.cs
Original file line number Diff line number Diff line change
Expand Up @@ -18,20 +18,20 @@ public class CosmosReadItemEventData : EventData
/// <param name="messageGenerator">A delegate that generates a log message for this event.</param>
/// <param name="resourceId">The ID of the resource being read.</param>
/// <param name="containerId">The ID of the Cosmos container being queried.</param>
/// <param name="partitionKey">The key of the Cosmos partition that the query is using.</param>
/// <param name="partitionKeyValue">The key value of the Cosmos partition that the query is using.</param>
/// <param name="logSensitiveData">Indicates whether the application allows logging of sensitive data.</param>
public CosmosReadItemEventData(
EventDefinitionBase eventDefinition,
Func<EventDefinitionBase, EventData, string> messageGenerator,
string resourceId,
string containerId,
string? partitionKey,
PartitionKey partitionKeyValue,
bool logSensitiveData)
: base(eventDefinition, messageGenerator)
{
ResourceId = resourceId;
ContainerId = containerId;
PartitionKey = partitionKey;
PartitionKeyValue = partitionKeyValue;
LogSensitiveData = logSensitiveData;
}

Expand All @@ -48,7 +48,7 @@ public CosmosReadItemEventData(
/// <summary>
/// The key of the Cosmos partition that the query is using.
/// </summary>
public virtual string? PartitionKey { get; }
public virtual PartitionKey PartitionKeyValue { get; }

/// <summary>
/// Indicates whether the application allows logging of sensitive data.
Expand Down
Loading

0 comments on commit a970d4f

Please sign in to comment.