Use `Microsoft.PowerShell.MarkdownRender` package from `nuget.org` (#14090)

This commit is contained in:
Aditya Patwardhan 2020-12-09 12:29:45 -08:00 committed by GitHub
parent f74acaa768
commit 600b658990
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
22 changed files with 9 additions and 1053 deletions

View File

@ -1,5 +1,5 @@
Microsoft Visual Studio Solution File, Format Version 12.00
# Visual Studio Version 16
# Visual Studio Version 16
# https://github.com/dotnet/project-system/blob/master/docs/opening-with-new-project-system.md#project-type-guids
VisualStudioVersion = 15.0.26730.12
MinimumVisualStudioVersion = 10.0.40219.1
@ -29,8 +29,6 @@ Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "Microsoft.WSMan.Runtime", "
EndProject
Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "powershell-unix", "src\powershell-unix\powershell-unix.csproj", "{73EA0BE6-C0C5-4B56-A5AA-DADA4C01D690}"
EndProject
Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "Microsoft.PowerShell.MarkdownRender", "src\Microsoft.PowerShell.MarkdownRender\Microsoft.PowerShell.MarkdownRender.csproj", "{43D4F8DA-A7DE-494B-81B0-BDE3CFD7B1F1}"
EndProject
Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "xUnit.tests", "test\xUnit\xUnit.tests.csproj", "{08704934-9764-48CE-86DB-BCF0A1CF7899}"
EndProject
# Configuration mapping comment

View File

@ -1163,9 +1163,6 @@
<Component Id="cmpf2a3c81eb19246b6be74af07e70a06f0">
<File Id="fil90f9e9f09d6744f68331100e6d7da03d" KeyPath="yes" Source="$(var.ProductSourcePath)\Microsoft.PowerShell.MarkdownRender.dll" />
</Component>
<Component Id="cmp75c6b7b418bb4f439dd5519c570a14e0">
<File Id="fil1c8a95614a8348f9ac6982b3340a303c" KeyPath="yes" Source="$(var.ProductSourcePath)\Microsoft.PowerShell.MarkdownRender.xml" />
</Component>
<Directory Id="dir23E9C47466D341314C603F5C7118348B" Name="ref">
<Component Id="cmp50D8B0DCCF114B58987590FF8212ACB9">
<File Id="filAAF1E2DE95144FAD97B91D1E8EA8ADC6" KeyPath="yes" Source="$(var.ProductSourcePath)\ref\System.Data.DataSetExtensions.dll" />
@ -3451,7 +3448,6 @@
<ComponentRef Id="cmp557A49B03E72CD07149A6CD0595C9245" />
<ComponentRef Id="cmp51F2F26684B5C4D0FFFFFBD72174D1BC" />
<ComponentRef Id="cmpf2a3c81eb19246b6be74af07e70a06f0" />
<ComponentRef Id="cmp75c6b7b418bb4f439dd5519c570a14e0" />
<ComponentRef Id="cmp50D8B0DCCF114B58987590FF8212ACB9" />
<ComponentRef Id="cmpC39C65F1709E407B9D6AD3AF64F710D3" />
<ComponentRef Id="cmp2C63290BD1A34304BAF371F4146D9EFD" />

View File

@ -8,7 +8,7 @@
<ItemGroup>
<ProjectReference Include="..\System.Management.Automation\System.Management.Automation.csproj" />
<ProjectReference Include="..\Microsoft.PowerShell.MarkdownRender\Microsoft.PowerShell.MarkdownRender.csproj" />
<PackageReference Include="Microsoft.PowerShell.MarkdownRender" Version="7.2.0-preview.2" />
</ItemGroup>
<PropertyGroup>

View File

@ -1,18 +0,0 @@
// Copyright (c) Microsoft Corporation.
// Licensed under the MIT License.
using Markdig.Syntax.Inlines;
namespace Microsoft.PowerShell.MarkdownRender
{
/// <summary>
/// Renderer for adding VT100 escape sequences for inline code elements.
/// </summary>
internal class CodeInlineRenderer : VT100ObjectRenderer<CodeInline>
{
protected override void Write(VT100Renderer renderer, CodeInline obj)
{
renderer.Write(renderer.EscapeSequences.FormatCode(obj.Content, isInline: true));
}
}
}

View File

@ -1,18 +0,0 @@
// Copyright (c) Microsoft Corporation.
// Licensed under the MIT License.
using Markdig.Syntax.Inlines;
namespace Microsoft.PowerShell.MarkdownRender
{
/// <summary>
/// Renderer for adding VT100 escape sequences for bold and italics elements.
/// </summary>
internal class EmphasisInlineRenderer : VT100ObjectRenderer<EmphasisInline>
{
protected override void Write(VT100Renderer renderer, EmphasisInline obj)
{
renderer.Write(renderer.EscapeSequences.FormatEmphasis(obj.FirstChild.ToString(), isBold: obj.DelimiterCount == 2));
}
}
}

View File

@ -1,41 +0,0 @@
// Copyright (c) Microsoft Corporation.
// Licensed under the MIT License.
using System;
using Markdig.Helpers;
using Markdig.Syntax;
namespace Microsoft.PowerShell.MarkdownRender
{
/// <summary>
/// Renderer for adding VT100 escape sequences for code blocks with language type.
/// </summary>
internal class FencedCodeBlockRenderer : VT100ObjectRenderer<FencedCodeBlock>
{
protected override void Write(VT100Renderer renderer, FencedCodeBlock obj)
{
if (obj?.Lines.Lines != null)
{
foreach (StringLine codeLine in obj.Lines.Lines)
{
if (!string.IsNullOrWhiteSpace(codeLine.ToString()))
{
// If the code block is of type YAML, then tab to right to improve readability.
// This specifically helps for parameters help content.
if (string.Equals(obj.Info, "yaml", StringComparison.OrdinalIgnoreCase))
{
renderer.Write("\t").WriteLine(codeLine.ToString());
}
else
{
renderer.WriteLine(renderer.EscapeSequences.FormatCode(codeLine.ToString(), isInline: false));
}
}
}
// Add a blank line after the code block for better readability.
renderer.WriteLine();
}
}
}
}

View File

@ -1,55 +0,0 @@
// Copyright (c) Microsoft Corporation.
// Licensed under the MIT License.
using Markdig.Syntax;
namespace Microsoft.PowerShell.MarkdownRender
{
/// <summary>
/// Renderer for adding VT100 escape sequences for headings.
/// </summary>
internal class HeaderBlockRenderer : VT100ObjectRenderer<HeadingBlock>
{
protected override void Write(VT100Renderer renderer, HeadingBlock obj)
{
string headerText = obj?.Inline?.FirstChild?.ToString();
if (!string.IsNullOrEmpty(headerText))
{
// Format header and then add blank line to improve readability.
switch (obj.Level)
{
case 1:
renderer.WriteLine(renderer.EscapeSequences.FormatHeader1(headerText));
renderer.WriteLine();
break;
case 2:
renderer.WriteLine(renderer.EscapeSequences.FormatHeader2(headerText));
renderer.WriteLine();
break;
case 3:
renderer.WriteLine(renderer.EscapeSequences.FormatHeader3(headerText));
renderer.WriteLine();
break;
case 4:
renderer.WriteLine(renderer.EscapeSequences.FormatHeader4(headerText));
renderer.WriteLine();
break;
case 5:
renderer.WriteLine(renderer.EscapeSequences.FormatHeader5(headerText));
renderer.WriteLine();
break;
case 6:
renderer.WriteLine(renderer.EscapeSequences.FormatHeader6(headerText));
renderer.WriteLine();
break;
}
}
}
}
}

View File

@ -1,28 +0,0 @@
// Copyright (c) Microsoft Corporation.
// Licensed under the MIT License.
using Markdig.Syntax.Inlines;
namespace Microsoft.PowerShell.MarkdownRender
{
/// <summary>
/// Renderer for adding VT100 escape sequences for leaf elements like plain text in paragraphs.
/// </summary>
internal class LeafInlineRenderer : VT100ObjectRenderer<LeafInline>
{
protected override void Write(VT100Renderer renderer, LeafInline obj)
{
// If the next sibling is null, then this is the last line in the paragraph.
// Add new line character at the end.
// Else just write without newline at the end.
if (obj.NextSibling == null)
{
renderer.WriteLine(obj.ToString());
}
else
{
renderer.Write(obj.ToString());
}
}
}
}

View File

@ -1,27 +0,0 @@
// Copyright (c) Microsoft Corporation.
// Licensed under the MIT License.
using Markdig.Syntax.Inlines;
namespace Microsoft.PowerShell.MarkdownRender
{
/// <summary>
/// Renderer for adding VT100 escape sequences for line breaks.
/// </summary>
internal class LineBreakRenderer : VT100ObjectRenderer<LineBreakInline>
{
protected override void Write(VT100Renderer renderer, LineBreakInline obj)
{
// If it is a hard line break add new line at the end.
// Else, add a space for after the last character to improve readability.
if (obj.IsHard)
{
renderer.WriteLine();
}
else
{
renderer.Write(" ");
}
}
}
}

View File

@ -1,28 +0,0 @@
// Copyright (c) Microsoft Corporation.
// Licensed under the MIT License.
using Markdig.Syntax.Inlines;
namespace Microsoft.PowerShell.MarkdownRender
{
/// <summary>
/// Renderer for adding VT100 escape sequences for links.
/// </summary>
internal class LinkInlineRenderer : VT100ObjectRenderer<LinkInline>
{
protected override void Write(VT100Renderer renderer, LinkInline obj)
{
string text = obj.FirstChild?.ToString();
// Format link as image or link.
if (obj.IsImage)
{
renderer.Write(renderer.EscapeSequences.FormatImage(text));
}
else
{
renderer.Write(renderer.EscapeSequences.FormatLink(text, obj.Url));
}
}
}
}

View File

@ -1,48 +0,0 @@
// Copyright (c) Microsoft Corporation.
// Licensed under the MIT License.
using Markdig.Syntax;
namespace Microsoft.PowerShell.MarkdownRender
{
/// <summary>
/// Renderer for adding VT100 escape sequences for list blocks.
/// </summary>
internal class ListBlockRenderer : VT100ObjectRenderer<ListBlock>
{
protected override void Write(VT100Renderer renderer, ListBlock obj)
{
// start index of a numbered block.
int index = 1;
foreach (var item in obj)
{
if (item is ListItemBlock listItem)
{
if (obj.IsOrdered)
{
RenderNumberedList(renderer, listItem, index++);
}
else
{
renderer.Write(listItem);
}
}
}
renderer.WriteLine();
}
private static void RenderNumberedList(VT100Renderer renderer, ListItemBlock block, int index)
{
// For a numbered list, we need to make sure the index is incremented.
foreach (var line in block)
{
if (line is ParagraphBlock paragraphBlock)
{
renderer.Write(index.ToString()).Write(". ").Write(paragraphBlock.Inline);
}
}
}
}
}

View File

@ -1,80 +0,0 @@
// Copyright (c) Microsoft Corporation.
// Licensed under the MIT License.
using System.Threading;
using Markdig.Syntax;
namespace Microsoft.PowerShell.MarkdownRender
{
/// <summary>
/// Renderer for adding VT100 escape sequences for items in a list block.
/// </summary>
internal class ListItemBlockRenderer : VT100ObjectRenderer<ListItemBlock>
{
protected override void Write(VT100Renderer renderer, ListItemBlock obj)
{
if (obj.Parent is ListBlock parent)
{
if (!parent.IsOrdered)
{
foreach (var line in obj)
{
RenderWithIndent(renderer, line, parent.BulletType, 0);
}
}
}
}
private void RenderWithIndent(VT100Renderer renderer, MarkdownObject block, char listBullet, int indentLevel)
{
// Indent left by 2 for each level on list.
string indent = Padding(indentLevel * 2);
if (block is ParagraphBlock paragraphBlock)
{
renderer.Write(indent).Write(listBullet).Write(" ").Write(paragraphBlock.Inline);
}
else
{
// If there is a sublist, the block is a ListBlock instead of ParagraphBlock.
if (block is ListBlock subList)
{
foreach (var subListItem in subList)
{
if (subListItem is ListItemBlock subListItemBlock)
{
foreach (var line in subListItemBlock)
{
// Increment indent level for sub list.
RenderWithIndent(renderer, line, listBullet, indentLevel + 1);
}
}
}
}
}
}
// Typical padding is at most a screen's width, any more than that and we won't bother caching.
private const int IndentCacheMax = 120;
private static readonly string[] IndentCache = new string[IndentCacheMax];
internal static string Padding(int countOfSpaces)
{
if (countOfSpaces >= IndentCacheMax)
{
return new string(' ', countOfSpaces);
}
var result = IndentCache[countOfSpaces];
if (result == null)
{
Interlocked.CompareExchange(ref IndentCache[countOfSpaces], new string(' ', countOfSpaces), comparand: null);
result = IndentCache[countOfSpaces];
}
return result;
}
}
}

View File

@ -1,90 +0,0 @@
// Copyright (c) Microsoft Corporation.
// Licensed under the MIT License.
using System;
using System.IO;
using Markdig;
namespace Microsoft.PowerShell.MarkdownRender
{
/// <summary>
/// Type of conversion from Markdown.
/// </summary>
[Flags]
public enum MarkdownConversionType
{
/// <summary>
/// Convert to HTML.
/// </summary>
HTML = 1,
/// <summary>
/// Convert to VT100 encoded string.
/// </summary>
VT100 = 2
}
/// <summary>
/// Object representing the conversion from Markdown.
/// </summary>
public class MarkdownInfo
{
/// <summary>
/// Gets the Html content after conversion.
/// </summary>
public string Html { get; internal set; }
/// <summary>
/// Gets the VT100 encoded string after conversion.
/// </summary>
public string VT100EncodedString { get; internal set; }
/// <summary>
/// Gets the AST of the Markdown string.
/// </summary>
public Markdig.Syntax.MarkdownDocument Tokens { get; internal set; }
}
/// <summary>
/// Class to convert a Markdown string to VT100, HTML or AST.
/// </summary>
public sealed class MarkdownConverter
{
/// <summary>
/// Convert from Markdown string to VT100 encoded string or HTML. Returns MarkdownInfo object.
/// </summary>
/// <param name="markdownString">String with Markdown content to be converted.</param>
/// <param name="conversionType">Specifies type of conversion, either VT100 or HTML.</param>
/// <param name="optionInfo">Specifies the rendering options for VT100 rendering.</param>
/// <returns>MarkdownInfo object with the converted output.</returns>
public static MarkdownInfo Convert(string markdownString, MarkdownConversionType conversionType, PSMarkdownOptionInfo optionInfo)
{
var renderInfo = new MarkdownInfo();
var writer = new StringWriter();
MarkdownPipeline pipeline = null;
if (conversionType.HasFlag(MarkdownConversionType.HTML))
{
pipeline = new MarkdownPipelineBuilder().UseAdvancedExtensions().Build();
var renderer = new Markdig.Renderers.HtmlRenderer(writer);
renderInfo.Html = Markdig.Markdown.Convert(markdownString, renderer, pipeline).ToString();
}
if (conversionType.HasFlag(MarkdownConversionType.VT100))
{
pipeline = new MarkdownPipelineBuilder().Build();
// Use the VT100 renderer.
var renderer = new VT100Renderer(writer, optionInfo);
renderInfo.VT100EncodedString = Markdig.Markdown.Convert(markdownString, renderer, pipeline).ToString();
}
// Always have AST available.
var parsed = Markdig.Markdown.Parse(markdownString, pipeline);
renderInfo.Tokens = parsed;
return renderInfo;
}
}
}

View File

@ -1,15 +0,0 @@
<Project Sdk="Microsoft.NET.Sdk" ToolsVersion="15.0">
<Import Project="..\..\PowerShell.Common.props" />
<PropertyGroup>
<Description>PowerShell's Markdown Rendering project</Description>
<AssemblyName>Microsoft.PowerShell.MarkdownRender</AssemblyName>
</PropertyGroup>
<ItemGroup>
<!-- Source: https://github.com/lunet-io/markdig/ -->
<ProjectReference Include="../System.Management.Automation/System.Management.Automation.csproj" />
<PackageReference Include="Markdig.Signed" Version="0.22.1" />
</ItemGroup>
</Project>

View File

@ -1,22 +0,0 @@
// Copyright (c) Microsoft Corporation.
// Licensed under the MIT License.
using Markdig.Syntax;
namespace Microsoft.PowerShell.MarkdownRender
{
/// <summary>
/// Renderer for adding VT100 escape sequences for paragraphs.
/// </summary>
internal class ParagraphBlockRenderer : VT100ObjectRenderer<ParagraphBlock>
{
protected override void Write(VT100Renderer renderer, ParagraphBlock obj)
{
// Call the renderer for children, leaf inline or line breaks.
renderer.WriteChildren(obj.Inline);
// Add new line at the end of the paragraph.
renderer.WriteLine();
}
}
}

View File

@ -1,25 +0,0 @@
// Copyright (c) Microsoft Corporation.
// Licensed under the MIT License.
using Markdig.Syntax;
namespace Microsoft.PowerShell.MarkdownRender
{
/// <summary>
/// Renderer for adding VT100 escape sequences for quote blocks.
/// </summary>
internal class QuoteBlockRenderer : VT100ObjectRenderer<QuoteBlock>
{
protected override void Write(VT100Renderer renderer, QuoteBlock obj)
{
// Iterate through each item and add the quote character before the content.
foreach (var item in obj)
{
renderer.Write(obj.QuoteChar).Write(" ").Write(item);
}
// Add blank line after the quote block.
renderer.WriteLine();
}
}
}

View File

@ -1,478 +0,0 @@
// Copyright (c) Microsoft Corporation.
// Licensed under the MIT License.
using System;
using System.Management.Automation;
namespace Microsoft.PowerShell.MarkdownRender
{
/// <summary>
/// Enum to name all the properties of PSMarkdownOptionInfo.
/// </summary>
public enum MarkdownOptionInfoProperty
{
/// <summary>
/// Property name Header1.
/// </summary>
Header1,
/// <summary>
/// Property name Header2.
/// </summary>
Header2,
/// <summary>
/// Property name Header3.
/// </summary>
Header3,
/// <summary>
/// Property name Header4.
/// </summary>
Header4,
/// <summary>
/// Property name Header5.
/// </summary>
Header5,
/// <summary>
/// Property name Header6.
/// </summary>
Header6,
/// <summary>
/// Property name Code.
/// </summary>
Code,
/// <summary>
/// Property name Link.
/// </summary>
Link,
/// <summary>
/// Property name Image.
/// </summary>
Image,
/// <summary>
/// Property name EmphasisBold.
/// </summary>
EmphasisBold,
/// <summary>
/// Property name EmphasisItalics.
/// </summary>
EmphasisItalics
}
/// <summary>
/// Class to represent color preference options for various Markdown elements.
/// </summary>
public sealed class PSMarkdownOptionInfo
{
private const char Esc = (char)0x1b;
private const string EndSequence = "[0m";
/// <summary>
/// Gets or sets current VT100 escape sequence for header 1.
/// </summary>
public string Header1 { get; set; }
/// <summary>
/// Gets or sets current VT100 escape sequence for header 2.
/// </summary>
public string Header2 { get; set; }
/// <summary>
/// Gets or sets current VT100 escape sequence for header 3.
/// </summary>
public string Header3 { get; set; }
/// <summary>
/// Gets or sets current VT100 escape sequence for header 4.
/// </summary>
public string Header4 { get; set; }
/// <summary>
/// Gets or sets current VT100 escape sequence for header 5.
/// </summary>
public string Header5 { get; set; }
/// <summary>
/// Gets or sets current VT100 escape sequence for header 6.
/// </summary>
public string Header6 { get; set; }
/// <summary>
/// Gets or sets current VT100 escape sequence for code inline and code blocks.
/// </summary>
public string Code { get; set; }
/// <summary>
/// Gets or sets current VT100 escape sequence for links.
/// </summary>
public string Link { get; set; }
/// <summary>
/// Gets or sets current VT100 escape sequence for images.
/// </summary>
public string Image { get; set; }
/// <summary>
/// Gets or sets current VT100 escape sequence for bold text.
/// </summary>
public string EmphasisBold { get; set; }
/// <summary>
/// Gets or sets current VT100 escape sequence for italics text.
/// </summary>
public string EmphasisItalics { get; set; }
/// <summary>
/// Gets or sets a value indicating whether VT100 escape sequences should be added. Default it true.
/// </summary>
public bool EnableVT100Encoding { get; set; }
/// <summary>
/// Get the property as an rendered escape sequence.
/// This is used by formatting system for displaying.
/// </summary>
/// <param name="propertyName">Name of the property to get as escape sequence.</param>
/// <returns>Specified property name as escape sequence.</returns>
public string AsEscapeSequence(MarkdownOptionInfoProperty propertyName)
{
switch (propertyName)
{
case MarkdownOptionInfoProperty.Header1:
return string.Concat(Esc, Header1, Header1, Esc, EndSequence);
case MarkdownOptionInfoProperty.Header2:
return string.Concat(Esc, Header2, Header2, Esc, EndSequence);
case MarkdownOptionInfoProperty.Header3:
return string.Concat(Esc, Header3, Header3, Esc, EndSequence);
case MarkdownOptionInfoProperty.Header4:
return string.Concat(Esc, Header4, Header4, Esc, EndSequence);
case MarkdownOptionInfoProperty.Header5:
return string.Concat(Esc, Header5, Header5, Esc, EndSequence);
case MarkdownOptionInfoProperty.Header6:
return string.Concat(Esc, Header6, Header6, Esc, EndSequence);
case MarkdownOptionInfoProperty.Code:
return string.Concat(Esc, Code, Code, Esc, EndSequence);
case MarkdownOptionInfoProperty.Link:
return string.Concat(Esc, Link, Link, Esc, EndSequence);
case MarkdownOptionInfoProperty.Image:
return string.Concat(Esc, Image, Image, Esc, EndSequence);
case MarkdownOptionInfoProperty.EmphasisBold:
return string.Concat(Esc, EmphasisBold, EmphasisBold, Esc, EndSequence);
case MarkdownOptionInfoProperty.EmphasisItalics:
return string.Concat(Esc, EmphasisItalics, EmphasisItalics, Esc, EndSequence);
default:
break;
}
return null;
}
/// <summary>
/// Initializes a new instance of the <see cref="PSMarkdownOptionInfo"/> class and sets dark as the default theme.
/// </summary>
public PSMarkdownOptionInfo()
{
SetDarkTheme();
EnableVT100Encoding = true;
}
private const string Header1Dark = "[7m";
private const string Header2Dark = "[4;93m";
private const string Header3Dark = "[4;94m";
private const string Header4Dark = "[4;95m";
private const string Header5Dark = "[4;96m";
private const string Header6Dark = "[4;97m";
private const string CodeDark = "[48;2;155;155;155;38;2;30;30;30m";
private const string CodeMacOS = "[107;95m";
private const string LinkDark = "[4;38;5;117m";
private const string ImageDark = "[33m";
private const string EmphasisBoldDark = "[1m";
private const string EmphasisItalicsDark = "[36m";
private const string Header1Light = "[7m";
private const string Header2Light = "[4;33m";
private const string Header3Light = "[4;34m";
private const string Header4Light = "[4;35m";
private const string Header5Light = "[4;36m";
private const string Header6Light = "[4;30m";
private const string CodeLight = "[48;2;155;155;155;38;2;30;30;30m";
private const string LinkLight = "[4;38;5;117m";
private const string ImageLight = "[33m";
private const string EmphasisBoldLight = "[1m";
private const string EmphasisItalicsLight = "[36m";
/// <summary>
/// Set all preference for dark theme.
/// </summary>
public void SetDarkTheme()
{
Header1 = Header1Dark;
Header2 = Header2Dark;
Header3 = Header3Dark;
Header4 = Header4Dark;
Header5 = Header5Dark;
Header6 = Header6Dark;
Link = LinkDark;
Image = ImageDark;
EmphasisBold = EmphasisBoldDark;
EmphasisItalics = EmphasisItalicsDark;
SetCodeColor(isDarkTheme: true);
}
/// <summary>
/// Set all preference for light theme.
/// </summary>
public void SetLightTheme()
{
Header1 = Header1Light;
Header2 = Header2Light;
Header3 = Header3Light;
Header4 = Header4Light;
Header5 = Header5Light;
Header6 = Header6Light;
Link = LinkLight;
Image = ImageLight;
EmphasisBold = EmphasisBoldLight;
EmphasisItalics = EmphasisItalicsLight;
SetCodeColor(isDarkTheme: false);
}
private void SetCodeColor(bool isDarkTheme)
{
// MacOS terminal app does not support extended colors for VT100, so we special case for it.
Code = Platform.IsMacOS ? CodeMacOS : isDarkTheme ? CodeDark : CodeLight;
}
}
/// <summary>
/// Class to represent default VT100 escape sequences.
/// </summary>
public class VT100EscapeSequences
{
private const char Esc = (char)0x1B;
private readonly string endSequence = Esc + "[0m";
// For code blocks, [500@ make sure that the whole line has background color.
private const string LongBackgroundCodeBlock = "[500@";
private readonly PSMarkdownOptionInfo options;
/// <summary>
/// Initializes a new instance of the <see cref="VT100EscapeSequences"/> class.
/// </summary>
/// <param name="optionInfo">PSMarkdownOptionInfo object to initialize with.</param>
public VT100EscapeSequences(PSMarkdownOptionInfo optionInfo)
{
if (optionInfo == null)
{
throw new ArgumentNullException(nameof(optionInfo));
}
options = optionInfo;
}
/// <summary>
/// Class to represent default VT100 escape sequences.
/// </summary>
/// <param name="headerText">Text of the header to format.</param>
/// <returns>Formatted Header 1 string.</returns>
public string FormatHeader1(string headerText)
{
return FormatHeader(headerText, options.Header1);
}
/// <summary>
/// Class to represent default VT100 escape sequences.
/// </summary>
/// <param name="headerText">Text of the header to format.</param>
/// <returns>Formatted Header 2 string.</returns>
public string FormatHeader2(string headerText)
{
return FormatHeader(headerText, options.Header2);
}
/// <summary>
/// Class to represent default VT100 escape sequences.
/// </summary>
/// <param name="headerText">Text of the header to format.</param>
/// <returns>Formatted Header 3 string.</returns>
public string FormatHeader3(string headerText)
{
return FormatHeader(headerText, options.Header3);
}
/// <summary>
/// Class to represent default VT100 escape sequences.
/// </summary>
/// <param name="headerText">Text of the header to format.</param>
/// <returns>Formatted Header 4 string.</returns>
public string FormatHeader4(string headerText)
{
return FormatHeader(headerText, options.Header4);
}
/// <summary>
/// Class to represent default VT100 escape sequences.
/// </summary>
/// <param name="headerText">Text of the header to format.</param>
/// <returns>Formatted Header 5 string.</returns>
public string FormatHeader5(string headerText)
{
return FormatHeader(headerText, options.Header5);
}
/// <summary>
/// Class to represent default VT100 escape sequences.
/// </summary>
/// <param name="headerText">Text of the header to format.</param>
/// <returns>Formatted Header 6 string.</returns>
public string FormatHeader6(string headerText)
{
return FormatHeader(headerText, options.Header6);
}
/// <summary>
/// Class to represent default VT100 escape sequences.
/// </summary>
/// <param name="codeText">Text of the code block to format.</param>
/// <param name="isInline">True if it is a inline code block, false otherwise.</param>
/// <returns>Formatted code block string.</returns>
public string FormatCode(string codeText, bool isInline)
{
bool isVT100Enabled = options.EnableVT100Encoding;
if (isInline)
{
if (isVT100Enabled)
{
return string.Concat(Esc, options.Code, codeText, endSequence);
}
else
{
return codeText;
}
}
else
{
if (isVT100Enabled)
{
return string.Concat(Esc, options.Code, codeText, Esc, LongBackgroundCodeBlock, endSequence);
}
else
{
return codeText;
}
}
}
/// <summary>
/// Class to represent default VT100 escape sequences.
/// </summary>
/// <param name="linkText">Text of the link to format.</param>
/// <param name="url">URL of the link.</param>
/// <param name="hideUrl">True url should be hidden, false otherwise. Default is true.</param>
/// <returns>Formatted link string.</returns>
public string FormatLink(string linkText, string url, bool hideUrl = true)
{
bool isVT100Enabled = options.EnableVT100Encoding;
if (hideUrl)
{
if (isVT100Enabled)
{
return string.Concat(Esc, options.Link, "\"", linkText, "\"", endSequence);
}
else
{
return string.Concat("\"", linkText, "\"");
}
}
else
{
if (isVT100Enabled)
{
return string.Concat("\"", linkText, "\" (", Esc, options.Link, url, endSequence, ")");
}
else
{
return string.Concat("\"", linkText, "\" (", url, ")");
}
}
}
/// <summary>
/// Class to represent default VT100 escape sequences.
/// </summary>
/// <param name="emphasisText">Text to format as emphasis.</param>
/// <param name="isBold">True if it is to be formatted as bold, false to format it as italics.</param>
/// <returns>Formatted emphasis string.</returns>
public string FormatEmphasis(string emphasisText, bool isBold)
{
var sequence = isBold ? options.EmphasisBold : options.EmphasisItalics;
if (options.EnableVT100Encoding)
{
return string.Concat(Esc, sequence, emphasisText, endSequence);
}
else
{
return emphasisText;
}
}
/// <summary>
/// Class to represent default VT100 escape sequences.
/// </summary>
/// <param name="altText">Text of the image to format.</param>
/// <returns>Formatted image string.</returns>
public string FormatImage(string altText)
{
var text = altText;
if (string.IsNullOrEmpty(altText))
{
text = "Image";
}
if (options.EnableVT100Encoding)
{
return string.Concat(Esc, options.Image, "[", text, "]", endSequence);
}
else
{
return string.Concat("[", text, "]");
}
}
private string FormatHeader(string headerText, string headerEscapeSequence)
{
if (options.EnableVT100Encoding)
{
return string.Concat(Esc, headerEscapeSequence, headerText, endSequence);
}
else
{
return headerText;
}
}
}
}

View File

@ -1,16 +0,0 @@
// Copyright (c) Microsoft Corporation.
// Licensed under the MIT License.
using Markdig.Renderers;
using Markdig.Syntax;
namespace Microsoft.PowerShell.MarkdownRender
{
/// <summary>
/// Implement the MarkdownObjectRenderer with VT100Renderer.
/// </summary>
/// <typeparam name="T">The element type of the renderer.</typeparam>
public abstract class VT100ObjectRenderer<T> : MarkdownObjectRenderer<VT100Renderer, T> where T : MarkdownObject
{
}
}

View File

@ -1,42 +0,0 @@
// Copyright (c) Microsoft Corporation.
// Licensed under the MIT License.
using System.IO;
using Markdig.Renderers;
namespace Microsoft.PowerShell.MarkdownRender
{
/// <summary>
/// Initializes an instance of the VT100 renderer.
/// </summary>
public sealed class VT100Renderer : TextRendererBase<VT100Renderer>
{
/// <summary>
/// Initializes a new instance of the <see cref="VT100Renderer"/> class.
/// </summary>
/// <param name="writer">TextWriter to write to.</param>
/// <param name="optionInfo">PSMarkdownOptionInfo object with options.</param>
public VT100Renderer(TextWriter writer, PSMarkdownOptionInfo optionInfo) : base(writer)
{
EscapeSequences = new VT100EscapeSequences(optionInfo);
// Add the various element renderers.
ObjectRenderers.Add(new HeaderBlockRenderer());
ObjectRenderers.Add(new LineBreakRenderer());
ObjectRenderers.Add(new CodeInlineRenderer());
ObjectRenderers.Add(new FencedCodeBlockRenderer());
ObjectRenderers.Add(new EmphasisInlineRenderer());
ObjectRenderers.Add(new ParagraphBlockRenderer());
ObjectRenderers.Add(new LeafInlineRenderer());
ObjectRenderers.Add(new LinkInlineRenderer());
ObjectRenderers.Add(new ListBlockRenderer());
ObjectRenderers.Add(new ListItemBlockRenderer());
ObjectRenderers.Add(new QuoteBlockRenderer());
}
/// <summary>
/// Gets the current escape sequences.
/// </summary>
public VT100EscapeSequences EscapeSequences { get; }
}
}

View File

@ -1825,8 +1825,7 @@ function New-ILNugetPackage
"Microsoft.PowerShell.SDK.dll",
"Microsoft.WSMan.Management.dll",
"Microsoft.WSMan.Runtime.dll",
"System.Management.Automation.dll",
"Microsoft.PowerShell.MarkdownRender.dll")
"System.Management.Automation.dll")
$linuxExceptionList = @(
"Microsoft.Management.Infrastructure.CimCmdlets.dll",
@ -1934,7 +1933,6 @@ function New-ILNugetPackage
'Microsoft.PowerShell.Commands.Utility' {
$deps.Add([tuple]::Create([tuple]::Create('id', 'System.Management.Automation'), [tuple]::Create('version', $PackageVersion))) > $null
$deps.Add([tuple]::Create([tuple]::Create('id', 'Microsoft.PowerShell.MarkdownRender'), [tuple]::Create('version', $PackageVersion))) > $null
foreach($packageInfo in (Get-ProjectPackageInformation -ProjectName $fileBaseName))
{
@ -1996,14 +1994,6 @@ function New-ILNugetPackage
$deps.Add([tuple]::Create([tuple]::Create('id', $packageInfo.Name), [tuple]::Create('version', $packageInfo.Version))) > $null
}
}
'Microsoft.PowerShell.MarkdownRender' {
$deps.Add([tuple]::Create([tuple]::Create('id', 'System.Management.Automation'), [tuple]::Create('version', $PackageVersion))) > $null
foreach($packageInfo in (Get-ProjectPackageInformation -ProjectName $fileBaseName))
{
$deps.Add([tuple]::Create([tuple]::Create('id', $packageInfo.Name), [tuple]::Create('version', $packageInfo.Version))) > $null
}
}
}
New-NuSpec -PackageId $fileBaseName -PackageVersion $PackageVersion -Dependency $deps -FilePath (Join-Path $filePackageFolder.FullName "$fileBaseName.nuspec")
@ -2321,7 +2311,6 @@ function CleanupGeneratedSourceCode
'[Microsoft.PowerShell.Commands.AddMemberCommand'
'[System.Management.Automation.ArgumentCompleterAttribute(typeof(Microsoft.PowerShell.Commands.Utility.JoinItemCompleter))]'
'[System.Management.Automation.ArgumentCompleterAttribute(typeof(System.Management.Automation.PropertyNameCompleter))]'
'[System.Management.Automation.OutputTypeAttribute(typeof(Microsoft.PowerShell.MarkdownRender'
'[Microsoft.PowerShell.Commands.ArgumentToTypeNameTransformationAttribute]'
'[System.Management.Automation.Internal.ArchitectureSensitiveAttribute]'
'[Microsoft.PowerShell.Commands.SelectStringCommand.FileinfoToStringAttribute]'

View File

@ -124,13 +124,18 @@ jobs:
"$($fullSymbolsFolder)\System.Management.Automation.dll" = ""
}
$itemsToExclude = @{
# This package is retrieved from https://www.github.com/powershell/MarkdownRender
"$($fullSymbolsFolder)\Microsoft.PowerShell.MarkdownRender.dll"
}
if ("$env:Architecture" -notlike 'fxdependent*')
{
$itemsToCopy += @{"$($fullSymbolsFolder)\pwsh.exe" = ""}
}
Write-Verbose -verbose "recusively copying $($itemsToCopyWithRecurse | out-string) to $filesToSignDirectory"
Copy-Item -Path $itemsToCopyWithRecurse -Destination $filesToSignDirectory -Recurse -verbose
Copy-Item -Path $itemsToCopyWithRecurse -Destination $filesToSignDirectory -Recurse -verbose -exclude $itemsToExclude
foreach($pattern in $itemsToCopy.Keys) {
$destinationFolder = Join-Path $filesToSignDirectory -ChildPath $itemsToCopy.$pattern

View File

@ -8,7 +8,6 @@
<file src="__INPATHROOT__\Microsoft.PowerShell.Commands.Utility.dll" signType="AuthenticodeFormer" dest="__OUTPATHROOT__\Microsoft.PowerShell.Commands.Utility.dll" />
<file src="__INPATHROOT__\Microsoft.PowerShell.ConsoleHost.dll" signType="AuthenticodeFormer" dest="__OUTPATHROOT__\Microsoft.PowerShell.ConsoleHost.dll" />
<file src="__INPATHROOT__\Microsoft.PowerShell.CoreCLR.Eventing.dll" signType="AuthenticodeFormer" dest="__OUTPATHROOT__\Microsoft.PowerShell.CoreCLR.Eventing.dll" />
<file src="__INPATHROOT__\Microsoft.PowerShell.MarkdownRender.dll" signType="AuthenticodeFormer" dest="__OUTPATHROOT__\Microsoft.PowerShell.MarkdownRender.dll" />
<file src="__INPATHROOT__\Microsoft.PowerShell.GlobalTool.Shim.dll" signType="AuthenticodeFormer" dest="__OUTPATHROOT__\Microsoft.PowerShell.GlobalTool.Shim.dll" />
<file src="__INPATHROOT__\Microsoft.PowerShell.Security.dll" signType="AuthenticodeFormer" dest="__OUTPATHROOT__\Microsoft.PowerShell.Security.dll" />
<file src="__INPATHROOT__\Microsoft.WSMan.Management.dll" signType="AuthenticodeFormer" dest="__OUTPATHROOT__\Microsoft.WSMan.Management.dll" />