Reputation: 385
Posted a few variations of a theme on this question but don't seem to have asked the right question and have also dug more into my problem.
So...
I am querying Azure Table Storage using the Azure.Data.Table TableClient
with the GetEntityAsync<Type>(partitionKey, rowKey)
method
Update - TableClient Calling Code
using the following code:
Initialize the tableclient:
public AzureTableService(string tableName, string storageUri, string accountName, string storageAccountKey)
{
tableClient = new TableClient(
new Uri(storageUri),
tableName,
new TableSharedKeyCredential(accountName, storageAccountKey));
}
Get the TableEntity
public async Task<TableEntity> GetEntityAsync(string partitionKey, string rowKey)
{
var response = await tableClient.GetEntityAsync<TableEntity>(partitionKey, rowKey);
return response.Value;
}
in two ways:
TableEntity
is the type Azure.Data.Table.TableEntity
which itself inherits Azure.Data.Table.ITableEntity
. ITableEntity
defines the properties ETag Etag
, string PartitionKey
, string RowKey
, and DateTimeoOffset? Timestamp
.
User
is a class which inherits from ITableEntity
and therefore has those same properties alongside strings for Forename, Surname, Mobile and Address.
Update - User Object Definition
public class User : ITableEntity
{
public User() { }
public string PartitionKey { get; set; }
public string RowKey { get; set; }
public DateTimeOffset? Timestamp { get; set; }
public ETag ETag { get; set; }
public string Forename { get; set; }
public string Surname { get; set; }
public string Mobile { get; set; }
public string Address { get; set; }
}
As such both are valid to use as the type for the method GetEntityAsync<type>
as they both implement the same interface.
If I use the User
type the returned object serialised as Json is:
{
"partitionKey": "partitionKey",
"rowKey": "rowKey",
"timestamp": "2023-02-09T22:28:54.0242121+00:00",
"eTag": {},
"forename": "forename",
"surname": "surname",
"mobile": "mobile",
"address": "address"
}
If I use the TableEntity
type the returned object serialised as Json is:
{
"odata.etag": "W/\"datetime'2023-02-09T22%3A28%3A54.0242121Z'\"",
"PartitionKey": "partitionKey",
"RowKey": "rowKey",
"Timestamp": "2023-02-09T22:28:54.0242121+00:00",
"Address": "address",
"Forename": "forename",
"Mobile": "mobile",
"Surname": "surname"
}
Neither is populating the ETag correctly - User
has a value of ETag: {}
and TableEntity
has a valid string value of an ETag "W/\"datetime'2023-02-09T22%3A28%3A54.0242121Z'\""
BUT it is is a string
with a property name of odata.etag
NOT an object of type ETag
named ETag as per the ITableEntity
implementation.
Further to this...
when I do a delete operation and require the ETag ifMatch for validation the validation works using the odata.etag
property value and seemingly not using the ETag property as implemented with ITableEntity.
Update - Delete Method
public async Task<bool> DeleteItemAsync(TableEntity item, bool forceDelete)
{
var response = await tableClient.DeleteEntityAsync(item.PartitionKey, item.RowKey, forceDelete? ETag.All : item.ETag);
if (response.Status == 200 || response.Status == 201 || response.Status == 204) { return true; }
else { throw new Exception($"The response was {response.Status} - {response.ReasonPhrase}"); }
}
So in effect - the ITableEntity implements a property ETag that is not being set and does not support the ETag property for validation.
I am SO confused - what do I need to do to get the ITableEntity ETag property assigned using the Azure.Data.Table.GetEntityAsync<TableEntity>(PK, RK)
method and used in the Azure.Data.Table.DeleteEntityAsync(PK, RK, ETag)
validation?
Upvotes: 3
Views: 1851