Results 1 to 10 of 10

Thread: How to Implement Hibernate OpenSessionInView with WCF Services?

  1. #1
    Join Date
    Jul 2005
    Location
    China , ShangHai
    Posts
    43

    Default How to Integrate Hibernate OpenSessionInView and Lazy-Init within WCF Services?

    Hi,

    As I'm using nhibernate LazyInitial feature, I need to Load a entity,then Init it.
    So, how can i keep all of these mess operation in the same SESSION? as OpenSessionInView pattern ?

    Also, dealing with Entity Recursive Reference when WCF serialization is a BIG headache.

    Any suggestion is appriciate.
    Last edited by crabo; 04-03-2008 at 02:28 AM.

  2. #2
    Join Date
    Jul 2005
    Location
    China , ShangHai
    Posts
    43

    Default

    I achieved OSIV by adding a EndPointBehavior as below:

    Code:
    class WcfCallInterceptorBehavior : IEndpointBehavior
        {
            public void AddBindingParameters(ServiceEndpoint endpoint, BindingParameterCollection bindingParameters) { }
            public void ApplyClientBehavior(ServiceEndpoint endpoint, ClientRuntime clientRuntime) { }
            public void ApplyDispatchBehavior(ServiceEndpoint endpoint, EndpointDispatcher endpointDispatcher)
            {
                //register WcfOpenSessionInView
                foreach (DispatchOperation op in endpointDispatcher.DispatchRuntime.Operations)
                    op.CallContextInitializers.Add(new WcfOpenSessionInView());
            }
            public void Validate(ServiceEndpoint endpoint) { }
        }
    I'm still working on serializing Lazy-Init entities for AJAX client over WCF.
    A week passed,and I'm almost there now!

    Cheers!
    Last edited by crabo; 04-02-2008 at 02:22 PM.

  3. #3
    Join Date
    Jul 2005
    Location
    China , ShangHai
    Posts
    43

    Default

    Finally, I got my answer!

    1. Replace all DataContractSerializerOperationBehavior.DataContra ctSurrogate to WcfHibernateDataContractSurrogate.

    2.Create a WcfHibernateDataContractSurrogate as <b>Tim Vasil</b> described here:
    WCF serialization with NHibernate object graphs
    [link]timvasil.com/blog14/post/2008/02/WCF-serialization-with-NHibernate.aspx[/link]

    3.Also add a KnownTypesProvider to all of your Exported Service Contracts.

  4. #4
    Join Date
    Oct 2006
    Location
    Bergen, Norway
    Posts
    365

    Default

    Hi!

    Good work!

    3.Also add a KnownTypesProvider to all of your Exported Service Contracts.
    If you are not doing SOA, if you know who will consume your services and if you want to reuse your domain assemblies on the other side of the network, then you can use the NetDataContractSerializer instead and avoid having to declare all your types.

    Cheers,
    Steinar.
    Last edited by steinard; 04-06-2008 at 11:20 PM. Reason: Spelling...

  5. #5
    Join Date
    Jul 2005
    Location
    China , ShangHai
    Posts
    43

    Default

    Yah, "KnowTypeProvider" is just a assmbly type exporter. It check all the "Contract Types",and return as a type array to the Caller. Note this: I use AJAX as WCF client.

  6. #6
    Join Date
    Jul 2005
    Location
    China , ShangHai
    Posts
    43

    Default

    Finally, I changed my SessionScopeHandler into "IDispatchMessageInspector" Extension.

    Because Operation.AfterInvoke always happened before WCF Serializing.

    Now it looks like:
    Code:
    public class MessageInspector:IDispatchMessageInspector
        {
            private Spring.Data.NHibernate.Support.SessionScope Osiv;
            public MessageInspector(Spring.Data.NHibernate.Support.SessionScope osiv)
            {
                Osiv = osiv;
            }
    
            public object AfterReceiveRequest(ref Message request, IClientChannel channel, InstanceContext instanceContext)
            {
                if (Osiv != null && !Osiv.IsOpen) Osiv.Open();
            }
            public void BeforeSendReply(ref Message reply, object correlationState)
            {
                if (Osiv != null) Osiv.Close();
            }
    }
    Tell me what you thinks.

  7. #7
    Join Date
    Oct 2006
    Location
    Bergen, Norway
    Posts
    365

    Default

    Hi!

    This looks really good and useful. I need to start considering switching to WCF soon I guess...

    Cheers,
    Steinar.

  8. #8
    Join Date
    May 2008
    Location
    Boston, MA
    Posts
    7

    Default

    Crabo,

    Have you had any issues with Sessions being closed to soon by using the IDispatchMessageInspector extension? Is the thread that closes the session always going to be the one that opened it?

    Thanks,
    Corey

  9. #9
    Join Date
    Jul 2005
    Location
    China , ShangHai
    Posts
    43

    Default

    Sorry for my dev enviroment, but, I havn't encounter any error yet.

    But I doubt it would be the right way.

    May be you should try it and tell me how it's going.

  10. #10
    Join Date
    Jul 2005
    Location
    China , ShangHai
    Posts
    43

    Default

    Some more details here:

    In Service.xml :

    Code:
    <object id="WcfOsiv" lazy-init="true" type="Spring.Data.NHibernate.Support.SessionScope,Spring.Data.NHibernate12" />
    
    <object id="WcfNhLazy" lazy-init="true" type="Framework.Integration.WCF.NHibernate.HibernateDataContractSurrogate, Framework.Integration" />
    
    <object id="WcfMsgLog" lazy-init="true" type="Framework.Integration.WCF.DispatchMessageInspector, Framework.Integration">
        <constructor-arg name="osiv" ref="WcfOsiv"/>
      </object>
    So I inject OSIV in my every in/out message. and also replace default to HibernateDataContractSurrogate.

    Framework.Integration.WCF.DispatchMessageInspector .cs
    Code:
    public object AfterReceiveRequest(ref Message request, IClientChannel channel, InstanceContext instanceContext)
            {
                if (Osiv != null && !Osiv.IsOpen) Osiv.Open();
    }
    
     public void BeforeSendReply(ref Message reply, object correlationState)
            {
                if (Osiv != null) Osiv.Close();
    }

    Framework.Integration.WCF.InterceptBehavior.cs
    Code:
    public void ApplyDispatchBehavior(ServiceEndpoint endpoint, EndpointDispatcher endpointDispatcher)
            {
                if (this.Enabled)
                {
                    #region ICallContextInitializer
                    //IDictionary ctxs = ctx.GetObjectsOfType(typeof(ICallContextInitializer));
                    //foreach (DictionaryEntry de in ctxs)
                    //{
                    //    //For all operations!
                    //    foreach (DispatchOperation op in endpointDispatcher.DispatchRuntime.Operations)
                    //        op.CallContextInitializers.Add((ICallContextInitializer)de.Value);
    
    
                    //}
                    #endregion
    
                    #region IDataContractSurrogate
                    IDictionary surs = ctx.GetObjectsOfType(typeof(IDataContractSurrogate));
                    foreach (DictionaryEntry de in surs)
                    {
                        //Register HibernateDataContractSurrogate for Lazy-Properties serialization
                        foreach (OperationDescription od in endpoint.Contract.Operations)
                        {
                            DataContractSerializerOperationBehavior dcsob =
                                od.Behaviors.Find<DataContractSerializerOperationBehavior>();
                            if (dcsob != null)
                                dcsob.DataContractSurrogate = (IDataContractSurrogate)de.Value;
                        }
    
                    }
                    #endregion
    
                    #region IDispatchMessageInspector
                    IDictionary msgs = ctx.GetObjectsOfType(typeof(IDispatchMessageInspector));
                    foreach (DictionaryEntry de in msgs)
                    {
                        endpointDispatcher.DispatchRuntime.MessageInspectors.Add((IDispatchMessageInspector)de.Value);
    
                    }
                    #endregion
                }
            }

Posting Permissions

  • You may not post new threads
  • You may not post replies
  • You may not post attachments
  • You may not edit your posts
  •