/// <summary> /// This is called if indexing completes successfully /// </summary> private void Completed(IndexedCommentsCache cache) { indexThread = null; pbWait.Visible = lblLoading.Visible = false; tvEntities.Enabled = true; codeEntities = cache.GetKeys(); if (cboContentType.SelectedIndex == (int)EntityType.CodeEntities) { txtFindName.Enabled = true; txtFindName.ReadOnly = false; } }
/// <summary> /// This is called if indexing completes successfully /// </summary> /// <param name="cache">The index cache</param> private void IndexCompleted(IndexedCommentsCache cache) { this.DisposeOfTask(); spIndexingPanel.Visibility = Visibility.Collapsed; codeEntities = new List <string>(cache.AllKeys); if (cboEntityType.SelectedIndex == (int)EntityType.CodeEntity) { txtFindName.IsReadOnly = false; txtFindName.Text = "<Enter text or reg ex to find here, then click Go>"; txtFindName.SelectAll(); tvEntities.IsEnabled = btnGo.IsEnabled = true; } }
/// <summary> /// This is called if indexing completes successfully /// </summary> /// <param name="cache">The index cache</param> private void IndexCompleted(IndexedCommentsCache cache) { this.DisposeOfTask(); spIndexingPanel.Visibility = Visibility.Collapsed; codeEntities = new List <string>(cache.AllKeys); // Add an entry for the root namespace container codeEntities.Add("R:Project_" + currentProject.HtmlHelpName.Replace(" ", "_")); if (cboEntityType.SelectedIndex == (int)EntityType.CodeEntity) { txtFindName.IsReadOnly = false; txtFindName.Text = "<Enter text or reg ex to find here, then click Go>"; txtFindName.SelectAll(); tvEntities.IsEnabled = btnGo.IsEnabled = true; } }
/// <summary> /// This is called if indexing completes successfully /// </summary> /// <param name="cache">The index cache</param> private void IndexCompleted(IndexedCommentsCache cache) { this.DisposeOfTask(); spIndexingPanel.Visibility = Visibility.Collapsed; var allEntities = new HashSet <string>(cache.AllKeys); // Add entries for all namespaces in the project namespace summaries foreach (var ns in currentProject.NamespaceSummaries.Where(n => n.IsDocumented)) { string name; if (!ns.IsGroup) { name = "N:" + ns.Name; } else { name = "G:" + ns.Name.Replace(" (Group)", String.Empty); } if (!allEntities.Contains(name)) { allEntities.Add(name); } } // Add an entry for the root namespace container allEntities.Add("R:Project_" + currentProject.HtmlHelpName.Replace(" ", "_")); codeEntities = new List <string>(allEntities); if (cboEntityType.SelectedIndex == (int)EntityType.CodeEntity) { txtFindName.IsReadOnly = false; txtFindName.Text = "<Enter text or reg ex to find here, then click Go>"; txtFindName.SelectAll(); tvEntities.IsEnabled = btnGo.IsEnabled = true; } }
/// <summary> /// This is the method that indexes the comments files /// </summary> /// <remarks>Rather than a partial build, we'll just index the comments files.</remarks> private IndexedCommentsCache IndexComments() { HashSet <string> projectDictionary = new HashSet <string>(); IndexedCommentsCache cache = new IndexedCommentsCache(100); MSBuildProject projRef; string lastSolution = null; // Index the framework comments based on the framework version in the project var reflectionDataDictionary = new ReflectionDataSetDictionary(new[] { currentProject.ComponentPath, Path.GetDirectoryName(currentProject.Filename) }); var frameworkReflectionData = reflectionDataDictionary.CoreFrameworkByTitle( currentProject.FrameworkVersion, true); if (frameworkReflectionData == null) { throw new InvalidOperationException(String.Format(CultureInfo.CurrentCulture, "Unable to locate information for a framework version or its redirect: {0}", currentProject.FrameworkVersion)); } foreach (var location in frameworkReflectionData.CommentsFileLocations(currentProject.Language)) { indexTokenSource.Token.ThrowIfCancellationRequested(); cache.IndexCommentsFiles(Path.GetDirectoryName(location), Path.GetFileName(location), false, null); } // Index the comments file documentation sources foreach (string file in currentProject.DocumentationSources.SelectMany(ds => ds.CommentsFiles)) { indexTokenSource.Token.ThrowIfCancellationRequested(); cache.IndexCommentsFiles(Path.GetDirectoryName(file), Path.GetFileName(file), false, null); } // Also, index the comments files in project documentation sources foreach (DocumentationSource ds in currentProject.DocumentationSources) { foreach (var sourceProject in ds.Projects( !String.IsNullOrEmpty(ds.Configuration) ? ds.Configuration : currentProject.Configuration, !String.IsNullOrEmpty(ds.Platform) ? ds.Platform : currentProject.Platform)) { indexTokenSource.Token.ThrowIfCancellationRequested(); // NOTE: This code should be similar to the code in BuildProcess.ValidateDocumentationSources! // Solutions are followed by the projects that they contain if (sourceProject.ProjectFileName.EndsWith(".sln", StringComparison.OrdinalIgnoreCase)) { lastSolution = sourceProject.ProjectFileName; continue; } // Ignore projects that we've already seen if (projectDictionary.Add(sourceProject.ProjectFileName)) { using (projRef = new MSBuildProject(sourceProject.ProjectFileName)) { // Use the project file configuration and platform properties if they are set. If // not, use the documentation source values. If they are not set, use the SHFB // project settings. projRef.SetConfiguration( !String.IsNullOrEmpty(sourceProject.Configuration) ? sourceProject.Configuration : !String.IsNullOrEmpty(ds.Configuration) ? ds.Configuration : currentProject.Configuration, !String.IsNullOrEmpty(sourceProject.Platform) ? sourceProject.Platform : !String.IsNullOrEmpty(ds.Platform) ? ds.Platform : currentProject.Platform, currentProject.MSBuildOutDir, false); // Add Visual Studio solution macros if necessary if (lastSolution != null) { projRef.SetSolutionMacros(lastSolution); } if (!String.IsNullOrEmpty(projRef.XmlCommentsFile)) { cache.IndexCommentsFiles(Path.GetDirectoryName(projRef.XmlCommentsFile), Path.GetFileName(projRef.XmlCommentsFile), false, null); } } } } } return(cache); }
//===================================================================== /// <summary> /// Load the configuration file /// </summary> /// <param name="configFile">The configuration file to load</param> /// <exception cref="ArgumentException">This is thrown if the configuration file does not exist.</exception> /// <exception cref="ConfigurationErrorsException">This is thrown if the configuration file is not /// valid.</exception> private static void LoadConfiguration(string configFile) { XPathDocument config; XPathNavigator navConfig, navComments, element; string path, wildcard, attrValue; bool recurse; int cacheSize = 100; if (!File.Exists(configFile)) { throw new ArgumentException("Configuration file not found: " + configFile, "configFile"); } config = new XPathDocument(configFile); navConfig = config.CreateNavigator(); // Show duplicate key warnings? showDupWarning = (navConfig.SelectSingleNode("configuration/showDuplicateWarning") != null); // Get the reflection information files reflectionFiles = new ReflectionFiles(); foreach (XPathNavigator refFile in navConfig.Select("configuration/reflectionInfo/@file")) { if (!File.Exists(refFile.Value)) { throw new ConfigurationErrorsException("The reflectionFile element's target file '" + refFile.Value + "' does not exist"); } Console.WriteLine("Reflection information will be retrieved from '{0}'", refFile.Value); reflectionFiles.AddReflectionFile(refFile.Value); } if (reflectionFiles.Count == 0) { throw new ConfigurationErrorsException("At least one reflectionFile element is required"); } // Get the inherited documentation filename element = navConfig.SelectSingleNode("configuration/inheritedDocs/@file"); if (element == null) { throw new ConfigurationErrorsException("The inheritedDocs element does not exist or is not valid"); } inheritedDocsFilename = element.Value; Console.WriteLine("Inherited documentation will be written to '{0}'", inheritedDocsFilename); // Load the comments file information navComments = navConfig.SelectSingleNode("configuration/commentsFiles"); attrValue = navComments.GetAttribute("cacheSize", String.Empty); if (attrValue.Length != 0) { cacheSize = Convert.ToInt32(attrValue, CultureInfo.InvariantCulture); } commentsCache = new IndexedCommentsCache(cacheSize) { ShowDuplicatesWarning = showDupWarning }; commentsCache.ReportWarning += (s, e) => Console.WriteLine(e.Message); foreach (XPathNavigator nav in navComments.Select("*")) { path = nav.GetAttribute("path", String.Empty); wildcard = nav.GetAttribute("file", String.Empty); attrValue = nav.GetAttribute("recurse", String.Empty); if (path.Length == 0) { path = Path.GetDirectoryName(wildcard); wildcard = Path.GetFileName(wildcard); } path = Environment.ExpandEnvironmentVariables(path); if (wildcard.Length != 0) { wildcard = Environment.ExpandEnvironmentVariables(wildcard); } else { wildcard = "*.xml"; } if (attrValue.Length == 0) { recurse = false; } else { recurse = Convert.ToBoolean(attrValue, CultureInfo.InvariantCulture); } Console.WriteLine("Indexing {0}\\{1}", path, wildcard); commentsCache.IndexCommentsFiles(path, wildcard, recurse, (nav.Name == "scan") ? commentsFiles : null); } if (commentsCache.FilesIndexed == 0 || commentsCache.IndexCount == 0) { throw new ConfigurationErrorsException("No comments files were specified or they did not " + "contain valid information to index"); } if (commentsFiles.Count == 0) { throw new ConfigurationErrorsException("No comments files were specified to scan for " + "<inheritdoc /> tags."); } Console.WriteLine("Indexed {0} members in {1} file(s). {2} file(s) to scan for <inheritdoc /> tags.", commentsCache.IndexCount, commentsCache.FilesIndexed, commentsFiles.Count); }
/// <summary> /// This is the thread method that indexes the comments files /// </summary> /// <remarks>Rather than a partial build, we'll just index the /// comments files.</remarks> private void IndexComments() { HashSet <string> projectDictionary = new HashSet <string>(); Collection <string> frameworkLocations = new Collection <string>(); Dictionary <string, string> cacheName = new Dictionary <string, string>(); IndexedCommentsCache cache = new IndexedCommentsCache(100); MSBuildProject projRef; string path, lastSolution = null; try { BuildProcess.GetFrameworkCommentsFiles(frameworkLocations, cacheName, currentProject.Language, currentProject.FrameworkVersion); // Index the framework comments foreach (string location in frameworkLocations) { path = Environment.ExpandEnvironmentVariables(location); cache.IndexCommentsFiles(path, null, true, null); } // Index the comments file documentation sources foreach (string file in currentProject.DocumentationSources.CommentsFiles) { cache.IndexCommentsFiles(Path.GetDirectoryName(file), Path.GetFileName(file), false, null); } // Also, index the comments files in project documentation sources foreach (DocumentationSource ds in currentProject.DocumentationSources) { foreach (var sourceProject in DocumentationSource.Projects(ds.SourceFile, ds.IncludeSubFolders, !String.IsNullOrEmpty(ds.Configuration) ? ds.Configuration : currentProject.Configuration, !String.IsNullOrEmpty(ds.Platform) ? ds.Platform : currentProject.Platform)) { // NOTE: This code should be similar to the code in BuildProcess.ValidateDocumentationSources! // Solutions are followed by the projects that they contain if (sourceProject.ProjectFileName.EndsWith(".sln", StringComparison.OrdinalIgnoreCase)) { lastSolution = sourceProject.ProjectFileName; continue; } // Ignore projects that we've already seen if (projectDictionary.Add(sourceProject.ProjectFileName)) { projRef = new MSBuildProject(sourceProject.ProjectFileName); // Use the project file configuration and platform properties if they are set. If not, // use the documentation source values. If they are not set, use the SHFB project settings. projRef.SetConfiguration( !String.IsNullOrEmpty(sourceProject.Configuration) ? sourceProject.Configuration : !String.IsNullOrEmpty(ds.Configuration) ? ds.Configuration : currentProject.Configuration, !String.IsNullOrEmpty(sourceProject.Platform) ? sourceProject.Platform : !String.IsNullOrEmpty(ds.Platform) ? ds.Platform : currentProject.Platform, currentProject.MSBuildOutDir); // Add Visual Studio solution macros if necessary if (lastSolution != null) { projRef.SetSolutionMacros(lastSolution); } if (!String.IsNullOrEmpty(projRef.XmlCommentsFile)) { cache.IndexCommentsFiles(Path.GetDirectoryName(projRef.XmlCommentsFile), Path.GetFileName(projRef.XmlCommentsFile), false, null); } } } } this.Invoke(new IndexingCompleted(this.Completed), new object[] { cache }); } catch (Exception ex) { System.Diagnostics.Debug.WriteLine(ex.ToString()); this.Invoke(new IndexingFailed(this.Failed), new object[] { ex.Message }); } }