When you send your entities over the wire, you better don't inherit
from ActiveRecordBase.
Perhaps this solves your problem.

-Markus

2010/1/3 dylanj <dylancjan...@gmail.com>:
> Hi All,
>
> Sorry if this is a n00b thing to ask - I've only been into DotNet/C#
> for about two weeks.
>
> But basicly what I am trying to do is expose DAO's throught WCF
> services.
>
> The problem is when I try to call the Service from the client I get
> the following exception : Test method
> jTekPos.Client.RemoteProxy.Tests.UserProxy_Fixture.Can_We_Lookup_A_Member
> threw exception:  System.ServiceModel.FaultException`1
> [System.ServiceModel.ExceptionDetail]: No persister for: User.
>
> I believe ( from what I have googled ) that it has something to do
> with the Serializer not serializing the references properly, But I
> have spent way to long googling and really need some help now.
>
> My User.cs is defined here :
>
> [code]
> namespace jTekPos.Data.Model
> {
>    [Serializable]
>    [DataContract]
>    [ActiveRecord("usrs")]
>    public class User : ActiveRecordBase<User>
>    {
>        [DataMember]
>        [PrimaryKey("user_id")]
>        public int UserId { get; set; }
>
>        [DataMember]
>        [Property("user_name")]
>        public String Username { get; set; }
>
>        [DataMember]
>        [Property("pass_word")]
>        public String Password { get; set; }
>
>        [DataMember]
>        [Property("firstname")]
>        public String Firstname { get; set; }
>
>        [DataMember]
>        [Property("surname")]
>        public String Surname { get; set; }
>
>        [DataMember]
>        [HasAndBelongsToMany(typeof(Role),
>            Table = "usr_role_link", ColumnKey = "user_id", ColumnRef
> = "role_id",
>            Cascade = ManyRelationCascadeEnum.AllDeleteOrphan, Lazy =
> true)]
>        public IList<Role> Roles { get; set; }
>    }
> }
> [/code]
>
> My Role.cs is defined here :
> [code]
> namespace jTekPos.Data.Model
> {
>    [Serializable]
>    [DataContract]
>    [ActiveRecord("user_role")]
>    public class Role : ActiveRecordBase<Role>
>    {
>        [DataMember]
>        [PrimaryKey("role_id")]
>        public int RoleId { get; set; }
>
>        [DataMember]
>        [Property("role_name")]
>        public String RoleName { get; set; }
>
>        [DataMember]
>        [Property("role_desc")]
>        public String RoleDescription { get; set; }
>
>        [DataMember]
>        [HasAndBelongsToMany(typeof(User),
>            Table = "user_role_link", ColumnKey = "role_id", ColumnRef
> = "user_id",
>            Inverse = true, Cascade =
> ManyRelationCascadeEnum.SaveUpdate, Lazy = true)]
>        public IList<User> Users { get; set; }
>
>        [DataMember]
>        [HasAndBelongsToMany(typeof(Permission),
>            Table = "role_perm_link", ColumnKey = "role_id", ColumnRef
> = "perm_id",
>            Cascade = ManyRelationCascadeEnum.AllDeleteOrphan, Lazy =
> true)]
>        public IList<Permission> Permissions { get; set; }
>    }
> }
> [/code]
>
>
> The DAO that I expose (UserDAO.cs) :
> [code]
> namespace jTekPos.Data.AccessObject
> {
>    [ServiceContract(Namespace="www.#####co.za/jTekPos/
> DataAccessObject/User")]
>    [ServiceBehavior(IncludeExceptionDetailInFaults=true,
> MaxItemsInObjectGraph=1000)]
>    public class UserDao : StandardDao<User>
>    {
>        [OperationContract]
>        [PreserveCircularReferences]
>        public virtual User FindUserById( int id )
>        {
>            return GetSingleResultFromCriteria
> (MakeOneParamSimpleEqCriteria("Id", id));
>        }
>
>        [OperationContract]
>        [PreserveCircularReferences]
>        public virtual User FindUserByUsername(String username)
>        {
>            return GetSingleResultFromCriteria
> (MakeOneParamSimpleEqCriteria("Username", username));
>        }
>    }
> }
> [/code]
>
> The UserDao extends StandardDAO.cs thats this :
> [code]
>
> namespace jTekPos.Data.AccessObject
> {
>    public abstract class StandardDao<T>
>    {
>        public readonly ISession _Session;
>        public T _BaseEntity;
>
>        public StandardDao()
>        {
>            ISessionFactory factory =
>                ObjectFactory.GetInstance<ISessionFactory>();
>            _Session = factory.OpenSession();
>            _BaseEntity = (T)
>                typeof(T).GetConstructor(new Type[]{}).Invoke(new
> Object[]{});
>        }
>
>        public ICriteria MakeCriteria()
>        {
>            return _Session.CreateCriteria(typeof(T).Name);
>        }
>
>        public ICriteria MakeOneParamSimpleEqCriteria(String
> PropertyName, Object Value)
>        {
>            ICriteria crit = MakeCriteria();
>            crit.Add(Restrictions.Eq(PropertyName, Value));
>            return crit;
>        }
>
>        public T GetSingleResultFromCriteria(ICriteria iCrit)
>        {
>            iCrit.SetMaxResults(1);
>            IList<T> lst = iCrit.List<T>();
>            if (lst == null || lst.Count == 0)
>                return default(T);
>            return lst[0];
>        }
>    }
> }
>
> [/code]
>
> I followed an Microsoft article recommending me to create these
> (supposed to help the dataContractSerializer preserver my
> references) :
>
> [b]OpBehaviourPreserveRefs.cs[/b]
> [code]
> public class OpBehaviourPreserveRefs :
> DataContractSerializerOperationBehavior
>    {
>         public OpBehaviourPreserveRefs ( OperationDescription
> operationDescription) : base(operationDescription) { }
>
>         public override XmlObjectSerializer CreateSerializer( Type
> type, string name, string ns, IList<Type> knownTypes)
>         {
>            return CreateDataContractSerializer(type, name, ns,
> knownTypes);
>         }
>
>         private static XmlObjectSerializer
> CreateDataContractSerializer( Type type, string name, string ns,
> IList<Type> knownTypes)
>         {
>            return CreateDataContractSerializer(type, name, ns,
> knownTypes);
>         }
>
>         public override XmlObjectSerializer CreateSerializer( Type
> type, XmlDictionaryString name, XmlDictionaryString ns, IList<Type>
> knownTypes)
>         {
>             return new DataContractSerializer(type, name, ns,
> knownTypes, 0x7FFF, false, true, null);
>         }
>    }
> [/code]
>
> [b]The attribute : [/b]
> [code]
>  public class PreserveCircularReferencesAttribute : Attribute,
> IOperationBehavior
>    {
>        public void AddBindingParameters(OperationDescription
> description, BindingParameterCollection parameters) { }
>
>        public void ApplyClientBehavior(OperationDescription
> description, ClientOperation proxy) {
>            IOperationBehavior innerBehavior =
>              new OpBehaviourPreserveRefs(description);
>            innerBehavior.ApplyClientBehavior(description, proxy);
>        }
>
>        public void ApplyDispatchBehavior(OperationDescription
> description, DispatchOperation dispatch)
>        {
>            IOperationBehavior innerBehavior =
>              new OpBehaviourPreserveRefs(description);
>            innerBehavior.ApplyDispatchBehavior(description,
> dispatch);
>        }
>
>        public void Validate(OperationDescription description) { }
>    }
> [/code]
>
> And Then to host these I tried the standard selfHost option, and tried
> the WcfIntegration package from Castle :
>
> [b]IServiceHostCache.cs[/b]
> [code]
>  public abstract class IServiceHostCache
>    {
>        public const String URI_TEMPLATE =
>            "http://${BindAddress}:${Port}/jtek/wcf/${ServiceType}/$
> {ServiceName}";
>
>        public IList<Object> RunningServiceHosts =
>            new List<Object>();
>
>        public abstract void HostService(String ServiceName, String
> ServiceType, Type ServiceContractImpl);
>
>        public Uri GenerateServiceUri(string ServiceName, string
> ServiceType)
>        {
>            return new Uri(URI_TEMPLATE
>                .Replace("${BindAddress}", "localhost")
>                .Replace("${Port}", "8000")
>                .Replace("${ServiceType}", ServiceType)
>                .Replace("${ServiceName}", ServiceName));
>        }
>
>        public abstract void Destroy();
> [/code]
>
> [b]Standard WCF impl:[/b]
> [code]
>  public class WcfBasedServiceHostCache : IServiceHostCache
>    {
>        public override void HostService(String ServiceName, String
> ServiceType, Type ServiceContractImpl)
>        {
>            Uri uri = GenerateServiceUri( ServiceName, ServiceType );
>            ServiceHost host =
>                new ServiceHost( ServiceContractImpl , uri );
>            try
>            {
>                host.AddServiceEndpoint(
>                    ServiceContractImpl,
>                    new WSHttpBinding(),
>                    ServiceName);
>                ServiceMetadataBehavior httpGetBehaviour =
>                    new ServiceMetadataBehavior();
>                httpGetBehaviour.HttpGetEnabled = true;
>                host.Description.Behaviors.Add( httpGetBehaviour );
>                host.Open();
>                RunningServiceHosts.Add(host);
>            }
>            catch (CommunicationException ce)
>            {
>                host.Abort();
>                throw new Exception("Something Bad Happened", ce);
>            }
>        }
>
>        public override void Destroy()
>        {
>            foreach (ServiceHost host in RunningServiceHosts)
>            {
>                host.Close();
>            }
>            this.RunningServiceHosts.Clear();
>        }
>    }
> [/code]
>
> [b]The Windsor Impl[/b]
> [code]
> public class WindsorServiceHostCache : IServiceHostCache
>    {
>        public override void HostService(String ServiceName, String
> ServiceType, Type ServiceContractImpl)
>        {
>            Uri uri = this.GenerateServiceUri(ServiceName,
> ServiceType);
>            DefaultServiceHostFactory.RegisterContainer
> (((IWindsorContainer) ObjectFactory.FetchDelegate()).Kernel);
>            DefaultServiceHost host =
>                new DefaultServiceHost(ServiceContractImpl, uri);
>            try
>            {
>                host.AddServiceEndpoint(
>                    ServiceContractImpl,
>                    new WSHttpBinding(),
>                    ServiceName);
>                ServiceMetadataBehavior httpGetBehaviour =
>                    new ServiceMetadataBehavior();
>                httpGetBehaviour.HttpGetEnabled = true;
>                host.Description.Behaviors.Add(httpGetBehaviour);
>                host.Open();
>                RunningServiceHosts.Add(host);
>            }
>            catch (CommunicationException ce)
>            {
>                host.Abort();
>                throw new Exception("Something Bad Happened", ce);
>            }
>            this.RunningServiceHosts.Add(host);
>        }
>
>        public override void Destroy()
>        {
>            foreach (DefaultServiceHost host in
> this.RunningServiceHosts)
>            {
>                host.Close();
>            }
>            this.RunningServiceHosts.Clear();
>        }
>    }
> [/code]
>
> [b]My Application Configuration[/b]
> [code]
> <?xml version="1.0" encoding="utf-8" ?>
> <configuration>
>  <configSections>
>    <section name="castle"
>
> type="Castle.Windsor.Configuration.AppDomain.CastleSectionHandler,
> Castle.Windsor" />
>  </configSections>
>
>  <castle>
>  <facilities>
>    <!-- NHibernate Active Record Facility -->
>    <facility
>        id="arfacility"
>
> type="Castle.Facilities.ActiveRecordIntegration.ActiveRecordFacility,
> Castle.Facilities.ActiveRecordIntegration"
>        isDebug="true"
>        isWeb="false">
>      <assemblies>
>        <item>jTekPos.Data.Model</item>
>      </assemblies>
>      <config>
>        <add key="connection.driver_class"
> value="NHibernate.Driver.MySqlDataDriver" />
>        <add key="dialect" value="NHibernate.Dialect.MySQLDialect" />
>        <add key="connection.provider"
> value="NHibernate.Connection.DriverConnectionProvider" />
>        <add key="connection.connection_string"
> value="Database=jtekposclientdb;Data Source=localhost;User
> Id=root;Password=mrozio" />
>        <add key="proxyfactory.factory_class"
> value="NHibernate.ByteCode.LinFu.ProxyFactoryFactory,
> NHibernate.ByteCode.LinFu" />
>        <add key="hbm2ddl.keywords" value="none" />
>      </config>
>    </facility>
>
>    <!-- ActiveRecord Automatic Transaction Management -->
>    <facility
>           id="atm"
>
> type="Castle.Facilities.AutomaticTransactionManagement.TransactionFacility,
> Castle.Facilities.AutomaticTransactionManagement" />
>  </facilities>
>  </castle>
> </configuration>
> [/code]
>
> And the remote client I use is basicly the selfgenerated code from
> that svcutil.exe thing.
>
> Sorry for asking you guys for help - But I have been struggling with
> this whole project setup the whole of today and yesterday.
>
> Please if I'm posting in the wrong place - just lemme know.
>
> [/code]
>
> --
>
> You received this message because you are subscribed to the Google Groups 
> "Castle Project Users" group.
> To post to this group, send email to castle-project-us...@googlegroups.com.
> To unsubscribe from this group, send email to 
> castle-project-users+unsubscr...@googlegroups.com.
> For more options, visit this group at 
> http://groups.google.com/group/castle-project-users?hl=en.
>
>
>

--

You received this message because you are subscribed to the Google Groups 
"Castle Project Users" group.
To post to this group, send email to castle-project-us...@googlegroups.com.
To unsubscribe from this group, send email to 
castle-project-users+unsubscr...@googlegroups.com.
For more options, visit this group at 
http://groups.google.com/group/castle-project-users?hl=en.


Reply via email to