Add autoconf checks for platforms without IPv6
[mono.git] / mcs / class / monodoc / Monodoc / providers / ecma-provider.cs
index 248ab3930f86b3b5c3d82b118b7b7f0bb0a1c2d5..4e82c2c76689bd81af84490e706f5dd2523e5323 100644 (file)
@@ -25,9 +25,60 @@ using Mono.Utilities;
 
 namespace Monodoc.Providers
 {
+       public interface IEcmaProviderFileSource {
+               XmlReader GetIndexReader(string path);
+               XDocument GetTypeDocument(string path);
+               XElement GetNamespaceElement(string path);
+               string GetTypeXmlPath(string basePath, string nsName, string typeName);
+               string GetNamespaceXmlPath(string basePath, string ns);
+               XElement ExtractNamespaceSummary (string path);
+       }
+
+       internal class DefaultEcmaProviderFileSource : IEcmaProviderFileSource {
+               public static readonly IEcmaProviderFileSource Default = new DefaultEcmaProviderFileSource();
+
+               public XmlReader GetIndexReader(string path) {
+                       return XmlReader.Create (File.OpenRead (path));
+               }
+
+               public XElement GetNamespaceElement(string path) {
+                       return XElement.Load (path);
+               }
+
+               public string GetTypeXmlPath(string basePath, string nsName, string typeName) {
+                       string finalPath = Path.Combine (basePath, nsName, Path.ChangeExtension (typeName, ".xml"));
+                       return finalPath;
+               }
+
+               public XDocument GetTypeDocument(string path) {
+                       return XDocument.Load (path);
+               }
+
+               public string GetNamespaceXmlPath(string basePath, string ns) {
+                       string finalPath = Path.Combine(basePath, String.Format("ns-{0}.xml", ns));
+                       return finalPath;
+               }
+
+               public XElement ExtractNamespaceSummary (string path)
+               {
+                       using (var reader = XmlReader.Create (path)) {
+                               reader.ReadToFollowing ("Namespace");
+                               var name = reader.GetAttribute ("Name");
+                               var summary = reader.ReadToFollowing ("summary") ? XElement.Load (reader.ReadSubtree ()) : new XElement ("summary");
+                               var remarks = reader.ReadToFollowing ("remarks") ? XElement.Load (reader.ReadSubtree ()) : new XElement ("remarks");
+
+                               return new XElement ("namespace",
+                                                    new XAttribute ("ns", name ?? string.Empty),
+                                                    summary,
+                                                    remarks);
+                       }
+               }
+       }
+
        public class EcmaProvider : Provider
        {
                HashSet<string> directories = new HashSet<string> ();
+               IEcmaProviderFileSource fileSource;
 
                public EcmaProvider ()
                {
@@ -38,6 +89,16 @@ namespace Monodoc.Providers
                        AddDirectory (baseDir);
                }
 
+               public IEcmaProviderFileSource FileSource { 
+                       get {
+                               if (fileSource == null) {
+                                       fileSource = new DefaultEcmaProviderFileSource();
+                               }
+                               return fileSource;
+                       }
+                       set { fileSource = value; }
+               }
+
                public void AddDirectory (string directory)
                {
                        if (string.IsNullOrEmpty (directory))
@@ -59,7 +120,7 @@ namespace Monodoc.Providers
                                        continue;
                                }
 
-                               EcmaDoc.PopulateTreeFromIndexFile (indexFilePath, EcmaHelpSource.EcmaPrefix, tree, storage, nsSummaries, _ => resID++.ToString ());
+                               EcmaDoc.PopulateTreeFromIndexFile (indexFilePath, EcmaHelpSource.EcmaPrefix, tree, storage, nsSummaries, _ => resID++.ToString (), FileSource);
                        }
 
                        foreach (var summary in nsSummaries)
@@ -68,26 +129,11 @@ namespace Monodoc.Providers
                        var masterSummary = new XElement ("elements",
                                                          directories
                                                          .SelectMany (d => Directory.EnumerateFiles (d, "ns-*.xml"))
-                                                         .Select (ExtractNamespaceSummary));
+                                                         .Select (FileSource.ExtractNamespaceSummary));
                        storage.Store ("mastersummary.xml", masterSummary.ToString ());
                }
 
-               XElement ExtractNamespaceSummary (string nsFile)
-               {
-                       using (var reader = XmlReader.Create (nsFile)) {
-                               reader.ReadToFollowing ("Namespace");
-                               var name = reader.GetAttribute ("Name");
-                               reader.ReadToFollowing ("summary");
-                               var summary = reader.ReadInnerXml ();
-                               reader.ReadToFollowing ("remarks");
-                               var remarks = reader.ReadInnerXml ();
 
-                               return new XElement ("namespace",
-                                                    new XAttribute ("ns", name ?? string.Empty),
-                                                    new XElement ("summary", new XCData (summary)),
-                                                    new XElement ("remarks", new XCData (remarks)));
-                       }
-               }
 
                public override void CloseTree (HelpSource hs, Tree tree)
                {
@@ -192,7 +238,10 @@ namespace Monodoc.Providers
                public override Stream GetHelpStream (string id)
                {
                        var idParts = id.Split ('?');
-                       return base.GetHelpStream (idParts[0]);
+                       var name = idParts[0];
+                       if (name == "root:")
+                               name = "mastersummary.xml";
+                       return base.GetHelpStream (name);
                }
 
                public override Stream GetCachedHelpStream (string id)
@@ -273,7 +322,8 @@ namespace Monodoc.Providers
                Node GetNodeTypeParent (Node node)
                {
                        // Type nodes are always at level 2 so we just need to get there
-                       while (node != null && node.Parent != null && !node.Parent.Parent.Element.StartsWith ("root:/", StringComparison.OrdinalIgnoreCase))
+                       while (node != null && node.Parent != null
+                              && !node.Parent.Parent.Element.StartsWith ("root:/", StringComparison.OrdinalIgnoreCase) && node.Parent.Parent.Parent != null)
                                node = node.Parent;
                        return node;
                }
@@ -340,8 +390,8 @@ namespace Monodoc.Providers
 
                public override void PopulateIndex (IndexMaker index_maker)
                {
-                       foreach (Node ns_node in Tree.RootNode.Nodes){
-                               foreach (Node type_node in ns_node.Nodes){
+                       foreach (Node ns_node in Tree.RootNode.ChildNodes){
+                               foreach (Node type_node in ns_node.ChildNodes){
                                        string typename = type_node.Caption.Substring (0, type_node.Caption.IndexOf (' '));
                                        string full = ns_node.Caption + "." + typename;
 
@@ -370,7 +420,7 @@ namespace Monodoc.Providers
                                                index_maker.Add (type_node.Caption, typename, url);
                                                index_maker.Add (full + " " + doc_tag, full, url);
 
-                                               foreach (Node c in type_node.Nodes){
+                                               foreach (Node c in type_node.ChildNodes){
                                                        switch (c.Caption){
                                                        case "Constructors":
                                                                index_maker.Add ("  constructors", typename+"0", url + "/C");
@@ -399,10 +449,10 @@ namespace Monodoc.Providers
                                                //
                                                string keybase = typename + "6.";
 
-                                               foreach (Node c in type_node.Nodes){
+                                               foreach (Node c in type_node.ChildNodes){
                                                        var type = c.Caption[0];
 
-                                                       foreach (Node nc in c.Nodes) {
+                                                       foreach (Node nc in c.ChildNodes) {
                                                                string res = nc.Caption;
                                                                string nurl = nc.PublicUrl;
 
@@ -492,8 +542,8 @@ namespace Monodoc.Providers
                        StringBuilder text = new StringBuilder ();
                        SearchableDocument searchDoc = new SearchableDocument ();
 
-                       foreach (Node ns_node in Tree.RootNode.Nodes) {
-                               foreach (Node type_node in ns_node.Nodes) {
+                       foreach (Node ns_node in Tree.RootNode.ChildNodes) {
+                               foreach (Node type_node in ns_node.ChildNodes) {
                                        string typename = type_node.Caption.Substring (0, type_node.Caption.IndexOf (' '));
                                        string full = ns_node.Caption + "." + typename;
                                        string url = type_node.PublicUrl;
@@ -530,22 +580,22 @@ namespace Monodoc.Providers
                                                var exportParsable = doc_tag[0] == 'C' && (ns_node.Caption.StartsWith ("MonoTouch") || ns_node.Caption.StartsWith ("MonoMac"));
 
                                                //Add docs for contructors, methods, etc.
-                                               foreach (Node c in type_node.Nodes) { // c = Constructors || Fields || Events || Properties || Methods || Operators
+                                               foreach (Node c in type_node.ChildNodes) { // c = Constructors || Fields || Events || Properties || Methods || Operators
                                                        if (c.Element == "*")
                                                                continue;
                                                        const float innerTypeBoost = 0.2f;
 
-                                                       IEnumerable<Node> ncnodes = c.Nodes;
+                                                       IEnumerable<Node> ncnodes = c.ChildNodes;
                                                        // The rationale is that we need to properly handle method overloads
                                                        // so for those method node which have children, flatten them
                                                        if (c.Caption == "Methods") {
                                                                ncnodes = ncnodes
-                                                                       .Where (n => n.Nodes == null || n.Nodes.Count == 0)
-                                                                       .Concat (ncnodes.Where (n => n.Nodes.Count > 0).SelectMany (n => n.Nodes));
+                                                                       .Where (n => n.ChildNodes == null || n.ChildNodes.Count == 0)
+                                                                       .Concat (ncnodes.Where (n => n.ChildNodes.Count > 0).SelectMany (n => n.ChildNodes));
                                                        } else if (c.Caption == "Operators") {
                                                                ncnodes = ncnodes
                                                                        .Where (n => !n.Caption.EndsWith ("Conversion"))
-                                                                       .Concat (ncnodes.Where (n => n.Caption.EndsWith ("Conversion")).SelectMany (n => n.Nodes));
+                                                                       .Concat (ncnodes.Where (n => n.Caption.EndsWith ("Conversion")).SelectMany (n => n.ChildNodes));
                                                        }
 
                                                        var prematchedMembers = xdoc.Root.Element ("Members").Elements ("Member").ToLookup (n => (string)n.Attribute ("MemberName"), n => n);