Question

I got the following exception:

System.Workflow.Runtime.Hosting.PersistenceException: Type ‘Microsoft.SharePoint.SPWeb’ in Assembly ‘Microsoft.SharePoint, Version=12.0.0.0, Culture=neutral, PublicKeyToken=71e9bce111e9429c’ is not marked as serializable. —> System.Runtime.Serialization.SerializationException: Type ‘Microsoft.SharePoint.SPWeb’ in Assembly ‘Microsoft.SharePoint, Version=12.0.0.0, Culture=neutral, PublicKeyToken=71e9bce111e9429c’ is not marked as serializable

The error came from here:

public sealed partial class MyWorkflow : StateMachineWorkflowActivity
{
    public SPWorkflowActiviationProperties workflowProperties = new SPWorkflowActivationProperties();
    private SPWeb spWebtemp;

    private SPWeb spWeb
    {
        get { return spWebtemp ?? (spWebtemp = workflowProperties.Web); }
    }

    ...

There are two blog posts I found:

There is one solution to be found to this problem: Not have complex member objects as global variables, but as a local variables - i.e. declare SPWeb locally (workflowProperties.Web) instead of on a global level.

So I would have to redeclare spWeb in every method I am using - which I deem rather ugly.

What I also tried is this:

...
[NonSerialized]
private SPWeb spWebtemp;

private SPWeb spWeb
{
    get { return spWebtemp ?? (spWebtemp = workflowProperties.Web); }
}
...

==> no more serialization exception!

Are there any negative implications when using the NonSerialized attribute on this field?
Or in other words - what are the implications?

Was it helpful?

Solution

Why don't you simply do :

private SPWeb spWeb
{
    get { return workflowProperties.Web; }
}

the lazy load of the spweb object is already handled by the properties property

OTHER TIPS

This looks like it also would also work (the OnDeserialized Attribute):

http://msdn.microsoft.com/en-us/library/system.runtime.serialization.ondeserializedattribute.aspx

[EDIT]

I haven't tested this, but I'm thinking something like this:

public sealed partial class MyWorkflow : StateMachineWorkflowActivity
{

public SPWorkflowActiviationProperties workflowProperties = new SPWorkflowActivationProperties();

[NonSerialized()]
private SPWeb spWebtemp;

private SPWeb spWeb
{
    get { return spWebtemp ?? (spWebtemp = workflowProperties.Web); }
}

[OnDeserialized()]
internal void OnDeserializedMethod(StreamingContext context)
{
    spWebTemp = workflowProperties.Web;
}


...

Also, why not initialize the spWebtemp object in the constructor, or is that not possible with workflows?

Licensed under: CC-BY-SA with attribution
Not affiliated with StackOverflow
scroll top