Exemplo n.º 1
0
      private static bool _structuralEquals(this BplObject object1, BplObject object2, HashSet<BplObject> visited) {
         // assumption: object1 != object2
         if (object1 == null || object2 == null) return false;
         if (object1.Class != object2.Class) return false;

         var flag = true;
         visited.Add(object1);
         foreach (var prop in object1.Class.Properties.Where(p => !p.IsCalculated)) {
            if (prop.IsPrimitive) {
               flag = Object.Equals(prop.GetValue(object1), prop.GetValue(object2));
            } else {
               var refs1 = prop.GetReferences(object1).ToArray();
               var refs2 = prop.GetReferences(object2).ToArray();
               flag = (refs1.Length == refs2.Length);
               for (var j = 0; flag && j < refs1.Length; j++) {
                  var r1 = refs1[j];
                  var r2 = refs2[j];
                  if (r1 != r2 && !visited.Contains(r1)) {
                     flag = _structuralEquals(r1, r2, visited);
                  }
               }
            }
            if (!flag) break;
         }
         visited.Remove(object1);
         return flag;
      }
Exemplo n.º 2
0
      /// <summary>Formats the input BPL object into the output XML document.</summary>
      public override bool Format(BplObject input) {
         if (!PrepareFormatter(input)) return false;

         try {
            OutputXml = new XDocument {
               Declaration = new XDeclaration("1.0", "UTF-8", "yes")
            };
            _serializeObject(OutputXml, Input, null);
            NSMapping.Write(OutputXml.Root);
         } catch (Exception e) {
            AddException(e);
         }

         if (Success) {
            try {
               using (var strWriter = new Utf8StringWriter(CultureInfo.InvariantCulture)) {
                  using (var xmlWriter = XmlWriter.Create(strWriter, _getWriterSettings())) {
                     OutputXml.Save(xmlWriter);
                  }
                  Output = strWriter.ToString();
               }
            } catch (Exception e) {
               AddException(e);
            }
         }

         if (!Success) {
            Output = null;
            OutputXml = null;
         }

         return Success;
      }
Exemplo n.º 3
0
 /// <summary>Adds a target object and indexes it under the specified id.</summary>
 /// <returns><c>true</c> if the target was successfully added; <c>false</c> if an object with the specified id already exists.</returns>
 public bool AddTarget(BplIdentity targetId, BplObject target) {
    if (_targets.ContainsKey(targetId)) {
       return false;
    } else {
       _targets[targetId] = target;
       return true;
    }
 }
Exemplo n.º 4
0
 private bool _inScope(BplObject target) {
    if (_closure.Contains(target)) return true;
    if (target is BplContextNode) {
       var parent = ((BplContextNode)target).Parent;
       if (parent != null && _inScope(parent)) {
          _closure.Add(target);
          return true;
       }
    }
    return false;
 }
Exemplo n.º 5
0
      /// <summary>Formats the input BPL object into the output XML document.</summary>
      public override bool Format(BplObject input) {
         if (!PrepareFormatter(input)) return false;

         try {
            var writer = new BplBinaryWriter();
            writer.Serialize(input);
            Output = _toHexString(writer.ToByteArray());
         } catch (Exception e) {
            AddException(e);
         }

         return Success;
      }
Exemplo n.º 6
0
 /// <summary>Creates a new <see cref="BplObjectProxy"/> instance that wraps the given BPL object.</summary>
 /// <param name="source">The source BPL object on the debuggee-side.</param>
 protected BplObjectProxy(BplObject source) : this() {
    BplClass = source.Class.Name;
    BplNamespace = source.Class.Namespace.Name;
    IsEmpty = !source.Children.Any();
    if (IsEmpty) {
       IsLoaded = true;
    } else {
       Nodes.Add(new TreeNode());
    }
    var nameProperty = source.Class.GetProperty("Name");
    if (nameProperty != null) {
       NameProperty = nameProperty.GetValue(source) as string;
    }
    Text = BplClass;
 }
Exemplo n.º 7
0
      /// <summary>Formats the input BPL object into the output XML document.</summary>
      public override bool Format(BplObject input) {
         if (!PrepareFormatter(input)) return false;

         _output = new TextBuffer(this);
         try {
            _serializeObject(null, Input);
            _injectMapping(NSMapping);
            Output = _output.ToString();
         } catch (Exception e) {
            AddException(e);
         }
         _output = null;

         return Success;
      }
Exemplo n.º 8
0
      private bool _isEqual(BplObject o1, BplObject o2) {
         var w1 = new BplBinaryWriter();
         w1.Serialize(o1);
         var b1 = w1.ToByteArray();

         var w2 = new BplBinaryWriter();
         w2.Serialize(o2);
         var b2 = w2.ToByteArray();

         if (b1.Length != b2.Length) {
            return false;
         }

         for (var i = 0; i < b1.Length; i++) {
            if (b1[i] != b2[i]) {
               return false;
            }
         }

         return true;
      }
Exemplo n.º 9
0
      /// <summary>Creates a new <see cref="BplTrigger"/> instance.</summary>
      protected BplTrigger(BplObject source, string path, BplTriggerHandler handler) {
         PathString = path;
         var pathStrings = PathString.Split(@"\s*\;\s*");
         var pathCollection = new List<BplPropertyPath>();
         for (var i = 0; i < pathStrings.Length; i++) {
            pathCollection.Add(new BplPropertyPath(pathStrings[i].Trim()));
         }
         PathCollection = new ReadOnlyCollection<BplPropertyPath>(pathCollection);
         if (PathCollection.Count == 0) {
            BplRuntimeException.Throw("Path string is empty");
         }

         Source = source;

         TargetMethod = handler.Method;
         var targetObject = handler.Target;
         if (targetObject != null) {
            _targetObject = new WeakReference(targetObject);
            _isInstanceHandler = true;
         }

      }
Exemplo n.º 10
0
      /// <summary>Validates the target object and if there are no errors converts it to a string reference. The target object must 
      /// have a valid and non-empty identity property, and must be contained at some level under the root object.</summary>
      public string ToReference(BplObject target, BplProperty property) {
         var targetEntity = target as BplEntity;
         if (target == null) {
            BplRuntimeException.Throw("Association target is invalid or missing.");
         }
         
         var targetId = targetEntity.Id;
         if (targetId.IsEmpty) {
            BplRuntimeException.Throw("Association target {0} has no Id.", target);
         }

         bool? flag = null;
         if (CustomVerifier != null) {
            flag = CustomVerifier(target);
         }
         if (!flag.HasValue) {
            flag = (target.IsA<BplTaxonomy>() || _inScope(target));
         }
         if (!flag.Value) {
            BplRuntimeException.Throw("Association target {0} is out of serialization scope. It must be either contained in {1} or be a taxonomy.".Substitute(target, Root));
         }
         return targetId.ToString(property.ReferencedClass.IdentityScope);
      }
Exemplo n.º 11
0
 private void _deserializeAssociation(BplObject bplObject, BplProperty property, XAttribute target) {
    _resolver.AddSource(target.Value, bplObject, property);
 }
Exemplo n.º 12
0
 private void _deserializeContainer(BplObject bplObject, BplProperty property, XElement[] children) {
    var collection = property.GetValue(bplObject) as IBplCollection;
    for (var i = 0; i < children.Length; i++) {
       var childObject = _deserializeObject(children[i]);
       if (childObject != null) {
          collection.Add(childObject);
       }
    }
 }
Exemplo n.º 13
0
 private void _deserializeContainer(BplObject bplObject, BplProperty property, XElement child) {
    var childObject = _deserializeObject(child);
    if (childObject != null) {
       property.SetValue(bplObject, childObject);
    }
 }
Exemplo n.º 14
0
 private void _deserializeArray(BplObject bplObject, BplProperty property, XElement[] children) {
    var arrayValues = new object[children.Length];
    var arrayConverter = BplLanguage.XmlConverters[property];
    var itemConverter = BplLanguage.XmlConverters[property.PrimitiveItemType];
    var itemTag = XNamespaces.none + property.PrimitiveItemType.TagName.LocalName;
    for (var i = 0; i < children.Length; i++) {
       var child = children[i];
       try {
          if (child.Name != itemTag) {
             throw new Exception("Expected tag name '{0}'".Substitute(itemTag));
          }
          arrayValues[i] = _parseScalar(property, itemConverter, child);
       } catch (Exception e) {
          AddError("Invalid value in BPL property '{0}[{1}]', {:where}. {2}", property.Name, i, e.Message, child);
       }
    }
    if (arrayConverter is BplArrayConverter) {
       var array = ((BplArrayConverter)arrayConverter).CreateInstance(null, arrayValues);
       property.SetValue(bplObject, array);
    } else {
       AddError("Could not instantiate BPL array property '{0}'", property.Name);
    }
 }
Exemplo n.º 15
0
 private void _deserializeArray(BplObject bplObject, BplProperty property, XAttribute attr) {
    try {
       var value = BplLanguage.XmlConverters[property].Parse(attr.Value);
       property.SetValue(bplObject, value);
    } catch (Exception e) {
       AddError("Invalid value in BPL property '{:name}', {:where}. {0}", e.Message, attr);
    }
 }
Exemplo n.º 16
0
 // serializes an association (singleton)
 private void _serializeAssociation(XElement element, BplProperty property, BplObject bplObject) {
    if (bplObject != null) {
       try {
          element.Add(new XAttribute(property.TagName, Verifier.ToReference(bplObject, property)));
       } catch (BplRuntimeException e) {
          AddException(e);
       }
    }
 }
Exemplo n.º 17
0
 /// <summary>Throws a <see cref="BplRuntimeException"/> with the given parameters.</summary>
 public static void Throw(string message, BplObject sourceObject) {
    var formattedMessage = Assumption.TidyMessage(message.Substitute(sourceObject));
    throw new BplRuntimeException(formattedMessage, null, sourceObject, null);
 }
Exemplo n.º 18
0
 /// <summary>Tests the visualizer (see remarks at the head of this class).</summary>
 public static void TestVisualizer(BplObject source) {
    var dbg = new VisualizerDevelopmentHost(source, typeof(BplDebuggerVisualizer), typeof(BplDebuggeeObjectSource));
    dbg.ShowVisualizer();
 }
Exemplo n.º 19
0
 /// <summary>Creates a new <see cref="BplItemReplaced"/> instance.</summary>
 internal BplItemReplaced(BplObject source, BplProperty property, int index, BplContextNode oldItem, BplContextNode newItem)
    : base(source, property) {
    Index = index;
    OldItem = oldItem;
    NewItem = newItem;
 }
Exemplo n.º 20
0
      /// <summary>Dettaches this node from the specified source object.</summary>
      internal void DetachFrom(BplObject source, BplProperty property) {
         if (source == null || property == null) {
            BplRuntimeException.Throw("Source object or property are missing");
         }
         if (source.IsSealed) {
            BplRuntimeException.Throw("Node cannot be detached from a sealed object");
         }

         var isEntity = (this is BplEntity);
         var isTaxonomy = (this is BplTaxonomy);
         if ((source is BplTaxonomy) && !isTaxonomy) {
            BplRuntimeException.Throw("'{0}' cannot be referenced from a taxonomy", this);
         }

         if (property.IsContainer) {

            // property is a container, so we need to reparent the node

            if (Parent != source || ParentContainer != property) {
               // this happens when the node has been attached to another container
               return;
            } else {
               // this happens when the node has been truly detached
               Parent = null;
               ParentContainer = null;
            }

         } else {
            // property is an assocation, so we need to update the backward associations

            if (!isEntity) {
               // association target must be an entity
               BplRuntimeException.Throw("'{0}' cannot be the target of association since it is not an entity", this);
            }

            //if (!isTaxonomy) {
               // no backward association from taxonomies
               Sources.RemoveTuple(source, property);
            //}

         }

         // detach the node and all its dependents from this context
         if (Context != null) {
            _detachFromContext(this);
         }

      }
Exemplo n.º 21
0
 /// <summary>Adds a source object/property reference to the specified target id.</summary>
 /// <returns><c>true</c> if the source was successfully added; <c>false</c> otherwise.</returns>
 public bool AddSource(string targetId, BplObject source, BplProperty property) {
    var fullTargetId = BplIdentity.Get(targetId, property.ReferencedClass.IdentityScope);
    _pending.Add(new BplPendingReference(source, property, fullTargetId));
    return true;
 }
Exemplo n.º 22
0
 /// <summary>Creates a new <see cref="BplItemRemoved"/> instance.</summary>
 internal BplItemRemoved(BplObject source, BplProperty property, int oldIndex, BplContextNode oldItem)
    : base(source, property) {
    OldIndex = oldIndex;
    OldItem = oldItem;
 }
Exemplo n.º 23
0
      // recursively serializes a BPL object
      private void _serializeObject(XContainer parent, BplObject bplObject, BplClass expectedClass) {
         if (bplObject == null) return;

         var bplClass = bplObject.Class;
         var schema = bplClass.Schema;
         var prefix = BplLanguage.Schemas[schema];
         NSMapping.AddIfNeeded(prefix, schema);

         XElement element = null;
         if (expectedClass == null || schema == expectedClass.Schema) {
            element = new XElement(bplClass.TagName);
         } else {
            NSMapping.AddIfNeeded("xsi", xsi);
            element = new XElement(expectedClass.TagName);
            element.Add(new XAttribute(xsi + "type", prefix + ":" + bplClass.TagName.LocalName));
         }

         var identityProperty = bplClass.IdentityProperty;
         if (identityProperty != null) {
            var id = (BplIdentity)identityProperty.GetValue(bplObject);
            if (!id.IsEmpty) {
               element.Add(new XAttribute(identityProperty.TagName, id.ToString(bplClass.IdentityScope)));
            } else if (bplClass.IsA<BplEntity>()) {
               AddError("{0} is missing Id.", bplObject);
            }
         }

         // invariant: write the properties according to their "ProtocolIndex" order
         foreach (var property in bplClass.PropertiesSorted) {
            if (property.IsCalculated || property.IsVirtual || property == identityProperty) continue;

            var value = property.GetValue(bplObject);
            if (value == null) continue;

            if (!ShouldSerialize(property, bplObject)) continue;

            if (property.IsPrimitive) {
               if (property.IsScalar) {
                  _serializeScalar(element, property, value);
               } else if (property.IsArray) {
                  _serializeArray(element, property, (IEnumerable)value);
               }
            } else if (property.IsContainer) {
               if (property.IsReference) {
                  _serializeContainer(element, property, (BplObject)value);
               } else {
                  _serializeContainer(element, property, (IBplCollection)value);
               }
            } else if (property.IsAssociation) {
               if (property.IsReference) {
                  _serializeAssociation(element, property, (BplObject)value);
               } else {
                  _serializeAssociation(element, property, (IBplCollection)value);
               }
            }
         }

         parent.Add(element);
      }
Exemplo n.º 24
0
 private void _deserializeAssociation(BplObject bplObject, BplProperty property, XElement[] targets) {
    var idTagName = XNamespaces.none + BplPrimitive.Get<BplIdentity>().TagName.LocalName;
    for (var i = 0; i < targets.Length; i++) {
       var target = targets[i];
       if (target.Name != idTagName) {
          AddError("Invalid value in BPL property '{0}[{1}]', {:where}. Expected tag name '{2}'.", property.Name, i, idTagName, target);
       }
       _resolver.AddSource(target.Value, bplObject, property);
    }
 }
Exemplo n.º 25
0
 /// <summary>Creates a new <see cref="BplRuntimeException"/> instance.</summary>
 private BplRuntimeException(String message, Exception inner, BplObject sourceObject, BplProperty sourceProperty)
    : base(message, inner) {
    SourceObject = sourceObject;
    SourceProperty = sourceProperty;
 }
Exemplo n.º 26
0
 private void _deserializeScalar(BplObject bplObject, BplProperty property, XObject node) {
    try {
       var value = _parseScalar(property, BplLanguage.XmlConverters[property], node);
       property.SetValue(bplObject, value);
    } catch (Exception e) {
       AddError("Invalid value in BPL property '{:name}', {:where}. {0}", e.Message, node);
    }
 }
Exemplo n.º 27
0
 /// <summary>Throws a <see cref="BplRuntimeException"/> with the given parameters.</summary>
 public static void Throw(string message, Exception innerException, BplObject sourceObject, BplProperty sourceProperty) {
    var formattedMessage = Assumption.TidyMessage(message.Substitute(sourceObject, sourceProperty.Name));
    throw new BplRuntimeException(formattedMessage, innerException, sourceObject, sourceProperty);
 }
Exemplo n.º 28
0
 // serializes a container (singleton)
 private void _serializeContainer(XElement element, BplProperty property, BplObject bplObject) {
    if (bplObject == null) return;
    var singleton = new XElement(property.TagName);
    var targetClass = property.ReferencedClass;
    _serializeObject(singleton, bplObject, targetClass);
    element.Add(singleton);
 }
Exemplo n.º 29
0
      /// <summary>Attaches this node to the specified source object.</summary>
      internal void AttachTo(BplObject source, BplProperty property) {
         if (source == null || property == null) {
            BplRuntimeException.Throw("Source object or property are missing");
         }
         if (source.IsSealed) {
            BplRuntimeException.Throw("Node cannot be attached to a sealed object");
         }

         var isEntity = (this is BplEntity);
         var isTaxonomy = (this is BplTaxonomy);
         var sourceIsTaxonomy = (source is BplTaxonomy);
         if (sourceIsTaxonomy && !isTaxonomy) {
            BplRuntimeException.Throw("'{0}' cannot be referenced from a taxonomy", this);
         }

         if (property.IsContainer) {

            // property is a container, so we need to reparent the node

            var oldParent = Parent;
            var oldContainer = ParentContainer;
            if (oldParent == source && oldContainer == property) {
               BplRuntimeException.Throw("Node is already contained in '{1}' in {0}.", source, property);
            }

            // attach to new parent
            Parent = source;
            ParentContainer = property;

            // detach from old parent (this is done after attaching the new parent, so the node does not get disconnected from the context)
            if (oldContainer != null) {
               if (oldContainer.IsReference) {
                  oldContainer.SetValue(oldParent, null);
               } else {
                  oldContainer.GetCollection(oldParent).Remove(this);
               }
            }

         } else {

            // property is an assocation, so we need to update the backward associations

            if (!isEntity) {
               // association target must be an entity
               BplRuntimeException.Throw("'{0}' cannot be the target of association since it is not an entity", this);
            }

            if (!(sourceIsTaxonomy ^ isTaxonomy)) {
               // no backward association between taxonomies and non-taxonomies
               Sources.AddTuple(source, property);
            }

         }

         // attach the source and target to same context
         var sourceContext = BplContext.GetOwner(source);
         var targetContext = Context;
         if (sourceContext != targetContext) {
            if (sourceContext == null) {
               _attachToContext((BplContextNode)source, targetContext);
            } else if (targetContext == null) {
               _attachToContext(this, sourceContext);
            } else {
               _verifyContextCompatibility(sourceContext, targetContext);
            }
         }

      }
Exemplo n.º 30
0
 // Internal constructor (to prevent direct inheritance by external plugins)
 internal BplCollectionChange(BplObject source, BplProperty property) : base(source, property) {
 }