Пример #1
0
 public void AddRequiredViewField(SPFieldAttribute field)
 {
     CommonHelper.ConfirmNotNull(field, "field");
     if (field.IncludeInQuery || field.IncludeInViewFields)
     {
         requiredViewFields.Add(field.ListFieldInternalName);
         AddInterfaceDepenedentField(field);
         if (this.Parent != null)
         {
             this.Parent.AddRequiredViewField(field);
         }
     }
 }
Пример #2
0
 public void AddInterfaceDepenedentField(SPFieldAttribute field)
 {
     CommonHelper.ConfirmNotNull(field, "field");
     if (IsTwoColumnField(field))
     {
         foreach (SPModelDescriptor d in EnumerableHelper.AncestorsAndSelf(this, v => v.Parent))
         {
             if (!d.fieldAttributes.Contains(field))
             {
                 d.hiddenFields.Add(field);
             }
         }
         foreach (SPModelDescriptor d in EnumerableHelper.Descendants(this, v => v.Children))
         {
             if (!d.fieldAttributes.Contains(field))
             {
                 d.hiddenFields.Add(field);
             }
         }
     }
 }
Пример #3
0
 protected void CheckFieldConsistency(SPModelDescriptor other)
 {
     foreach (SPFieldAttribute definition in fieldAttributes)
     {
         SPFieldAttribute parentDefinition = other.fieldAttributes.FirstOrDefault(v => v.InternalName == definition.InternalName);
         if (parentDefinition != null)
         {
             if (definition.GetType() != parentDefinition.GetType())
             {
                 throw new SPModelProvisionException(String.Format("Definition for field '{0}' in content type '{1}' conflicts with parent content type.", definition.InternalName, contentTypeAttribute.Name));
             }
             foreach (PropertyInfo property in definition.GetType().GetProperties())
             {
                 object myValue = property.GetValue(definition, null);
                 object paValue = property.GetValue(parentDefinition, null);
                 if (!Object.Equals(myValue, paValue))
                 {
                     if (property.PropertyType == typeof(SPOption) && (SPOption)myValue == SPOption.Unspecified)
                     {
                         continue;
                     }
                     if (property.PropertyType == typeof(StringCollection))
                     {
                         StringCollection sourceCollection = (StringCollection)myValue;
                         StringCollection targetCollection = (StringCollection)paValue;
                         if (sourceCollection.Count == targetCollection.Count && !sourceCollection.Cast <string>().Except(targetCollection.Cast <string>()).Any())
                         {
                             continue;
                         }
                     }
                     throw new SPModelProvisionException(String.Format("Definition for field '{0}' in content type '{1}' conflicts with parent content type.", definition.InternalName, contentTypeAttribute.Name));
                 }
             }
         }
     }
 }
Пример #4
0
        internal static Type BuildTypeFromAbstractBaseType(Type baseType)
        {
            Random      random         = new Random();
            string      chars          = "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789";
            string      randomTypeName = String.Concat(baseType.Name, "__", new String(Enumerable.Repeat(chars, 8).Select(s => s[random.Next(s.Length)]).ToArray()));
            TypeBuilder typeBuilder    = ModuleBuilder.DefineType(randomTypeName, TypeAttributes.Public | TypeAttributes.AutoClass | TypeAttributes.AnsiClass | TypeAttributes.BeforeFieldInit, baseType);

            MethodInfo spModelGetAdapterMethod           = typeof(SPModel).GetMethod("get_Adapter", true);
            MethodInfo spModelGetManagerMethod           = typeof(SPModel).GetMethod("get_Manager", true);
            MethodInfo spModelGetParentCollectionMethod  = typeof(SPModel).GetMethod("get_ParentCollection", true);
            MethodInfo ispModelManagerGetTermStoreMethod = typeof(ISPModelManager).GetMethod("get_TermStore");

            foreach (PropertyInfo sourceProperty in baseType.GetProperties(BindingFlags.Public | BindingFlags.NonPublic | BindingFlags.Instance))
            {
                MethodInfo sourceGetter = sourceProperty.GetGetMethod(true);
                MethodInfo sourceSetter = sourceProperty.GetSetMethod(true);
                if ((sourceGetter != null && sourceGetter.IsAbstract) || (sourceSetter != null && sourceSetter.IsAbstract))
                {
                    SPModelFieldAssociationCollection association = SPModelFieldAssociationCollection.GetByMember(sourceProperty);
                    if (!association.Queryable)
                    {
                        continue;
                    }
                    SPFieldAttribute field               = association.Fields.First();
                    MethodInfo       getterMethod        = null;
                    MethodInfo       setterMethod        = null;
                    MethodInfo       postGetterMethod    = null;
                    MethodInfo       preSetterMethod     = null;
                    Type             secondParameterType = null;

                    if (sourceProperty.PropertyType == typeof(bool))
                    {
                        getterMethod = typeof(ISPListItemAdapter).GetMethod("GetBoolean");
                        setterMethod = typeof(ISPListItemAdapter).GetMethod("SetBoolean");
                    }
                    else if (sourceProperty.PropertyType == typeof(int))
                    {
                        getterMethod = typeof(ISPListItemAdapter).GetMethod("GetInteger");
                        setterMethod = typeof(ISPListItemAdapter).GetMethod("SetInteger");
                    }
                    else if (sourceProperty.PropertyType == typeof(double))
                    {
                        getterMethod = typeof(ISPListItemAdapter).GetMethod("GetNumber");
                        setterMethod = typeof(ISPListItemAdapter).GetMethod("SetNumber");
                    }
                    else if (sourceProperty.PropertyType == typeof(string))
                    {
                        if (field.Type == SPFieldType.Lookup)
                        {
                            getterMethod = typeof(ISPListItemAdapter).GetMethod("GetLookupFieldValue");
                            setterMethod = typeof(ISPListItemAdapter).GetMethod("SetLookupFieldValue");
                        }
                        else if (field.Type == SPFieldType.URL)
                        {
                            getterMethod     = typeof(ISPListItemAdapter).GetMethod("GetUrlFieldValue");
                            setterMethod     = typeof(SPExtension).GetMethod("SetUrlFieldValue", new[] { typeof(ISPListItemAdapter), typeof(string), typeof(string) });
                            postGetterMethod = typeof(SPFieldUrlValue).GetProperty("Url").GetGetMethod();
                        }
                        else
                        {
                            getterMethod = typeof(ISPListItemAdapter).GetMethod("GetString");
                            setterMethod = typeof(ISPListItemAdapter).GetMethod("SetString");
                        }
                    }
                    else if (sourceProperty.PropertyType == typeof(Guid))
                    {
                        getterMethod = typeof(ISPListItemAdapter).GetMethod("GetGuid");
                        setterMethod = typeof(ISPListItemAdapter).GetMethod("SetGuid");
                    }
                    else if (sourceProperty.PropertyType == typeof(DateTime?))
                    {
                        getterMethod = typeof(ISPListItemAdapter).GetMethod("GetDateTime");
                        setterMethod = typeof(ISPListItemAdapter).GetMethod("SetDateTime");
                    }
                    else if (sourceProperty.PropertyType == typeof(DateTime))
                    {
                        getterMethod    = typeof(SPExtension).GetMethod("GetDateTimeOrMin");
                        setterMethod    = typeof(ISPListItemAdapter).GetMethod("SetDateTime");
                        preSetterMethod = typeof(DateTime?).GetMethod("op_Implicit");
                    }
                    else if (sourceProperty.PropertyType == typeof(Term))
                    {
                        getterMethod        = typeof(ISPListItemAdapter).GetMethod("GetTaxonomy");
                        setterMethod        = typeof(ISPListItemAdapter).GetMethod("SetTaxonomy");
                        secondParameterType = typeof(TermStore);
                    }
                    else if (sourceProperty.PropertyType == typeof(SPFieldUrlValue))
                    {
                        getterMethod = typeof(ISPListItemAdapter).GetMethod("GetUrlFieldValue");
                        setterMethod = typeof(ISPListItemAdapter).GetMethod("SetUrlFieldValue");
                    }
                    else if (sourceProperty.PropertyType == typeof(SPPrincipal))
                    {
                        getterMethod = typeof(ISPListItemAdapter).GetMethod("GetUserFieldValue");
                        setterMethod = typeof(ISPListItemAdapter).GetMethod("SetUserFieldValue");
                    }
                    else if (sourceProperty.PropertyType.IsOf <Enum>())
                    {
                        getterMethod = typeof(ISPListItemAdapter).GetMethod("GetEnum").MakeGenericMethod(sourceProperty.PropertyType);
                        setterMethod = typeof(ISPListItemAdapter).GetMethod("SetEnum").MakeGenericMethod(sourceProperty.PropertyType);
                    }
                    else if (sourceProperty.PropertyType.IsOf <SPModel>())
                    {
                        getterMethod        = typeof(ISPListItemAdapter).GetMethod("GetModel").MakeGenericMethod(sourceProperty.PropertyType);
                        setterMethod        = typeof(ISPListItemAdapter).GetMethod("SetModel").MakeGenericMethod(sourceProperty.PropertyType);
                        secondParameterType = typeof(SPModelCollection);
                    }
                    else
                    {
                        Type elementType;
                        if (sourceProperty.PropertyType.IsOf(typeof(IEnumerable <>), out elementType))
                        {
                            bool isReadOnly = sourceProperty.PropertyType.IsOf(typeof(ReadOnlyCollection <>));
                            if (elementType == typeof(Term))
                            {
                                getterMethod        = typeof(ISPListItemAdapter).GetMethod(isReadOnly ? "GetTaxonomyMultiReadOnly" : "GetTaxonomyMulti");
                                secondParameterType = typeof(TermStore);
                            }
                            else if (elementType == typeof(SPPrincipal))
                            {
                                getterMethod = typeof(ISPListItemAdapter).GetMethod(isReadOnly ? "GetMultiUserFieldValueReadOnly" : "GetMultiUserFieldValue");
                            }
                            else if (elementType == typeof(string))
                            {
                                if (field.Type == SPFieldType.MultiChoice)
                                {
                                    getterMethod = typeof(ISPListItemAdapter).GetMethod(isReadOnly ? "GetMultiChoiceFieldValueReadOnly" : "GetMultiChoiceFieldValue");
                                }
                                else
                                {
                                    getterMethod = typeof(ISPListItemAdapter).GetMethod(isReadOnly ? "GetMultiLookupFieldValueReadOnly" : "GetMultiLookupFieldValue");
                                }
                            }
                            else
                            {
                                try {
                                    SPModelDescriptor.Resolve(elementType);
                                    getterMethod        = typeof(ISPListItemAdapter).GetMethod(isReadOnly ? "GetModelCollectionReadOnly" : "GetModelCollection").MakeGenericMethod(elementType);
                                    secondParameterType = typeof(SPModelCollection);
                                } catch (ArgumentException) { }
                            }
                            if (sourceSetter != null)
                            {
                                throw new InvalidOperationException("Collection property cannot have setter.");
                            }
                        }
                    }
                    if ((sourceGetter != null && getterMethod == null) || (sourceSetter != null && setterMethod == null))
                    {
                        throw new InvalidOperationException(String.Format("Unable to find suitable method for '{0}.{1}'.", baseType.Name, sourceProperty.Name));
                    }

                    PropertyBuilder property = typeBuilder.DefineProperty(sourceProperty.Name, PropertyAttributes.HasDefault, sourceProperty.PropertyType, null);
                    if (sourceGetter != null)
                    {
                        MethodBuilder propertyGetter   = typeBuilder.DefineMethod(sourceGetter.Name, GetMethodVisibility(sourceGetter) | MethodAttributes.ReuseSlot | MethodAttributes.Virtual | MethodAttributes.SpecialName | MethodAttributes.HideBySig, sourceProperty.PropertyType, Type.EmptyTypes);
                        ILGenerator   propertyGetterIL = propertyGetter.GetILGenerator();
                        propertyGetterIL.Emit(OpCodes.Ldarg_0);
                        propertyGetterIL.Emit(OpCodes.Call, spModelGetAdapterMethod);
                        propertyGetterIL.Emit(OpCodes.Ldstr, field.InternalName);
                        if (secondParameterType != null)
                        {
                            if (secondParameterType == typeof(TermStore))
                            {
                                propertyGetterIL.Emit(OpCodes.Ldarg_0);
                                propertyGetterIL.Emit(OpCodes.Call, spModelGetManagerMethod);
                                propertyGetterIL.Emit(OpCodes.Callvirt, ispModelManagerGetTermStoreMethod);
                            }
                            else if (secondParameterType == typeof(SPModelCollection))
                            {
                                propertyGetterIL.Emit(OpCodes.Ldarg_0);
                                propertyGetterIL.Emit(OpCodes.Call, spModelGetParentCollectionMethod);
                            }
                            else
                            {
                                throw new NotSupportedException();
                            }
                        }
                        if (getterMethod.DeclaringType.IsInterface || getterMethod.IsAbstract)
                        {
                            propertyGetterIL.Emit(OpCodes.Callvirt, getterMethod);
                        }
                        else
                        {
                            propertyGetterIL.Emit(OpCodes.Call, getterMethod);
                        }
                        if (postGetterMethod != null)
                        {
                            propertyGetterIL.Emit(OpCodes.Call, postGetterMethod);
                        }
                        propertyGetterIL.Emit(OpCodes.Ret);
                        property.SetGetMethod(propertyGetter);
                    }
                    if (sourceSetter != null)
                    {
                        MethodBuilder propertySetter   = typeBuilder.DefineMethod(sourceSetter.Name, GetMethodVisibility(sourceSetter) | MethodAttributes.ReuseSlot | MethodAttributes.Virtual | MethodAttributes.SpecialName | MethodAttributes.HideBySig, null, new Type[] { sourceProperty.PropertyType });
                        ILGenerator   propertySetterIL = propertySetter.GetILGenerator();
                        propertySetterIL.Emit(OpCodes.Ldarg_0);
                        propertySetterIL.Emit(OpCodes.Call, spModelGetAdapterMethod);
                        propertySetterIL.Emit(OpCodes.Ldstr, field.InternalName);
                        propertySetterIL.Emit(OpCodes.Ldarg_1);
                        if (preSetterMethod != null)
                        {
                            propertySetterIL.Emit(OpCodes.Call, preSetterMethod);
                        }
                        if (setterMethod.DeclaringType.IsInterface || setterMethod.IsAbstract)
                        {
                            propertySetterIL.Emit(OpCodes.Callvirt, setterMethod);
                        }
                        else
                        {
                            propertySetterIL.Emit(OpCodes.Call, setterMethod);
                        }
                        propertySetterIL.Emit(OpCodes.Nop);
                        propertySetterIL.Emit(OpCodes.Ret);
                        property.SetSetMethod(propertySetter);
                    }
                }
            }
            return(typeBuilder.CreateType());
        }
Пример #5
0
 private static bool IsTwoColumnField(SPFieldAttribute field)
 {
     return(field.Type == SPFieldType.Lookup || field.Type == SPFieldType.User || field.Type == SPFieldType.URL);
 }
Пример #6
0
        private SPModelDescriptor(Type targetType, SPModelDefaultsAttribute defaultsAttribute)
        {
            this.ModelType = targetType;
            TargetTypeDictionary.TryAdd(targetType, this);
            TargetTypeDictionary.TryGetValue(targetType.BaseType, out this.Parent);
            if (this.Parent is SPModelInterfaceTypeDescriptor)
            {
                this.Parent = null;
            }

            this.contentTypeAttribute = targetType.GetCustomAttribute <SPContentTypeAttribute>(false);
            ResolveContentTypeId(contentTypeAttribute, targetType);
            ContentTypeDictionary.Add(contentTypeAttribute.ContentTypeId, this);

            this.defaultManagerType         = GetDefaultManagerType(targetType);
            this.provisionEventReceiverType = contentTypeAttribute.ProvisionEventReceiverType;
            this.hasExplicitListAttribute   = targetType.GetCustomAttribute <SPListAttribute>(false) != null;
            this.listAttribute   = targetType.GetCustomAttribute <SPListAttribute>(true) ?? new SPListAttribute();
            this.fieldAttributes = SPModelFieldAssociationCollection.EnumerateFieldAttributes(this, targetType).ToArray();

            if (contentTypeAttribute.Group == null && defaultsAttribute != null)
            {
                contentTypeAttribute.Group = defaultsAttribute.DefaultContentTypeGroup;
            }
            foreach (SPFieldAttribute attribute in fieldAttributes)
            {
                if (attribute.Group == null)
                {
                    if (this.Parent != null)
                    {
                        SPFieldAttribute baseAttribute = this.Parent.fieldAttributes.FirstOrDefault(v => v.InternalName == attribute.InternalName);
                        if (baseAttribute != null)
                        {
                            attribute.Group = baseAttribute.Group;
                            continue;
                        }
                    }
                    if (defaultsAttribute != null)
                    {
                        attribute.Group = defaultsAttribute.DefaultFieldGroup;
                    }
                }
            }

            if (contentTypeAttribute.ContentTypeId.IsChildOf(ContentTypeId.Page))
            {
                this.ItemType = SPModelItemType.PublishingPage;
            }
            else if (contentTypeAttribute.ContentTypeId.IsChildOf(SPBuiltInContentTypeId.DocumentSet))
            {
                this.ItemType = SPModelItemType.DocumentSet;
            }
            else if (contentTypeAttribute.ContentTypeId.IsChildOf(SPBuiltInContentTypeId.Folder))
            {
                this.ItemType = SPModelItemType.Folder;
            }
            else if (contentTypeAttribute.ContentTypeId.IsChildOf(SPBuiltInContentTypeId.Document))
            {
                this.ItemType = SPModelItemType.File;
            }

            if (this.ItemType == SPModelItemType.GenericItem)
            {
                this.baseType = SPBaseType.GenericList;
            }
            else if (contentTypeAttribute.ContentTypeId.IsChildOf(SPBuiltInContentTypeId.Issue))
            {
                this.baseType = SPBaseType.Issue;
            }
            else
            {
                this.baseType = SPBaseType.DocumentLibrary;
            }

            if (this.Parent != null)
            {
                this.Parent.Children.Add(this);
                this.fieldAttributes = fieldAttributes.Concat(this.Parent.fieldAttributes).Distinct().ToArray();
                if (provisionEventReceiverType == null)
                {
                    this.provisionEventReceiverType = this.Parent.provisionEventReceiverType;
                }
            }

            foreach (SPFieldAttribute v in fieldAttributes)
            {
                AddRequiredViewField(v);
            }
            foreach (Type interfaceType in targetType.GetInterfaces())
            {
                if (!interfaceType.IsDefined(typeof(SPModelIgnoreAttribute), true))
                {
                    SPModelInterfaceTypeDescriptor interfaceDescriptor = (SPModelInterfaceTypeDescriptor)TargetTypeDictionary.EnsureKeyValue(interfaceType, SPModelInterfaceTypeDescriptor.Create);
                    interfaceDescriptor.AddImplementedType(this);
                    this.Interfaces.Add(interfaceDescriptor);
                }
            }
            if (targetType.BaseType != typeof(SPModel) && targetType.BaseType.GetCustomAttribute <SPContentTypeAttribute>(false) == null)
            {
                SPModelInterfaceTypeDescriptor interfaceDescriptor = (SPModelInterfaceTypeDescriptor)TargetTypeDictionary.EnsureKeyValue(targetType.BaseType, SPModelInterfaceTypeDescriptor.Create);
                interfaceDescriptor.AddImplementedType(this);
                this.Interfaces.Add(interfaceDescriptor);
            }
            if (!targetType.IsAbstract)
            {
                instanceType = new Lazy <Type>(() => targetType);
            }
            else
            {
                instanceType = new Lazy <Type>(() => SPModel.BuildTypeFromAbstractBaseType(targetType), LazyThreadSafetyMode.ExecutionAndPublication);
            }
        }