Azure 表存储、WCF 服务和枚举
这是我的问题。定义订单的类有一个名为 PaymentStatus
的属性,它是一个定义如下的 enum
:
public enum PaymentStatuses : int
{
OnDelivery = 1,
Paid = 2,
Processed = 3,
Cleared = 4
}
然后,在类本身中,属性定义非常简单:
public PaymentStatuses? PaymentStatus { get; set; }
但是,如果我尝试将订单保存到 Azure 表存储,则会出现以下异常:
System.InvalidOperationException: The type Order+PaymentStatuses' has no settable properties.
此时我认为使用 enum
是不可能的,但快速 Google 搜索返回了以下内容:http://social.msdn.microsoft .com/Forums/en-US/windowsazure/thread/7eb1a2ca-6c1b-4440-b40e-012db98ccb0a
此页面列出了两个答案,其中一个似乎忽略了问题,并建议使用 enum< Azure 存储中的 /code> 没问题。
现在,我不需要将enum
存储在Azure表存储中,我也可以存储相应的int
,但是,我确实需要这个属性在 WCF 服务中公开。
我尝试让属性使用 get
和 set
从存储的 integer
返回 enum
,并删除通过在我的 DataContext
上使用 WritingEntity
事件从 Azure 获取此属性,但我在触发该实体的事件之前收到该异常。
此时,我不知所措,我不知道我还能做些什么来将此属性作为 enum
放在 WCF 中,但让 Azure 仅存储 int
代码>.
Here's my problem. A class which defines an order has a property called PaymentStatus
, which is an enum
defined like so:
public enum PaymentStatuses : int
{
OnDelivery = 1,
Paid = 2,
Processed = 3,
Cleared = 4
}
And later on, in the class itself, the property definition is very simple:
public PaymentStatuses? PaymentStatus { get; set; }
However, if I try to save an order to the Azure Table Storage, I get the following exception:
System.InvalidOperationException: The type Order+PaymentStatuses' has no settable properties.
At this point I thought using enum
isn't possible, but a quick Google search returned this: http://social.msdn.microsoft.com/Forums/en-US/windowsazure/thread/7eb1a2ca-6c1b-4440-b40e-012db98ccb0a
This page lists two answers, one of which seems to ignore the problems and suggests that using an enum
in Azure Storage is fine.
Now, I don't NEED to store the enum
in the Azure Table Storage as such, I could just as well store a corresponding int
, however, I do need this property to be exposed in the WCF service.
I've tried making the property use get
and set
to return the enum
from a stored integer
, and remove this property from Azure by using the WritingEntity
event on my DataContext
, but I get that exception before the event for this entity is fired.
At this point, I'm at a loss, I don't know what else I can do to have this property in WCF as an enum
, but have Azure store just the int
.
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。
绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论
评论(6)
不支持枚举。尽管它的定义类似于 int,但它实际上不是表存储支持的整型类型。 这是类型列表支持。 枚举只是具有面向对象风格的整数的字符串表达式。
您可以将 int 存储在表存储中,然后使用 Enum.Parse 进行转换。
Enum is not supported. Even though it is defined like an int, it is really not an integral type supported by Table Storage. Here is the list of types supported. An enum is just a string expression of an integral number with an object-oriented flavor.
You can store int in table storage and then convert it using Enum.Parse.
这里有一个简单的解决方法:
如果可以使用一个简单的支持值而不是额外的(公共!)属性,那就更好了 - 没有覆盖
ReadEntity
/WriteEntity
当然。我打开了一个用户语音票来促进这一点,所以你可能想投票。Here's a simple workaround:
It would have been nicer if a simple backing value could have been employed rather than an additional (public!) property - without the hassle of overriding
ReadEntity
/WriteEntity
of course. I opened a user voice ticket that would facilitate that, so you might want to upvote it.是的,我也遇到了同样的问题
我将之前的 enum 属性更改为 int 属性。现在这个 int 属性解析传入的 int 并将其保存到相同枚举类型的变量中,所以现在代码被
更改为
ya i was having this same problem
i changed my property which was earlier enum to int. now this int property parses the incoming int and saves it into a variale of the same enum type so now the code that was
is chaged to
只是建议...
我记得在 WCF 中您必须使用特殊属性标记枚举: http://msdn.microsoft.com/en-us/library/aa347875.aspx
另外,当您声明
PaymentStatuses 时? PaymentStatus
,您声明Nullable付款状态
。?
语法只是语法糖。尝试删除?
并看看会发生什么(您可以添加 PaymentStatuses.NoSet = 0 ,因为 Int32 的默认值为 0)。祝你好运。
Just suggestions...
I remember that in WCF you have to mark enums with special attributes: http://msdn.microsoft.com/en-us/library/aa347875.aspx
Also, when you declare
PaymentStatuses? PaymentStatus
, you are declaringNullable<PaymentStatuses> PaymentStatus
. The?
sintax is just syntactic sugar. Try to remove the?
and see what happen (you could add a PaymentStatuses.NoSet = 0 , because the default value for an Int32 is 0).Good luck.
Parvs 解决方案让我走上了正轨,但我做了一些细微的调整。
Parvs solution put me on the right track but I had some minor adjustments.
我遇到了类似的问题,并实现了一个通用的对象扁平化器/重构器 API,它将把复杂的实体扁平化为扁平的 EntityProperty 字典,并使它们可以以 DynamicTableEntity 的形式写入表存储。
然后,相同的 API 将从
DynamicTableEntity
的EntityProperty
字典中重新组合整个复杂对象。这与您的问题相关,因为 ObjectFlattenerRecomposer API 支持展平通常不可写入 Azure 表存储的属性类型,例如
Enum
、TimeSpan
、所有Nullable
类型、ulong
和uint
,将它们转换为可写的 EntityProperties。API 还处理从扁平化
EntityProperty
字典到原始复杂对象的转换。客户端需要做的就是告诉 API,我有一个刚刚从 Azure 表中读取的 EntityProperty 字典(以 DynamicTableEntity.Properties 的形式),您可以将其转换为以下对象吗这个特定类型。 API 将重构完整的复杂对象及其所有属性,包括“Enum”属性及其原始正确值。所有这些原始对象的扁平化和重组对于客户端(API 用户)来说都是透明的。客户端不需要向 ObjectFlattenerRecomposer API 提供有关其想要写入的复杂对象的任何架构或任何知识,只需将对象作为“对象”传递给 API 即可对其进行扁平化。当将其转换回来时,客户端只需要提供它想要将扁平化
EntityProperty
字典转换为的实际对象类型。 API 的通用 ConvertBack 方法将简单地重构 Type T 的原始对象并将其返回给客户端。请参阅下面的用法示例。这些对象不需要实现任何接口(如“ITableEntity”)或从特定基类继承。他们不需要提供一组特殊的构造函数。
博客: https://doguarslan.wordpress.com/2016/02/03/writing-complex-objects-to-azure-table-storage/
Nuget 包: https://www.nuget.org/packages/ObjectFlattenerRecomposer/
用法:
I have come across a similar problem and have implemented a generic object flattener/recomposer API that will flatten your complex entities into flat
EntityProperty
dictionaries and make them writeable to Table Storage, in the form ofDynamicTableEntity
.Same API will then recompose the entire complex object back from the
EntityProperty
dictionary of theDynamicTableEntity
.This is relevant to your question because the ObjectFlattenerRecomposer API supports flattening property types that are normally not writeable to Azure Table Storage like
Enum
,TimeSpan
, allNullable
types,ulong
anduint
by converting them into writeable EntityProperties.The API also handles the conversion back to the original complex object from the flattened
EntityProperty
Dictionary. All that the client needs to do is to tell the API, I have thisEntityProperty
Dictionary that I just read from Azure Table (in the form of DynamicTableEntity.Properties), can you convert it to an object of this specific type. The API will recompose the full complex object with all of its properties including 'Enum' properties with their original correct values.All of this flattening and recomposing of the original object is done transparently to the client (user of the API). Client does not need to provide any schema or any knowledge to the ObjectFlattenerRecomposer API about the complex object that it wants to write, it just passes the object to the API as 'object' to flatten it. When converting it back, the client only needs to provide the actual type of object it wants the flattened
EntityProperty
Dictionary to be converted to. The generic ConvertBack method of the API will simply recompose the original object of Type T and return it to the client.See the usage example below. The objects do not need to implement any interface like 'ITableEntity' or inherit from a particular base class either. They do not need to provide a special set of constructors.
Blog: https://doguarslan.wordpress.com/2016/02/03/writing-complex-objects-to-azure-table-storage/
Nuget Package: https://www.nuget.org/packages/ObjectFlattenerRecomposer/
Usage: