Exemplo n.º 1
0
            private static bool IsProjectionPath(MemberExpression m)
            {
                while (m.Expression is MemberExpression)
                {
                    m = (MemberExpression)m.Expression;
                }

                PropertyDescriptor pd         = TypeDescriptor.GetProperties(m.Member.DeclaringType)[m.Member.Name];
                IncludeAttribute   includeAtt = (IncludeAttribute)pd.Attributes[typeof(IncludeAttribute)];

                return(includeAtt != null && includeAtt.IsProjection);
            }
        /// <summary>
        /// Called to attempt to resolve unresolved member references during query deserialization.
        /// </summary>
        /// <param name="type">The Type the member is expected on.</param>
        /// <param name="member">The member name.</param>
        /// <param name="instance">The instance to form the MemberExpression on.</param>
        /// <returns>A MemberExpression if the member can be resolved, null otherwise.</returns>
        public override MemberExpression ResolveMember(Type type, string member, Expression instance)
        {
            MemberExpression mex = null;
            IDictionary <PropertyDescriptor, IncludeAttribute[]> entityIncludeMap = MetaType.GetMetaType(type).ProjectionMemberMap;

            if (entityIncludeMap.Any())
            {
                // Do a reverse lookup in the include map for the type, looking
                // for the source of the member (if present)
                PropertyDescriptor pd         = null;
                IncludeAttribute   projection = null;
                foreach (var entry in entityIncludeMap)
                {
                    projection = entry.Value.SingleOrDefault(p => p.IsProjection && p.MemberName == member);
                    if (projection != null)
                    {
                        pd = entry.Key;
                        break;
                    }
                }

                if (projection == null)
                {
                    return(null);
                }

                // Found the source projection. Form the corresponding MemberExpression
                // for the projection path
                string[]   pathMembers = projection.Path.Split('.');
                Type       currType    = type;
                MemberInfo memberInfo  = currType.GetMember(pd.Name).Single();
                mex = Expression.MakeMemberAccess(instance, memberInfo);
                foreach (string pathMember in pathMembers)
                {
                    currType   = mex.Type;
                    memberInfo = currType.GetMember(pathMember).Single();
                    mex        = Expression.MakeMemberAccess(mex, memberInfo);
                }
            }

            return(mex);
        }
Exemplo n.º 3
0
        public void ConstructorTest()
        {
            var includeAttribute = new IncludeAttribute();

            Assert.IsNotNull(includeAttribute);
        }
        protected virtual IEnumerable <Attribute> GetEntityMemberAttributes(PropertyDescriptor propertyDescriptor)
        {
            if (_classMetadata == null)
            {
                return(null);
            }
            var attributes = new List <Attribute>();

            //KeyAttributes
            if (_classMetadata.Identifier != null)
            {
                foreach (Column id in _identifierCols)
                {
                    if (id.Name == propertyDescriptor.Name)
                    {
                        if (propertyDescriptor.Attributes[typeof(KeyAttribute)] == null)
                        {
                            attributes.Add(new KeyAttribute());
                        }
                        if (propertyDescriptor.Attributes[typeof(EditableAttribute)] == null)
                        {
                            //An identifier is not editable, sometimes anyway it allow an initial value
                            var editable = new EditableAttribute(false);
                            if (id.Value is SimpleValue)
                            {
                                editable.AllowInitialValue =
                                    "assigned".Equals(((SimpleValue)id.Value).IdentifierGeneratorStrategy,
                                                      StringComparison.InvariantCultureIgnoreCase);
                            }
                            attributes.Add(editable);
                        }
                        break;
                    }
                }
            }
            Property member = _classMetadata.PropertyIterator.FirstOrDefault(x => x.Name == propertyDescriptor.Name);

            if (member == null)             //If ther's no mapping in nhibernate...
            {
                return(attributes);
            }
            //Required
            if ((!member.IsNullable) &&
                (propertyDescriptor.PropertyType.IsValueType &&
                 (propertyDescriptor.Attributes[typeof(RequiredAttribute)] == null)))
            {
                attributes.Add(new RequiredAttribute());
            }
            //Association
            if (member.Type.IsAssociationType &&
                (propertyDescriptor.Attributes[typeof(AssociationAttribute)] == null))
            {
                string name;
                string thisKey  = "";
                string otherkey = "";
                if (member.Type.IsCollectionType)
                {
                    name = propertyDescriptor.ComponentType.FullName + "_" + member.Name;

                    if (member.Type.ReturnedClass.GetGenericArguments().Length != 1)
                    {
                        throw new Exception(
                                  String.Format(
                                      "The property {0} is not a generic collection as expected (like IList<T>)...",
                                      member.Name));
                    }
                    Type targetClassType = member.Type.ReturnedClass.GetGenericArguments()[0];

                    foreach (Column col in _identifierCols)
                    {
                        thisKey += (thisKey != "" ? ", " : "") + col.Name;

                        //*****Naming convention****
                        //Here I'm assuming that the name of each field in the type that holds the foreign key observe
                        //the following structure:

                        string field = member.Name.Replace(Inflector.Pluralize(targetClassType.Name), "") +
                                       propertyDescriptor.ComponentType.Name + "_" + col.Name;

                        otherkey += (otherkey != "" ? ", " : "") + field;

                        if (targetClassType.GetProperties(BindingFlags.Public | BindingFlags.Instance).SingleOrDefault(x => x.Name == field) == null)
                        {
                            throw new Exception(String.Format("The class {0} doesn't contain a Property named {1}",
                                                              targetClassType.Name, field));
                        }
                    }
                }
                else //Member is a class type
                {
                    //Key could be composite, cycle every identifier on "the other side"
                    PersistentClass otherMappingClass = _nhibernateConfiguration.GetClassMapping(member.Type.ReturnedClass);
                    foreach (Column col in otherMappingClass.Key.ColumnIterator)
                    {
                        //Naming Convention:
                        //The name of each foreign key field be MUST BE the name of the class field + "_" + the name of the key field in the targetclass
                        thisKey  += (thisKey != "" ? ", " : "") + member.Name + "_" + col.Name;
                        otherkey += (otherkey != "" ? ", " : "") + col.Name;
                    }

                    //Check: this name MUST ALWAYS BE the same on the both side of a bi-directional association
                    name = member.Type.ReturnedClass.FullName
                           + "_" + Inflector.Pluralize(member.PersistentClass.NodeName);
                }

                //CHECK: When do you want to add an IncludeAttribute ?
                if (!_classMetadata.IsLazy)
                {
                    var incAttr = new IncludeAttribute();
                    attributes.Add(incAttr);
                }

                var attribute = new AssociationAttribute(
                    name,
                    thisKey,
                    otherkey
                    );
                Type fromParent = ForeignKeyDirection.ForeignKeyFromParent.GetType();
                attribute.IsForeignKey =
                    fromParent.IsInstanceOfType(((IAssociationType)member.Type).ForeignKeyDirection);
                attributes.Add(attribute);
            }
            //RoundtripOriginal
            if (member == _classMetadata.Version)
            {
                attributes.Add(new RoundtripOriginalAttribute());
            }
            return(attributes.ToArray());
        }