@rushstack/terminal 0.21.0 → 0.22.1

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (172) hide show
  1. package/CHANGELOG.json +40 -0
  2. package/CHANGELOG.md +15 -1
  3. package/dist/tsdoc-metadata.json +1 -1
  4. package/lib-esm/AnsiEscape.js +131 -0
  5. package/lib-esm/AnsiEscape.js.map +1 -0
  6. package/lib-esm/CallbackWritable.js +27 -0
  7. package/lib-esm/CallbackWritable.js.map +1 -0
  8. package/lib-esm/Colorize.js +158 -0
  9. package/lib-esm/Colorize.js.map +1 -0
  10. package/lib-esm/ConsoleTerminalProvider.js +58 -0
  11. package/lib-esm/ConsoleTerminalProvider.js.map +1 -0
  12. package/lib-esm/DiscardStdoutTransform.js +90 -0
  13. package/lib-esm/DiscardStdoutTransform.js.map +1 -0
  14. package/lib-esm/IProblemCollector.js +4 -0
  15. package/lib-esm/IProblemCollector.js.map +1 -0
  16. package/lib-esm/ITerminal.js +4 -0
  17. package/lib-esm/ITerminal.js.map +1 -0
  18. package/lib-esm/ITerminalChunk.js +18 -0
  19. package/lib-esm/ITerminalChunk.js.map +1 -0
  20. package/lib-esm/ITerminalProvider.js +29 -0
  21. package/lib-esm/ITerminalProvider.js.map +1 -0
  22. package/lib-esm/MockWritable.js +28 -0
  23. package/lib-esm/MockWritable.js.map +1 -0
  24. package/lib-esm/NoOpTerminalProvider.js +30 -0
  25. package/lib-esm/NoOpTerminalProvider.js.map +1 -0
  26. package/lib-esm/NormalizeNewlinesTextRewriter.js +66 -0
  27. package/lib-esm/NormalizeNewlinesTextRewriter.js.map +1 -0
  28. package/lib-esm/PrefixProxyTerminalProvider.js +58 -0
  29. package/lib-esm/PrefixProxyTerminalProvider.js.map +1 -0
  30. package/lib-esm/PrintUtilities.js +146 -0
  31. package/lib-esm/PrintUtilities.js.map +1 -0
  32. package/lib-esm/ProblemCollector.js +85 -0
  33. package/lib-esm/ProblemCollector.js.map +1 -0
  34. package/lib-esm/RemoveColorsTextRewriter.js +91 -0
  35. package/lib-esm/RemoveColorsTextRewriter.js.map +1 -0
  36. package/lib-esm/SplitterTransform.js +74 -0
  37. package/lib-esm/SplitterTransform.js.map +1 -0
  38. package/lib-esm/StdioLineTransform.js +111 -0
  39. package/lib-esm/StdioLineTransform.js.map +1 -0
  40. package/lib-esm/StdioSummarizer.js +95 -0
  41. package/lib-esm/StdioSummarizer.js.map +1 -0
  42. package/lib-esm/StdioWritable.js +27 -0
  43. package/lib-esm/StdioWritable.js.map +1 -0
  44. package/lib-esm/StringBufferTerminalProvider.js +185 -0
  45. package/lib-esm/StringBufferTerminalProvider.js.map +1 -0
  46. package/lib-esm/Terminal.js +150 -0
  47. package/lib-esm/Terminal.js.map +1 -0
  48. package/lib-esm/TerminalStreamWritable.js +49 -0
  49. package/lib-esm/TerminalStreamWritable.js.map +1 -0
  50. package/lib-esm/TerminalTransform.js +53 -0
  51. package/lib-esm/TerminalTransform.js.map +1 -0
  52. package/lib-esm/TerminalWritable.js +119 -0
  53. package/lib-esm/TerminalWritable.js.map +1 -0
  54. package/lib-esm/TextRewriter.js +35 -0
  55. package/lib-esm/TextRewriter.js.map +1 -0
  56. package/lib-esm/TextRewriterTransform.js +90 -0
  57. package/lib-esm/TextRewriterTransform.js.map +1 -0
  58. package/lib-esm/index.js +38 -0
  59. package/lib-esm/index.js.map +1 -0
  60. package/package.json +30 -6
  61. /package/{lib → lib-commonjs}/AnsiEscape.js +0 -0
  62. /package/{lib → lib-commonjs}/AnsiEscape.js.map +0 -0
  63. /package/{lib → lib-commonjs}/CallbackWritable.js +0 -0
  64. /package/{lib → lib-commonjs}/CallbackWritable.js.map +0 -0
  65. /package/{lib → lib-commonjs}/Colorize.js +0 -0
  66. /package/{lib → lib-commonjs}/Colorize.js.map +0 -0
  67. /package/{lib → lib-commonjs}/ConsoleTerminalProvider.js +0 -0
  68. /package/{lib → lib-commonjs}/ConsoleTerminalProvider.js.map +0 -0
  69. /package/{lib → lib-commonjs}/DiscardStdoutTransform.js +0 -0
  70. /package/{lib → lib-commonjs}/DiscardStdoutTransform.js.map +0 -0
  71. /package/{lib → lib-commonjs}/IProblemCollector.js +0 -0
  72. /package/{lib → lib-commonjs}/IProblemCollector.js.map +0 -0
  73. /package/{lib → lib-commonjs}/ITerminal.js +0 -0
  74. /package/{lib → lib-commonjs}/ITerminal.js.map +0 -0
  75. /package/{lib → lib-commonjs}/ITerminalChunk.js +0 -0
  76. /package/{lib → lib-commonjs}/ITerminalChunk.js.map +0 -0
  77. /package/{lib → lib-commonjs}/ITerminalProvider.js +0 -0
  78. /package/{lib → lib-commonjs}/ITerminalProvider.js.map +0 -0
  79. /package/{lib → lib-commonjs}/MockWritable.js +0 -0
  80. /package/{lib → lib-commonjs}/MockWritable.js.map +0 -0
  81. /package/{lib → lib-commonjs}/NoOpTerminalProvider.js +0 -0
  82. /package/{lib → lib-commonjs}/NoOpTerminalProvider.js.map +0 -0
  83. /package/{lib → lib-commonjs}/NormalizeNewlinesTextRewriter.js +0 -0
  84. /package/{lib → lib-commonjs}/NormalizeNewlinesTextRewriter.js.map +0 -0
  85. /package/{lib → lib-commonjs}/PrefixProxyTerminalProvider.js +0 -0
  86. /package/{lib → lib-commonjs}/PrefixProxyTerminalProvider.js.map +0 -0
  87. /package/{lib → lib-commonjs}/PrintUtilities.js +0 -0
  88. /package/{lib → lib-commonjs}/PrintUtilities.js.map +0 -0
  89. /package/{lib → lib-commonjs}/ProblemCollector.js +0 -0
  90. /package/{lib → lib-commonjs}/ProblemCollector.js.map +0 -0
  91. /package/{lib → lib-commonjs}/RemoveColorsTextRewriter.js +0 -0
  92. /package/{lib → lib-commonjs}/RemoveColorsTextRewriter.js.map +0 -0
  93. /package/{lib → lib-commonjs}/SplitterTransform.js +0 -0
  94. /package/{lib → lib-commonjs}/SplitterTransform.js.map +0 -0
  95. /package/{lib → lib-commonjs}/StdioLineTransform.js +0 -0
  96. /package/{lib → lib-commonjs}/StdioLineTransform.js.map +0 -0
  97. /package/{lib → lib-commonjs}/StdioSummarizer.js +0 -0
  98. /package/{lib → lib-commonjs}/StdioSummarizer.js.map +0 -0
  99. /package/{lib → lib-commonjs}/StdioWritable.js +0 -0
  100. /package/{lib → lib-commonjs}/StdioWritable.js.map +0 -0
  101. /package/{lib → lib-commonjs}/StringBufferTerminalProvider.js +0 -0
  102. /package/{lib → lib-commonjs}/StringBufferTerminalProvider.js.map +0 -0
  103. /package/{lib → lib-commonjs}/Terminal.js +0 -0
  104. /package/{lib → lib-commonjs}/Terminal.js.map +0 -0
  105. /package/{lib → lib-commonjs}/TerminalStreamWritable.js +0 -0
  106. /package/{lib → lib-commonjs}/TerminalStreamWritable.js.map +0 -0
  107. /package/{lib → lib-commonjs}/TerminalTransform.js +0 -0
  108. /package/{lib → lib-commonjs}/TerminalTransform.js.map +0 -0
  109. /package/{lib → lib-commonjs}/TerminalWritable.js +0 -0
  110. /package/{lib → lib-commonjs}/TerminalWritable.js.map +0 -0
  111. /package/{lib → lib-commonjs}/TextRewriter.js +0 -0
  112. /package/{lib → lib-commonjs}/TextRewriter.js.map +0 -0
  113. /package/{lib → lib-commonjs}/TextRewriterTransform.js +0 -0
  114. /package/{lib → lib-commonjs}/TextRewriterTransform.js.map +0 -0
  115. /package/{lib → lib-commonjs}/index.js +0 -0
  116. /package/{lib → lib-commonjs}/index.js.map +0 -0
  117. /package/{lib → lib-dts}/AnsiEscape.d.ts +0 -0
  118. /package/{lib → lib-dts}/AnsiEscape.d.ts.map +0 -0
  119. /package/{lib → lib-dts}/CallbackWritable.d.ts +0 -0
  120. /package/{lib → lib-dts}/CallbackWritable.d.ts.map +0 -0
  121. /package/{lib → lib-dts}/Colorize.d.ts +0 -0
  122. /package/{lib → lib-dts}/Colorize.d.ts.map +0 -0
  123. /package/{lib → lib-dts}/ConsoleTerminalProvider.d.ts +0 -0
  124. /package/{lib → lib-dts}/ConsoleTerminalProvider.d.ts.map +0 -0
  125. /package/{lib → lib-dts}/DiscardStdoutTransform.d.ts +0 -0
  126. /package/{lib → lib-dts}/DiscardStdoutTransform.d.ts.map +0 -0
  127. /package/{lib → lib-dts}/IProblemCollector.d.ts +0 -0
  128. /package/{lib → lib-dts}/IProblemCollector.d.ts.map +0 -0
  129. /package/{lib → lib-dts}/ITerminal.d.ts +0 -0
  130. /package/{lib → lib-dts}/ITerminal.d.ts.map +0 -0
  131. /package/{lib → lib-dts}/ITerminalChunk.d.ts +0 -0
  132. /package/{lib → lib-dts}/ITerminalChunk.d.ts.map +0 -0
  133. /package/{lib → lib-dts}/ITerminalProvider.d.ts +0 -0
  134. /package/{lib → lib-dts}/ITerminalProvider.d.ts.map +0 -0
  135. /package/{lib → lib-dts}/MockWritable.d.ts +0 -0
  136. /package/{lib → lib-dts}/MockWritable.d.ts.map +0 -0
  137. /package/{lib → lib-dts}/NoOpTerminalProvider.d.ts +0 -0
  138. /package/{lib → lib-dts}/NoOpTerminalProvider.d.ts.map +0 -0
  139. /package/{lib → lib-dts}/NormalizeNewlinesTextRewriter.d.ts +0 -0
  140. /package/{lib → lib-dts}/NormalizeNewlinesTextRewriter.d.ts.map +0 -0
  141. /package/{lib → lib-dts}/PrefixProxyTerminalProvider.d.ts +0 -0
  142. /package/{lib → lib-dts}/PrefixProxyTerminalProvider.d.ts.map +0 -0
  143. /package/{lib → lib-dts}/PrintUtilities.d.ts +0 -0
  144. /package/{lib → lib-dts}/PrintUtilities.d.ts.map +0 -0
  145. /package/{lib → lib-dts}/ProblemCollector.d.ts +0 -0
  146. /package/{lib → lib-dts}/ProblemCollector.d.ts.map +0 -0
  147. /package/{lib → lib-dts}/RemoveColorsTextRewriter.d.ts +0 -0
  148. /package/{lib → lib-dts}/RemoveColorsTextRewriter.d.ts.map +0 -0
  149. /package/{lib → lib-dts}/SplitterTransform.d.ts +0 -0
  150. /package/{lib → lib-dts}/SplitterTransform.d.ts.map +0 -0
  151. /package/{lib → lib-dts}/StdioLineTransform.d.ts +0 -0
  152. /package/{lib → lib-dts}/StdioLineTransform.d.ts.map +0 -0
  153. /package/{lib → lib-dts}/StdioSummarizer.d.ts +0 -0
  154. /package/{lib → lib-dts}/StdioSummarizer.d.ts.map +0 -0
  155. /package/{lib → lib-dts}/StdioWritable.d.ts +0 -0
  156. /package/{lib → lib-dts}/StdioWritable.d.ts.map +0 -0
  157. /package/{lib → lib-dts}/StringBufferTerminalProvider.d.ts +0 -0
  158. /package/{lib → lib-dts}/StringBufferTerminalProvider.d.ts.map +0 -0
  159. /package/{lib → lib-dts}/Terminal.d.ts +0 -0
  160. /package/{lib → lib-dts}/Terminal.d.ts.map +0 -0
  161. /package/{lib → lib-dts}/TerminalStreamWritable.d.ts +0 -0
  162. /package/{lib → lib-dts}/TerminalStreamWritable.d.ts.map +0 -0
  163. /package/{lib → lib-dts}/TerminalTransform.d.ts +0 -0
  164. /package/{lib → lib-dts}/TerminalTransform.d.ts.map +0 -0
  165. /package/{lib → lib-dts}/TerminalWritable.d.ts +0 -0
  166. /package/{lib → lib-dts}/TerminalWritable.d.ts.map +0 -0
  167. /package/{lib → lib-dts}/TextRewriter.d.ts +0 -0
  168. /package/{lib → lib-dts}/TextRewriter.d.ts.map +0 -0
  169. /package/{lib → lib-dts}/TextRewriterTransform.d.ts +0 -0
  170. /package/{lib → lib-dts}/TextRewriterTransform.d.ts.map +0 -0
  171. /package/{lib → lib-dts}/index.d.ts +0 -0
  172. /package/{lib → lib-dts}/index.d.ts.map +0 -0
@@ -0,0 +1 @@
1
+ {"version":3,"file":"StringBufferTerminalProvider.js","sourceRoot":"","sources":["../src/StringBufferTerminalProvider.ts"],"names":[],"mappings":"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","sourcesContent":["// Copyright (c) Microsoft Corporation. All rights reserved. Licensed under the MIT license.\n// See LICENSE in the project root for license information.\n\nimport { StringBuilder, Text } from '@rushstack/node-core-library';\n\nimport { type ITerminalProvider, TerminalProviderSeverity } from './ITerminalProvider';\nimport { AnsiEscape } from './AnsiEscape';\n\n/**\n * @beta\n */\nexport interface IStringBufferOutputOptions {\n /**\n * If set to true, special characters like \\\\n, \\\\r, and the \\\\u001b character\n * in color control tokens will get normalized to [-n-], [-r-], and [-x-] respectively\n *\n * This option defaults to `true`\n */\n normalizeSpecialCharacters?: boolean;\n}\n\n/**\n * @beta\n */\nexport interface IStringBufferOutputChunksOptions extends IStringBufferOutputOptions {\n /**\n * If true, the output will be returned as an array of lines prefixed with severity tokens.\n */\n asLines?: boolean;\n}\n\n/**\n * @beta\n */\nexport interface IAllStringBufferOutput {\n log: string;\n warning: string;\n error: string;\n verbose: string;\n debug: string;\n}\n\n/**\n * @beta\n */\nexport type TerminalProviderSeverityName = keyof typeof TerminalProviderSeverity;\n\n/**\n * @beta\n */\nexport interface IOutputChunk {\n text: string;\n severity: TerminalProviderSeverityName;\n}\n\nfunction _normalizeOptions<TOptions extends IStringBufferOutputOptions>(\n options: TOptions\n): TOptions & Required<IStringBufferOutputOptions> {\n return {\n normalizeSpecialCharacters: true,\n ...options\n };\n}\n\nfunction _normalizeOutput(s: string, options: IStringBufferOutputOptions | undefined): string {\n const { normalizeSpecialCharacters } = _normalizeOptions(options ?? {});\n return _normalizeOutputInner(s, normalizeSpecialCharacters);\n}\n\nfunction _normalizeOutputInner(s: string, normalizeSpecialCharacters: boolean): string {\n s = Text.convertToLf(s);\n\n if (normalizeSpecialCharacters) {\n return AnsiEscape.formatForTests(s, { encodeNewlines: true });\n } else {\n return s;\n }\n}\n\nconst LONGEST_SEVERITY_NAME_LENGTH: number = Object.keys(TerminalProviderSeverity).reduce(\n (max: number, k: string) => Math.max(max, k.length),\n 0\n);\n\n/**\n * Terminal provider that stores written data in buffers separated by severity.\n * This terminal provider is designed to be used when code that prints to a terminal\n * is being unit tested.\n *\n * @beta\n */\nexport class StringBufferTerminalProvider implements ITerminalProvider {\n private _standardBuffer: StringBuilder = new StringBuilder();\n private _verboseBuffer: StringBuilder = new StringBuilder();\n private _debugBuffer: StringBuilder = new StringBuilder();\n private _warningBuffer: StringBuilder = new StringBuilder();\n private _errorBuffer: StringBuilder = new StringBuilder();\n private _allOutputChunks: IOutputChunk[] = [];\n\n /**\n * {@inheritDoc ITerminalProvider.supportsColor}\n */\n public readonly supportsColor: boolean;\n\n public constructor(supportsColor: boolean = false) {\n this.supportsColor = supportsColor;\n }\n\n /**\n * {@inheritDoc ITerminalProvider.write}\n */\n public write(text: string, severity: TerminalProviderSeverity): void {\n const severityName: TerminalProviderSeverityName = TerminalProviderSeverity[\n severity\n ] as TerminalProviderSeverityName;\n\n const lastChunk: IOutputChunk | undefined = this._allOutputChunks[this._allOutputChunks.length - 1];\n if (lastChunk && lastChunk.severity === severityName) {\n lastChunk.text += text;\n } else {\n this._allOutputChunks.push({\n text,\n severity: severityName\n });\n }\n\n switch (severity) {\n case TerminalProviderSeverity.warning: {\n this._warningBuffer.append(text);\n break;\n }\n\n case TerminalProviderSeverity.error: {\n this._errorBuffer.append(text);\n break;\n }\n\n case TerminalProviderSeverity.verbose: {\n this._verboseBuffer.append(text);\n break;\n }\n\n case TerminalProviderSeverity.debug: {\n this._debugBuffer.append(text);\n break;\n }\n\n case TerminalProviderSeverity.log:\n default: {\n this._standardBuffer.append(text);\n break;\n }\n }\n }\n\n /**\n * {@inheritDoc ITerminalProvider.eolCharacter}\n */\n public get eolCharacter(): string {\n return '\\n';\n }\n\n /**\n * Get everything that has been written at log-level severity.\n */\n public getOutput(options?: IStringBufferOutputOptions): string {\n return _normalizeOutput(this._standardBuffer.toString(), options);\n }\n\n /**\n * @deprecated - use {@link StringBufferTerminalProvider.getVerboseOutput}\n */\n public getVerbose(options?: IStringBufferOutputOptions): string {\n return this.getVerboseOutput(options);\n }\n\n /**\n * Get everything that has been written at verbose-level severity.\n */\n public getVerboseOutput(options?: IStringBufferOutputOptions): string {\n return _normalizeOutput(this._verboseBuffer.toString(), options);\n }\n\n /**\n * Get everything that has been written at debug-level severity.\n */\n public getDebugOutput(options?: IStringBufferOutputOptions): string {\n return _normalizeOutput(this._debugBuffer.toString(), options);\n }\n\n /**\n * Get everything that has been written at error-level severity.\n */\n public getErrorOutput(options?: IStringBufferOutputOptions): string {\n return _normalizeOutput(this._errorBuffer.toString(), options);\n }\n\n /**\n * Get everything that has been written at warning-level severity.\n */\n public getWarningOutput(options?: IStringBufferOutputOptions): string {\n return _normalizeOutput(this._warningBuffer.toString(), options);\n }\n\n /**\n * Get everything that has been written at all severity levels.\n */\n public getAllOutput(sparse?: false, options?: IStringBufferOutputOptions): IAllStringBufferOutput;\n public getAllOutput(sparse: true, options?: IStringBufferOutputOptions): Partial<IAllStringBufferOutput>;\n public getAllOutput(\n sparse: boolean | undefined,\n options?: IStringBufferOutputOptions\n ): Partial<IAllStringBufferOutput> {\n const result: Partial<IAllStringBufferOutput> = {};\n\n const log: string = this.getOutput(options);\n if (!sparse || log) {\n result.log = log;\n }\n\n const warning: string = this.getWarningOutput(options);\n if (!sparse || warning) {\n result.warning = warning;\n }\n\n const error: string = this.getErrorOutput(options);\n if (!sparse || error) {\n result.error = error;\n }\n\n const verbose: string = this.getVerboseOutput(options);\n if (!sparse || verbose) {\n result.verbose = verbose;\n }\n\n const debug: string = this.getDebugOutput(options);\n if (!sparse || debug) {\n result.debug = debug;\n }\n\n return result;\n }\n\n /**\n * Get everything that has been written as an array of output chunks, preserving order.\n */\n public getAllOutputAsChunks(\n options?: IStringBufferOutputChunksOptions & { asLines?: false }\n ): IOutputChunk[];\n public getAllOutputAsChunks(\n options: IStringBufferOutputChunksOptions & { asLines: true }\n ): `[${string}] ${string}`[];\n public getAllOutputAsChunks(options: IStringBufferOutputChunksOptions = {}): IOutputChunk[] | string[] {\n const { asLines, normalizeSpecialCharacters } = _normalizeOptions(options);\n if (asLines) {\n const lines: `[${string}] ${string}`[] = [];\n\n for (const { text: rawText, severity: rawSeverity } of this._allOutputChunks) {\n const severity: string = (rawSeverity as TerminalProviderSeverityName).padStart(\n LONGEST_SEVERITY_NAME_LENGTH,\n ' '\n );\n\n const lfText: string = Text.convertToLf(rawText);\n const rawLines: string[] = lfText.split('\\n');\n\n // Emit one entry per logical line.\n for (let i: number = 0; i < rawLines.length; i++) {\n const isLast: boolean = i === rawLines.length - 1;\n const isFinalTrailingEmpty: boolean = isLast && rawLines[i] === '';\n\n if (isFinalTrailingEmpty) {\n continue;\n }\n\n const hasNewlineAfter: boolean = i < rawLines.length - 1;\n\n // If the original output had a newline after this line, preserve it as the special token\n // (e.g. \"[n]\") when normalization is enabled.\n const shouldIncludeNewlineToken: boolean = normalizeSpecialCharacters && hasNewlineAfter;\n const lineText: string = shouldIncludeNewlineToken ? `${rawLines[i]}\\n` : rawLines[i];\n\n const text: string = _normalizeOutputInner(lineText, normalizeSpecialCharacters);\n lines.push(`[${severity}] ${text}`);\n }\n }\n\n return lines;\n } else {\n return this._allOutputChunks.map(({ text: rawText, severity }) => {\n const text: string = _normalizeOutputInner(rawText, normalizeSpecialCharacters);\n return {\n text,\n severity\n };\n });\n }\n }\n}\n"]}
@@ -0,0 +1,150 @@
1
+ // Copyright (c) Microsoft Corporation. All rights reserved. Licensed under the MIT license.
2
+ // See LICENSE in the project root for license information.
3
+ import { TerminalProviderSeverity } from './ITerminalProvider';
4
+ import { Colorize } from './Colorize';
5
+ import { AnsiEscape } from './AnsiEscape';
6
+ /**
7
+ * This class facilitates writing to a console.
8
+ *
9
+ * @beta
10
+ */
11
+ export class Terminal {
12
+ constructor(provider) {
13
+ this._providers = new Set([provider]);
14
+ }
15
+ /**
16
+ * {@inheritdoc ITerminal.registerProvider}
17
+ */
18
+ registerProvider(provider) {
19
+ this._providers.add(provider);
20
+ }
21
+ /**
22
+ * {@inheritdoc ITerminal.unregisterProvider}
23
+ */
24
+ unregisterProvider(provider) {
25
+ this._providers.delete(provider);
26
+ }
27
+ /**
28
+ * {@inheritdoc ITerminal.write}
29
+ */
30
+ write(...messageParts) {
31
+ const { parts } = this._normalizeWriteParameters(messageParts);
32
+ this._writeSegmentsToProviders(parts, TerminalProviderSeverity.log, false);
33
+ }
34
+ /**
35
+ * {@inheritdoc ITerminal.writeLine}
36
+ */
37
+ writeLine(...messageParts) {
38
+ const { parts } = this._normalizeWriteParameters(messageParts);
39
+ this._writeSegmentsToProviders(parts, TerminalProviderSeverity.log, true);
40
+ }
41
+ /**
42
+ * {@inheritdoc ITerminal.writeWarning}
43
+ */
44
+ writeWarning(...messageParts) {
45
+ const { parts, options: { doNotOverrideSgrCodes } } = this._normalizeWriteParameters(messageParts);
46
+ this._writeSegmentsToProviders(doNotOverrideSgrCodes
47
+ ? parts
48
+ : parts.map((part) => Colorize.yellow(AnsiEscape.removeCodes(part))), TerminalProviderSeverity.warning, false);
49
+ }
50
+ /**
51
+ * {@inheritdoc ITerminal.writeWarningLine}
52
+ */
53
+ writeWarningLine(...messageParts) {
54
+ const { parts, options: { doNotOverrideSgrCodes } } = this._normalizeWriteParameters(messageParts);
55
+ this._writeSegmentsToProviders(doNotOverrideSgrCodes
56
+ ? parts
57
+ : parts.map((part) => Colorize.yellow(AnsiEscape.removeCodes(part))), TerminalProviderSeverity.warning, true);
58
+ }
59
+ /**
60
+ * {@inheritdoc ITerminal.writeError}
61
+ */
62
+ writeError(...messageParts) {
63
+ const { parts, options: { doNotOverrideSgrCodes } } = this._normalizeWriteParameters(messageParts);
64
+ this._writeSegmentsToProviders(doNotOverrideSgrCodes ? parts : parts.map((part) => Colorize.red(AnsiEscape.removeCodes(part))), TerminalProviderSeverity.error, false);
65
+ }
66
+ /**
67
+ * {@inheritdoc ITerminal.writeErrorLine}
68
+ */
69
+ writeErrorLine(...messageParts) {
70
+ const { parts, options: { doNotOverrideSgrCodes } } = this._normalizeWriteParameters(messageParts);
71
+ this._writeSegmentsToProviders(doNotOverrideSgrCodes ? parts : parts.map((part) => Colorize.red(AnsiEscape.removeCodes(part))), TerminalProviderSeverity.error, true);
72
+ }
73
+ /**
74
+ * {@inheritdoc ITerminal.writeVerbose}
75
+ */
76
+ writeVerbose(...messageParts) {
77
+ const { parts } = this._normalizeWriteParameters(messageParts);
78
+ this._writeSegmentsToProviders(parts, TerminalProviderSeverity.verbose, false);
79
+ }
80
+ /**
81
+ * {@inheritdoc ITerminal.writeVerboseLine}
82
+ */
83
+ writeVerboseLine(...messageParts) {
84
+ const { parts } = this._normalizeWriteParameters(messageParts);
85
+ this._writeSegmentsToProviders(parts, TerminalProviderSeverity.verbose, true);
86
+ }
87
+ /**
88
+ * {@inheritdoc ITerminal.writeDebug}
89
+ */
90
+ writeDebug(...messageParts) {
91
+ const { parts } = this._normalizeWriteParameters(messageParts);
92
+ this._writeSegmentsToProviders(parts, TerminalProviderSeverity.debug, false);
93
+ }
94
+ /**
95
+ * {@inheritdoc ITerminal.writeDebugLine}
96
+ */
97
+ writeDebugLine(...messageParts) {
98
+ const { parts } = this._normalizeWriteParameters(messageParts);
99
+ this._writeSegmentsToProviders(parts, TerminalProviderSeverity.debug, true);
100
+ }
101
+ _writeSegmentsToProviders(segments, severity, followedByEol) {
102
+ const lines = [segments.join('')];
103
+ if (followedByEol) {
104
+ lines.push('');
105
+ }
106
+ let linesWithoutColor;
107
+ const concatenatedLinesWithColorByNewlineChar = new Map();
108
+ const concatenatedLinesWithoutColorByNewlineChar = new Map();
109
+ for (const provider of this._providers) {
110
+ let textToWrite;
111
+ const eol = provider.eolCharacter;
112
+ if (provider.supportsColor) {
113
+ textToWrite = concatenatedLinesWithColorByNewlineChar.get(eol);
114
+ if (!textToWrite) {
115
+ textToWrite = lines.join(eol);
116
+ concatenatedLinesWithColorByNewlineChar.set(eol, textToWrite);
117
+ }
118
+ }
119
+ else {
120
+ textToWrite = concatenatedLinesWithoutColorByNewlineChar.get(eol);
121
+ if (!textToWrite) {
122
+ if (!linesWithoutColor) {
123
+ linesWithoutColor = [];
124
+ for (const line of lines) {
125
+ linesWithoutColor.push(AnsiEscape.removeCodes(line));
126
+ }
127
+ }
128
+ textToWrite = linesWithoutColor.join(eol);
129
+ concatenatedLinesWithoutColorByNewlineChar.set(eol, textToWrite);
130
+ }
131
+ }
132
+ provider.write(textToWrite, severity);
133
+ }
134
+ }
135
+ _normalizeWriteParameters(parameters) {
136
+ if (parameters.length === 0) {
137
+ return { parts: [], options: {} };
138
+ }
139
+ else {
140
+ const lastParameter = parameters[parameters.length - 1];
141
+ if (typeof lastParameter === 'string') {
142
+ return { parts: parameters, options: {} };
143
+ }
144
+ else {
145
+ return { parts: parameters.slice(0, -1), options: lastParameter };
146
+ }
147
+ }
148
+ }
149
+ }
150
+ //# sourceMappingURL=Terminal.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"Terminal.js","sourceRoot":"","sources":["../src/Terminal.ts"],"names":[],"mappings":"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","sourcesContent":["// Copyright (c) Microsoft Corporation. All rights reserved. Licensed under the MIT license.\n// See LICENSE in the project root for license information.\n\nimport { type ITerminalProvider, TerminalProviderSeverity } from './ITerminalProvider';\nimport { Colorize } from './Colorize';\nimport type { ITerminal, ITerminalWriteOptions, TerminalWriteParameters } from './ITerminal';\nimport { AnsiEscape } from './AnsiEscape';\n\n/**\n * This class facilitates writing to a console.\n *\n * @beta\n */\nexport class Terminal implements ITerminal {\n private readonly _providers: Set<ITerminalProvider>;\n\n public constructor(provider: ITerminalProvider) {\n this._providers = new Set<ITerminalProvider>([provider]);\n }\n\n /**\n * {@inheritdoc ITerminal.registerProvider}\n */\n public registerProvider(provider: ITerminalProvider): void {\n this._providers.add(provider);\n }\n\n /**\n * {@inheritdoc ITerminal.unregisterProvider}\n */\n public unregisterProvider(provider: ITerminalProvider): void {\n this._providers.delete(provider);\n }\n\n /**\n * {@inheritdoc ITerminal.write}\n */\n public write(...messageParts: TerminalWriteParameters): void {\n const { parts } = this._normalizeWriteParameters(messageParts);\n this._writeSegmentsToProviders(parts, TerminalProviderSeverity.log, false);\n }\n\n /**\n * {@inheritdoc ITerminal.writeLine}\n */\n public writeLine(...messageParts: TerminalWriteParameters): void {\n const { parts } = this._normalizeWriteParameters(messageParts);\n this._writeSegmentsToProviders(parts, TerminalProviderSeverity.log, true);\n }\n\n /**\n * {@inheritdoc ITerminal.writeWarning}\n */\n public writeWarning(...messageParts: TerminalWriteParameters): void {\n const {\n parts,\n options: { doNotOverrideSgrCodes }\n } = this._normalizeWriteParameters(messageParts);\n this._writeSegmentsToProviders(\n doNotOverrideSgrCodes\n ? parts\n : parts.map((part): string => Colorize.yellow(AnsiEscape.removeCodes(part))),\n TerminalProviderSeverity.warning,\n false\n );\n }\n\n /**\n * {@inheritdoc ITerminal.writeWarningLine}\n */\n public writeWarningLine(...messageParts: TerminalWriteParameters): void {\n const {\n parts,\n options: { doNotOverrideSgrCodes }\n } = this._normalizeWriteParameters(messageParts);\n this._writeSegmentsToProviders(\n doNotOverrideSgrCodes\n ? parts\n : parts.map((part): string => Colorize.yellow(AnsiEscape.removeCodes(part))),\n TerminalProviderSeverity.warning,\n true\n );\n }\n\n /**\n * {@inheritdoc ITerminal.writeError}\n */\n public writeError(...messageParts: TerminalWriteParameters): void {\n const {\n parts,\n options: { doNotOverrideSgrCodes }\n } = this._normalizeWriteParameters(messageParts);\n this._writeSegmentsToProviders(\n doNotOverrideSgrCodes ? parts : parts.map((part): string => Colorize.red(AnsiEscape.removeCodes(part))),\n TerminalProviderSeverity.error,\n false\n );\n }\n\n /**\n * {@inheritdoc ITerminal.writeErrorLine}\n */\n public writeErrorLine(...messageParts: TerminalWriteParameters): void {\n const {\n parts,\n options: { doNotOverrideSgrCodes }\n } = this._normalizeWriteParameters(messageParts);\n this._writeSegmentsToProviders(\n doNotOverrideSgrCodes ? parts : parts.map((part): string => Colorize.red(AnsiEscape.removeCodes(part))),\n TerminalProviderSeverity.error,\n true\n );\n }\n\n /**\n * {@inheritdoc ITerminal.writeVerbose}\n */\n public writeVerbose(...messageParts: TerminalWriteParameters): void {\n const { parts } = this._normalizeWriteParameters(messageParts);\n this._writeSegmentsToProviders(parts, TerminalProviderSeverity.verbose, false);\n }\n\n /**\n * {@inheritdoc ITerminal.writeVerboseLine}\n */\n public writeVerboseLine(...messageParts: TerminalWriteParameters): void {\n const { parts } = this._normalizeWriteParameters(messageParts);\n this._writeSegmentsToProviders(parts, TerminalProviderSeverity.verbose, true);\n }\n\n /**\n * {@inheritdoc ITerminal.writeDebug}\n */\n public writeDebug(...messageParts: TerminalWriteParameters): void {\n const { parts } = this._normalizeWriteParameters(messageParts);\n this._writeSegmentsToProviders(parts, TerminalProviderSeverity.debug, false);\n }\n\n /**\n * {@inheritdoc ITerminal.writeDebugLine}\n */\n public writeDebugLine(...messageParts: TerminalWriteParameters): void {\n const { parts } = this._normalizeWriteParameters(messageParts);\n this._writeSegmentsToProviders(parts, TerminalProviderSeverity.debug, true);\n }\n\n private _writeSegmentsToProviders(\n segments: string[],\n severity: TerminalProviderSeverity,\n followedByEol: boolean\n ): void {\n const lines: string[] = [segments.join('')];\n if (followedByEol) {\n lines.push('');\n }\n\n let linesWithoutColor: string[] | undefined;\n\n const concatenatedLinesWithColorByNewlineChar: Map<string, string> = new Map();\n const concatenatedLinesWithoutColorByNewlineChar: Map<string, string> = new Map();\n for (const provider of this._providers) {\n let textToWrite: string | undefined;\n const eol: string = provider.eolCharacter;\n if (provider.supportsColor) {\n textToWrite = concatenatedLinesWithColorByNewlineChar.get(eol);\n if (!textToWrite) {\n textToWrite = lines.join(eol);\n concatenatedLinesWithColorByNewlineChar.set(eol, textToWrite);\n }\n } else {\n textToWrite = concatenatedLinesWithoutColorByNewlineChar.get(eol);\n if (!textToWrite) {\n if (!linesWithoutColor) {\n linesWithoutColor = [];\n for (const line of lines) {\n linesWithoutColor.push(AnsiEscape.removeCodes(line));\n }\n }\n\n textToWrite = linesWithoutColor.join(eol);\n concatenatedLinesWithoutColorByNewlineChar.set(eol, textToWrite);\n }\n }\n\n provider.write(textToWrite, severity);\n }\n }\n\n private _normalizeWriteParameters(parameters: TerminalWriteParameters): {\n parts: string[];\n options: ITerminalWriteOptions;\n } {\n if (parameters.length === 0) {\n return { parts: [], options: {} };\n } else {\n const lastParameter: string | ITerminalWriteOptions = parameters[parameters.length - 1];\n if (typeof lastParameter === 'string') {\n return { parts: parameters as string[], options: {} };\n } else {\n return { parts: parameters.slice(0, -1) as string[], options: lastParameter };\n }\n }\n }\n}\n"]}
@@ -0,0 +1,49 @@
1
+ // Copyright (c) Microsoft Corporation. All rights reserved. Licensed under the MIT license.
2
+ // See LICENSE in the project root for license information.
3
+ import { Writable } from 'node:stream';
4
+ import { TerminalProviderSeverity } from './ITerminalProvider';
5
+ /**
6
+ * A adapter to allow writing to a provided terminal using Writable streams.
7
+ *
8
+ * @beta
9
+ */
10
+ export class TerminalStreamWritable extends Writable {
11
+ constructor(options) {
12
+ const { terminal, severity, writableOptions } = options;
13
+ super(writableOptions);
14
+ this._writev = undefined;
15
+ switch (severity) {
16
+ case TerminalProviderSeverity.log:
17
+ this._writeMethod = terminal.write.bind(terminal);
18
+ break;
19
+ case TerminalProviderSeverity.verbose:
20
+ this._writeMethod = terminal.writeVerbose.bind(terminal);
21
+ break;
22
+ case TerminalProviderSeverity.debug:
23
+ this._writeMethod = terminal.writeDebug.bind(terminal);
24
+ break;
25
+ case TerminalProviderSeverity.warning:
26
+ this._writeMethod = terminal.writeWarning.bind(terminal);
27
+ break;
28
+ case TerminalProviderSeverity.error:
29
+ this._writeMethod = terminal.writeError.bind(terminal);
30
+ break;
31
+ default:
32
+ throw new Error(`Unknown severity: ${severity}`);
33
+ }
34
+ }
35
+ _write(chunk, encoding,
36
+ // eslint-disable-next-line @rushstack/no-new-null
37
+ callback) {
38
+ try {
39
+ const chunkData = typeof chunk === 'string' ? chunk : Buffer.from(chunk);
40
+ this._writeMethod(chunkData.toString());
41
+ }
42
+ catch (e) {
43
+ callback(e);
44
+ return;
45
+ }
46
+ callback();
47
+ }
48
+ }
49
+ //# sourceMappingURL=TerminalStreamWritable.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"TerminalStreamWritable.js","sourceRoot":"","sources":["../src/TerminalStreamWritable.ts"],"names":[],"mappings":"AAAA,4FAA4F;AAC5F,2DAA2D;AAE3D,OAAO,EAAE,QAAQ,EAAwB,MAAM,aAAa,CAAC;AAG7D,OAAO,EAAE,wBAAwB,EAAE,MAAM,qBAAqB,CAAC;AAsB/D;;;;GAIG;AACH,MAAM,OAAO,sBAAuB,SAAQ,QAAQ;IAGlD,YAAmB,OAAuC;QACxD,MAAM,EAAE,QAAQ,EAAE,QAAQ,EAAE,eAAe,EAAE,GAAG,OAAO,CAAC;QACxD,KAAK,CAAC,eAAe,CAAC,CAAC;QAEvB,IAAI,CAAC,OAAO,GAAG,SAAS,CAAC;QACzB,QAAQ,QAAQ,EAAE,CAAC;YACjB,KAAK,wBAAwB,CAAC,GAAG;gBAC/B,IAAI,CAAC,YAAY,GAAG,QAAQ,CAAC,KAAK,CAAC,IAAI,CAAC,QAAQ,CAAC,CAAC;gBAClD,MAAM;YACR,KAAK,wBAAwB,CAAC,OAAO;gBACnC,IAAI,CAAC,YAAY,GAAG,QAAQ,CAAC,YAAY,CAAC,IAAI,CAAC,QAAQ,CAAC,CAAC;gBACzD,MAAM;YACR,KAAK,wBAAwB,CAAC,KAAK;gBACjC,IAAI,CAAC,YAAY,GAAG,QAAQ,CAAC,UAAU,CAAC,IAAI,CAAC,QAAQ,CAAC,CAAC;gBACvD,MAAM;YACR,KAAK,wBAAwB,CAAC,OAAO;gBACnC,IAAI,CAAC,YAAY,GAAG,QAAQ,CAAC,YAAY,CAAC,IAAI,CAAC,QAAQ,CAAC,CAAC;gBACzD,MAAM;YACR,KAAK,wBAAwB,CAAC,KAAK;gBACjC,IAAI,CAAC,YAAY,GAAG,QAAQ,CAAC,UAAU,CAAC,IAAI,CAAC,QAAQ,CAAC,CAAC;gBACvD,MAAM;YACR;gBACE,MAAM,IAAI,KAAK,CAAC,qBAAqB,QAAQ,EAAE,CAAC,CAAC;QACrD,CAAC;IACH,CAAC;IAEM,MAAM,CACX,KAAmC,EACnC,QAAgB;IAChB,kDAAkD;IAClD,QAAwC;QAExC,IAAI,CAAC;YACH,MAAM,SAAS,GAAoB,OAAO,KAAK,KAAK,QAAQ,CAAC,CAAC,CAAC,KAAK,CAAC,CAAC,CAAC,MAAM,CAAC,IAAI,CAAC,KAAK,CAAC,CAAC;YAC1F,IAAI,CAAC,YAAY,CAAC,SAAS,CAAC,QAAQ,EAAE,CAAC,CAAC;QAC1C,CAAC;QAAC,OAAO,CAAU,EAAE,CAAC;YACpB,QAAQ,CAAC,CAAU,CAAC,CAAC;YACrB,OAAO;QACT,CAAC;QACD,QAAQ,EAAE,CAAC;IACb,CAAC;CACF","sourcesContent":["// Copyright (c) Microsoft Corporation. All rights reserved. Licensed under the MIT license.\n// See LICENSE in the project root for license information.\n\nimport { Writable, type WritableOptions } from 'node:stream';\n\nimport type { ITerminal } from './ITerminal';\nimport { TerminalProviderSeverity } from './ITerminalProvider';\n\n/**\n * Options for {@link TerminalStreamWritable}.\n *\n * @beta\n */\nexport interface ITerminalStreamWritableOptions {\n /**\n * The {@link ITerminal} that the Writable will write to.\n */\n terminal: ITerminal;\n /**\n * The severity of the messages that will be written to the {@link ITerminal}.\n */\n severity: TerminalProviderSeverity;\n /**\n * Options for the underlying Writable.\n */\n writableOptions?: WritableOptions;\n}\n\n/**\n * A adapter to allow writing to a provided terminal using Writable streams.\n *\n * @beta\n */\nexport class TerminalStreamWritable extends Writable {\n private _writeMethod: (data: string) => void;\n\n public constructor(options: ITerminalStreamWritableOptions) {\n const { terminal, severity, writableOptions } = options;\n super(writableOptions);\n\n this._writev = undefined;\n switch (severity) {\n case TerminalProviderSeverity.log:\n this._writeMethod = terminal.write.bind(terminal);\n break;\n case TerminalProviderSeverity.verbose:\n this._writeMethod = terminal.writeVerbose.bind(terminal);\n break;\n case TerminalProviderSeverity.debug:\n this._writeMethod = terminal.writeDebug.bind(terminal);\n break;\n case TerminalProviderSeverity.warning:\n this._writeMethod = terminal.writeWarning.bind(terminal);\n break;\n case TerminalProviderSeverity.error:\n this._writeMethod = terminal.writeError.bind(terminal);\n break;\n default:\n throw new Error(`Unknown severity: ${severity}`);\n }\n }\n\n public _write(\n chunk: string | Buffer | Uint8Array,\n encoding: string,\n // eslint-disable-next-line @rushstack/no-new-null\n callback: (error?: Error | null) => void\n ): void {\n try {\n const chunkData: string | Buffer = typeof chunk === 'string' ? chunk : Buffer.from(chunk);\n this._writeMethod(chunkData.toString());\n } catch (e: unknown) {\n callback(e as Error);\n return;\n }\n callback();\n }\n}\n"]}
@@ -0,0 +1,53 @@
1
+ // Copyright (c) Microsoft Corporation. All rights reserved. Licensed under the MIT license.
2
+ // See LICENSE in the project root for license information.
3
+ import { TerminalWritable } from './TerminalWritable';
4
+ /**
5
+ * The abstract base class for {@link TerminalWritable} objects that receive an input,
6
+ * transform it somehow, and then write the output to another `TerminalWritable`.
7
+ *
8
+ * @remarks
9
+ *
10
+ * The `TerminalTransform` and {@link SplitterTransform} base classes formalize the idea
11
+ * of modeling data flow as a directed acyclic graph of reusable transforms, whose
12
+ * final outputs are `TerminalWritable` objects.
13
+ *
14
+ * The design is based loosely on the `WritableStream` and `TransformStream` classes from
15
+ * the system {@link https://developer.mozilla.org/en-US/docs/Web/API/Streams_API/Concepts
16
+ * | Streams API}, except that instead of asynchronous byte streams, the `TerminalWritable`
17
+ * system synchronously transmits human readable messages intended to be rendered on a
18
+ * text console or log file.
19
+ *
20
+ * The main feature of the `TerminalTransform` class is its {@link TerminalTransform.destination}
21
+ * property, which tracks the next link in the graph.
22
+ *
23
+ * @public
24
+ */
25
+ export class TerminalTransform extends TerminalWritable {
26
+ constructor(options) {
27
+ super();
28
+ this.destination = options.destination;
29
+ this.preventDestinationAutoclose = !!options.preventDestinationAutoclose;
30
+ }
31
+ /** @override */
32
+ onClose() {
33
+ this.autocloseDestination();
34
+ }
35
+ /**
36
+ * The default implementation of {@link TerminalTransform.onClose} calls this
37
+ * method, which closes the {@link TerminalTransform.destination} if appropriate.
38
+ *
39
+ * @remarks
40
+ * The destination will not be closed if its {@link TerminalWritable.preventAutoclose}
41
+ * property is `true`. The destination will not be closed if
42
+ * {@link ITerminalTransformOptions.preventDestinationAutoclose}
43
+ * is `true`.
44
+ *
45
+ * @sealed
46
+ */
47
+ autocloseDestination() {
48
+ if (!this.preventDestinationAutoclose && !this.destination.preventAutoclose) {
49
+ this.destination.close();
50
+ }
51
+ }
52
+ }
53
+ //# sourceMappingURL=TerminalTransform.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"TerminalTransform.js","sourceRoot":"","sources":["../src/TerminalTransform.ts"],"names":[],"mappings":"AAAA,4FAA4F;AAC5F,2DAA2D;AAE3D,OAAO,EAAE,gBAAgB,EAAiC,MAAM,oBAAoB,CAAC;AA2BrF;;;;;;;;;;;;;;;;;;;;GAoBG;AACH,MAAM,OAAgB,iBAAkB,SAAQ,gBAAgB;IAO9D,YAAmB,OAAkC;QACnD,KAAK,EAAE,CAAC;QACR,IAAI,CAAC,WAAW,GAAG,OAAO,CAAC,WAAW,CAAC;QACvC,IAAI,CAAC,2BAA2B,GAAG,CAAC,CAAC,OAAO,CAAC,2BAA2B,CAAC;IAC3E,CAAC;IAED,gBAAgB;IACN,OAAO;QACf,IAAI,CAAC,oBAAoB,EAAE,CAAC;IAC9B,CAAC;IAED;;;;;;;;;;;OAWG;IACO,oBAAoB;QAC5B,IAAI,CAAC,IAAI,CAAC,2BAA2B,IAAI,CAAC,IAAI,CAAC,WAAW,CAAC,gBAAgB,EAAE,CAAC;YAC5E,IAAI,CAAC,WAAW,CAAC,KAAK,EAAE,CAAC;QAC3B,CAAC;IACH,CAAC;CACF","sourcesContent":["// Copyright (c) Microsoft Corporation. All rights reserved. Licensed under the MIT license.\n// See LICENSE in the project root for license information.\n\nimport { TerminalWritable, type ITerminalWritableOptions } from './TerminalWritable';\n\n/**\n * Constructor options for {@link TerminalTransform}.\n *\n * @public\n */\nexport interface ITerminalTransformOptions extends ITerminalWritableOptions {\n /**\n * The target `TerminalWritable` that the `TerminalTransform` will write its\n * output to.\n */\n destination: TerminalWritable;\n\n /**\n * Prevents the {@link TerminalTransform.destination} object from being\n * closed automatically when the transform is closed.\n *\n * @remarks\n * When a transform is closed, normally it will automatically close its destination\n * `TerminalWritable` object. There are two ways to prevent that: either by setting\n * `preventDestinationAutoclose` to `true` for the transform, or by setting\n * {@link TerminalWritable.preventAutoclose} to `true` for the `destination` object.\n */\n preventDestinationAutoclose?: boolean;\n}\n\n/**\n * The abstract base class for {@link TerminalWritable} objects that receive an input,\n * transform it somehow, and then write the output to another `TerminalWritable`.\n *\n * @remarks\n *\n * The `TerminalTransform` and {@link SplitterTransform} base classes formalize the idea\n * of modeling data flow as a directed acyclic graph of reusable transforms, whose\n * final outputs are `TerminalWritable` objects.\n *\n * The design is based loosely on the `WritableStream` and `TransformStream` classes from\n * the system {@link https://developer.mozilla.org/en-US/docs/Web/API/Streams_API/Concepts\n * | Streams API}, except that instead of asynchronous byte streams, the `TerminalWritable`\n * system synchronously transmits human readable messages intended to be rendered on a\n * text console or log file.\n *\n * The main feature of the `TerminalTransform` class is its {@link TerminalTransform.destination}\n * property, which tracks the next link in the graph.\n *\n * @public\n */\nexport abstract class TerminalTransform extends TerminalWritable {\n /** {@inheritDoc ITerminalTransformOptions.destination} */\n public readonly destination: TerminalWritable;\n\n /** {@inheritDoc ITerminalTransformOptions.preventDestinationAutoclose} */\n public readonly preventDestinationAutoclose: boolean;\n\n public constructor(options: ITerminalTransformOptions) {\n super();\n this.destination = options.destination;\n this.preventDestinationAutoclose = !!options.preventDestinationAutoclose;\n }\n\n /** @override */\n protected onClose(): void {\n this.autocloseDestination();\n }\n\n /**\n * The default implementation of {@link TerminalTransform.onClose} calls this\n * method, which closes the {@link TerminalTransform.destination} if appropriate.\n *\n * @remarks\n * The destination will not be closed if its {@link TerminalWritable.preventAutoclose}\n * property is `true`. The destination will not be closed if\n * {@link ITerminalTransformOptions.preventDestinationAutoclose}\n * is `true`.\n *\n * @sealed\n */\n protected autocloseDestination(): void {\n if (!this.preventDestinationAutoclose && !this.destination.preventAutoclose) {\n this.destination.close();\n }\n }\n}\n"]}
@@ -0,0 +1,119 @@
1
+ // Copyright (c) Microsoft Corporation. All rights reserved. Licensed under the MIT license.
2
+ // See LICENSE in the project root for license information.
3
+ /**
4
+ * The abstract base class for objects that can present, route, or process text output for
5
+ * a console application. This output is typically prepared using
6
+ * the {@link Terminal} API.
7
+ *
8
+ * @remarks
9
+ *
10
+ * The design is based loosely on the `WritableStream` and `TransformStream` classes from
11
+ * the system {@link https://developer.mozilla.org/en-US/docs/Web/API/Streams_API/Concepts
12
+ * | Streams API}, except that instead of asynchronous byte streams, the `TerminalWritable`
13
+ * system synchronously transmits human readable messages intended to be rendered on a text
14
+ * console or log file.
15
+ *
16
+ * Consider a console application whose output may need to be processed in different ways
17
+ * before finally being output. The conceptual block diagram might look like this:
18
+ *
19
+ * ```
20
+ * [Terminal API]
21
+ * |
22
+ * V
23
+ * [normalize newlines]
24
+ * |
25
+ * V
26
+ * +----[splitter]-------+
27
+ * | |
28
+ * V V
29
+ * [shell console] [remove ANSI colors]
30
+ * |
31
+ * V
32
+ * [write to build.log]
33
+ * ```
34
+ *
35
+ * The application uses the `Terminal` API to print `stdout` and `stderr` messages, for example with standardized
36
+ * formatting for errors and warnings, and ANSI escapes to make nice colors. Maybe it also includes text
37
+ * received from external processes, whose newlines may be inconsistent. Ultimately we want to write the
38
+ * output to the shell console and a `build.log` file, but we don't want to put ANSI colors in the build log.
39
+ *
40
+ * For the above example, `[shell console]` and `[write to build.log]` would be modeled as subclasses of
41
+ * `TerminalWritable`. The `[normalize newlines]` and `[remove ANSI colors]` steps are modeled as subclasses
42
+ * of {@link TerminalTransform}, because they output to a "destination" object. The `[splitter]` would be
43
+ * implemented using {@link SplitterTransform}.
44
+ *
45
+ * The stream of messages are {@link ITerminalChunk} objects, which can represent both `stdout` and `stderr`
46
+ * channels. The pipeline operates synchronously on each chunk, but by processing one chunk at a time,
47
+ * it avoids storing the entire output in memory. This means that operations like `[remove ANSI colors]`
48
+ * cannot be simple regular expressions -- they must be implemented as state machines ({@link TextRewriter}
49
+ * subclasses) capable of matching substrings that span multiple chunks.
50
+ *
51
+ * @public
52
+ */
53
+ export class TerminalWritable {
54
+ constructor(options) {
55
+ this._isOpen = true;
56
+ if (!options) {
57
+ options = {};
58
+ }
59
+ this.preventAutoclose = !!options.preventAutoclose;
60
+ }
61
+ /**
62
+ * This property is initially `true` when the object is constructed, and becomes `false`
63
+ * when `close()` is called.
64
+ * @sealed
65
+ */
66
+ get isOpen() {
67
+ return this._isOpen;
68
+ }
69
+ /**
70
+ * Upstream objects call this method to provide inputs to this object.
71
+ *
72
+ * @remarks
73
+ * The subclass provides its implementation via the the {@link TerminalWritable.onWriteChunk}
74
+ * method, which is called by `writeChunk()`.
75
+ *
76
+ * The object that calls `writeChunk()` must call `close()` when it is finished;
77
+ * failing to do so may introduce a resource leak, or may prevent some buffered data from
78
+ * being written.
79
+ *
80
+ * @sealed
81
+ */
82
+ writeChunk(chunk) {
83
+ if (!this._isOpen) {
84
+ throw new Error('Writer was already closed');
85
+ }
86
+ this.onWriteChunk(chunk);
87
+ }
88
+ /**
89
+ * Calling this method flushes any remaining outputs and permanently transitions the
90
+ * `TerminalWritable` to a "closed" state, where no further chunks can be written.
91
+ *
92
+ * @remarks
93
+ * The subclass provides its implementation via the the {@link TerminalWritable.onClose}
94
+ * method, which is called by `close()`.
95
+ *
96
+ * If this method is called more than once, the additional calls are ignored;
97
+ * `TerminalWritable.onClose` will be called at most once.
98
+ *
99
+ * @sealed
100
+ */
101
+ close() {
102
+ if (this._isOpen) {
103
+ this.onClose();
104
+ this._isOpen = false;
105
+ }
106
+ }
107
+ /**
108
+ * Subclasses can override this empty method to perform additional operations
109
+ * such as closing a file handle.
110
+ *
111
+ * @remarks
112
+ * It is guaranteed that this method will be called at most once during the lifetime
113
+ * of a `TerminalWritable` object.
114
+ *
115
+ * @virtual
116
+ */
117
+ onClose() { }
118
+ }
119
+ //# sourceMappingURL=TerminalWritable.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"TerminalWritable.js","sourceRoot":"","sources":["../src/TerminalWritable.ts"],"names":[],"mappings":"AAAA,4FAA4F;AAC5F,2DAA2D;AAwB3D;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;GAiDG;AACH,MAAM,OAAgB,gBAAgB;IAKpC,YAAmB,OAAkC;QACnD,IAAI,CAAC,OAAO,GAAG,IAAI,CAAC;QAEpB,IAAI,CAAC,OAAO,EAAE,CAAC;YACb,OAAO,GAAG,EAAE,CAAC;QACf,CAAC;QAED,IAAI,CAAC,gBAAgB,GAAG,CAAC,CAAC,OAAO,CAAC,gBAAgB,CAAC;IACrD,CAAC;IAED;;;;OAIG;IACH,IAAW,MAAM;QACf,OAAO,IAAI,CAAC,OAAO,CAAC;IACtB,CAAC;IAED;;;;;;;;;;;;OAYG;IACI,UAAU,CAAC,KAAqB;QACrC,IAAI,CAAC,IAAI,CAAC,OAAO,EAAE,CAAC;YAClB,MAAM,IAAI,KAAK,CAAC,2BAA2B,CAAC,CAAC;QAC/C,CAAC;QACD,IAAI,CAAC,YAAY,CAAC,KAAK,CAAC,CAAC;IAC3B,CAAC;IAOD;;;;;;;;;;;;OAYG;IACI,KAAK;QACV,IAAI,IAAI,CAAC,OAAO,EAAE,CAAC;YACjB,IAAI,CAAC,OAAO,EAAE,CAAC;YACf,IAAI,CAAC,OAAO,GAAG,KAAK,CAAC;QACvB,CAAC;IACH,CAAC;IAED;;;;;;;;;OASG;IACO,OAAO,KAAU,CAAC;CAC7B","sourcesContent":["// Copyright (c) Microsoft Corporation. All rights reserved. Licensed under the MIT license.\n// See LICENSE in the project root for license information.\n\nimport type { ITerminalChunk } from './ITerminalChunk';\n\n/**\n * Constructor options for {@link TerminalWritable}\n *\n * @public\n */\nexport interface ITerminalWritableOptions {\n /**\n * When this object is the {@link TerminalTransform.destination} for a transform,\n * the transform will automatically close this object. Set `preventAutoclose` to `true`\n * to prevent that behavior.\n *\n * @remarks\n * When a transform is closed, normally it will automatically close its destination\n * `TerminalWritable` object. There are two ways to prevent that: either by setting\n * `preventDestinationAutoclose` to `true` for the transform, or by setting\n * {@link TerminalWritable.preventAutoclose} to `true` for the `destination` object.\n */\n preventAutoclose?: boolean;\n}\n\n/**\n * The abstract base class for objects that can present, route, or process text output for\n * a console application. This output is typically prepared using\n * the {@link Terminal} API.\n *\n * @remarks\n *\n * The design is based loosely on the `WritableStream` and `TransformStream` classes from\n * the system {@link https://developer.mozilla.org/en-US/docs/Web/API/Streams_API/Concepts\n * | Streams API}, except that instead of asynchronous byte streams, the `TerminalWritable`\n * system synchronously transmits human readable messages intended to be rendered on a text\n * console or log file.\n *\n * Consider a console application whose output may need to be processed in different ways\n * before finally being output. The conceptual block diagram might look like this:\n *\n * ```\n * [Terminal API]\n * |\n * V\n * [normalize newlines]\n * |\n * V\n * +----[splitter]-------+\n * | |\n * V V\n * [shell console] [remove ANSI colors]\n * |\n * V\n * [write to build.log]\n * ```\n *\n * The application uses the `Terminal` API to print `stdout` and `stderr` messages, for example with standardized\n * formatting for errors and warnings, and ANSI escapes to make nice colors. Maybe it also includes text\n * received from external processes, whose newlines may be inconsistent. Ultimately we want to write the\n * output to the shell console and a `build.log` file, but we don't want to put ANSI colors in the build log.\n *\n * For the above example, `[shell console]` and `[write to build.log]` would be modeled as subclasses of\n * `TerminalWritable`. The `[normalize newlines]` and `[remove ANSI colors]` steps are modeled as subclasses\n * of {@link TerminalTransform}, because they output to a \"destination\" object. The `[splitter]` would be\n * implemented using {@link SplitterTransform}.\n *\n * The stream of messages are {@link ITerminalChunk} objects, which can represent both `stdout` and `stderr`\n * channels. The pipeline operates synchronously on each chunk, but by processing one chunk at a time,\n * it avoids storing the entire output in memory. This means that operations like `[remove ANSI colors]`\n * cannot be simple regular expressions -- they must be implemented as state machines ({@link TextRewriter}\n * subclasses) capable of matching substrings that span multiple chunks.\n *\n * @public\n */\nexport abstract class TerminalWritable {\n private _isOpen: boolean;\n\n public readonly preventAutoclose: boolean;\n\n public constructor(options?: ITerminalWritableOptions) {\n this._isOpen = true;\n\n if (!options) {\n options = {};\n }\n\n this.preventAutoclose = !!options.preventAutoclose;\n }\n\n /**\n * This property is initially `true` when the object is constructed, and becomes `false`\n * when `close()` is called.\n * @sealed\n */\n public get isOpen(): boolean {\n return this._isOpen;\n }\n\n /**\n * Upstream objects call this method to provide inputs to this object.\n *\n * @remarks\n * The subclass provides its implementation via the the {@link TerminalWritable.onWriteChunk}\n * method, which is called by `writeChunk()`.\n *\n * The object that calls `writeChunk()` must call `close()` when it is finished;\n * failing to do so may introduce a resource leak, or may prevent some buffered data from\n * being written.\n *\n * @sealed\n */\n public writeChunk(chunk: ITerminalChunk): void {\n if (!this._isOpen) {\n throw new Error('Writer was already closed');\n }\n this.onWriteChunk(chunk);\n }\n\n /**\n * Subclasses should implement this `abstract` method to process the chunk.\n */\n protected abstract onWriteChunk(chunk: ITerminalChunk): void;\n\n /**\n * Calling this method flushes any remaining outputs and permanently transitions the\n * `TerminalWritable` to a \"closed\" state, where no further chunks can be written.\n *\n * @remarks\n * The subclass provides its implementation via the the {@link TerminalWritable.onClose}\n * method, which is called by `close()`.\n *\n * If this method is called more than once, the additional calls are ignored;\n * `TerminalWritable.onClose` will be called at most once.\n *\n * @sealed\n */\n public close(): void {\n if (this._isOpen) {\n this.onClose();\n this._isOpen = false;\n }\n }\n\n /**\n * Subclasses can override this empty method to perform additional operations\n * such as closing a file handle.\n *\n * @remarks\n * It is guaranteed that this method will be called at most once during the lifetime\n * of a `TerminalWritable` object.\n *\n * @virtual\n */\n protected onClose(): void {}\n}\n"]}
@@ -0,0 +1,35 @@
1
+ // Copyright (c) Microsoft Corporation. All rights reserved. Licensed under the MIT license.
2
+ // See LICENSE in the project root for license information.
3
+ /**
4
+ * The abstract base class for operations that can be applied by {@link TextRewriterTransform}.
5
+ *
6
+ * @remarks
7
+ * The {@link TextRewriterTransform} applies one or more character rewriting operations to its
8
+ * chunk stream. Since these operations are applied separately to `stderr` and `stdout`, the
9
+ * state is stored in an opaque `TextRewriterState` object.
10
+ *
11
+ * Conceptually, a `TextRewriter` subclass is very similar to a regular expression, with the difference
12
+ * that `RegExp` operates on a text string, whereas `TextRewriter` operates on a stream of characters.
13
+ *
14
+ * The two most common subclasses are {@link NormalizeNewlinesTextRewriter} and {@link RemoveColorsTextRewriter}.
15
+ *
16
+ * A rewriting operation starts with `initialize()`, followed by any number of `process()` calls, and
17
+ * then finishes with `close()`. For example:
18
+ *
19
+ * ```ts
20
+ * const rewriter: NormalizeNewlinesTextRewriter = new NormalizeNewlinesTextRewriter(NewlineKind.Lf);
21
+ * const state: TextRewriterState = rewriter.initialize();
22
+ * let output: string = rewriter.process(state, 'line 1\r');
23
+ * output += rewriter.process(state, '\nline 2\r\n');
24
+ * output += rewriter.close(state);
25
+ *
26
+ * // The final "output" value is: "line 1\nline 2\n"
27
+ * ```
28
+ *
29
+ * After `close()` has been called, the `TextRewriterState` state should not be reused.
30
+ *
31
+ * @public
32
+ */
33
+ export class TextRewriter {
34
+ }
35
+ //# sourceMappingURL=TextRewriter.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"TextRewriter.js","sourceRoot":"","sources":["../src/TextRewriter.ts"],"names":[],"mappings":"AAAA,4FAA4F;AAC5F,2DAA2D;AA6B3D;;;;;;;;;;;;;;;;;;;;;;;;;;;;;GA6BG;AACH,MAAM,OAAgB,YAAY;CAejC","sourcesContent":["// Copyright (c) Microsoft Corporation. All rights reserved. Licensed under the MIT license.\n// See LICENSE in the project root for license information.\n\nimport type { Brand } from '@rushstack/node-core-library';\n\n/**\n * Represents the internal state of a {@link TextRewriter} subclass.\n *\n * @remarks\n * For example, suppose that {@link NormalizeNewlinesTextRewriter} will be used to rewrite\n * the input `\"line 1\\r\\nline 2\\r\\n\"` to become `\"line 1\\nline 2\\n\"`. But suppose that the `\"\\r\\n\"`\n * pair is split across two chunks:\n *\n * ```ts\n * const rewriter: NormalizeNewlinesTextRewriter = new NormalizeNewlinesTextRewriter(NewlineKind.Lf);\n * const state: TextRewriterState = rewriter.initialize();\n * let output: string = rewriter.process(state, 'line 1\\r');\n * output += rewriter.process(state, '\\nline 2\\r\\n');\n * output += rewriter.close(state);\n *\n * // The final \"output\" value is: \"line 1\\nline 2\\n\"\n * ```\n *\n * The `TextRewriterState` keeps track of this context, so that split `\"\\r\"` and `\"\\n\"` are\n * interpreted as a single newline.\n *\n * @public\n */\nexport type TextRewriterState = Brand<unknown, 'TextRewriterState'>;\n\n/**\n * The abstract base class for operations that can be applied by {@link TextRewriterTransform}.\n *\n * @remarks\n * The {@link TextRewriterTransform} applies one or more character rewriting operations to its\n * chunk stream. Since these operations are applied separately to `stderr` and `stdout`, the\n * state is stored in an opaque `TextRewriterState` object.\n *\n * Conceptually, a `TextRewriter` subclass is very similar to a regular expression, with the difference\n * that `RegExp` operates on a text string, whereas `TextRewriter` operates on a stream of characters.\n *\n * The two most common subclasses are {@link NormalizeNewlinesTextRewriter} and {@link RemoveColorsTextRewriter}.\n *\n * A rewriting operation starts with `initialize()`, followed by any number of `process()` calls, and\n * then finishes with `close()`. For example:\n *\n * ```ts\n * const rewriter: NormalizeNewlinesTextRewriter = new NormalizeNewlinesTextRewriter(NewlineKind.Lf);\n * const state: TextRewriterState = rewriter.initialize();\n * let output: string = rewriter.process(state, 'line 1\\r');\n * output += rewriter.process(state, '\\nline 2\\r\\n');\n * output += rewriter.close(state);\n *\n * // The final \"output\" value is: \"line 1\\nline 2\\n\"\n * ```\n *\n * After `close()` has been called, the `TextRewriterState` state should not be reused.\n *\n * @public\n */\nexport abstract class TextRewriter {\n /**\n * Create a new `TextRewriterState` object that can be used to process a stream of characters.\n */\n public abstract initialize(): TextRewriterState;\n\n /**\n * Rewrite the next sequence of characters from the input stream, returning the modified output.\n */\n public abstract process(state: TextRewriterState, input: string): string;\n\n /**\n * Close the `TextRewriterState` object and return any buffered output.\n */\n public abstract close(state: TextRewriterState): string;\n}\n"]}
@@ -0,0 +1,90 @@
1
+ // Copyright (c) Microsoft Corporation. All rights reserved. Licensed under the MIT license.
2
+ // See LICENSE in the project root for license information.
3
+ import { TerminalChunkKind } from './ITerminalChunk';
4
+ import { TerminalTransform } from './TerminalTransform';
5
+ import { RemoveColorsTextRewriter } from './RemoveColorsTextRewriter';
6
+ import { NormalizeNewlinesTextRewriter } from './NormalizeNewlinesTextRewriter';
7
+ /**
8
+ * A {@link TerminalTransform} subclass that performs one or more {@link TextRewriter} operations.
9
+ * The most common operations are {@link NormalizeNewlinesTextRewriter} and {@link RemoveColorsTextRewriter}.
10
+ *
11
+ * @remarks
12
+ * The `TextRewriter` operations are applied separately to the `stderr` and `stdout` streams.
13
+ * If multiple {@link ITextRewriterTransformOptions.textRewriters} are configured, they are applied
14
+ * in the order that they appear in the array.
15
+ *
16
+ * @public
17
+ */
18
+ export class TextRewriterTransform extends TerminalTransform {
19
+ constructor(options) {
20
+ super(options);
21
+ const textRewriters = options.textRewriters || [];
22
+ if (options.removeColors) {
23
+ textRewriters.push(new RemoveColorsTextRewriter());
24
+ }
25
+ if (options.normalizeNewlines) {
26
+ textRewriters.push(new NormalizeNewlinesTextRewriter({
27
+ newlineKind: options.normalizeNewlines,
28
+ ensureNewlineAtEnd: options.ensureNewlineAtEnd
29
+ }));
30
+ }
31
+ if (textRewriters.length === 0) {
32
+ throw new Error('TextRewriterTransform requires at least one matcher');
33
+ }
34
+ this.textRewriters = textRewriters;
35
+ this._stderrStates = this.textRewriters.map((x) => x.initialize());
36
+ this._stdoutStates = this.textRewriters.map((x) => x.initialize());
37
+ }
38
+ onWriteChunk(chunk) {
39
+ if (chunk.kind === TerminalChunkKind.Stderr) {
40
+ this._processText(chunk, this._stderrStates);
41
+ }
42
+ else if (chunk.kind === TerminalChunkKind.Stdout) {
43
+ this._processText(chunk, this._stdoutStates);
44
+ }
45
+ else {
46
+ this.destination.writeChunk(chunk);
47
+ }
48
+ }
49
+ _processText(chunk, states) {
50
+ let text = chunk.text;
51
+ for (let i = 0; i < states.length; ++i) {
52
+ if (text.length > 0) {
53
+ text = this.textRewriters[i].process(states[i], text);
54
+ }
55
+ }
56
+ if (text.length > 0) {
57
+ // If possible, avoid allocating a new chunk
58
+ if (text === chunk.text) {
59
+ this.destination.writeChunk(chunk);
60
+ }
61
+ else {
62
+ this.destination.writeChunk({
63
+ text: text,
64
+ kind: chunk.kind
65
+ });
66
+ }
67
+ }
68
+ }
69
+ _closeRewriters(states, chunkKind) {
70
+ let text = '';
71
+ for (let i = 0; i < states.length; ++i) {
72
+ if (text.length > 0) {
73
+ text = this.textRewriters[i].process(states[i], text);
74
+ }
75
+ text += this.textRewriters[i].close(states[i]);
76
+ }
77
+ if (text.length > 0) {
78
+ this.destination.writeChunk({
79
+ text: text,
80
+ kind: chunkKind
81
+ });
82
+ }
83
+ }
84
+ onClose() {
85
+ this._closeRewriters(this._stderrStates, TerminalChunkKind.Stderr);
86
+ this._closeRewriters(this._stdoutStates, TerminalChunkKind.Stdout);
87
+ this.autocloseDestination();
88
+ }
89
+ }
90
+ //# sourceMappingURL=TextRewriterTransform.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"TextRewriterTransform.js","sourceRoot":"","sources":["../src/TextRewriterTransform.ts"],"names":[],"mappings":"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","sourcesContent":["// Copyright (c) Microsoft Corporation. All rights reserved. Licensed under the MIT license.\n// See LICENSE in the project root for license information.\n\nimport type { NewlineKind } from '@rushstack/node-core-library';\n\nimport { type ITerminalChunk, TerminalChunkKind } from './ITerminalChunk';\nimport { TerminalTransform, type ITerminalTransformOptions } from './TerminalTransform';\nimport type { TextRewriter, TextRewriterState } from './TextRewriter';\nimport { RemoveColorsTextRewriter } from './RemoveColorsTextRewriter';\nimport { NormalizeNewlinesTextRewriter } from './NormalizeNewlinesTextRewriter';\n\n/**\n * Constructor options for {@link TextRewriterTransform}.\n *\n * @public\n */\nexport interface ITextRewriterTransformOptions extends ITerminalTransformOptions {\n /**\n * A list of rewriters to be applied. More items may be appended to the list, for example\n * if {@link ITextRewriterTransformOptions.removeColors} is specified.\n *\n * @remarks\n * The final list must contain at least one item.\n */\n textRewriters?: TextRewriter[];\n\n /**\n * If specified, a {@link RemoveColorsTextRewriter} will be appended to the list of rewriters.\n */\n removeColors?: boolean;\n\n /**\n * If `normalizeNewlines` or `ensureNewlineAtEnd` is specified, a {@link NormalizeNewlinesTextRewriter}\n * will be appended to the list of rewriters with the specified settings.\n *\n * @remarks\n * See {@link INormalizeNewlinesTextRewriterOptions} for details.\n */\n normalizeNewlines?: NewlineKind;\n\n /**\n * If `normalizeNewlines` or `ensureNewlineAtEnd` is specified, a {@link NormalizeNewlinesTextRewriter}\n * will be appended to the list of rewriters with the specified settings.\n *\n * @remarks\n * See {@link INormalizeNewlinesTextRewriterOptions} for details.\n */\n ensureNewlineAtEnd?: boolean;\n}\n\n/**\n * A {@link TerminalTransform} subclass that performs one or more {@link TextRewriter} operations.\n * The most common operations are {@link NormalizeNewlinesTextRewriter} and {@link RemoveColorsTextRewriter}.\n *\n * @remarks\n * The `TextRewriter` operations are applied separately to the `stderr` and `stdout` streams.\n * If multiple {@link ITextRewriterTransformOptions.textRewriters} are configured, they are applied\n * in the order that they appear in the array.\n *\n * @public\n */\nexport class TextRewriterTransform extends TerminalTransform {\n private readonly _stderrStates: TextRewriterState[];\n private readonly _stdoutStates: TextRewriterState[];\n\n public readonly textRewriters: ReadonlyArray<TextRewriter>;\n\n public constructor(options: ITextRewriterTransformOptions) {\n super(options);\n\n const textRewriters: TextRewriter[] = options.textRewriters || [];\n\n if (options.removeColors) {\n textRewriters.push(new RemoveColorsTextRewriter());\n }\n if (options.normalizeNewlines) {\n textRewriters.push(\n new NormalizeNewlinesTextRewriter({\n newlineKind: options.normalizeNewlines,\n ensureNewlineAtEnd: options.ensureNewlineAtEnd\n })\n );\n }\n\n if (textRewriters.length === 0) {\n throw new Error('TextRewriterTransform requires at least one matcher');\n }\n\n this.textRewriters = textRewriters;\n\n this._stderrStates = this.textRewriters.map((x) => x.initialize());\n this._stdoutStates = this.textRewriters.map((x) => x.initialize());\n }\n\n protected onWriteChunk(chunk: ITerminalChunk): void {\n if (chunk.kind === TerminalChunkKind.Stderr) {\n this._processText(chunk, this._stderrStates);\n } else if (chunk.kind === TerminalChunkKind.Stdout) {\n this._processText(chunk, this._stdoutStates);\n } else {\n this.destination.writeChunk(chunk);\n }\n }\n\n private _processText(chunk: ITerminalChunk, states: TextRewriterState[]): void {\n let text: string = chunk.text;\n for (let i: number = 0; i < states.length; ++i) {\n if (text.length > 0) {\n text = this.textRewriters[i].process(states[i], text);\n }\n }\n if (text.length > 0) {\n // If possible, avoid allocating a new chunk\n if (text === chunk.text) {\n this.destination.writeChunk(chunk);\n } else {\n this.destination.writeChunk({\n text: text,\n kind: chunk.kind\n });\n }\n }\n }\n\n private _closeRewriters(states: TextRewriterState[], chunkKind: TerminalChunkKind): void {\n let text: string = '';\n for (let i: number = 0; i < states.length; ++i) {\n if (text.length > 0) {\n text = this.textRewriters[i].process(states[i], text);\n }\n text += this.textRewriters[i].close(states[i]);\n }\n if (text.length > 0) {\n this.destination.writeChunk({\n text: text,\n kind: chunkKind\n });\n }\n }\n\n protected onClose(): void {\n this._closeRewriters(this._stderrStates, TerminalChunkKind.Stderr);\n this._closeRewriters(this._stdoutStates, TerminalChunkKind.Stdout);\n\n this.autocloseDestination();\n }\n}\n"]}