breezeManager.createEntity()无法填充特定值的外键属性

时间:2015-01-30 23:47:39

标签: entity-framework entity-framework-6 breeze

我在这里有两个相关的表格:

public partial class List
{...
        public int RegionId { get; set; }

        [ForeignKey("RegionId")]
        public virtual Region Region { get; set; }
...}

public partial class Region
{
    public Region()
    {
        Lists = new HashSet<List>();
    }

    public int RegionId { get; set; }

    [Required]
    [StringLength(255)]
    public string Name { get; set; }

    public DateTime Added { get; set; }

    public virtual ICollection<List> Lists { get; set; }
}

这里是Regions表的内容:

RegionId    Name
1   Global
2   China
3   USA
4   UK
8   Canada
9   Spain
10  France

在微风的一面,我拉下了地区:

var query = new breeze.EntityQuery().from("Regions").select("RegionId,Name").orderBy("RegionId");
    return $rootScope.breezeManager.executeQuery(query).then(function (data) {
        service.regions = data.results;

似乎有效:

service.regions[2]; // Name: "USA", RegionId: 3

但是,当我尝试创建一个新实体时:

var newList = $rootScope.breezeManager.createEntity('List', listValues);

在listValues中,我指定{ RegionId: 3, ...}

newList.RegionId // 3
newList.Region   // null

这或许很奇怪,但真的令人沮丧的是,如果我指定另一个值,比如1,它就可以了。同样适用于2和4:

newList.RegionId     // 1
newList.Region.Name  // "Global"

我一直在仔细研究代码(和互联网)几个小时试图解决这个问题,但是它没有找到我,因此有资格获得我的第一个SO问题!

更新

我现在更加困惑。我计划通过createEntity调用后手动设置区域来解决此问题,因此我在createEntity正上方添加了这行代码:

var region = Enumerable.From(service.regions).Single("$.RegionId == " + listValues.RegionId);

然而,在这样做之后,没有其他更改,newList现在正确地获得了填充Region,即使是3(美国)!然后我评论了那条线并再次尝试,它仍然有效。尝试过其他几次,各种各样的事情组合,现在它再也没有工作,即使是那条线。不确定这是否有帮助。我会一直在试验。

1 个答案:

答案 0 :(得分:1)

我不知道你正在做什么,但我确实看到你有一个根本的误解。

我相信您希望第一个查询返回Region个实体,并且您认为service.regions在成功回调中填充了Region个实体。

两者都不是。您的查询包含select() clause,这就是我们所说的投影。投影返回数据对象,而非实体。缓存中也没有Region个实体。

  

您可能已经在别处看到过 - 也许是Pluralsight视频 - 投影查询确实返回了实体。当查询包含toType clause时,会发生这种情况,该{{3}}实际上将投影数据转换为目标类型的实例。这是一个技巧,你应该只是非常谨慎地执行,知道你在做什么,为什么,以及限制。但是你并没有在这个问题中进行投射,所以这个题外话就是重点。

以下service.regions数组包含一些包含Region数据的数据对象,但它不包含Region 实体

这也解释了为什么当您使用List创建新的RegionId:3实体时,新实体的Region属性返回null。当然是null。仅根据您告诉我们的内容,缓存中根本没有Region个实体,更不用说ID为3的Region

我无法解释您如何获得id = 1或id = 2的Region。我猜你还有什么东西告诉我们......就像你通过其他一些问题获得这些区域一样。

我不明白为什么你首先使用投影查询。为什么不只是查询所有区域并完成它?

 breeze.EntityQuery.from("Regions").orderBy("RegionId")
       .using(manager).execute(function(data) { 
           service.regions = data.results;
       });

我根本不了解你的更新;对我来说,这看起来不像是一个有效的EF查询。

切线问题

首先,为什么要使用HashSet<List>初始化服务器端Lists模型类中的Region属性?这是一种专门的收藏类型,只会让人感到困惑。它没有做到休闲读者可能认为的那样做。虽然它可以阻止某人两次添加相同的对象引用,但它不会阻止某人使用相同的List添加两个不同的RegionId对象。要做的简单,明显和正确的事情是......

Lists = new System.Collections.Generic.List<List>();

// the full type name is only necessary because you burned the name "List"
// when defining your model class.

其次,在客户端,请不要用任何方式扩展Angular $rootScope。这种全球变量&#34;污染&#34;被广泛认为是&#34;不良做法&#34;。将您的Breeze内容保存在适当的Angular服务中,并在需要时注入该服务。