Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

sorting parameters by position then by required and then by name in syntax generation #19

Merged
merged 1 commit into from
Apr 27, 2016
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
4 changes: 3 additions & 1 deletion XmlDoc2CmdletDoc.Core/Engine.cs
Original file line number Diff line number Diff line change
Expand Up @@ -324,7 +324,9 @@ private XElement GenerateSyntaxItemElement(ICommentReader commentReader, Command
{
var syntaxItemElement = new XElement(CommandNs + "syntaxItem",
new XElement(MamlNs + "name", command.Name));
foreach (var parameter in command.GetParameters(parameterSetName))
foreach (var parameter in command.GetParameters(parameterSetName).OrderBy(p => p.GetPosition(parameterSetName)).
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

p.GetPosition returns a string, which may be any of the following:

  • "n", where n is an integer, taken from the Position property of the Parameter attribute, if it is specified.
  • "named" if the Position property is equal to int.MinValue, which is the default value if the Position hasn't actually been set.. I cannot remember under what circumstances this might happen.
  • null if XmlDoc2CmdletDoc is unable to retrieve a value for the current parameter set being documented.

This rather relies on parameter positions being single digits, and that "1" and "2", for example, are lexicographically lower than "named" and null. This is probably good enough in most circumstances, but I'll probably revisit this area of the code at some point to make things a bit more explicit.

ThenBy(p => p.IsRequired(parameterSetName) ? "0" : "1").
ThenBy(p => p.Name))
{
syntaxItemElement.Add(GenerateComment("Parameter: " + parameter.Name));
syntaxItemElement.Add(GenerateParameterElement(commentReader, parameter, parameterSetName, reportWarning));
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,48 @@
using System.Management.Automation;

namespace XmlDoc2CmdletDoc.TestModule.PositionedParameters
{
/// <summary>
/// <para type="synopsis">This is part of the Test-PositionedParameters synopsis.</para>
/// <para type="description">This is part of the Test-PositionedParameters description.</para>
/// </summary>
[Cmdlet(VerbsDiagnostic.Test, "PositionedParameters")]
public class TestPositionedParametersCommand : Cmdlet
{
/// <summary>
/// <para type="description">This is part of the ParameterA description.</para>
/// </summary>
[Parameter(Position = 3)]
public string ParameterA { get; set; }

/// <summary>
/// <para type="description">This is part of the ParameterB description.</para>
/// </summary>
[Parameter(Position = 2)]
public string ParameterB { get; set; }

/// <summary>
/// <para type="description">This is part of the ParameterC description.</para>
/// </summary>
[Parameter(Position = 0)]
public string ParameterC { get; set; }

/// <summary>
/// <para type="description">This is part of the ParameterD description.</para>
/// </summary>
[Parameter(Position = 1)]
public string ParameterD { get; set; }

/// <summary>
/// <para type="description">This is part of the ParameterE description.</para>
/// </summary>
[Parameter]
public string ParameterE { get; set; }

/// <summary>
/// <para type="description">This is part of the ParameterF description.</para>
/// </summary>
[Parameter(Mandatory = true)]
public string ParameterF { get; set; }
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -47,6 +47,7 @@
<Compile Include="Maml\TestMamlElementsCommand.cs" />
<Compile Include="Manual\ManualClass.cs" />
<Compile Include="Manual\TestManualElementsCommand.cs" />
<Compile Include="PositionedParameters\TestPositionedParametersCommand.cs" />
<Compile Include="Properties\AssemblyInfo.cs" />
<Compile Include="InputTypes\InputTypeClass.cs" />
<Compile Include="References\TestReferencesCommand.cs" />
Expand Down
35 changes: 35 additions & 0 deletions XmlDoc2CmdletDoc.Tests/AcceptanceTests.cs
Original file line number Diff line number Diff line change
Expand Up @@ -38,6 +38,7 @@ static AcceptanceTests()
private XElement testMamlElementsCommandElement;
private XElement testReferencesCommandElement;
private XElement testInputTypesCommandElement;
private XElement testPositionedParametersCommandElement;

[TestFixtureSetUp]
public void SetUp()
Expand Down Expand Up @@ -67,6 +68,7 @@ public void SetUp()
testMamlElementsCommandElement = rootElement.XPathSelectElement("command:command[command:details/command:name/text() = 'Test-MamlElements']", resolver);
testReferencesCommandElement = rootElement.XPathSelectElement("command:command[command:details/command:name/text() = 'Test-References']", resolver);
testInputTypesCommandElement = rootElement.XPathSelectElement("command:command[command:details/command:name/text() = 'Test-InputTypes']", resolver);
testPositionedParametersCommandElement = rootElement.XPathSelectElement("command:command[command:details/command:name/text() = 'Test-PositionedParameters']", resolver);
}

[Test]
Expand Down Expand Up @@ -798,5 +800,38 @@ private void CheckMamlClassType(XElement type, bool expectADescription)
@"<maml:description xmlns:maml=""http://schemas.microsoft.com/maml/2004/10"">
<maml:para>This is the MamlClass description.</maml:para>
</maml:description>";

[Test]
public void Command_Syntax_Parameters_Ordered_By_Position()
{
Assert.That(testPositionedParametersCommandElement, Is.Not.Null);

var syntaxItemParameters = testPositionedParametersCommandElement.XPathSelectElements("command:syntax/command:syntaxItem/command:parameter", resolver).ToList();

Assert.That(syntaxItemParameters, Is.Not.Empty);
Assert.That(syntaxItemParameters.Count, Is.EqualTo(6));

var position = syntaxItemParameters[0].Attribute("position").Value;
Assert.That(position, Is.EqualTo("0"));

position = syntaxItemParameters[1].Attribute("position").Value;
Assert.That(position, Is.EqualTo("1"));

position = syntaxItemParameters[2].Attribute("position").Value;
Assert.That(position, Is.EqualTo("2"));

position = syntaxItemParameters[3].Attribute("position").Value;
Assert.That(position, Is.EqualTo("3"));

var require = syntaxItemParameters[4].Attribute("required").Value;
position = syntaxItemParameters[4].Attribute("position").Value;
Assert.That(position, Is.EqualTo("named"));
Assert.That(require, Is.EqualTo("true"));

require = syntaxItemParameters[5].Attribute("required").Value;
position = syntaxItemParameters[5].Attribute("position").Value;
Assert.That(position, Is.EqualTo("named"));
Assert.That(require, Is.EqualTo("false"));
}
}
}