예제 #1
0
파일: Module.cs 프로젝트: xafdelta/xafdelta
 internal bool DoBeforeLoadRecord(LoadRecordArgs e)
 {
     var handler = BeforeLoadRecord;
     if (handler != null) handler(this, e);
     return e.Done;
 }
        /// <summary>
        /// Loads the package record.
        /// </summary>
        /// <param name="context">The context.</param>
        private void loadPackageRecord(LoadPackageRecordContext context)
        {
            var args = new LoadRecordArgs(context);
            var objectSpace = getPlaybackObjectSpace(context.PackageSession, context.ActiveObjectSpaces);
            if (!Owner.DoBeforeLoadRecord(args))
            {
                var operationType =
                    (ProtocolEventType) Enum.Parse(typeof (ProtocolEventType), context.PackageRecord.OperationType);

                if (operationType == ProtocolEventType.CommitSession)
                {
                    commitObjectSpaceOnLoad(objectSpace, context.ActiveObjectSpaces);
                }
                else
                {
                    var senderNodeId = context.Package.SenderNodeId;
                    var targetObject = OidMap.FindApplicationObject(objectSpace,
                                                                    context.PackageRecord.AuditedObject, senderNodeId);

                    ITypeInfo targetTypeInfo = null;
                    if (targetObject != null)
                        targetTypeInfo = objectSpace.TypesInfo.FindTypeInfo(targetObject.GetType());

                    XPMemberInfo memberInfo = null;
                    var propertyIsEmpty = string.IsNullOrEmpty(context.PackageRecord.PropertyName);
                    if (!propertyIsEmpty && targetObject != null && targetTypeInfo != null)
                    {
                        memberInfo = ((ISessionProvider)targetObject).Session.GetClassInfo(targetObject)
                            .GetMember(context.PackageRecord.PropertyName);
                    }

                    bool oldObjectShouldExists;
                    var oldObject = restoreObjectFromRef(objectSpace, senderNodeId,
                                                         context.PackageRecord.OldObject, out oldObjectShouldExists);

                    bool newObjectShouldExists;
                    var newObject = restoreObjectFromRef(objectSpace, senderNodeId,
                                                         context.PackageRecord.NewObject, out newObjectShouldExists);

                    // collision resolving
                    var replres = resolveCollisions(context, oldObject, newObjectShouldExists,
                                                    newObject, operationType, oldObjectShouldExists, targetObject,
                                                    memberInfo, propertyIsEmpty);

                    if (replres == CollisionResult.Default)
                    {
                        switch (operationType)
                        {
                            case ProtocolEventType.MethodCall:
                                if(targetObject != null)
                                {
                                    if (targetTypeInfo != null)
                                    {
                                        var classType = targetTypeInfo.Type;
                                        if (context.PackageRecord != null
                                            && !string.IsNullOrEmpty(context.PackageRecord.PropertyName))
                                        {
                                            var callParameters = (MethodCallParams)oldObject;

                                            var methodInfo = (from m in classType.GetMethods()
                                                              where m.Name == context.PackageRecord.PropertyName
                                                              && m.GetParameters().Count() == callParameters.MethodParamValues.Count
                                                              select m).FirstOrDefault();

                                            if (methodInfo != null)
                                            {
                                                var paramValues = callParameters.GetParamValues();
                                                methodInfo.Invoke(targetObject, paramValues);
                                            }
                                        }
                                    }
                                }
                                break;

                            case ProtocolEventType.AddedToCollection:
                                if (memberInfo != null && memberInfo.IsAssociationList && oldObject != null)
                                {
                                    var collObj = memberInfo.GetValue(targetObject);
                                    if (collObj != null)
                                    {
                                        if(collObj.GetType().GetInterface("IList") != null)
                                        {
                                            var list = (IList) collObj;
                                            if(!list.Contains(oldObject))
                                                list.Add(oldObject);
                                        }
                                    }
                                }
                                break;

                            case ProtocolEventType.AggregatedObjectChanged:
                                break;

                            case ProtocolEventType.CollectionObjectChanged:
                                break;

                            case ProtocolEventType.InitialValueAssigned:
                            case ProtocolEventType.ObjectChanged:
                                if (memberInfo != null)
                                {
                                    object newValue = null;
                                    if (context.PackageRecord.NewBlobValue != null)
                                    {
                                        newValue = ValueTransform.RestoreFromBlob(context.PackageRecord.NewBlobValue);
                                    }
                                    else
                                    {
                                        // NewBlobValue is empty - restore value from context.PackageRecord.NewValue
                                        if (context.PackageRecord.NewValue != null)
                                        {
                                            if (memberInfo.ReferenceType == null)
                                            {
                                                if (!string.IsNullOrEmpty(context.PackageRecord.NewValue))
                                                    newValue = ValueTransform.StringToObject(context.PackageRecord.NewValue,
                                                        memberInfo.MemberType);
                                                else
                                                    newValue = memberInfo.MemberType.IsValueType ?
                                                        Activator.CreateInstance(memberInfo.MemberType) : null;
                                            }
                                            else
                                                newValue = newObject;
                                        }
                                    }

                                    // replace aggregated members initialization with oidmap redirection
                                    if (operationType == ProtocolEventType.InitialValueAssigned
                                        && memberInfo.IsAggregated && !memberInfo.IsAssociationList && newValue != null)
                                    {
                                        var oldAggregatedObj = memberInfo.GetValue(targetObject);
                                        if (oldAggregatedObj != null)
                                        {
                                            var mapItem = OidMap.GetOidMap(newValue, context.Package.SenderNodeId);
                                            if (mapItem != null)
                                            {
                                                // redirect aggregated object reference to oldAggregatedObj
                                                if (mapItem.Target == null)
                                                    mapItem.NewObject = oldAggregatedObj;
                                                else
                                                    mapItem.Target.Target = oldAggregatedObj;
                                            }
                                        }
                                        else
                                            memberInfo.SetValue(targetObject, newValue);
                                    }

                                    // skip object initialization for objects already exists in app database
                                    if (operationType == ProtocolEventType.InitialValueAssigned
                                        && !((ISessionProvider)targetObject).Session.IsNewObject(targetObject))
                                        break;

                                    memberInfo.SetValue(targetObject, newValue);
                                }
                                break;

                            case ProtocolEventType.ObjectCreated:
                                if (targetObject == null)
                                {
                                    var reference = context.PackageRecord.AuditedObject;
                                    var className = reference.ClassName;
                                    var classType = objectSpace.TypesInfo.FindTypeInfo(className).Type;

                                    targetObject = objectSpace.CreateObject(classType);
                                    OidMap.CreateOidMap(objectSpace, reference, senderNodeId, targetObject);
                                }
                                break;

                            case ProtocolEventType.ObjectDeleted:
                                if (targetObject != null)
                                    objectSpace.Delete(targetObject);
                                break;

                            case ProtocolEventType.RemovedFromCollection:
                                if (memberInfo != null && memberInfo.IsAssociationList && oldObject != null)
                                {
                                    var collObj = memberInfo.GetValue(targetObject);
                                    if (collObj != null)
                                    {
                                        if(collObj is XPBaseCollection)
                                        {
                                            var collection = (XPBaseCollection) collObj;
                                            if (collection.Cast<object>().Contains(oldObject))
                                                collection.BaseRemove(oldObject);
                                        }
                                        else if(collObj.GetType().GetInterface("IList") != null)
                                        {
                                            var list = (IList) collObj;
                                            if(list.Contains(oldObject))
                                                list.Remove(oldObject);
                                        }
                                    }
                                }
                                break;
                        }
                    }
                }
            }

            Owner.DoAfterLoadRecord(args);
        }
예제 #3
0
파일: Module.cs 프로젝트: xafdelta/xafdelta
 internal void DoAfterLoadRecord(LoadRecordArgs e)
 {
     var handler = AfterLoadRecord;
     if (handler != null) handler(this, e);
 }