Skip to content

Commit ca698f1

Browse files
committed
fix: Don't include columns when completing FROM statements.
1 parent 3111377 commit ca698f1

File tree

2 files changed

+55
-10
lines changed

2 files changed

+55
-10
lines changed

packages/server/src/complete/complete.ts

Lines changed: 17 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -255,20 +255,13 @@ class Completer {
255255
this.addCandidatesForExpectedLiterals(expectedLiteralNodes)
256256
this.addCandidatesForFunctions()
257257

258-
const { addedSome: addedSomeScopedColumnCandidates } =
259-
this.addCandidatesForScopedColumns(fromNodes, schemaAndSubqueries)
260-
if (!addedSomeScopedColumnCandidates) {
261-
this.addCandidatesForUnscopedColumns(fromNodes, schemaAndSubqueries)
262-
}
263-
264-
this.addCandidatesForAliases(fromNodes)
265-
258+
// Detect FROM clause context BEFORE adding column suggestions
266259
const fromNodesContainingCursor = fromNodes.filter((tableNode) =>
267260
isPosInLocation(tableNode.location, this.pos)
268261
)
269262
const isCursorInsideFromClause = fromNodesContainingCursor.length > 0
270263

271-
// Check if cursor is right after FROM keyword (no table typed yet)
264+
// Check if cursor is right after FROM keyword or typing a table name
272265
const afterFromClause = parsedFromClause.after?.trim().toUpperCase() || ''
273266
const isCursorAfterFromKeyword =
274267
afterFromClause === 'FROM' ||
@@ -277,7 +270,21 @@ class Completer {
277270
afterFromClause
278271
)
279272

280-
if (isCursorInsideFromClause || isCursorAfterFromKeyword) {
273+
const isTypingTableName =
274+
isCursorInsideFromClause || isCursorAfterFromKeyword
275+
276+
if (!isTypingTableName) {
277+
const { addedSome: addedSomeScopedColumnCandidates } =
278+
this.addCandidatesForScopedColumns(fromNodes, schemaAndSubqueries)
279+
280+
if (!addedSomeScopedColumnCandidates) {
281+
this.addCandidatesForUnscopedColumns(fromNodes, schemaAndSubqueries)
282+
}
283+
}
284+
285+
this.addCandidatesForAliases(fromNodes)
286+
287+
if (isTypingTableName) {
281288
// add table candidates if the cursor is inside a FROM clause, JOIN clause,
282289
// or right after FROM/JOIN keyword waiting for a table name
283290
this.addCandidatesForTables(schemaAndSubqueries, true)

packages/server/test/complete/complete_table.test.ts

Lines changed: 38 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -112,4 +112,42 @@ describe('TableName completion', () => {
112112
]
113113
expect(result.candidates).toEqual(expect.arrayContaining(expected))
114114
})
115+
116+
test('complete table name after FROM keyword with partial input', () => {
117+
const schema = {
118+
tables: [
119+
{
120+
catalog: null,
121+
database: null,
122+
tableName: 'notes',
123+
columns: [{ columnName: 'id', description: '' }],
124+
},
125+
{
126+
catalog: null,
127+
database: null,
128+
tableName: 'users',
129+
columns: [{ columnName: 'name', description: '' }],
130+
},
131+
],
132+
functions: [],
133+
}
134+
135+
const result = complete(
136+
'SELECT * FROM not',
137+
{ line: 0, column: 17 },
138+
schema
139+
)
140+
141+
// Should suggest table names, not columns
142+
expect(result.candidates).toEqual(
143+
expect.arrayContaining([expect.objectContaining({ label: 'notes' })])
144+
)
145+
// Should NOT include column suggestions
146+
expect(result.candidates).not.toEqual(
147+
expect.arrayContaining([expect.objectContaining({ label: 'id' })])
148+
)
149+
expect(result.candidates).not.toEqual(
150+
expect.arrayContaining([expect.objectContaining({ label: 'name' })])
151+
)
152+
})
115153
})

0 commit comments

Comments
 (0)