fix(agent): fix postprocess indentation filter to check if the block closing line is duplicated. (#586)

r0.4
Zhiming Ma 2023-10-18 18:11:55 +08:00 committed by GitHub
parent e0f16ff5d6
commit 4a87bcf431
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
2 changed files with 18 additions and 12 deletions

View File

@ -33,7 +33,7 @@ describe("postprocess", () => {
expect(limitScopeByIndentation(context)(completion)).to.eq(completion); expect(limitScopeByIndentation(context)(completion)).to.eq(completion);
}); });
it("should allow multiline completions, when the suffix only have special chars that will be replaced in the current line, such as `)]}`.", () => { it("should allow multiline completions, when the suffix only have auto-closed chars that will be replaced in the current line, such as `)]}`.", () => {
const context = { const context = {
...documentContext` ...documentContext`
function findMax(arr) {} function findMax(arr) {}
@ -274,8 +274,7 @@ describe("postprocess", () => {
const expected = inline` const expected = inline`
return JSON.parse(json); return JSON.parse(json);
} catch (e) { } catch (e) {
return null; return null;
}
`; `;
expect(limitScopeByIndentation(context)(completion)).to.eq(expected); expect(limitScopeByIndentation(context)(completion)).to.eq(expected);

View File

@ -17,8 +17,9 @@ function processContext(
lines: string[], lines: string[],
prefixLines: string[], prefixLines: string[],
suffixLines: string[], suffixLines: string[],
): { indentLevelLimit: number; allowClosingLine: boolean } { ): { indentLevelLimit: number; allowClosingLine: (closingLine: string) => boolean } {
let result = { indentLevelLimit: 0, allowClosingLine: false }; let allowClosingLine = false;
let result = { indentLevelLimit: 0, allowClosingLine: (closingLine: string) => allowClosingLine };
if (lines.length == 0 || prefixLines.length == 0) { if (lines.length == 0 || prefixLines.length == 0) {
return result; // guard for empty input, technically unreachable return result; // guard for empty input, technically unreachable
} }
@ -58,22 +59,22 @@ function processContext(
result.indentLevelLimit = referenceLineInPrefixIndent + 1; // + 1 for comparison, no matter how many spaces indent result.indentLevelLimit = referenceLineInPrefixIndent + 1; // + 1 for comparison, no matter how many spaces indent
// allow closing line if first line is opening a new indent block // allow closing line if first line is opening a new indent block
result.allowClosingLine = !!lines[1] && calcIndentLevel(lines[1]) > referenceLineInPrefixIndent; allowClosingLine = !!lines[1] && calcIndentLevel(lines[1]) > referenceLineInPrefixIndent;
} else if (referenceLineInCompletionIndent > referenceLineInPrefixIndent) { } else if (referenceLineInCompletionIndent > referenceLineInPrefixIndent) {
// if reference line in completion has more indent than reference line in prefix, it is opening a new indent block // if reference line in completion has more indent than reference line in prefix, it is opening a new indent block
result.indentLevelLimit = referenceLineInPrefixIndent + 1; result.indentLevelLimit = referenceLineInPrefixIndent + 1;
result.allowClosingLine = true; allowClosingLine = true;
} else if (referenceLineInCompletionIndent < referenceLineInPrefixIndent) { } else if (referenceLineInCompletionIndent < referenceLineInPrefixIndent) {
// if reference line in completion has less indent than reference line in prefix, allow this closing // if reference line in completion has less indent than reference line in prefix, allow this closing
result.indentLevelLimit = referenceLineInPrefixIndent; result.indentLevelLimit = referenceLineInPrefixIndent;
result.allowClosingLine = true; allowClosingLine = true;
} else { } else {
// otherwise, it is starting a new sentence at same indent level // otherwise, it is starting a new sentence at same indent level
result.indentLevelLimit = referenceLineInPrefixIndent; result.indentLevelLimit = referenceLineInPrefixIndent;
result.allowClosingLine = false; allowClosingLine = true;
} }
// check if suffix context allows closing line // check if suffix context allows closing line
@ -83,7 +84,13 @@ function processContext(
firstNonBlankLineInSuffix++; firstNonBlankLineInSuffix++;
} }
if (firstNonBlankLineInSuffix < suffixLines.length) { if (firstNonBlankLineInSuffix < suffixLines.length) {
result.allowClosingLine &&= calcIndentLevel(suffixLines[firstNonBlankLineInSuffix]) < result.indentLevelLimit; allowClosingLine &&= calcIndentLevel(suffixLines[firstNonBlankLineInSuffix]) < result.indentLevelLimit;
result.allowClosingLine = (closingLine: string) => {
const duplicatedClosingLine =
closingLine.startsWith(suffixLines[firstNonBlankLineInSuffix]) ||
suffixLines[firstNonBlankLineInSuffix].startsWith(closingLine);
return allowClosingLine && !duplicatedClosingLine;
};
} }
return result; return result;
} }
@ -114,8 +121,8 @@ export const limitScopeByIndentation: (context: CompletionContext) => Postproces
// We include this closing line here if context allows // We include this closing line here if context allows
// For python, if previous line is blank, we don't include this line // For python, if previous line is blank, we don't include this line
if ( if (
(context.language !== "python" && indentContext.allowClosingLine) || indentContext.allowClosingLine(inputLines[index]) &&
(context.language === "python" && indentContext.allowClosingLine && !isBlank(inputLines[index - 1])) (context.language !== "python" || !isBlank(inputLines[index - 1]))
) { ) {
index++; index++;
} }