Removed unused help providers and related classes. (#3795)

* Removed unused help providers and related classes.

We do not publish any help content for FAQ, General and Glossary help providers. These were only used in v1 of Powershell.

* Removed XSDs for obsolete help providers

* Removed references from other XSDs.
This commit is contained in:
Aditya Patwardhan
2017-05-17 17:27:48 -07:00
committed by Travis Plunk
parent e00161a8af
commit 779d563d7d
11 changed files with 0 additions and 1373 deletions
-1
View File
@@ -12,7 +12,6 @@
<import schemaLocation="developer.xsd" namespace="http://schemas.microsoft.com/maml/dev/2004/10" />
<include schemaLocation="ITPro.xsd" />
<include schemaLocation="base.xsd" />
<include schemaLocation="glossary.xsd" />
<include schemaLocation="conditionSet.xsd" />
<include schemaLocation="task.xsd" />
</schema>
-1
View File
@@ -19,7 +19,6 @@
-->
<!-- include and import declarations -->
<include schemaLocation="hierarchy.xsd"/>
<include schemaLocation="faq.xsd"/>
<include schemaLocation="troubleshooting.xsd"/>
<include schemaLocation="task.xsd"/>
<include schemaLocation="shellExecute.xsd"/>
-89
View File
@@ -1,89 +0,0 @@
<?xml version="1.0" encoding="utf-8"?>
<schema targetNamespace="http://schemas.microsoft.com/maml/2004/10"
xmlns:doc="http://schemas.microsoft.com/maml/internal"
xmlns:maml="http://schemas.microsoft.com/maml/2004/10"
xmlns="http://www.w3.org/2001/XMLSchema"
elementFormDefault="qualified"
attributeFormDefault="unqualified"
blockDefault="#all"
xml:lang="en">
<!-- Schema documentation -->
<annotation>
<documentation>This schema definition defines the FAQ content model for the Content Studio schema. This schema is part of the base layer.</documentation>
</annotation>
<!-- include and import declarations -->
<include schemaLocation="hierarchy.xsd"/>
<element name="faq" type="maml:faqType">
<annotation>
<documentation>Describes the content model for the FAQ content type. The FAQ content type is used to create frequently asked question (FAQ) documents. A document that uses the FAQ content type can consist of one or more sets of questions and answers.</documentation>
</annotation>
</element>
<element name="faqDiv">
<annotation>
<documentation>Describes a titled division within a frequently asked question (FAQ) document. Each faqDiv element can contain one or more faqEntry elements.</documentation>
</annotation>
<complexType>
<sequence>
<element ref="maml:title"/>
<element ref="maml:subTitle" minOccurs="0"/>
<element ref="maml:introduction" minOccurs="0"/>
<element ref="maml:faqEntry" minOccurs="1" maxOccurs="unbounded"/>
<element ref="maml:transition" minOccurs="0"/>
</sequence>
<attributeGroup ref="maml:contentIdentificationSharingAndConditionGroup"/>
<attribute name="class" type="string"/>
</complexType>
</element>
<element name="faqEntry">
<annotation>
<documentation>Describes a question-answer pair within a frequently asked question (FAQ) document.</documentation>
</annotation>
<complexType>
<sequence>
<element ref="maml:title" minOccurs="0" maxOccurs="1"/>
<element ref="maml:question" minOccurs="1" maxOccurs="1"/>
<element ref="maml:answer" minOccurs="1" maxOccurs="1"/>
<element ref="maml:crossReference" minOccurs="0" maxOccurs="unbounded"/>
</sequence>
<attributeGroup ref="maml:expandCollapseGroup"/>
<attributeGroup ref="maml:contentIdentificationSharingAndConditionGroup"/>
</complexType>
</element>
<element name="question" type="maml:structureSimpleType">
<annotation>
<documentation>Describes the question text for a frequently asked question (FAQ) entry.</documentation>
</annotation>
</element>
<element name="answer" type="maml:structureType">
<annotation>
<documentation>Describes an answer to a frequently asked question (FAQ) entry.</documentation>
</annotation>
</element>
<complexType name="faqType">
<sequence>
<element ref="maml:title"/>
<element ref="maml:subTitle" minOccurs="0"/>
<element ref="maml:introduction" minOccurs="0"/>
<element name="byLine" type="maml:structureSimpleType" minOccurs="0">
<annotation>
<documentation>Specifies the name of the document author.</documentation>
</annotation>
</element>
<element ref="maml:crossReference" minOccurs="0" maxOccurs="unbounded"/>
<choice>
<element ref="maml:faqDiv" maxOccurs="unbounded"/>
<element ref="maml:faqEntry" maxOccurs="unbounded"/>
</choice>
<element ref="maml:transition" minOccurs="0"/>
<element ref="maml:alertSet" minOccurs="0"/>
<element ref="maml:relatedLinks" minOccurs="0"/>
<element ref="maml:reusableContent" minOccurs="0"/>
<element ref="maml:copyright" minOccurs="0"/>
</sequence>
<attribute name="contentType" type="token">
<annotation>
<documentation>Specifies the type of content for the document.</documentation>
</annotation>
</attribute>
</complexType>
</schema>
-54
View File
@@ -1,54 +0,0 @@
<?xml version="1.0" encoding="utf-8"?>
<schema targetNamespace="http://schemas.microsoft.com/maml/2004/10"
xmlns:doc="http://schemas.microsoft.com/maml/internal"
xmlns:maml="http://schemas.microsoft.com/maml/2004/10"
xmlns="http://www.w3.org/2001/XMLSchema"
elementFormDefault="qualified"
attributeFormDefault="unqualified"
blockDefault="#all"
xml:lang="en">
<!-- Schema documentation -->
<annotation>
<documentation>This schema definition defines the glossary content type for the Content Studio Schema. This schema is part of the base layer.</documentation>
</annotation>
<include schemaLocation="structure.xsd"/>
<!-- element declarations -->
<element name="glossary">
<annotation>
<documentation>Describes the content model for the glossary content type. Glossary topics contain a set of terms and associated definitions.</documentation>
</annotation>
<complexType>
<sequence>
<element ref="maml:title"/>
<element ref="maml:subTitle" minOccurs="0"/>
<choice>
<element ref="maml:glossaryDiv" maxOccurs="unbounded"/>
<element ref="maml:glossaryEntry" maxOccurs="unbounded"/>
</choice>
</sequence>
<attribute name="contentType" type="token">
<annotation>
<documentation>Specifies the type of content for the document.</documentation>
</annotation>
</attribute>
<attributeGroup ref="maml:contentIdentificationSharingAndConditionGroup"/>
</complexType>
</element>
<element name="glossaryDiv">
<annotation>
<documentation>Describes a titled section within a glossary. Each glossaryDiv element can contain one or more glossaryEntry elements. </documentation>
</annotation>
<complexType>
<sequence>
<element ref="maml:title"/>
<element ref="maml:glossaryEntry" maxOccurs="unbounded"/>
</sequence>
<attributeGroup ref="maml:contentIdentificationSharingAndConditionGroup"/>
<attribute name="class" type="string">
<annotation>
<documentation>Specifies the class of the element.</documentation>
</annotation>
</attribute>
</complexType>
</element>
</schema>
@@ -1,221 +0,0 @@
/********************************************************************++
Copyright (c) Microsoft Corporation. All rights reserved.
--********************************************************************/
using System.Collections;
using System.Xml;
using System.Diagnostics.CodeAnalysis; // for fxcop
namespace System.Management.Automation
{
/// <summary>
///
/// Class FaqHelpInfo keeps track of help information to be returned by
/// faq help provider.
///
/// </summary>
internal class FaqHelpInfo : HelpInfo
{
/// <summary>
/// Constructor for FaqHelpInfo
/// </summary>
/// <remarks>
/// This constructor is can be called only from constructors of derived class
/// for FaqHelpInfo. The only way to to create a FaqHelpInfo is through
/// static function
/// Load(XmlNode node)
/// where some sanity check is done.
/// </remarks>
[SuppressMessage("Microsoft.Usage", "CA2214:DoNotCallOverridableMethodsInConstructors", Justification = "This is internal code and is verified.")]
protected FaqHelpInfo(XmlNode xmlNode)
{
MamlNode mamlNode = new MamlNode(xmlNode);
_fullHelpObject = mamlNode.PSObject;
this.Errors = mamlNode.Errors;
_fullHelpObject.TypeNames.Clear();
_fullHelpObject.TypeNames.Add(string.Format(Globalization.CultureInfo.InvariantCulture,
"FaqHelpInfo#{0}", Name));
_fullHelpObject.TypeNames.Add("FaqHelpInfo");
_fullHelpObject.TypeNames.Add("HelpInfo");
}
#region Basic Help Properties / Methods
/// <summary>
/// Name of faq.
/// </summary>
/// <value>Name of faq</value>
internal override string Name
{
get
{
if (_fullHelpObject == null)
return "";
if (_fullHelpObject.Properties["Title"] == null)
return "";
if (_fullHelpObject.Properties["Title"].Value == null)
return "";
string name = _fullHelpObject.Properties["Title"].Value.ToString();
if (name == null)
return "";
return name.Trim();
}
}
/// <summary>
/// Synopsis for this faq help.
/// </summary>
/// <value>Synopsis for this faq help</value>
internal override string Synopsis
{
get
{
if (_fullHelpObject == null)
return "";
if (_fullHelpObject.Properties["question"] == null)
return "";
if (_fullHelpObject.Properties["question"].Value == null)
return "";
string synopsis = _fullHelpObject.Properties["question"].Value.ToString();
if (synopsis == null)
return "";
return synopsis.Trim();
}
}
/// <summary>
/// Help category for this faq help, which is constantly HelpCategory.FAQ.
/// </summary>
/// <value>Help category for this faq help</value>
internal override HelpCategory HelpCategory
{
get
{
return HelpCategory.FAQ;
}
}
private PSObject _fullHelpObject;
/// <summary>
/// Full help object for this help item.
/// </summary>
/// <value>Full help object for this help item.</value>
internal override PSObject FullHelp
{
get
{
return _fullHelpObject;
}
}
/// <summary>
/// Returns true if help content in help info matches the
/// pattern contained in <paramref name="pattern"/>.
/// The underlying code will usually run pattern.IsMatch() on
/// content it wants to search.
/// FAQ help info looks for pattern in Synopsis and
/// Answers
/// </summary>
/// <param name="pattern"></param>
/// <returns></returns>
internal override bool MatchPatternInContent(WildcardPattern pattern)
{
Diagnostics.Assert(null != pattern, "pattern cannot be null");
string synopsis = Synopsis;
string answers = Answers;
if (null == synopsis)
{
synopsis = string.Empty;
}
if (null == Answers)
{
answers = string.Empty;
}
return pattern.IsMatch(synopsis) || pattern.IsMatch(answers);
}
#endregion
#region Private Methods / Properties
/// <summary>
/// Answers string of this FAQ help info.
/// </summary>
private string Answers
{
get
{
if (this.FullHelp == null)
return "";
if (this.FullHelp.Properties["answer"] == null ||
this.FullHelp.Properties["answer"].Value == null)
{
return "";
}
IList answerItems = FullHelp.Properties["answer"].Value as IList;
if (answerItems == null || answerItems.Count == 0)
{
return "";
}
Text.StringBuilder result = new Text.StringBuilder();
foreach (object answerItem in answerItems)
{
PSObject answerObject = PSObject.AsPSObject(answerItem);
if ((null == answerObject) ||
(null == answerObject.Properties["Text"]) ||
(null == answerObject.Properties["Text"].Value))
{
continue;
}
string text = answerObject.Properties["Text"].Value.ToString();
result.Append(text);
result.Append(Environment.NewLine);
}
return result.ToString().Trim();
}
}
#endregion
#region Load
/// <summary>
/// Create a FaqHelpInfo object from an XmlNode.
/// </summary>
/// <param name="xmlNode">xmlNode that contains help info</param>
/// <returns>FaqHelpInfo object created</returns>
internal static FaqHelpInfo Load(XmlNode xmlNode)
{
FaqHelpInfo faqHelpInfo = new FaqHelpInfo(xmlNode);
if (String.IsNullOrEmpty(faqHelpInfo.Name))
return null;
faqHelpInfo.AddCommonHelpProperties();
return faqHelpInfo;
}
#endregion
}
}
@@ -1,232 +0,0 @@
/********************************************************************++
Copyright (c) Microsoft Corporation. All rights reserved.
--********************************************************************/
using System.IO;
using System.Collections;
using System.Collections.ObjectModel;
using System.Xml;
using System.Reflection;
namespace System.Management.Automation
{
/// <summary>
/// Class FaqHelpProvider implement the help provider for faq's.
/// </summary>
///
/// <remarks>
/// Faq Help information are stored in 'faq.xml' files. These files are
/// located in the Monad / CustomShell Path as well as in the Application Base
/// of PSSnapIns
/// </remarks>
internal class FaqHelpProvider : HelpProviderWithFullCache
{
/// <summary>
/// Constructor for FaqHelpProvider
/// </summary>
internal FaqHelpProvider(HelpSystem helpSystem) : base(helpSystem)
{
}
#region Common Properties
/// <summary>
/// Name of this provider
/// </summary>
/// <value>Name of this provider</value>
internal override string Name
{
get
{
return "FAQ Help Provider";
}
}
/// <summary>
/// Help category for this provider, which is a constant: HelpCategory.FAQ.
/// </summary>
/// <value>Help category for this provider</value>
internal override HelpCategory HelpCategory
{
get
{
return HelpCategory.FAQ;
}
}
#endregion
#region Load cache
/// <summary>
/// Load cache for faq help's
/// </summary>
internal sealed override void LoadCache()
{
Collection<String> files = MUIFileSearcher.SearchFiles("*.faq.xml", GetSearchPaths());
if (files == null)
return;
foreach (string file in files)
{
if (!_helpFiles.ContainsKey(file))
{
LoadHelpFile(file);
// Add this file into _helpFiles hashtable to prevent it to be loaded again.
_helpFiles[file] = 0;
}
}
}
/// <summary>
/// Load help file for HelpInfo objects. The HelpInfo objects will be
/// put into help cache.
/// </summary>
/// <remarks>
/// 1. Needs to pay special attention about error handling in this function.
/// Common errors include: file not found and invalid xml. None of these error
/// should cause help search to stop.
/// </remarks>
/// <param name="helpFile"></param>
private void LoadHelpFile(string helpFile)
{
if (String.IsNullOrEmpty(helpFile))
{
return;
}
XmlDocument doc;
try
{
doc = InternalDeserializer.LoadUnsafeXmlDocument(
new FileInfo(helpFile),
false, /* ignore whitespace, comments, etc. */
null); /* default maxCharactersInDocument */
}
catch (IOException ioException)
{
ErrorRecord errorRecord = new ErrorRecord(ioException, "HelpFileLoadFailure", ErrorCategory.OpenError, null);
errorRecord.ErrorDetails = new ErrorDetails(typeof(FaqHelpProvider).GetTypeInfo().Assembly, "HelpErrors", "HelpFileLoadFailure", helpFile, ioException.Message);
this.HelpSystem.LastErrors.Add(errorRecord);
return;
}
catch (System.Security.SecurityException securityException)
{
ErrorRecord errorRecord = new ErrorRecord(securityException, "HelpFileNotAccessible", ErrorCategory.OpenError, null);
errorRecord.ErrorDetails = new ErrorDetails(typeof(FaqHelpProvider).GetTypeInfo().Assembly, "HelpErrors", "HelpFileNotAccessible", helpFile, securityException.Message);
this.HelpSystem.LastErrors.Add(errorRecord);
return;
}
catch (XmlException xmlException)
{
ErrorRecord errorRecord = new ErrorRecord(xmlException, "HelpFileNotValid", ErrorCategory.SyntaxError, null);
errorRecord.ErrorDetails = new ErrorDetails(typeof(FaqHelpProvider).GetTypeInfo().Assembly, "HelpErrors", "HelpFileNotValid", helpFile, xmlException.Message);
this.HelpSystem.LastErrors.Add(errorRecord);
return;
}
XmlNode helpItemsNode = null;
if (doc.HasChildNodes)
{
for (int i = 0; i < doc.ChildNodes.Count; i++)
{
XmlNode node = doc.ChildNodes[i];
if (node.NodeType == XmlNodeType.Element && String.Compare(node.Name, "faq", StringComparison.OrdinalIgnoreCase) == 0)
{
helpItemsNode = node;
break;
}
}
}
if (helpItemsNode == null)
return;
using (this.HelpSystem.Trace(helpFile))
{
if (helpItemsNode.HasChildNodes)
{
for (int i = 0; i < helpItemsNode.ChildNodes.Count; i++)
{
XmlNode node = helpItemsNode.ChildNodes[i];
if (node.NodeType == XmlNodeType.Element && String.Compare(node.Name, "faqEntry", StringComparison.OrdinalIgnoreCase) == 0)
{
HelpInfo helpInfo = null;
helpInfo = FaqHelpInfo.Load(node);
if (helpInfo != null)
{
this.HelpSystem.TraceErrors(helpInfo.Errors);
AddCache(helpInfo.Name, helpInfo);
}
continue;
}
if (node.NodeType == XmlNodeType.Element && String.Compare(node.Name, "faqDiv", StringComparison.OrdinalIgnoreCase) == 0)
{
LoadFaqDiv(node);
}
}
}
}
}
/// <summary>
///
/// </summary>
/// <param name="xmlNode"></param>
private void LoadFaqDiv(XmlNode xmlNode)
{
if (xmlNode == null)
return;
for (int i = 0; i < xmlNode.ChildNodes.Count; i++)
{
XmlNode node = xmlNode.ChildNodes[i];
if (node.NodeType == XmlNodeType.Element && String.Compare(node.Name, "faqEntry", StringComparison.OrdinalIgnoreCase) == 0)
{
HelpInfo helpInfo = null;
helpInfo = FaqHelpInfo.Load(node);
if (helpInfo != null)
{
this.HelpSystem.TraceErrors(helpInfo.Errors);
AddCache(helpInfo.Name, helpInfo);
}
}
}
}
#endregion
# region Help Provider Interface
/// <summary>
/// This will reset the help cache. Normally this corresponds to a
/// help culture change.
/// </summary>
internal override void Reset()
{
base.Reset();
_helpFiles.Clear();
}
#endregion
#region Private Data
/// <summary>
/// This is a hashtable to track which help files are loaded already.
///
/// This will avoid one help file getting loaded again and again.
/// </summary>
private readonly Hashtable _helpFiles = new Hashtable();
#endregion
}
}
@@ -1,130 +0,0 @@
/********************************************************************++
Copyright (c) Microsoft Corporation. All rights reserved.
--********************************************************************/
using System.Xml;
using System.Diagnostics.CodeAnalysis; // for fxcop
namespace System.Management.Automation
{
/// <summary>
///
/// Class GeneralHelpInfo keeps track of help information to be returned by
/// general help provider.
///
/// </summary>
internal class GeneralHelpInfo : HelpInfo
{
/// <summary>
/// Constructor for GeneralHelpInfo
/// </summary>
/// <remarks>
/// This constructor is can be called only from constructors of derived class
/// for GeneralHelpInfo. The only way to to create a GeneralHelpInfo is through
/// static function
/// Load(XmlNode node)
/// where some sanity check is done.
/// </remarks>
[SuppressMessage("Microsoft.Usage", "CA2214:DoNotCallOverridableMethodsInConstructors", Justification = "This is internal and the code path is verified.")]
protected GeneralHelpInfo(XmlNode xmlNode)
{
MamlNode mamlNode = new MamlNode(xmlNode);
_fullHelpObject = mamlNode.PSObject;
this.Errors = mamlNode.Errors;
_fullHelpObject.TypeNames.Clear();
_fullHelpObject.TypeNames.Add(string.Format(Globalization.CultureInfo.InvariantCulture,
"GeneralHelpInfo#{0}", Name));
_fullHelpObject.TypeNames.Add("GeneralHelpInfo");
_fullHelpObject.TypeNames.Add("HelpInfo");
}
#region Basic Help Properties
/// <summary>
/// Name of help content.
/// </summary>
/// <value>Name of help content</value>
internal override string Name
{
get
{
if (_fullHelpObject == null)
return "";
if (_fullHelpObject.Properties["Title"] == null)
return "";
if (_fullHelpObject.Properties["Title"].Value == null)
return "";
string name = _fullHelpObject.Properties["Title"].Value.ToString();
if (name == null)
return "";
return name.Trim();
}
}
/// <summary>
/// Synopsis for this general help.
/// </summary>
/// <value>Synopsis for this general help</value>
internal override string Synopsis
{
get
{
return "";
}
}
/// <summary>
/// Help category for this general help, which is constantly HelpCategory.General.
/// </summary>
/// <value>Help category for general help</value>
internal override HelpCategory HelpCategory
{
get
{
return HelpCategory.General;
}
}
private PSObject _fullHelpObject;
/// <summary>
/// Full help object for this help item.
/// </summary>
/// <value>Full help object for this help item.</value>
internal override PSObject FullHelp
{
get
{
return _fullHelpObject;
}
}
#endregion
#region Load
/// <summary>
/// Create a GeneralHelpInfo object from an XmlNode.
/// </summary>
/// <param name="xmlNode">xmlNode that contains help info</param>
/// <returns>GeneralHelpInfo object created</returns>
internal static GeneralHelpInfo Load(XmlNode xmlNode)
{
GeneralHelpInfo generalHelpInfo = new GeneralHelpInfo(xmlNode);
if (String.IsNullOrEmpty(generalHelpInfo.Name))
return null;
generalHelpInfo.AddCommonHelpProperties();
return generalHelpInfo;
}
#endregion
}
}
@@ -1,200 +0,0 @@
/********************************************************************++
Copyright (c) Microsoft Corporation. All rights reserved.
--********************************************************************/
using System.IO;
using System.Collections;
using System.Collections.ObjectModel;
using System.Xml;
using System.Reflection;
namespace System.Management.Automation
{
/// <summary>
/// Class GeneralHelpProvider implement the help provider for general help topics.
/// </summary>
///
/// <remarks>
/// General Help information are stored in 'concept.xml' files. These files are
/// located in the Monad / CustomShell Path as well as in the Application Base
/// of PSSnapIns
/// </remarks>
internal class GeneralHelpProvider : HelpProviderWithFullCache
{
/// <summary>
/// Constructor for GeneralHelpProvider
/// </summary>
internal GeneralHelpProvider(HelpSystem helpSystem) : base(helpSystem)
{
}
#region Common Properties
/// <summary>
/// Name of this provider
/// </summary>
/// <value>Name of this provider</value>
internal override string Name
{
get
{
return "General Help Provider";
}
}
/// <summary>
/// Help category for this provider, which is a constant: HelpCategory.Command.
/// </summary>
/// <value>Help category for this provider</value>
internal override HelpCategory HelpCategory
{
get
{
return HelpCategory.General;
}
}
#endregion
#region Load cache
/// <summary>
/// Load cache for general help's
/// </summary>
internal sealed override void LoadCache()
{
Collection<String> files = MUIFileSearcher.SearchFiles("*.concept.xml", GetSearchPaths());
if (files == null)
return;
foreach (string file in files)
{
if (!_helpFiles.ContainsKey(file))
{
LoadHelpFile(file);
// Add this file into _helpFiles hashtable to prevent it to be loaded again.
_helpFiles[file] = 0;
}
}
}
/// <summary>
/// Load help file for HelpInfo objects. The HelpInfo objects will be
/// put into help cache.
/// </summary>
/// <remarks>
/// 1. Needs to pay special attention about error handling in this function.
/// Common errors include: file not found and invalid xml. None of these error
/// should cause help search to stop.
/// </remarks>
/// <param name="helpFile"></param>
private void LoadHelpFile(string helpFile)
{
if (String.IsNullOrEmpty(helpFile))
{
return;
}
XmlDocument doc;
try
{
doc = InternalDeserializer.LoadUnsafeXmlDocument(
new FileInfo(helpFile),
false, /* ignore whitespace, comments, etc. */
null); /* default maxCharactersInDocument */
}
catch (IOException ioException)
{
ErrorRecord errorRecord = new ErrorRecord(ioException, "HelpFileLoadFailure", ErrorCategory.OpenError, null);
errorRecord.ErrorDetails = new ErrorDetails(typeof(GeneralHelpProvider).GetTypeInfo().Assembly, "HelpErrors", "HelpFileLoadFailure", helpFile, ioException.Message);
this.HelpSystem.LastErrors.Add(errorRecord);
return;
}
catch (System.Security.SecurityException securityException)
{
ErrorRecord errorRecord = new ErrorRecord(securityException, "HelpFileNotAccessible", ErrorCategory.OpenError, null);
errorRecord.ErrorDetails = new ErrorDetails(typeof(GeneralHelpProvider).GetTypeInfo().Assembly, "HelpErrors", "HelpFileNotAccessible", helpFile, securityException.Message);
this.HelpSystem.LastErrors.Add(errorRecord);
return;
}
catch (XmlException xmlException)
{
ErrorRecord errorRecord = new ErrorRecord(xmlException, "HelpFileNotValid", ErrorCategory.SyntaxError, null);
errorRecord.ErrorDetails = new ErrorDetails(typeof(GeneralHelpProvider).GetTypeInfo().Assembly, "HelpErrors", "HelpFileNotValid", helpFile, xmlException.Message);
this.HelpSystem.LastErrors.Add(errorRecord);
return;
}
XmlNode helpItemsNode = null;
if (doc.HasChildNodes)
{
for (int i = 0; i < doc.ChildNodes.Count; i++)
{
XmlNode node = doc.ChildNodes[i];
if (node.NodeType == XmlNodeType.Element && String.Compare(node.Name, "conceptuals", StringComparison.OrdinalIgnoreCase) == 0)
{
helpItemsNode = node;
break;
}
}
}
if (helpItemsNode == null)
return;
using (this.HelpSystem.Trace(helpFile))
{
if (helpItemsNode.HasChildNodes)
{
for (int i = 0; i < helpItemsNode.ChildNodes.Count; i++)
{
XmlNode node = helpItemsNode.ChildNodes[i];
if (node.NodeType == XmlNodeType.Element && String.Compare(node.Name, "conceptual", StringComparison.OrdinalIgnoreCase) == 0)
{
HelpInfo helpInfo = null;
helpInfo = GeneralHelpInfo.Load(node);
if (helpInfo != null)
{
this.HelpSystem.TraceErrors(helpInfo.Errors);
AddCache(helpInfo.Name, helpInfo);
}
}
}
}
}
}
#endregion
# region Help Provider Interface
/// <summary>
/// This will reset the help cache. Normally this corresponds to a
/// help culture change.
/// </summary>
internal override void Reset()
{
base.Reset();
_helpFiles.Clear();
}
#endregion
#region Private Data
/// <summary>
/// This is a hashtable to track which help files are loaded already.
///
/// This will avoid one help file getting loaded again and again.
/// </summary>
private readonly Hashtable _helpFiles = new Hashtable();
#endregion
}
}
@@ -1,168 +0,0 @@
/********************************************************************++
Copyright (c) Microsoft Corporation. All rights reserved.
--********************************************************************/
using System.Xml;
using System.Text;
using System.Diagnostics.CodeAnalysis;
namespace System.Management.Automation
{
/// <summary>
///
/// Class GlossaryHelpInfo keeps track of help information to be returned by
/// glossary help provider.
///
/// </summary>
internal class GlossaryHelpInfo : HelpInfo
{
/// <summary>
/// Constructor for GlossaryHelpInfo
/// </summary>
/// <remarks>
/// This constructor is can be called only from constructors of derived class
/// for GlossaryHelpInfo. The only way to to create a GlossaryHelpInfo is through
/// static function
/// Load(XmlNode node)
/// where some sanity check is done.
/// </remarks>
[SuppressMessage("Microsoft.Usage", "CA2214:DoNotCallOverridableMethodsInConstructors", Justification = "This is internal code and is verified.")]
protected GlossaryHelpInfo(XmlNode xmlNode)
{
MamlNode mamlNode = new MamlNode(xmlNode);
_fullHelpObject = mamlNode.PSObject;
this.Errors = mamlNode.Errors;
Name = GetTerm();
_fullHelpObject.TypeNames.Clear();
_fullHelpObject.TypeNames.Add(string.Format(Globalization.CultureInfo.InvariantCulture,
"GlossaryHelpInfo#{0}", Name));
_fullHelpObject.TypeNames.Add("GlossaryHelpInfo");
_fullHelpObject.TypeNames.Add("HelpInfo");
}
#region Basic Help Properties
/// <summary>
/// Name of glossary.
/// </summary>
/// <value>Name of glossary</value>
internal override string Name { get; } = "";
private string GetTerm()
{
if (_fullHelpObject == null)
return "";
if (_fullHelpObject.Properties["Terms"] == null)
return "";
if (_fullHelpObject.Properties["Terms"].Value == null)
return "";
PSObject terms = (PSObject)_fullHelpObject.Properties["Terms"].Value;
if (terms.Properties["Term"] == null)
return "";
if (terms.Properties["Term"].Value == null)
return "";
if (terms.Properties["Term"].Value.GetType().Equals(typeof(PSObject)))
{
PSObject term = (PSObject)terms.Properties["Term"].Value;
return term.ToString();
}
if (terms.Properties["Term"].Value.GetType().Equals(typeof(PSObject[])))
{
PSObject[] term = (PSObject[])terms.Properties["Term"].Value;
StringBuilder result = new StringBuilder();
for (int i = 0; i < term.Length; i++)
{
string str = term[i].ToString();
if (str == null)
continue;
str = str.Trim();
if (String.IsNullOrEmpty(str))
continue;
if (result.Length > 0)
result.Append(", ");
result.Append(str);
}
return result.ToString();
}
return "";
}
/// <summary>
/// Synopsis for this glossary help.
/// </summary>
/// <value>Synopsis for this glossary help</value>
internal override string Synopsis
{
get
{
return "";
}
}
/// <summary>
/// Help category for this glossary help, which is constantly HelpCategory.Glossary.
/// </summary>
/// <value>Help category for this glossary help</value>
internal override HelpCategory HelpCategory
{
get
{
return HelpCategory.Glossary;
}
}
private PSObject _fullHelpObject;
/// <summary>
/// Full help object for this help item.
/// </summary>
/// <value>Full help object for this help item.</value>
internal override PSObject FullHelp
{
get
{
return _fullHelpObject;
}
}
#endregion
#region Load
/// <summary>
/// Create a GlossaryHelpInfo object from an XmlNode.
/// </summary>
/// <param name="xmlNode">xmlNode that contains help info</param>
/// <returns>GlossaryHelpInfo object created</returns>
internal static GlossaryHelpInfo Load(XmlNode xmlNode)
{
GlossaryHelpInfo glossaryHelpInfo = new GlossaryHelpInfo(xmlNode);
if (String.IsNullOrEmpty(glossaryHelpInfo.Name))
return null;
glossaryHelpInfo.AddCommonHelpProperties();
return glossaryHelpInfo;
}
#endregion
}
}
@@ -1,268 +0,0 @@
/********************************************************************++
Copyright (c) Microsoft Corporation. All rights reserved.
--********************************************************************/
using System.IO;
using System.Collections;
using System.Collections.ObjectModel;
using System.Xml;
using System.Reflection;
namespace System.Management.Automation
{
/// <summary>
/// Class GlossaryHelpProvider implement the help provider for glossary's.
/// </summary>
///
/// <remarks>
/// Glossary Help information are stored in 'glossary.xml' files. These files are
/// located in the Monad / CustomShell Path as well as in the Application Base
/// of PSSnapIns
/// </remarks>
internal class GlossaryHelpProvider : HelpProviderWithFullCache
{
/// <summary>
/// Constructor for GlossaryHelpProvider
/// </summary>
internal GlossaryHelpProvider(HelpSystem helpSystem) : base(helpSystem)
{
this.HasCustomMatch = true;
}
#region Common Properties
/// <summary>
/// Name of this provider
/// </summary>
/// <value>Name of this provider</value>
internal override string Name
{
get
{
return "Glossary Help Provider";
}
}
/// <summary>
/// Help category for this provider, which is a constant: HelpCategory.Command.
/// </summary>
/// <value>Help category for this provider</value>
internal override HelpCategory HelpCategory
{
get
{
return HelpCategory.Glossary;
}
}
#endregion
#region Load cache
/// <summary>
/// This is for implementing CustomMatch algorithm to be used in
/// HelpProviderWithCache for matching a help target with keys in
/// help cache.
///
/// For each glossary entry, it can contain multiple terms. The
/// key stored in help cache is a concatenation of keys. For example,
/// if there are two terms "foo" and "bar", the key to be used in
/// help cache will be "foo, bar".
///
/// Because of this mangling, key "foo, bar" should match both
/// "foo" and "bar".
///
/// </summary>
/// <param name="target">target to search</param>
/// <param name="key">key used in cache table</param>
/// <returns></returns>
protected sealed override bool CustomMatch(string target, string key)
{
if (String.IsNullOrEmpty(target) || String.IsNullOrEmpty(key))
return false;
string[] terms = key.Split(Utils.Separators.Comma);
for (int i = 0; i < terms.Length; i++)
{
string term = terms[i].Trim();
if (term.Equals(target, StringComparison.OrdinalIgnoreCase))
return true;
}
return false;
}
/// <summary>
/// Load cache for glossary help's
/// </summary>
internal sealed override void LoadCache()
{
Collection<String> files = MUIFileSearcher.SearchFiles("*.glossary.xml", GetSearchPaths());
if (files == null)
return;
foreach (string file in files)
{
if (!_helpFiles.ContainsKey(file))
{
LoadHelpFile(file);
// Add this file into _helpFiles hashtable to prevent it to be loaded again.
_helpFiles[file] = 0;
}
}
}
/// <summary>
/// Load help file for HelpInfo objects. The HelpInfo objects will be
/// put into help cache.
/// </summary>
/// <remarks>
/// 1. Needs to pay special attention about error handling in this function.
/// Common errors include: file not found and invalid xml. None of these error
/// should cause help search to stop.
/// </remarks>
/// <param name="helpFile"></param>
private void LoadHelpFile(string helpFile)
{
if (String.IsNullOrEmpty(helpFile))
{
return;
}
XmlDocument doc;
try
{
doc = InternalDeserializer.LoadUnsafeXmlDocument(
new FileInfo(helpFile),
false, /* ignore whitespace, comments, etc. */
null); /* default maxCharactersInDocument */
}
catch (IOException ioException)
{
ErrorRecord errorRecord = new ErrorRecord(ioException, "HelpFileLoadFailure", ErrorCategory.OpenError, null);
errorRecord.ErrorDetails = new ErrorDetails(typeof(GlossaryHelpProvider).GetTypeInfo().Assembly, "HelpErrors", "HelpFileLoadFailure", helpFile, ioException.Message);
this.HelpSystem.LastErrors.Add(errorRecord);
return;
}
catch (System.Security.SecurityException securityException)
{
ErrorRecord errorRecord = new ErrorRecord(securityException, "HelpFileNotAccessible", ErrorCategory.OpenError, null);
errorRecord.ErrorDetails = new ErrorDetails(typeof(GlossaryHelpProvider).GetTypeInfo().Assembly, "HelpErrors", "HelpFileNotAccessible", helpFile, securityException.Message);
this.HelpSystem.LastErrors.Add(errorRecord);
return;
}
catch (XmlException xmlException)
{
ErrorRecord errorRecord = new ErrorRecord(xmlException, "HelpFileNotValid", ErrorCategory.SyntaxError, null);
errorRecord.ErrorDetails = new ErrorDetails(typeof(GlossaryHelpProvider).GetTypeInfo().Assembly, "HelpErrors", "HelpFileNotValid", helpFile, xmlException.Message);
this.HelpSystem.LastErrors.Add(errorRecord);
return;
}
XmlNode helpItemsNode = null;
if (doc.HasChildNodes)
{
for (int i = 0; i < doc.ChildNodes.Count; i++)
{
XmlNode node = doc.ChildNodes[i];
if (node.NodeType == XmlNodeType.Element && String.Compare(node.Name, "glossary", StringComparison.OrdinalIgnoreCase) == 0)
{
helpItemsNode = node;
break;
}
}
}
if (helpItemsNode == null)
return;
using (this.HelpSystem.Trace(helpFile))
{
if (helpItemsNode.HasChildNodes)
{
for (int i = 0; i < helpItemsNode.ChildNodes.Count; i++)
{
XmlNode node = helpItemsNode.ChildNodes[i];
if (node.NodeType == XmlNodeType.Element && String.Compare(node.Name, "glossaryEntry", StringComparison.OrdinalIgnoreCase) == 0)
{
HelpInfo helpInfo = null;
helpInfo = GlossaryHelpInfo.Load(node);
if (helpInfo != null)
{
this.HelpSystem.TraceErrors(helpInfo.Errors);
AddCache(helpInfo.Name, helpInfo);
}
continue;
}
if (node.NodeType == XmlNodeType.Element && String.Compare(node.Name, "glossaryDiv", StringComparison.OrdinalIgnoreCase) == 0)
{
LoadGlossaryDiv(node);
}
}
}
}
}
/// <summary>
///
/// </summary>
/// <param name="xmlNode"></param>
private void LoadGlossaryDiv(XmlNode xmlNode)
{
if (xmlNode == null)
return;
for (int i = 0; i < xmlNode.ChildNodes.Count; i++)
{
XmlNode node = xmlNode.ChildNodes[i];
if (node.NodeType == XmlNodeType.Element && String.Compare(node.Name, "glossaryEntry", StringComparison.OrdinalIgnoreCase) == 0)
{
HelpInfo helpInfo = null;
helpInfo = GlossaryHelpInfo.Load(node);
if (helpInfo != null)
{
this.HelpSystem.TraceErrors(helpInfo.Errors);
AddCache(helpInfo.Name, helpInfo);
}
}
}
}
#endregion
# region Help Provider Interface
/// <summary>
/// This will reset the help cache. Normally this corresponds to a
/// help culture change.
/// </summary>
internal override void Reset()
{
base.Reset();
_helpFiles.Clear();
}
#endregion
#region Private Data
/// <summary>
/// This is a hashtable to track which help files are loaded already.
///
/// This will avoid one help file getting loaded again and again.
/// </summary>
private readonly Hashtable _helpFiles = new Hashtable();
#endregion
}
}
@@ -612,15 +612,6 @@ namespace System.Management.Automation
helpProvider = new HelpFileHelpProvider(this);
_helpProviders.Add(helpProvider);
helpProvider = new FaqHelpProvider(this);
_helpProviders.Add(helpProvider);
helpProvider = new GlossaryHelpProvider(this);
_helpProviders.Add(helpProvider);
helpProvider = new GeneralHelpProvider(this);
_helpProviders.Add(helpProvider);
helpProvider = new DefaultHelpProvider(this);
_helpProviders.Add(helpProvider);
}