Warning: file_get_contents(/data/phpspider/zhask/data//catemap/2/csharp/269.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
C# 使用TableServiceEntity将复杂对象插入azure表_C#_Azure_Entity_Azure Table Storage - Fatal编程技术网

C# 使用TableServiceEntity将复杂对象插入azure表

C# 使用TableServiceEntity将复杂对象插入azure表,c#,azure,entity,azure-table-storage,C#,Azure,Entity,Azure Table Storage,我在考虑将一个复杂的对象添加到一个表中。由于采用了良好的老式SQL方法,我显然会将其分为表,但我正在尝试一种不同的方法。所以基本上我有一个对象,它是由一个嵌套类组成的(当你反序列化一个json集合时,你会得到一种东西),它有一个普通的Customer、Business和一个InvoiceItems列表 public class Business { public string _id { get; set; } public string name { get; set; }

我在考虑将一个复杂的对象添加到一个表中。由于采用了良好的老式SQL方法,我显然会将其分为表,但我正在尝试一种不同的方法。所以基本上我有一个对象,它是由一个嵌套类组成的(当你反序列化一个json集合时,你会得到一种东西),它有一个普通的Customer、Business和一个InvoiceItems列表

public class Business
{
    public string _id { get; set; }
    public string name { get; set; }
    public string street_1 { get; set; }
    public string street_2 { get; set; }
    public string town { get; set; }
    public string county { get; set; }
    public string postcode { get; set; }

 //other fields as needed
}

public class Customer
{
    public string _id { get; set; }
    public string name { get; set; }
    public string street_1 { get; set; }
    public string street_2 { get; set; }
    public string town { get; set; }
    public string county { get; set; }
    public string postcode { get; set; }

    //other fields as needed
 }

public class InvoiceItems
{
    public string item_id { get; set; }
    public string price_per_unit { get; set; }
    public string quanity { get; set; }
    public string date { get; set; }
}

public class WholeObject
{

    public Customer customer { get; set; }
    public Business address { get; set; }
    public List<InvoiceItems> items { get; set; }
}
公共类业务
{
公共字符串_id{get;set;}
公共字符串名称{get;set;}
公共字符串street_1{get;set;}
公共字符串street_2{get;set;}
公共字符串{get;set;}
公共字符串country{get;set;}
公共字符串邮政编码{get;set;}
//其他需要的字段
}
公共类客户
{
公共字符串_id{get;set;}
公共字符串名称{get;set;}
公共字符串street_1{get;set;}
公共字符串street_2{get;set;}
公共字符串{get;set;}
公共字符串country{get;set;}
公共字符串邮政编码{get;set;}
//其他需要的字段
}
公共类发票项
{
公共字符串项_id{get;set;}
公共字符串每单位价格{get;set;}
公共字符串数量{get;set;}
公共字符串日期{get;set;}
}
公共类全局对象
{
公共客户客户{get;set;}
公共业务地址{get;set;}
公共列表项{get;set;}
}
(示例类)

除了1MB大小外,是否有其他限制将其插入表中?我已经读过了,哪些应该映射C#对象,但它能处理吗?
在这个阶段,这是一个非常假设性的问题,因为我实际上还没有尝试编写代码。任何帮助都将不胜感激。

复杂属性不会保存到表存储中。只能持久化标准数据类型的子集。有关支持哪些数据类型的更多信息,请查看此链接:(查看“属性类型”部分)

然而,您想要做的是可能的,只是实现起来有点困难。有两种方法可以做到这一点:

  • 在WholeObject类上公开CustomerSerialized、AddressSerialized和ItemsSerialized属性。让这些属性将其关联的复杂对象序列化/反序列化为字节数组、json或xml。这种方法有两个缺点:a)即使您只需要客户对象,也总是从azure表存储加载完整的对象树;b) 每个对象的每个属性限制为64kb,因此最好确保InvoiceItems集合可以容纳64kb的序列化

  • 提出一个PartitionKey/RowKey模式,允许您将所有类型的相关对象保存为单个实体,但PartitionKey/RowKey指示它们之间的关系。这将允许您独立地获取完整的对象树或单个子对象。这种方法没有第一种方法的两个缺点,但在实现时它肯定是复杂的。它还限制了您根据其他业务需要调整PartitionKey/RowKey的能力。我为一家大型电子商务公司采用了这种方法,并取得了巨大成功。
    在我的项目中,所有实体(根和子实体)的PartitionKey映射到“WholeObject”的ID,而RowKey由ParentObjectID、ChildObjectID和ChildObjectType的串联组合组成。当需要检索整个对象中的所有对象时,只需对PartitionKey发出查询,否则使用PartitionKey和部分RowKey获取特定类型的对象(即:所有地址),或使用PartitionKey和full RowKey获取单个实体。这种方法支持无限深的对象树结构,但是,一旦实体数超过100,将对象存储在一个事务中是一件令人头痛的事情


HTH

我遇到了一个类似的问题,并实现了一个通用的对象展平器/重新编译器API,该API将把复杂的实体展平为平面
EntityProperty
字典,并以
DynamicTableEntity
的形式将它们写入表存储

然后,相同的API将从
DynamicTableEntity
EntityProperty
字典重新组合整个复杂对象

看看:

用法:

//Flatten object of type Order) and convert it to EntityProperty Dictionary
 Dictionary<string, EntityProperty> flattenedProperties = EntityPropertyConverter.Flatten(order);

// Create a DynamicTableEntity and set its PK and RK
DynamicTableEntity dynamicTableEntity = new DynamicTableEntity(partitionKey, rowKey);
dynamicTableEntity.Properties = flattenedProperties;

// Write the DynamicTableEntity to Azure Table Storage using client SDK

//Read the entity back from AzureTableStorage as DynamicTableEntity using the same PK and RK
DynamicTableEntity entity = [Read from Azure using the PK and RK];

//Convert the DynamicTableEntity back to original complex object.
 Order order = EntityPropertyConverter.ConvertBack<Order>(entity.Properties);
//展平类型顺序的对象)并将其转换为EntityProperty字典
Dictionary FlattedProperties=EntityPropertyConverter.Flatte(顺序);
//创建DynamicTableEntity并设置其PK和RK
DynamicTableEntity DynamicTableEntity=新的DynamicTableEntity(partitionKey,rowKey);
dynamicTableEntity.Properties=扁平化属性;
//使用客户端SDK将DynamicTableEntity写入Azure表存储
//使用相同的PK和RK将实体作为DynamicTableEntity从AzureTableStorage读回
DynamicTableEntity=[使用PK和RK从Azure读取];
//将DynamicTableEntity转换回原始复杂对象。
Order Order=EntityPropertyConverter.ConvertBack(entity.Properties);
从那时起,我与azure团队合作,并将此功能集成到azure存储SDK 8.0版

需要注意的是,Azure SDK中的api不支持
IEnumerable
ICollection
类型属性。但是,如果您在上面的链接中获得nuget package v2,您几乎可以将任何对象写入Azure表存储,包括具有可枚举集合类型属性的对象

我还将
TableEntityAdapter
class添加到SDK版本8.2.0中,以简化使用。只需将您的复杂实体传递给它的构造函数,它就可以透明地处理在写入和读取时展平/转换回您的复杂对象。

因此,基本上将其视为一组单独的实体(将其保存),然后使用查询重新生成对象,并循环或序列化整个对象