Ejemplo n.º 1
0
        /// <summary>
        /// Creates a delegate to clone the specified
        /// </summary>
        /// <returns>Function to clone this data record</returns>
        private static Func <TRecord, TRecord> CreateCloneDelegate()
        {
            // --- Create a dynamic method
            var cloneMethod = new DynamicMethod("CloneFactory" + s_CloneMethods.Count,
                                                typeof(TRecord),
                                                new[] { typeof(TRecord) },
                                                true);
            var il          = cloneMethod.GetILGenerator();
            var metadata    = RecordMetadataManager.GetMetadata <TRecord>();
            var cloneObject = il.DeclareLocal(typeof(TRecord));

            // --- Create an empty clone of TRecord and store it
            il.Emit(OpCodes.Newobj, typeof(TRecord).GetConstructor(BindingFlags.Instance | BindingFlags.Public | BindingFlags.NonPublic,
                                                                   null, Type.EmptyTypes, null));
            il.Emit(OpCodes.Stloc, cloneObject);

            // --- Copy each property value
            foreach (var dataColumn in metadata.DataColumns)
            {
                il.Emit(OpCodes.Ldloc, cloneObject);                           // cloneObject
                il.Emit(OpCodes.Ldarg_0);                                      // cloneObject, origObject
                il.Emit(OpCodes.Call, dataColumn.PropertyInfo.GetGetMethod()); // cloneObject, origObject.dataColumn.Value
                il.Emit(OpCodes.Call, dataColumn.PropertyInfo.GetSetMethod());
            }

            il.Emit(OpCodes.Ldloc, cloneObject);
            il.Emit(OpCodes.Ret);

            // --- Create the delegate
            var cloneDelegate = cloneMethod.CreateDelegate(Expression.GetFuncType(typeof(TRecord), typeof(TRecord)));

            return((Func <TRecord, TRecord>)cloneDelegate);
        }
Ejemplo n.º 2
0
        /// <summary>
        /// Touches all data fields as if those had been modified.
        /// </summary>
        public void TouchAllFields()
        {
            // --- Let's assume this record has already been loaded
            _isLoaded = true;
            var metadata = RecordMetadataManager.GetMetadata <TRecord>();

            foreach (var dataColumn in metadata.DataColumns)
            {
                if (!dataColumn.IsAutoGenerated)
                {
                    _modifiedColumns.Add(dataColumn.ColumnName);
                }
            }
        }
Ejemplo n.º 3
0
        /// <summary>
        /// Merges the changed properties from another object
        /// </summary>
        /// <param name="other">Other data record object</param>
        public void MergeChangesFrom(TRecord other)
        {
            // --- Let's assume this record has already been loaded
            _isLoaded = true;
            var metadata = RecordMetadataManager.GetMetadata <TRecord>();

            foreach (var dataColumn in metadata.DataColumns)
            {
                var propInfo = typeof(TRecord).GetProperty(dataColumn.Name);
                var oldVal   = propInfo.GetValue(this);
                var newVal   = propInfo.GetValue(other);
                if (oldVal == null && newVal != null || oldVal != null && !oldVal.Equals(newVal))
                {
                    propInfo.SetValue(this, newVal);
                }
            }
        }