internal ExtensionNodeDescription FindExtensionNode(string path, bool lookInDeps) { // Look in the extensions of this add-in foreach (Extension ext in MainModule.Extensions) { if (path.StartsWith(ext.Path + "/")) { string subp = path.Substring(ext.Path.Length).Trim('/'); ExtensionNodeDescriptionCollection nodes = ext.ExtensionNodes; ExtensionNodeDescription node = null; foreach (string p in subp.Split('/')) { if (p.Length == 0) { continue; } node = nodes [p]; if (node == null) { break; } nodes = node.ChildNodes; } if (node != null) { return(node); } } } if (!lookInDeps || OwnerDatabase == null) { return(null); } // Look in dependencies foreach (Dependency dep in MainModule.Dependencies) { AddinDependency adep = dep as AddinDependency; if (adep == null) { continue; } Addin ad = OwnerDatabase.GetInstalledAddin(Domain, adep.FullAddinId); if (ad != null && ad.Description != null) { ExtensionNodeDescription node = ad.Description.FindExtensionNode(path, false); if (node != null) { return(node); } } } return(null); }
/// <summary> /// Gets the object extended by this extension /// </summary> /// <returns> /// The extended object can be an <see cref="Mono.Addins.Description.ExtensionPoint"/> or /// an <see cref="Mono.Addins.Description.ExtensionNodeDescription"/>. /// </returns> /// <remarks> /// This method only works when the add-in description to which the extension belongs has been /// loaded from an add-in registry. /// </remarks> public ObjectDescription GetExtendedObject() { AddinDescription desc = ParentAddinDescription; if (desc == null) { return(null); } ExtensionPoint ep = FindExtensionPoint(desc, path); if (ep == null && desc.OwnerDatabase != null) { foreach (Dependency dep in desc.MainModule.Dependencies) { AddinDependency adep = dep as AddinDependency; if (adep == null) { continue; } Addin ad = desc.OwnerDatabase.GetInstalledAddin(ParentAddinDescription.Domain, adep.FullAddinId); if (ad != null && ad.Description != null) { ep = FindExtensionPoint(ad.Description, path); if (ep != null) { break; } } } } if (ep != null) { string subp = path.Substring(ep.Path.Length).Trim('/'); if (subp.Length == 0) { return(ep); // The extension is directly extending the extension point } // The extension is extending a node of the extension point return(desc.FindExtensionNode(path, true)); } return(null); }
public bool DependsOnAddin(string addinId) { AddinDescription desc = Parent as AddinDescription; if (desc == null) { throw new InvalidOperationException(); } foreach (Dependency dep in Dependencies) { AddinDependency adep = dep as AddinDependency; if (adep == null) { continue; } if (Addin.GetFullId(desc.Namespace, adep.AddinId, adep.Version) == addinId) { return(true); } } return(false); }
static void ReadDependencies(DependencyCollection deps, DependencyCollection opDeps, XmlElement elem) { foreach (XmlElement dep in elem.SelectNodes ("Dependencies/Addin")) { AddinDependency adep = new AddinDependency (); adep.AddinId = dep.GetAttribute ("id"); string v = dep.GetAttribute ("version"); if (v.Length != 0) adep.Version = v; deps.Add (adep); } foreach (XmlElement dep in elem.SelectNodes ("Dependencies/Assembly")) { AssemblyDependency adep = new AssemblyDependency (); adep.FullName = dep.GetAttribute ("name"); adep.Package = dep.GetAttribute ("package"); deps.Add (adep); } foreach (XmlElement mod in elem.SelectNodes ("Module")) ReadDependencies (opDeps, opDeps, mod); }
void ScanAssemblyContents(IAssemblyReflector reflector, AddinDescription config, ModuleDescription module, object asm, AddinScanResult scanResult) { bool isMainModule = module == config.MainModule; // Get dependencies object[] deps = reflector.GetCustomAttributes (asm, typeof(AddinDependencyAttribute), false); foreach (AddinDependencyAttribute dep in deps) { AddinDependency adep = new AddinDependency (); adep.AddinId = dep.Id; adep.Version = dep.Version; module.Dependencies.Add (adep); } if (isMainModule) { // Get properties object[] props = reflector.GetCustomAttributes (asm, typeof(AddinPropertyAttribute), false); foreach (AddinPropertyAttribute prop in props) config.Properties.SetPropertyValue (prop.Name, prop.Value, prop.Locale); // Get extension points object[] extPoints = reflector.GetCustomAttributes (asm, typeof(ExtensionPointAttribute), false); foreach (ExtensionPointAttribute ext in extPoints) { ExtensionPoint ep = config.AddExtensionPoint (ext.Path); ep.Description = ext.Description; ep.Name = ext.Name; ExtensionNodeType nt = ep.AddExtensionNode (ext.NodeName, ext.NodeTypeName); nt.ExtensionAttributeTypeName = ext.ExtensionAttributeTypeName; } } // Look for extension nodes declared using assembly attributes foreach (CustomAttribute att in reflector.GetRawCustomAttributes (asm, typeof(CustomExtensionAttribute), true)) AddCustomAttributeExtension (module, att, "Type"); // Get extensions or extension points applied to types foreach (object t in reflector.GetAssemblyTypes (asm)) { string typeFullName = reflector.GetTypeFullName (t); // Look for extensions object[] extensionAtts = reflector.GetCustomAttributes (t, typeof(ExtensionAttribute), false); if (extensionAtts.Length > 0) { Dictionary<string,ExtensionNodeDescription> nodes = new Dictionary<string, ExtensionNodeDescription> (); ExtensionNodeDescription uniqueNode = null; foreach (ExtensionAttribute eatt in extensionAtts) { string path; string nodeName = eatt.NodeName; if (eatt.TypeName.Length > 0) { path = "$" + eatt.TypeName; } else if (eatt.Path.Length == 0) { path = GetBaseTypeNameList (reflector, t); if (path == "$") { // The type does not implement any interface and has no superclass. // Will be reported later as an error. path = "$" + typeFullName; } } else { path = eatt.Path; } ExtensionNodeDescription elem = module.AddExtensionNode (path, nodeName); nodes [path] = elem; uniqueNode = elem; if (eatt.Id.Length > 0) { elem.SetAttribute ("id", eatt.Id); elem.SetAttribute ("type", typeFullName); } else { elem.SetAttribute ("id", typeFullName); } if (eatt.InsertAfter.Length > 0) elem.SetAttribute ("insertafter", eatt.InsertAfter); if (eatt.InsertBefore.Length > 0) elem.SetAttribute ("insertbefore", eatt.InsertBefore); } // Get the node attributes foreach (ExtensionAttributeAttribute eat in reflector.GetCustomAttributes (t, typeof(ExtensionAttributeAttribute), false)) { ExtensionNodeDescription node; if (!string.IsNullOrEmpty (eat.Path)) nodes.TryGetValue (eat.Path, out node); else if (eat.TypeName.Length > 0) nodes.TryGetValue ("$" + eat.TypeName, out node); else { if (nodes.Count > 1) throw new Exception ("Missing type or extension path value in ExtensionAttribute for type '" + typeFullName + "'."); node = uniqueNode; } if (node == null) throw new Exception ("Invalid type or path value in ExtensionAttribute for type '" + typeFullName + "'."); node.SetAttribute (eat.Name ?? string.Empty, eat.Value ?? string.Empty); } } else { // Look for extension points extensionAtts = reflector.GetCustomAttributes (t, typeof(TypeExtensionPointAttribute), false); if (extensionAtts.Length > 0 && isMainModule) { foreach (TypeExtensionPointAttribute epa in extensionAtts) { ExtensionPoint ep; ExtensionNodeType nt = new ExtensionNodeType (); if (epa.Path.Length > 0) { ep = config.AddExtensionPoint (epa.Path); } else { ep = config.AddExtensionPoint (GetDefaultTypeExtensionPath (config, typeFullName)); nt.ObjectTypeName = typeFullName; } nt.Id = epa.NodeName; nt.TypeName = epa.NodeTypeName; nt.ExtensionAttributeTypeName = epa.ExtensionAttributeTypeName; ep.NodeSet.NodeTypes.Add (nt); ep.Description = epa.Description; ep.Name = epa.Name; ep.RootAddin = config.AddinId; ep.SetExtensionsAddinId (config.AddinId); } } else { // Look for custom extension attribtues foreach (CustomAttribute att in reflector.GetRawCustomAttributes (t, typeof(CustomExtensionAttribute), false)) { ExtensionNodeDescription elem = AddCustomAttributeExtension (module, att, "Type"); elem.SetAttribute ("type", typeFullName); if (string.IsNullOrEmpty (elem.GetAttribute ("id"))) elem.SetAttribute ("id", typeFullName); } } } } }
void ScanAssemblyContents (AddinDescription config, Assembly asm, ArrayList hostExtensionClasses, AddinScanResult scanResult) { // Get dependencies object[] deps = asm.GetCustomAttributes (typeof(AddinDependencyAttribute), false); foreach (AddinDependencyAttribute dep in deps) { AddinDependency adep = new AddinDependency (); adep.AddinId = dep.Id; adep.Version = dep.Version; config.MainModule.Dependencies.Add (adep); } // Get extension points object[] extPoints = asm.GetCustomAttributes (typeof(ExtensionPointAttribute), false); foreach (ExtensionPointAttribute ext in extPoints) { ExtensionPoint ep = config.AddExtensionPoint (ext.Path); ep.Description = ext.Description; ep.Name = ext.Name; ep.AddExtensionNode (ext.NodeName, ext.NodeType.FullName); } foreach (Type t in asm.GetTypes ()) { if (Attribute.IsDefined (t, typeof(ExtensionAttribute))) { foreach (ExtensionAttribute eatt in t.GetCustomAttributes (typeof(ExtensionAttribute), false)) { string path; string nodeName; if (eatt.Path.Length == 0) { if (config.IsRoot) { // The extension point must be one of the defined by the assembly // Look for it later, when the assembly has been fully scanned. hostExtensionClasses.Add (t); continue; } else { path = GetBaseTypeNameList (t); if (path == "$") { // The type does not implement any interface and has no superclass. // Will be reported later as an error. path = "$" + t.FullName; } nodeName = "Type"; } } else { path = eatt.Path; nodeName = eatt.NodeName; } ExtensionNodeDescription elem = config.MainModule.AddExtensionNode (path, nodeName); if (eatt.Id.Length > 0) { elem.SetAttribute ("id", eatt.Id); elem.SetAttribute ("type", t.FullName); } else { elem.SetAttribute ("id", t.FullName); } if (eatt.InsertAfter.Length > 0) elem.SetAttribute ("insertafter", eatt.InsertAfter); if (eatt.InsertBefore.Length > 0) elem.SetAttribute ("insertbefore", eatt.InsertAfter); } } else if (Attribute.IsDefined (t, typeof(TypeExtensionPointAttribute))) { foreach (TypeExtensionPointAttribute epa in t.GetCustomAttributes (typeof(TypeExtensionPointAttribute), false)) { ExtensionPoint ep; ExtensionNodeType nt = new ExtensionNodeType (); if (epa.Path.Length > 0) { ep = config.AddExtensionPoint (epa.Path); } else { ep = config.AddExtensionPoint (GetDefaultTypeExtensionPath (config, t)); nt.ObjectTypeName = t.FullName; } nt.Id = epa.NodeName; nt.TypeName = epa.NodeType.FullName; ep.NodeSet.NodeTypes.Add (nt); ep.Description = epa.Description; ep.Name = epa.Name; ep.RootAddin = config.AddinId; ep.SetExtensionsAddinId (config.AddinId); } } } }