3 // Sebastien Pouliot <sebastien.pouliot@microsoft.com>
5 // Copyright 2018 Microsoft Inc.
7 // Permission is hereby granted, free of charge, to any person obtaining
8 // a copy of this software and associated documentation files (the
9 // "Software"), to deal in the Software without restriction, including
10 // without limitation the rights to use, copy, modify, merge, publish,
11 // distribute, sublicense, and/or sell copies of the Software, and to
12 // permit persons to whom the Software is furnished to do so, subject to
13 // the following conditions:
15 // The above copyright notice and this permission notice shall be
16 // included in all copies or substantial portions of the Software.
18 // THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
19 // EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
20 // MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
21 // NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
22 // LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
23 // OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
24 // WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
29 using System
.Collections
.Generic
;
31 using System
.Xml
.Linq
;
34 namespace Mono
.ApiTools
{
36 class MarkdownFormatter
: Formatter
{
38 public MarkdownFormatter (State state
)
43 public override string LesserThan
=> "<";
44 public override string GreaterThan
=> ">";
46 public override void BeginDocument (TextWriter output
, string title
)
48 output
.WriteLine ($"# {title}");
52 public override void BeginAssembly (TextWriter output
)
54 // this serves as ToC (table of content) entries so we skip the "Assembly: " prefix
55 output
.WriteLine ($"## {State.Assembly}.dll");
59 public override void BeginNamespace (TextWriter output
, string action
)
61 output
.WriteLine ($"### {action}Namespace {State.Namespace}");
65 public override void BeginTypeAddition (TextWriter output
)
67 output
.WriteLine ($"#### New Type: {@State.Namespace}.{State.Type}");
69 output
.WriteLine ("```csharp");
72 public override void EndTypeAddition (TextWriter output
)
74 output
.WriteLine ("```");
78 public override void BeginTypeModification (TextWriter output
)
80 output
.WriteLine ($"#### Type Changed: {State.Namespace}.{State.Type}");
84 public override void BeginTypeRemoval (TextWriter output
)
86 output
.WriteLine ($"#### Removed Type {State.Namespace}.{State.Type}");
89 public override void BeginMemberAddition (TextWriter output
, IEnumerable
<XElement
> list
, MemberComparer member
)
91 if (State
.BaseType
== "System.Enum") {
92 output
.WriteLine ("Added value{0}:", list
.Count () > 1 ? "s" : String
.Empty
);
94 output
.WriteLine ("Added {0}:", list
.Count () > 1 ? member
.GroupName
: member
.ElementName
);
97 output
.WriteLine ("```csharp");
100 public override void AddMember (TextWriter output
, MemberComparer member
, bool isInterfaceBreakingChange
, string obsolete
, string description
)
102 output
.Write (obsolete
);
103 output
.WriteLine (description
);
106 public override void EndMemberAddition (TextWriter output
)
108 output
.WriteLine ("```");
112 public override void BeginMemberModification (TextWriter output
, string sectionName
)
114 output
.WriteLine ($"{sectionName}:");
116 output
.WriteLine ("```diff");
119 public override void EndMemberModification (TextWriter output
)
121 output
.WriteLine ("```");
125 public override void BeginMemberRemoval (TextWriter output
, IEnumerable
<XElement
> list
, MemberComparer member
)
127 if (State
.BaseType
== "System.Enum") {
128 output
.WriteLine ("Removed value{0}:", list
.Count () > 1 ? "s" : String
.Empty
);
130 output
.WriteLine ("Removed {0}:", list
.Count () > 1 ? member
.GroupName
: member
.ElementName
);
133 output
.WriteLine ("```csharp");
136 public override void RemoveMember (TextWriter output
, MemberComparer member
, bool is_breaking
, string obsolete
, string description
)
138 output
.Write (obsolete
);
139 output
.WriteLine (description
);
142 public override void EndMemberRemoval (TextWriter output
)
144 output
.WriteLine ("```");
148 public override void RenderObsoleteMessage (StringBuilder output
, MemberComparer member
, string description
, string optionalObsoleteMessage
)
150 output
.Append ("[Obsolete (");
151 if (!String
.IsNullOrEmpty (optionalObsoleteMessage
))
152 output
.Append ('"').Append (optionalObsoleteMessage
).Append ('"');
153 output
.AppendLine (")]");
154 output
.Append (description
);
157 string Clean (string line
, string remove, string keep
)
159 var cleaned
= line
.Replace (remove, String
.Empty
);
160 int s
= cleaned
.IndexOf (keep
, StringComparison
.Ordinal
);
162 int e
= cleaned
.IndexOf (keep
, s
+ keep
.Length
, StringComparison
.Ordinal
);
163 cleaned
= cleaned
.Remove (s
, e
- s
+ keep
.Length
);
165 while (cleaned
.Contains (" "))
166 cleaned
= cleaned
.Replace (" ", " ");
170 public override void DiffAddition (StringBuilder output
, string text
, bool breaking
)
172 output
.Append ("+++");
173 output
.Append (text
);
174 output
.Append ("+++");
177 public override void DiffModification (StringBuilder output
, string old
, string @new, bool breaking
)
180 DiffAddition (output
, old
, breaking
);
182 DiffRemoval (output
, @new, true);
185 public override void DiffRemoval (StringBuilder output
, string text
, bool breaking
)
187 output
.Append ("---");
188 output
.Append (text
);
189 output
.Append ("---");
192 public override void Diff (TextWriter output
, ApiChange apichange
)
194 foreach (var line
in apichange
.Member
.ToString ().Split (new[] { Environment.NewLine }
, 0)) {
195 if (line
.Contains ("+++")) {
196 output
.WriteLine ("-{0}", Clean (line
, "+++", "---"));
197 output
.WriteLine ("+{0}", Clean (line
, "---", "+++"));
199 output
.WriteLine (" {0}", line
);