You're Invited:Meet the Socket Team at RSAC and BSidesSF 2026, March 23–26.RSVP
Socket
Book a DemoSign in
Socket

@parcel/codeframe

Package Overview
Dependencies
Maintainers
1
Versions
957
Alerts
File Explorer

Advanced tools

Socket logo

Install Socket

Detect and block malicious and high-risk dependencies

Install

@parcel/codeframe - npm Package Compare versions

Comparing version
2.0.0-alpha.3.1
to
2.0.0-beta.1
+111
-51
lib/codeframe.js

@@ -12,2 +12,6 @@ "use strict";

var _stringWidth = _interopRequireDefault(require("string-width"));
var _sliceAnsi = _interopRequireDefault(require("slice-ansi"));
function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; }

@@ -18,2 +22,3 @@

const TAB_REPLACEMENT = ' ';
const DEFAULT_TERMINAL_WIDTH = 80;

@@ -31,4 +36,5 @@ const highlightSyntax = (txt, lang) => {

function codeFrame(code, highlights, // $FlowFixMe
inputOpts = {}) {
function codeFrame(code, highlights, inputOpts = {}) {
var _inputOpts$maxLines;
if (highlights.length < 1) return '';

@@ -39,3 +45,4 @@ let opts = {

language: inputOpts.language,
maxLines: inputOpts.maxLines !== undefined ? inputOpts.maxLines : 12,
maxLines: (_inputOpts$maxLines = inputOpts.maxLines) !== null && _inputOpts$maxLines !== void 0 ? _inputOpts$maxLines : 12,
terminalWidth: inputOpts.terminalWidth || DEFAULT_TERMINAL_WIDTH,
padding: inputOpts.padding || {

@@ -45,3 +52,3 @@ before: 1,

}
};
}; // Highlights messages and prefixes when colors are enabled

@@ -56,4 +63,5 @@ const highlighter = (s, bold) => {

return s;
};
}; // Prefix lines with the line number
const lineNumberPrefixer = params => {

@@ -81,5 +89,7 @@ let {

};
});
}); // Find first and last highlight
let firstHighlight = highlights.length > 1 ? highlights.sort((a, b) => a.start.line - b.start.line)[0] : highlights[0];
let lastHighlight = highlights.length > 1 ? highlights.sort((a, b) => b.end.line - a.end.line)[0] : highlights[0];
let lastHighlight = highlights.length > 1 ? highlights.sort((a, b) => b.end.line - a.end.line)[0] : highlights[0]; // Calculate first and last line index of codeframe
let startLine = firstHighlight.start.line - opts.padding.before;

@@ -89,64 +99,114 @@ startLine = startLine < 0 ? 0 : startLine;

endLine = endLine - startLine > opts.maxLines ? startLine + opts.maxLines - 1 : endLine;
let endLineString = endLine.toString(10);
let resultLines = [];
let endLineString = endLine.toString(10); // Split input into lines and highlight syntax
let lines = code.split(NEWLINE);
let syntaxHighlightedLines = (opts.syntaxHighlighting ? highlightSyntax(code, opts.language) : code).replace(TAB_REPLACE_REGEX, TAB_REPLACEMENT).split(NEWLINE);
let syntaxHighlightedLines = (opts.syntaxHighlighting ? highlightSyntax(code, opts.language) : code).replace(TAB_REPLACE_REGEX, TAB_REPLACEMENT).split(NEWLINE); // Loop over all lines and create codeframe
for (let i = startLine; i < lines.length; i++) {
if (i > endLine) break;
let originalLine = lines[i];
let syntaxHighlightedLine = syntaxHighlightedLines[i];
let foundHighlights = highlights.filter(highlight => highlight.start.line <= i && highlight.end.line >= i);
let resultLines = [];
for (let currentLineIndex = startLine; currentLineIndex < syntaxHighlightedLines.length; currentLineIndex++) {
if (currentLineIndex > endLine) break;
if (currentLineIndex > syntaxHighlightedLines.length - 1) break; // Find highlights that need to get rendered on the current line
let lineHighlights = highlights.filter(highlight => highlight.start.line <= currentLineIndex && highlight.end.line >= currentLineIndex).sort((a, b) => (a.start.line < currentLineIndex ? 0 : a.start.column) - (b.start.line < currentLineIndex ? 0 : b.start.column)); // Check if this line has a full line highlight
let isWholeLine = lineHighlights.length && !!lineHighlights.find(h => h.start.line < currentLineIndex && h.end.line > currentLineIndex);
let lineLengthLimit = opts.terminalWidth > endLineString.length + 7 ? opts.terminalWidth - (endLineString.length + 5) : 10; // Split the line into line parts that will fit the provided terminal width
let colOffset = 0;
let lineEndCol = lineLengthLimit;
let syntaxHighlightedLine = syntaxHighlightedLines[currentLineIndex];
if ((0, _stringWidth.default)(syntaxHighlightedLine) > lineLengthLimit) {
if (lineHighlights.length > 0) {
if (lineHighlights[0].start.line === currentLineIndex) {
colOffset = lineHighlights[0].start.column - 5;
} else if (lineHighlights[0].end.line === currentLineIndex) {
colOffset = lineHighlights[0].end.column - 5;
}
}
colOffset = colOffset > 0 ? colOffset : 0;
lineEndCol = colOffset + lineLengthLimit;
syntaxHighlightedLine = (0, _sliceAnsi.default)(syntaxHighlightedLine, colOffset, lineEndCol);
} // Write the syntax highlighted line part
resultLines.push(lineNumberPrefixer({
lineNumber: (i + 1).toString(10),
lineNumber: (currentLineIndex + 1).toString(10),
endLine: endLineString,
isHighlighted: foundHighlights.length > 0
isHighlighted: lineHighlights.length > 0
}) + syntaxHighlightedLine);
let lineWidth = (0, _stringWidth.default)(syntaxHighlightedLine);
let highlightLine = '';
if (foundHighlights.length > 0) {
let highlightLine = lineNumberPrefixer({
endLine: endLineString,
isHighlighted: true
});
let isWholeLine = !!foundHighlights.find(h => h.start.line < i && h.end.line > i);
if (isWholeLine) {
highlightLine = highlighter('^'.repeat(lineWidth));
} else if (lineHighlights.length > 0) {
let lastCol = 0;
let highlight = null;
let highlightHasEnded = false;
if (isWholeLine) {
// If there's a whole line highlight
// don't even bother creating seperate highlight
highlightLine += highlighter('^'.repeat(originalLine.replace(TAB_REPLACE_REGEX, TAB_REPLACEMENT).length));
} else {
let sortedColumns = foundHighlights.length > 1 ? foundHighlights.sort((a, b) => (a.start.line < i ? 0 : a.start.column) - (b.start.line < i ? 0 : b.start.column)) : foundHighlights;
let lastCol = 0;
for (let highlightIndex = 0; highlightIndex < lineHighlights.length; highlightIndex++) {
// Set highlight to current highlight
highlight = lineHighlights[highlightIndex];
highlightHasEnded = false; // Calculate the startColumn and get the real width by doing a substring of the original
// line and replacing tabs with our tab replacement to support tab handling
for (let col of sortedColumns) {
let startCol = col.start.line === i ? col.start.column : 0;
let endCol = (col.end.line === i ? col.end.column : originalLine.length - (lastCol || 1)) + 1;
let startCol = 0;
if (startCol - lastCol > 0) {
let whitespace = originalLine.substring(lastCol, startCol).replace(TAB_REPLACE_REGEX, TAB_REPLACEMENT).replace(/\S/g, ' ');
highlightLine += whitespace;
}
if (highlight.start.line === currentLineIndex && highlight.start.column > colOffset) {
startCol = lines[currentLineIndex].substring(colOffset, highlight.start.column).replace(TAB_REPLACE_REGEX, TAB_REPLACEMENT).length;
} // Calculate the endColumn and get the real width by doing a substring of the original
// line and replacing tabs with our tab replacement to support tab handling
let highlightStartColumn = lastCol >= startCol ? lastCol : startCol;
if (endCol - highlightStartColumn > 0) {
let renderedHighlightLength = originalLine.substring(highlightStartColumn, endCol).replace(TAB_REPLACE_REGEX, TAB_REPLACEMENT).length;
highlightLine += highlighter('^'.repeat(renderedHighlightLength));
lastCol = endCol;
let endCol = lineWidth - 1;
if (highlight.end.line === currentLineIndex) {
endCol = lines[currentLineIndex].substring(colOffset, highlight.end.column).replace(TAB_REPLACE_REGEX, TAB_REPLACEMENT).length; // If the endCol is too big for this line part, trim it so we can handle it in the next one
if (endCol > lineWidth) {
endCol = lineWidth - 1;
}
}
let endsWithFullLine = !!sortedColumns.find(h => h.end.line > i);
highlightHasEnded = true;
} // If endcol is smaller than lastCol it overlaps with another highlight and is no longer visible, we can skip those
if (!endsWithFullLine) {
let sortedByEnd = sortedColumns.sort((a, b) => a.end.column - b.end.column);
let lastHighlightForColumn = sortedByEnd[sortedByEnd.length - 1];
if (lastHighlightForColumn.message) {
highlightLine += ' ' + highlighter(lastHighlightForColumn.message, true);
}
if (endCol >= lastCol) {
let characters = endCol - startCol + 1;
if (startCol > lastCol) {
// startCol is before lastCol, so add spaces as padding before the highlight indicators
highlightLine += ' '.repeat(startCol - lastCol);
} else if (lastCol > startCol) {
// If last column is larger than the start, there's overlap in highlights
// This line adjusts the characters count to ensure we don't add too many characters
characters += startCol - lastCol;
} // Append the highlight indicators
highlightLine += highlighter('^'.repeat(characters)); // Set the lastCol equal to character count between start of line part and highlight end-column
lastCol = endCol + 1;
} // There's no point in processing more highlights if we reached the end of the line
if (endCol >= lineEndCol - 1) {
break;
}
} // Append the highlight message if the current highlights ends on this line part
if (highlight && highlight.message && highlightHasEnded) {
highlightLine += ' ' + highlighter(highlight.message, true);
}
}
resultLines.push(highlightLine);
if (highlightLine) {
resultLines.push(lineNumberPrefixer({
endLine: endLineString,
isHighlighted: true
}) + highlightLine);
}

@@ -153,0 +213,0 @@ }

{
"name": "@parcel/codeframe",
"version": "2.0.0-alpha.3.1",
"version": "2.0.0-beta.1",
"description": "Blazing fast, zero configuration web application bundler",

@@ -20,5 +20,10 @@ "license": "MIT",

"chalk": "^2.4.2",
"emphasize": "^2.1.0"
"emphasize": "^2.1.0",
"slice-ansi": "^4.0.0",
"string-width": "^4.2.0"
},
"gitHead": "291f3e6815a1a857a6165fafb1691ceeb878b8f6"
"devDependencies": {
"strip-ansi": "^6.0.0"
},
"gitHead": "74335525be92e23bac4ed1bf30595443cfb238e3"
}

@@ -6,15 +6,11 @@ // @flow

import emphasize from 'emphasize';
import stringWidth from 'string-width';
import sliceAnsi from 'slice-ansi';
type CodeFramePadding = {|
before: number,
after: number
after: number,
|};
type CodeFrameOptionsInput = {|
useColor?: boolean,
maxLines?: number,
padding?: CodeFramePadding,
syntaxHighlighting?: boolean,
language?: string
|};
type CodeFrameOptionsInput = $Shape<CodeFrameOptions>;

@@ -26,3 +22,4 @@ type CodeFrameOptions = {|

padding: CodeFramePadding,
language?: string
terminalWidth: number,
language?: string,
|};

@@ -33,2 +30,3 @@

const TAB_REPLACEMENT = ' ';
const DEFAULT_TERMINAL_WIDTH = 80;

@@ -50,4 +48,3 @@ const highlightSyntax = (txt: string, lang?: string): string => {

highlights: Array<DiagnosticCodeHighlight>,
// $FlowFixMe
inputOpts: CodeFrameOptionsInput = {}
inputOpts: CodeFrameOptionsInput = {},
): string {

@@ -60,9 +57,11 @@ if (highlights.length < 1) return '';

language: inputOpts.language,
maxLines: inputOpts.maxLines !== undefined ? inputOpts.maxLines : 12,
maxLines: inputOpts.maxLines ?? 12,
terminalWidth: inputOpts.terminalWidth || DEFAULT_TERMINAL_WIDTH,
padding: inputOpts.padding || {
before: 1,
after: 2
}
after: 2,
},
};
// Highlights messages and prefixes when colors are enabled
const highlighter = (s: string, bold?: boolean) => {

@@ -77,6 +76,7 @@ if (opts.useColor) {

// Prefix lines with the line number
const lineNumberPrefixer = (params: {|
lineNumber?: string,
endLine: string,
isHighlighted: boolean
isHighlighted: boolean,
|}) => {

@@ -97,12 +97,13 @@ let {lineNumber, endLine, isHighlighted} = params;

column: h.start.column - 1,
line: h.start.line - 1
line: h.start.line - 1,
},
end: {
column: h.end.column - 1,
line: h.end.line - 1
line: h.end.line - 1,
},
message: h.message
message: h.message,
};
});
// Find first and last highlight
let firstHighlight =

@@ -117,2 +118,3 @@ highlights.length > 1

// Calculate first and last line index of codeframe
let startLine = firstHighlight.start.line - opts.padding.before;

@@ -127,3 +129,3 @@ startLine = startLine < 0 ? 0 : startLine;

let resultLines = [];
// Split input into lines and highlight syntax
let lines = code.split(NEWLINE);

@@ -136,91 +138,155 @@ let syntaxHighlightedLines = (opts.syntaxHighlighting

.split(NEWLINE);
for (let i = startLine; i < lines.length; i++) {
if (i > endLine) break;
let originalLine: string = lines[i];
let syntaxHighlightedLine = syntaxHighlightedLines[i];
// Loop over all lines and create codeframe
let resultLines = [];
for (
let currentLineIndex = startLine;
currentLineIndex < syntaxHighlightedLines.length;
currentLineIndex++
) {
if (currentLineIndex > endLine) break;
if (currentLineIndex > syntaxHighlightedLines.length - 1) break;
let foundHighlights = highlights.filter(
highlight => highlight.start.line <= i && highlight.end.line >= i
);
// Find highlights that need to get rendered on the current line
let lineHighlights = highlights
.filter(
highlight =>
highlight.start.line <= currentLineIndex &&
highlight.end.line >= currentLineIndex,
)
.sort(
(a, b) =>
(a.start.line < currentLineIndex ? 0 : a.start.column) -
(b.start.line < currentLineIndex ? 0 : b.start.column),
);
// Check if this line has a full line highlight
let isWholeLine =
lineHighlights.length &&
!!lineHighlights.find(
h => h.start.line < currentLineIndex && h.end.line > currentLineIndex,
);
let lineLengthLimit =
opts.terminalWidth > endLineString.length + 7
? opts.terminalWidth - (endLineString.length + 5)
: 10;
// Split the line into line parts that will fit the provided terminal width
let colOffset = 0;
let lineEndCol = lineLengthLimit;
let syntaxHighlightedLine = syntaxHighlightedLines[currentLineIndex];
if (stringWidth(syntaxHighlightedLine) > lineLengthLimit) {
if (lineHighlights.length > 0) {
if (lineHighlights[0].start.line === currentLineIndex) {
colOffset = lineHighlights[0].start.column - 5;
} else if (lineHighlights[0].end.line === currentLineIndex) {
colOffset = lineHighlights[0].end.column - 5;
}
}
colOffset = colOffset > 0 ? colOffset : 0;
lineEndCol = colOffset + lineLengthLimit;
syntaxHighlightedLine = sliceAnsi(
syntaxHighlightedLine,
colOffset,
lineEndCol,
);
}
// Write the syntax highlighted line part
resultLines.push(
lineNumberPrefixer({
lineNumber: (i + 1).toString(10),
lineNumber: (currentLineIndex + 1).toString(10),
endLine: endLineString,
isHighlighted: foundHighlights.length > 0
}) + syntaxHighlightedLine
isHighlighted: lineHighlights.length > 0,
}) + syntaxHighlightedLine,
);
if (foundHighlights.length > 0) {
let highlightLine = lineNumberPrefixer({
endLine: endLineString,
isHighlighted: true
});
let lineWidth = stringWidth(syntaxHighlightedLine);
let highlightLine = '';
if (isWholeLine) {
highlightLine = highlighter('^'.repeat(lineWidth));
} else if (lineHighlights.length > 0) {
let lastCol = 0;
let highlight = null;
let highlightHasEnded = false;
let isWholeLine = !!foundHighlights.find(
h => h.start.line < i && h.end.line > i
);
for (
let highlightIndex = 0;
highlightIndex < lineHighlights.length;
highlightIndex++
) {
// Set highlight to current highlight
highlight = lineHighlights[highlightIndex];
highlightHasEnded = false;
if (isWholeLine) {
// If there's a whole line highlight
// don't even bother creating seperate highlight
highlightLine += highlighter(
'^'.repeat(
originalLine.replace(TAB_REPLACE_REGEX, TAB_REPLACEMENT).length
)
);
} else {
let sortedColumns =
foundHighlights.length > 1
? foundHighlights.sort(
(a, b) =>
(a.start.line < i ? 0 : a.start.column) -
(b.start.line < i ? 0 : b.start.column)
)
: foundHighlights;
// Calculate the startColumn and get the real width by doing a substring of the original
// line and replacing tabs with our tab replacement to support tab handling
let startCol = 0;
if (
highlight.start.line === currentLineIndex &&
highlight.start.column > colOffset
) {
startCol = lines[currentLineIndex]
.substring(colOffset, highlight.start.column)
.replace(TAB_REPLACE_REGEX, TAB_REPLACEMENT).length;
}
let lastCol = 0;
for (let col of sortedColumns) {
let startCol = col.start.line === i ? col.start.column : 0;
let endCol =
(col.end.line === i
? col.end.column
: originalLine.length - (lastCol || 1)) + 1;
// Calculate the endColumn and get the real width by doing a substring of the original
// line and replacing tabs with our tab replacement to support tab handling
let endCol = lineWidth - 1;
if (highlight.end.line === currentLineIndex) {
endCol = lines[currentLineIndex]
.substring(colOffset, highlight.end.column)
.replace(TAB_REPLACE_REGEX, TAB_REPLACEMENT).length;
if (startCol - lastCol > 0) {
let whitespace = originalLine
.substring(lastCol, startCol)
.replace(TAB_REPLACE_REGEX, TAB_REPLACEMENT)
.replace(/\S/g, ' ');
highlightLine += whitespace;
// If the endCol is too big for this line part, trim it so we can handle it in the next one
if (endCol > lineWidth) {
endCol = lineWidth - 1;
}
let highlightStartColumn = lastCol >= startCol ? lastCol : startCol;
if (endCol - highlightStartColumn > 0) {
let renderedHighlightLength = originalLine
.substring(highlightStartColumn, endCol)
.replace(TAB_REPLACE_REGEX, TAB_REPLACEMENT).length;
highlightLine += highlighter('^'.repeat(renderedHighlightLength));
lastCol = endCol;
}
highlightHasEnded = true;
}
let endsWithFullLine = !!sortedColumns.find(h => h.end.line > i);
if (!endsWithFullLine) {
let sortedByEnd = sortedColumns.sort(
(a, b) => a.end.column - b.end.column
);
// If endcol is smaller than lastCol it overlaps with another highlight and is no longer visible, we can skip those
if (endCol >= lastCol) {
let characters = endCol - startCol + 1;
if (startCol > lastCol) {
// startCol is before lastCol, so add spaces as padding before the highlight indicators
highlightLine += ' '.repeat(startCol - lastCol);
} else if (lastCol > startCol) {
// If last column is larger than the start, there's overlap in highlights
// This line adjusts the characters count to ensure we don't add too many characters
characters += startCol - lastCol;
}
let lastHighlightForColumn = sortedByEnd[sortedByEnd.length - 1];
if (lastHighlightForColumn.message) {
highlightLine +=
' ' + highlighter(lastHighlightForColumn.message, true);
}
// Append the highlight indicators
highlightLine += highlighter('^'.repeat(characters));
// Set the lastCol equal to character count between start of line part and highlight end-column
lastCol = endCol + 1;
}
// There's no point in processing more highlights if we reached the end of the line
if (endCol >= lineEndCol - 1) {
break;
}
}
resultLines.push(highlightLine);
// Append the highlight message if the current highlights ends on this line part
if (highlight && highlight.message && highlightHasEnded) {
highlightLine += ' ' + highlighter(highlight.message, true);
}
}
if (highlightLine) {
resultLines.push(
lineNumberPrefixer({
endLine: endLineString,
isHighlighted: true,
}) + highlightLine,
);
}
}

@@ -227,0 +293,0 @@

@@ -15,8 +15,8 @@ import assert from 'assert';

column: 1,
line: 1
line: 1,
},
end: {
column: 1,
line: 1
}
line: 1,
},
},

@@ -26,11 +26,11 @@ {

column: 3,
line: 1
line: 1,
},
end: {
column: 5,
line: 1
}
}
line: 1,
},
},
],
{useColor: false}
{useColor: false},
);

@@ -50,8 +50,8 @@

column: 1,
line: 1
line: 1,
},
end: {
column: 1,
line: 1
}
line: 1,
},
},

@@ -61,11 +61,11 @@ {

column: 7,
line: 1
line: 1,
},
end: {
column: 10,
line: 2
}
}
line: 2,
},
},
],
{useColor: false}
{useColor: false},
);

@@ -87,8 +87,8 @@

column: 1,
line: 1
line: 1,
},
end: {
column: 1,
line: 1
}
line: 1,
},
},

@@ -98,8 +98,8 @@ {

column: 7,
line: 1
line: 1,
},
end: {
column: 10,
line: 2
}
line: 2,
},
},

@@ -109,11 +109,11 @@ {

column: 4,
line: 2
line: 2,
},
end: {
column: 7,
line: 2
}
}
line: 2,
},
},
],
{useColor: false}
{useColor: false},
);

@@ -135,8 +135,8 @@

column: 1,
line: 1
line: 1,
},
end: {
column: 1,
line: 1
}
line: 1,
},
},

@@ -146,8 +146,8 @@ {

column: 7,
line: 1
line: 1,
},
end: {
column: 10,
line: 2
}
line: 2,
},
},

@@ -157,11 +157,11 @@ {

column: 4,
line: 2
line: 2,
},
end: {
column: 12,
line: 2
}
}
line: 2,
},
},
],
{useColor: false}
{useColor: false},
);

@@ -183,12 +183,12 @@

column: 1,
line: 1
line: 1,
},
end: {
column: 6,
line: 1
line: 1,
},
message: 'test'
}
message: 'test',
},
],
{useColor: false}
{useColor: false},
);

@@ -209,9 +209,9 @@

column: 1,
line: 1
line: 1,
},
end: {
column: 3,
line: 1
line: 1,
},
message: 'test'
message: 'test',
},

@@ -221,12 +221,12 @@ {

column: 1,
line: 1
line: 1,
},
end: {
column: 6,
line: 1
line: 1,
},
message: 'this should be printed'
}
message: 'this should be printed',
},
],
{useColor: false}
{useColor: false},
);

@@ -247,9 +247,9 @@

column: 1,
line: 1
line: 1,
},
end: {
column: 1,
line: 1
line: 1,
},
message: 'test'
message: 'test',
},

@@ -259,12 +259,12 @@ {

column: 3,
line: 1
line: 1,
},
end: {
column: 7,
line: 1
line: 1,
},
message: 'this should be printed'
}
message: 'this should be printed',
},
],
{useColor: false}
{useColor: false},
);

@@ -285,9 +285,9 @@

column: 1,
line: 1
line: 1,
},
end: {
column: 1,
line: 1
line: 1,
},
message: 'test'
message: 'test',
},

@@ -297,9 +297,9 @@ {

column: 3,
line: 1
line: 1,
},
end: {
column: 7,
line: 1
line: 1,
},
message: 'this should be printed'
message: 'this should be printed',
},

@@ -309,12 +309,12 @@ {

column: 3,
line: 2
line: 2,
},
end: {
column: 7,
line: 3
line: 3,
},
message: 'message line 2'
}
message: 'message line 2',
},
],
{useColor: false}
{useColor: false},
);

@@ -338,9 +338,9 @@

column: 1,
line: 1
line: 1,
},
end: {
column: 1,
line: 1
line: 1,
},
message: 'test'
message: 'test',
},

@@ -350,9 +350,9 @@ {

column: 3,
line: 1
line: 1,
},
end: {
column: 7,
line: 1
line: 1,
},
message: 'this should be printed'
message: 'this should be printed',
},

@@ -362,12 +362,12 @@ {

column: 3,
line: 2
line: 2,
},
end: {
column: 7,
line: 3
line: 3,
},
message: 'message line 2'
}
message: 'message line 2',
},
],
{useColor: false}
{useColor: false},
);

@@ -391,10 +391,10 @@

column: 2,
line: 5
line: 5,
},
end: {
column: 2,
line: 5
line: 5,
},
message: 'test'
}
message: 'test',
},
],

@@ -405,5 +405,5 @@ {

before: 2,
after: 4
}
}
after: 4,
},
},
);

@@ -424,9 +424,9 @@

column: 2,
line: 99
line: 99,
},
end: {
column: 2,
line: 99
line: 99,
},
message: 'test'
message: 'test',
},

@@ -436,10 +436,10 @@ {

column: 2,
line: 100
line: 100,
},
end: {
column: 2,
line: 100
line: 100,
},
message: 'test'
}
message: 'test',
},
]);

@@ -458,9 +458,9 @@

column: 2,
line: 7
line: 7,
},
end: {
column: 2,
line: 7
line: 7,
},
message: 'test'
message: 'test',
},

@@ -470,10 +470,10 @@ {

column: 2,
line: 12
line: 12,
},
end: {
column: 2,
line: 12
line: 12,
},
message: 'test'
}
message: 'test',
},
]);

@@ -494,9 +494,9 @@

column: 2,
line: 5
line: 5,
},
end: {
column: 2,
line: 5
line: 5,
},
message: 'test'
message: 'test',
},

@@ -506,15 +506,15 @@ {

column: 2,
line: 12
line: 12,
},
end: {
column: 2,
line: 20
line: 20,
},
message: 'test'
}
message: 'test',
},
],
{
useColor: false,
maxLines: 10
}
maxLines: 10,
},
);

@@ -536,12 +536,12 @@

column: 5,
line: 1
line: 1,
},
end: {
column: 7,
line: 1
column: 8,
line: 1,
},
message: 'test'
}
message: 'test',
},
],
{useColor: false}
{useColor: false},
);

@@ -551,3 +551,3 @@

assert.equal(lines[0], '> 1 | hel lo wor ld');
assert.equal(lines[1], '> | ^^^ test');
assert.equal(lines[1], '> | ^^^^ test');
assert.equal(lines[2], ' 2 | Enjoy thi s nice cod eframe');

@@ -563,9 +563,9 @@ });

column: 3,
line: 1
line: 1,
},
end: {
column: 5,
line: 1
line: 1,
},
message: 'test'
message: 'test',
},

@@ -575,12 +575,12 @@ {

column: 7,
line: 1
line: 1,
},
end: {
column: 8,
line: 1
line: 1,
},
message: 'test'
}
message: 'test',
},
],
{useColor: false}
{useColor: false},
);

@@ -601,12 +601,12 @@

column: 3,
line: 1
line: 1,
},
end: {
column: 2,
line: 3
line: 3,
},
message: 'test'
}
message: 'test',
},
],
{useColor: false}
{useColor: false},
);

@@ -622,2 +622,158 @@

});
it('Should truncate long lines and print message', () => {
let originalLine = 'hello world '.repeat(1000);
let codeframeString = codeframe(
originalLine,
[
{
start: {
column: 1000,
line: 1,
},
end: {
column: 1200,
line: 1,
},
message: 'This is a message',
},
],
{useColor: false, terminalWidth: 25},
);
let lines = codeframeString.split(LINE_END);
assert.equal(lines.length, 2);
assert.equal(lines[0], '> 1 | d hello world hello');
assert.equal(lines[1], '> | ^^^^^^^^^^^^^^ This is a message');
});
it('Truncation across multiple lines', () => {
let originalLine =
'hello world '.repeat(100) + '\n' + 'new line '.repeat(100);
let codeframeString = codeframe(
originalLine,
[
{
start: {
column: 15,
line: 1,
},
end: {
column: 400,
line: 1,
},
message: 'This is the first line',
},
{
start: {
column: 2,
line: 2,
},
end: {
column: 100,
line: 2,
},
message: 'This is the second line',
},
],
{useColor: false, terminalWidth: 25},
);
let lines = codeframeString.split(LINE_END);
assert.equal(lines.length, 4);
assert.equal(lines[0], '> 1 | ld hello world hell');
assert.equal(lines[1], '> | ^^^^^^^^^^^^^^ This is the first line');
assert.equal(lines[2], '> 2 | new line new line n');
assert.equal(lines[3], '> | ^^^^^^^^^^^^^^^^^^ This is the second line');
});
it('Truncation across various types and positions of highlights', () => {
let originalLine =
'hello world '.repeat(100) + '\n' + 'new line '.repeat(100);
let codeframeString = codeframe(
originalLine,
[
{
start: {
column: 2,
line: 1,
},
end: {
column: 5,
line: 1,
},
},
{
start: {
column: 6,
line: 1,
},
end: {
column: 10,
line: 1,
},
message: 'I have a message',
},
{
start: {
column: 15,
line: 1,
},
end: {
column: 25,
line: 1,
},
message: 'I also have a message',
},
{
start: {
column: 2,
line: 2,
},
end: {
column: 5,
line: 2,
},
message: 'This is the second line',
},
],
{useColor: false, terminalWidth: 25},
);
let lines = codeframeString.split(LINE_END);
assert.equal(lines.length, 4);
assert.equal(lines[0], '> 1 | hello world hello w');
assert.equal(lines[1], '> | ^^^^^^^^^ ^^^^^ I also have a message');
assert.equal(lines[2], '> 2 | new line new line n');
assert.equal(lines[3], '> | ^^^^ This is the second line');
});
it('Multi-line highlight w/ truncation', () => {
let originalLine =
'hello world '.repeat(100) + '\n' + 'new line '.repeat(100);
let codeframeString = codeframe(
originalLine,
[
{
start: {
column: 2,
line: 1,
},
end: {
column: 151,
line: 2,
},
message: 'I have a message',
},
],
{useColor: false, terminalWidth: 25},
);
let lines = codeframeString.split(LINE_END);
assert.equal(lines.length, 4);
assert.equal(lines[0], '> 1 | hello world hello w');
assert.equal(lines[1], '> | ^^^^^^^^^^^^^^^^^^');
assert.equal(lines[2], '> 2 | ew line new line ne');
assert.equal(lines[3], '> | ^^^^^^ I have a message');
});
});
// @flow
export * from './src/codeframe';