使用WCF将Linq-to-Sql对象发送到服务器时出错 [英] Error when sending an Linq-to-Sql object to the server using WCF

查看:65
本文介绍了使用WCF将Linq-to-Sql对象发送到服务器时出错的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我正在尝试开发一个具有2层的系统:一个移动客户端和一个使用LINQ to SQL在数据库中存储信息的服务器. 我想创建一个在服务器中存储任务的WCF服务器,因此它将从客户端接收一个任务,并将使用LINQ进行SQL存储.

I am trying to develop a system that has 2 tiers: a mobile client and a server that uses LINQ to SQL to store information in the database. I want to create a WCF server that stores a task in the server, so it will receive a Task from the client and will use LINQ to SQL to store it.

要执行此服务,我创建了dbml文件,因此可以使用datacontext.

To do this service, I created the dbml file, so I can use the datacontext.

这是我的服务方式:

public Task SaveTask(string token, Task task)
    {
        TrackingDataContext dataConext = new TrackingDataContext();


        //Saves/Updates the task
        dataConext.Tasks.InsertOnSubmit(task);
        dataConext.SubmitChanges();

        return task;
    }

该令牌将在将来使用

这是我的客户端方法,它将调用该服务:

And this is my client method, which will call the service:

private void btnSave_Click(object sender, EventArgs e)
    {
        //Populate the object with the info
        Task task = new Task();
        task.Title = tbTitle.Text;
        task.Description = tbDescription.Text;
        //this is a FK to another table
        task.Severity = ((Severity)lbSeverities.SelectedItem);
        //the first state: "open"
        task.StateID = 1;

        //Save the task
        client.SaveTaskCompleted += new EventHandler<SaveTaskCompletedEventArgs>(client_SaveTaskCompleted);
        client.SaveTaskAsync(App.Token, task);
    }

如您所见,我正在创建一个新对象,将其填充并将其发送到我的服务,该服务将获取并存储它.从理论上讲,它可以正常工作.

As you can see, I am creating a new object, populating it and sending it to my service, which will get it and store it. Theoretically it would work ok.

客户端可以创建对象并将其发送到服务器. 当服务器接收到请求时,它尝试再次构建对象,但是随后我在此方法(从VS2010自动创建)中得到了System.Data.Linq.ForeignKeyReferenceAlreadyHasValueException:

The client is able to create the object and send to the server. When the server receives the request, it tried to build the object again, but then I get a System.Data.Linq.ForeignKeyReferenceAlreadyHasValueException in this method (created automatically from VS2010):

 [global::System.Data.Linq.Mapping.ColumnAttribute(Storage="_SeverityID", DbType="Int NOT NULL")]
        public int SeverityID
        {
            get
            {
                return this._SeverityID;
            }
            set
            {
                if ((this._SeverityID != value))
                {
                    if (this._Severity.HasLoadedOrAssignedValue)
                    {
                        throw new System.Data.Linq.ForeignKeyReferenceAlreadyHasValueException();
                    }
                    this.OnSeverityIDChanging(value);
                                    //The exception happens in this line                    
                                    this.SendPropertyChanging();
                    this._SeverityID = value;
                    this.SendPropertyChanged("SeverityID");
                    this.OnSeverityIDChanged();
                }
            }
        }

在我的服务器方法中不能有任何错误,因为: 1-非常简单,内部没有逻辑 2-我什至无法调试它,该错误发生在调用我的方法之前,可能是在整理请求时.

It can't be any error in my server method because: 1- it is very simple and has no logic inside 2- I can't even debug it, the error happens before my methos is called, probably when unmarshaling the request.

这样的事情会发生什么?我在哪里可以看一下?可能是配置问题吗?

What could happen something like this? Where can I take a look? Could that be a configuration issue?

谢谢你, 奥斯卡

找到此链接通过Wcf对Linq2Sql进行序列化-错误或误解? /a>,他们告诉它是错误,但这是1年前的错误.有谁知道它是否解决了?

found this link Serializing Linq2Sql over Wcf - bug or misunderstanding?, where they tell it is a bug, but it is from 1 year ago. Does anyone know if it was solved?

推荐答案

所以基本上,这里发生的是客户端正在发送一个物化对象图. Task对象具有Severity属性和相应的SeverityID属性.当服务器反序列化客户端的请求时,它会创建一个Task对象,然后可能首先反序列化Severity属性.现在,当SeverityID反序列化时,LINQ对SQL的限制就受到了攻击...

So basically what's happening here is that the client is sending a materialized object graph. The Task object has a Severity property and a corresponding SeverityID property. When the server deserializes the client's request, it creates a Task object, then probably deserializes the Severity property first. Now when SeverityID is deserialized, a limitation of LINQ to SQL is being hit...

if (this._Severity.HasLoadedOrAssignedValue) {
    throw new System.Data.Linq.ForeignKeyReferenceAlreadyHasValueException();
}

如果已经设置了相关对象的属性(Severity),则不能设置外键属性(SeverityID).

You can't set a foreign key property (SeverityID) if the related object's property (Severity) is already set.

我怀疑这就是为什么LINQ to SQL称其序列化模式为单向"的原因,因为将物化集合传递回会导致这种问题.

I suspect that this is why LINQ to SQL calls its serialization mode "unidirectional" because passing a materialized collection back will result in this kind of problem.

代替在客户端上设置Severity属性,而尝试设置SeverityID属性.您也可以尝试在服务器上禁用延迟加载,但是我不知道这样做是否会起作用.

Instead of setting the Severity property on the client, try setting the SeverityID property instead. You could also try disabling deferred loading on the server but I don't know if this will have any effect.

这篇关于使用WCF将Linq-to-Sql对象发送到服务器时出错的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆