Skip to content

Commit

Permalink
feat: render enum field remarks and obsolete attribute (#9327)
Browse files Browse the repository at this point in the history
  • Loading branch information
yufeih authored Oct 23, 2023
1 parent 5082454 commit e7b456c
Show file tree
Hide file tree
Showing 89 changed files with 1,094 additions and 106 deletions.
29 changes: 29 additions & 0 deletions samples/seed/dotnet/project/Project/Class1.cs
Original file line number Diff line number Diff line change
Expand Up @@ -160,4 +160,33 @@ public void Issue1887() { }
/// $$\left\{\begin{matrix}a, a<b \\ b, b>a\\ \end{matrix} \right.$$
/// </summary>
public static double Issue9216() => 0.0;

public enum Issue9260
{
/// <summary>
/// This is a regular enum value.
/// </summary>
/// <remarks>
/// This is a remarks section. Very important remarks about Value go here.
/// </remarks>
Value,

/// <summary>
/// This is old and unused. You shouldn't use it anymore.
/// </summary>
/// <remarks>
/// Don't use this, seriously! Use Value instead.
/// </remarks>
[Obsolete]
OldAndUnusedValue,

/// <summary>
/// This is old and unused. You shouldn't use it anymore.
/// </summary>
/// <remarks>
/// Don't use this, seriously! Use Value instead.
/// </remarks>
[Obsolete("Use Value")]
OldAndUnusedValue2,
}
}
71 changes: 47 additions & 24 deletions src/Docfx.Build/ApiPage/ApiPageHtmlTemplate.cs
Original file line number Diff line number Diff line change
Expand Up @@ -4,6 +4,7 @@
#if NET7_0_OR_GREATER

using System.Net;
using OneOf;
using static Docfx.Build.HtmlTemplate;

#nullable enable
Expand Down Expand Up @@ -47,28 +48,42 @@ HtmlTemplate Api(Api api)
? default
: UnsafeHtml(string.Join(" ", value.metadata.Select(m => $"data-{WebUtility.HtmlEncode(m.Key)}='{WebUtility.HtmlEncode(m.Value)}'")));

var isDeprecated = value.deprecated?.Value switch
var (level, title) = api.Value switch
{
bool b when b => true,
string s => true,
_ => false,
Api1 a1 => (1, a1.api1),
Api2 a2 => (2, a2.api2),
Api3 a3 => (3, a3.api3),
Api4 a4 => (4, a4.api4),
};
var deprecated = isDeprecated ? Html($" <span class='badge rounded-pill text-bg-danger' style='font-size: .5em; vertical-align: middle'>Deprecated</span>") : default;
var deprecatedReason = value.deprecated?.Value is string ds && !string.IsNullOrEmpty(ds)
? Html($"\n<div class='alert alert-warning' role='alert'>{UnsafeHtml(markup(ds))}</div>")
: default;

var deprecated = DeprecatedBadge(value.deprecated);
var deprecatedReason = DeprecatedReason(value.deprecated);
var titleHtml = deprecated is null ? Html($"{title}") : Html($"<span style='text-decoration: line-through'>{title}</span>");

var src = string.IsNullOrEmpty(value.src)
? default
: Html($" <a class='header-action link-secondary' title='View source' href='{value.src}'><i class='bi bi-code-slash'></i></a>");

return api.Value switch
return Html($"<h{level} class='section api' {attributes} id='{value.id}'>{titleHtml} {deprecated} {src}</h{level}> {deprecatedReason}");
}

HtmlTemplate? DeprecatedBadge(OneOf<bool, string>? value, string fontSize = ".5em")
{
var isDeprecated = value?.Value switch
{
Api1 api1 => Html($"<h1 class='section api' {attributes} id='{value.id}'>{api1.api1}{deprecated}{src}</h1>{deprecatedReason}"),
Api2 api2 => Html($"<h2 class='section api' {attributes} id='{value.id}'>{api2.api2}{deprecated}{src}</h2>{deprecatedReason}"),
Api3 api3 => Html($"<h3 class='section api' {attributes} id='{value.id}'>{api3.api3}{deprecated}{src}</h3>{deprecatedReason}"),
Api4 api4 => Html($"<h4 class='section api' {attributes} id='{value.id}'>{api4.api4}{deprecated}{src}</h4>{deprecatedReason}"),
bool b when b => true,
string s => true,
_ => false,
};

return isDeprecated ? Html($" <span class='badge rounded-pill text-bg-danger' style='font-size: {fontSize}; vertical-align: middle'>Deprecated</span>") : null;
}

HtmlTemplate DeprecatedReason(OneOf<bool, string>? value)
{
return value?.Value is string ds && !string.IsNullOrEmpty(ds)
? Html($"\n<div class='alert alert-warning' role='alert'>{UnsafeHtml(markup(ds))}</div>")
: default;
}

HtmlTemplate Facts(Facts facts) => facts.facts.Length is 0 ? default : Html(
Expand Down Expand Up @@ -102,17 +117,25 @@ HtmlTemplate Code(Code code)
HtmlTemplate Parameters(Parameters parameters) => parameters.parameters.Length is 0 ? default : Html(
$"<dl class='parameters'>{parameters.parameters.Select(Parameter)}</dl>");

HtmlTemplate Parameter(Parameter parameter) => Html(
$"""
<dt>
{(string.IsNullOrEmpty(parameter.name) ? default
: string.IsNullOrEmpty(parameter.@default)
? Html($"<code>{parameter.name}</code>")
: Html($"<code>{parameter.name} = {parameter.@default}</code>"))}
{Inline(parameter.type)}
</dt>
<dd>{(string.IsNullOrEmpty(parameter.description) ? default : UnsafeHtml(markup(parameter.description)))}</dd>
""");
HtmlTemplate Parameter(Parameter parameter)
{
var deprecated = DeprecatedBadge(parameter.deprecated, ".875em");
var lineThrough = deprecated is not null ? UnsafeHtml(" style='text-decoration: line-through'") : default;

var title = string.IsNullOrEmpty(parameter.name) ? default
: string.IsNullOrEmpty(parameter.@default)
? Html($"<code{lineThrough}>{parameter.name}</code>")
: Html($"<code{lineThrough}>{parameter.name} = {parameter.@default}</code>");

return Html(
$"""
<dt>{title} {Inline(parameter.type)} {deprecated}</dt>
<dd>
{DeprecatedReason(parameter.deprecated)}
{(string.IsNullOrEmpty(parameter.description) ? default : UnsafeHtml(markup(parameter.description)))}
</dd>
""");
}

HtmlTemplate Inline(Inline? inline) => inline?.Value switch
{
Expand Down
21 changes: 16 additions & 5 deletions src/Docfx.Dotnet/DotnetApiCatalog.ApiPage.cs
Original file line number Diff line number Diff line change
Expand Up @@ -124,9 +124,7 @@ void Api(int level, string title, ISymbol symbol, Compilation compilation)
var git = source is null || source.Remote is null ? null
: new GitSource(source.Remote.Repo, source.Remote.Branch, source.Remote.Path, source.StartLine + 1);
var src = git is null ? null : options.SourceUrl?.Invoke(git) ?? GitUtility.GetSourceUrl(git);
var obsoleteAttribute = symbol.GetAttributes().FirstOrDefault(a => a.AttributeClass?.Name == "ObsoleteAttribute");
var deprecated = obsoleteAttribute is null ? null :
obsoleteAttribute.ConstructorArguments.FirstOrDefault().Value is string reason && !string.IsNullOrEmpty(reason) ? (OneOf<bool, string>?)reason : true;
var deprecated = Deprecated(symbol);

body.Add(level switch
{
Expand All @@ -137,6 +135,13 @@ void Api(int level, string title, ISymbol symbol, Compilation compilation)
});
}

OneOf<bool, string>? Deprecated(ISymbol symbol)
{
if (symbol.GetAttributes().FirstOrDefault(a => a.AttributeClass?.Name == "ObsoleteAttribute") is { } obsoleteAttribute)
return obsoleteAttribute.ConstructorArguments.FirstOrDefault().Value is string reason && !string.IsNullOrEmpty(reason) ? (OneOf<bool, string>?)reason : true;
return null;
}

void Namespace()
{
var namespaceSymbols = symbols.Select(n => n.symbol).ToHashSet(SymbolEqualityComparer.Default);
Expand Down Expand Up @@ -579,8 +584,14 @@ void EnumFields(INamedTypeSymbol type)

Parameter ToParameter(IFieldSymbol item)
{
var docs = Comment(item, compilation) is { } comment ? comment.Summary : null;
return new() { name = item.Name, @default = $"{item.ConstantValue}", description = docs };
var docs = Comment(item, compilation) is { } comment ? string.Join("\n\n", comment.Summary, comment.Remarks) : null;

return new()
{
name = item.Name, @default = $"{item.ConstantValue}",
deprecated = Deprecated(item),
description = docs,
};
}
}

Expand Down
11 changes: 8 additions & 3 deletions templates/modern/src/dotnet.scss
Original file line number Diff line number Diff line change
Expand Up @@ -3,7 +3,7 @@
* The .NET Foundation licenses this file to you under the MIT license.
*/

body[data-yaml-mime="ManagedReference"], body[data-yaml-mime="ApiPage"] article {
body[data-yaml-mime="ManagedReference"] article, body[data-yaml-mime="ApiPage"] article {
h1[data-uid] {
position: relative;
padding-right: 1.6rem;
Expand Down Expand Up @@ -65,8 +65,13 @@ body[data-yaml-mime="ManagedReference"], body[data-yaml-mime="ApiPage"] article
}

dl.parameters {
>dt>code {
margin-right: .2em;
>dt {
margin: 1em 0;

&>code {
margin-right: .2em;
font-size: 1em;
}
}
}

Expand Down
Loading

0 comments on commit e7b456c

Please sign in to comment.