Path: blob/main/extensions/copilot/src/platform/inlineEdits/common/utils/tsExpr.ts
13405 views
/*---------------------------------------------------------------------------------------------1* Copyright (c) Microsoft Corporation. All rights reserved.2* Licensed under the MIT License. See License.txt in the project root for license information.3*--------------------------------------------------------------------------------------------*/45export class TsExpr {6static str(value: string): TsExpr;7static str(strings: TemplateStringsArray, ...values: unknown[]): TsExpr;8static str(strings: TemplateStringsArray | string, ...values: unknown[]): TsExpr {9if (typeof strings === 'string') {10return new TsExpr([strings]);11} else {12const parts: (string | { value: unknown })[] = [];13for (let i = 0; i < strings.length; i++) {14parts.push(strings[i]);15if (i < values.length) {16parts.push({ value: values[i] });17}18}1920// TODO remove indentation2122return new TsExpr(parts);23}2425}2627constructor(public readonly parts: (string | { value: unknown })[]) { }2829toString() {30return _serializeToTs(this, 0);31}32}3334function _serializeToTs(data: unknown, newLineIndentation: number): string {35if (data && typeof data === 'object') {3637if (data instanceof TsExpr) {38let lastIndentation = 0;39const result = data.parts.map(p => {40if (typeof p === 'string') {41lastIndentation = getIndentOfLastLine(p);42return p;43} else {44return _serializeToTs(p.value, lastIndentation);45}46}).join('');4748return indentNonFirstLines(result, newLineIndentation);49}5051if (Array.isArray(data)) {52const entries: string[] = [];53for (const value of data) {54entries.push(_serializeToTs(value, newLineIndentation + 1));55}5657return `[\n`58+ entries.map(e => indentLine(e, newLineIndentation + 1) + ',\n').join('')59+ indentLine(`]`, newLineIndentation);60}6162const entries: string[] = [];63for (const [key, value] of Object.entries(data)) {64entries.push(`${serializeObjectKey(key)}: ${_serializeToTs(value, newLineIndentation + 1)},\n`);65}66return `{\n`67+ entries.map(e => indentLine(e, newLineIndentation + 1)).join('')68+ indentLine(`}`, newLineIndentation);69}7071if (data === undefined) {72return indentNonFirstLines('undefined', newLineIndentation);73}7475return indentNonFirstLines(JSON.stringify(data, undefined, '\t'), newLineIndentation);76}7778function getIndentOfLastLine(str: string): number {79const lines = str.split('\n');80const lastLine = lines[lines.length - 1];81return lastLine.length - lastLine.trimStart().length;82}8384function indentNonFirstLines(str: string, indentation: number): string {85const lines = str.split('\n');86return lines.map((line, i) => i === 0 ? line : indentLine(line, indentation)).join('\n');87}8889function indentLine(str: string, indentation: number): string {90return '\t'.repeat(indentation) + str;91}9293function serializeObjectKey(key: string): string {94if (/^[a-zA-Z_]\w*$/.test(key)) {95return key;96}97return JSON.stringify(key);98}99100101