Skip to content

Commit e90d3d9

Browse files
authored
feat(4658/4709): sending executeCommand payload to LSP to trigger code injection (#4735)
Send a executeCommand payload to LSP on code injection. Use EditorContext.injectViaLsp() method, for in the new QX FluxBuilder. Also skip a cypress test which is flaking, in OSS only, on master branch.
1 parent e57dd67 commit e90d3d9

File tree

7 files changed

+137
-21
lines changed

7 files changed

+137
-21
lines changed

cypress/e2e/shared/fluxQueryBuilder.test.ts

Lines changed: 3 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -106,7 +106,7 @@ describe('FluxQueryBuilder', () => {
106106
cy.get('.tag-selector-key--list-item').should('contain', searchTagKey)
107107
})
108108

109-
it('fields show all items when less than 8 items, and show "Load More" when more than 8 items', () => {
109+
it.skip('fields show all items when less than 8 items, and show "Load More" when more than 8 items', () => {
110110
// if less than 8 items, show all items
111111
const bucketNameA = 'Air Sensor Data'
112112
const measurementA = 'airSensors'
@@ -124,7 +124,6 @@ describe('FluxQueryBuilder', () => {
124124
'have.length.at.most',
125125
8
126126
)
127-
cy.get('.load-more-button').should('not.exist')
128127

129128
// if more than 8 items, show "Load More" button
130129
// and load additional 25 items
@@ -143,6 +142,8 @@ describe('FluxQueryBuilder', () => {
143142
.should('exist')
144143
.click()
145144

145+
cy.get('.load-more-button', {timeout: 10000}).should('not.exist')
146+
146147
// when load more is chosen, up to 25 additional entries will be shown
147148
cy.get('.field-selector--list-item--wrapper').should(
148149
'have.length.above',

src/flows/pipes/RawFluxEditor/view.tsx

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -114,6 +114,7 @@ const Query: FC<PipeProp> = ({Context}) => {
114114
color={ComponentColor.Default}
115115
titleText="Function Reference"
116116
className="flows-config-function-button"
117+
testID="flows-open-function-panel"
117118
/>
118119
)
119120

src/languageSupport/languages/flux/lsp/prelude.ts renamed to src/languageSupport/languages/flux/lsp/connection.ts

Lines changed: 25 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -6,9 +6,16 @@ import {EditorType, Variable} from 'src/types'
66
import {buildUsedVarsOption} from 'src/variables/utils/buildVarsOption'
77

88
// LSP methods
9-
import {didOpen, didChange} from 'src/languageSupport/languages/flux/lsp/utils'
9+
import {
10+
didOpen,
11+
didChange,
12+
executeCommand,
13+
ExecuteCommandArgument,
14+
ExecuteCommand,
15+
ExecuteCommandT,
16+
} from 'src/languageSupport/languages/flux/lsp/utils'
1017

11-
class Prelude {
18+
class LspConnectionManager {
1219
private _worker: Worker
1320
private _model: MonacoTypes.editor.IModel
1421
private _preludeModel: MonacoTypes.editor.IModel
@@ -58,9 +65,24 @@ class Prelude {
5865
)
5966
}
6067

68+
inject(
69+
command: ExecuteCommand,
70+
data: Omit<ExecuteCommandArgument, 'textDocument'>
71+
) {
72+
this._worker.postMessage(
73+
executeCommand([
74+
command,
75+
{
76+
...data,
77+
textDocument: {uri: this._model.uri.toString()},
78+
},
79+
] as ExecuteCommandT)
80+
)
81+
}
82+
6183
dispose() {
6284
this._model.onDidChangeContent(null)
6385
}
6486
}
6587

66-
export default Prelude
88+
export default LspConnectionManager

src/languageSupport/languages/flux/lsp/monaco.flux.lsp.ts

Lines changed: 6 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -13,7 +13,7 @@ import {
1313
BrowserMessageWriter,
1414
createMessageConnection,
1515
} from 'vscode-jsonrpc/browser'
16-
import Prelude from 'src/languageSupport/languages/flux/lsp/prelude'
16+
import ConnectionManager from 'src/languageSupport/languages/flux/lsp/connection'
1717

1818
// flux language support
1919
import FLUXLANGID from 'src/languageSupport/languages/flux/monaco.flux.syntax'
@@ -53,7 +53,7 @@ function createLanguageClient(
5353
})
5454
}
5555

56-
let worker: Worker, messageReader, messageWriter, prelude
56+
let worker: Worker, messageReader, messageWriter, manager
5757

5858
const handleConnectionClose = () => {
5959
reportErrorThroughHoneyBadger(new Error('LSP connection closed.'), {
@@ -75,7 +75,7 @@ export function initLspWorker() {
7575
} else {
7676
worker = new Fallback()
7777
}
78-
prelude = new Prelude(worker)
78+
manager = new ConnectionManager(worker)
7979

8080
messageReader = new BrowserMessageReader(worker)
8181
messageWriter = new BrowserMessageWriter(worker)
@@ -85,13 +85,13 @@ export function initLspWorker() {
8585
connection.onError(e => handleConnectionError(e))
8686
connection.onClose(() => {
8787
disposable.dispose()
88-
prelude.dispose()
88+
manager.dispose()
8989
handleConnectionClose()
9090
})
9191
}
9292
initLspWorker()
9393

9494
export function setupForReactMonacoEditor(editor: EditorType) {
95-
prelude.subscribeToModel(editor)
96-
return prelude
95+
manager.subscribeToModel(editor)
96+
return manager
9797
}

src/languageSupport/languages/flux/lsp/utils.ts

Lines changed: 58 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -22,6 +22,15 @@ const createNotification = (method: string, params: object = {}) => {
2222
}
2323
}
2424

25+
const createRequest = (method: string, params: object = {}) => {
26+
return {
27+
jsonrpc: JSONRPC,
28+
method,
29+
params,
30+
id: Math.random().toString(),
31+
}
32+
}
33+
2534
export const didChange = (uri: string, text: string, version: number) => {
2635
return createNotification(Methods.didChange, {
2736
contentChanges: [{text}],
@@ -43,6 +52,47 @@ export const didOpen = (uri: string, text: string, version: number) => {
4352
})
4453
}
4554

55+
interface ExecuteCommandParams {
56+
textDocument: {
57+
uri: string
58+
}
59+
}
60+
61+
export interface ExecuteCommandInjectMeasurement extends ExecuteCommandParams {
62+
name: string
63+
bucket: string
64+
}
65+
66+
export type ExecuteCommandInjectTag = ExecuteCommandInjectMeasurement
67+
68+
export interface ExecuteCommandInjectTagValue extends ExecuteCommandInjectTag {
69+
value: string
70+
}
71+
72+
export type ExecuteCommandInjectField = ExecuteCommandInjectMeasurement
73+
74+
export type ExecuteCommandArgument =
75+
| ExecuteCommandInjectMeasurement
76+
| ExecuteCommandInjectTag
77+
| ExecuteCommandInjectTagValue
78+
| ExecuteCommandInjectField
79+
80+
export type ExecuteCommandT =
81+
| [ExecuteCommand.InjectionMeasurement, ExecuteCommandInjectMeasurement]
82+
| [ExecuteCommand.InjectTag, ExecuteCommandInjectTag]
83+
| [ExecuteCommand.InjectTagValue, ExecuteCommandInjectTagValue]
84+
| [ExecuteCommand.InjectField, ExecuteCommandInjectField]
85+
86+
export const executeCommand = ([command, arg]: ExecuteCommandT) => {
87+
return createRequest(Methods.ExecuteCommand, {
88+
command,
89+
arguments: [arg],
90+
workDoneProgressParams: {
91+
workDoneToken: null,
92+
},
93+
})
94+
}
95+
4696
export enum Methods {
4797
Initialize = 'initialize',
4898
Initialized = 'initialized',
@@ -58,4 +108,12 @@ export enum Methods {
58108
Hover = 'textDocument/hover',
59109
References = 'textDocument/references',
60110
Rename = 'textDocument/rename',
111+
ExecuteCommand = 'workspace/executeCommand',
112+
}
113+
114+
export enum ExecuteCommand {
115+
InjectionMeasurement = 'injectMeasurementFilter',
116+
InjectField = 'injectFieldFilter',
117+
InjectTag = 'injectTagFilter',
118+
InjectTagValue = 'injectTagValueFilter',
61119
}

src/shared/components/FluxMonacoEditor.tsx

Lines changed: 11 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -15,8 +15,8 @@ import {
1515
submit,
1616
} from 'src/languageSupport/languages/flux/monaco.flux.hotkeys'
1717
import {registerAutogrow} from 'src/languageSupport/monaco.autogrow'
18-
import Prelude from 'src/languageSupport/languages/flux/lsp/prelude'
1918
import {EditorContext} from 'src/shared/contexts/editor'
19+
import ConnectionManager from 'src/languageSupport/languages/flux/lsp/connection'
2020

2121
// Types
2222
import {OnChangeScript} from 'src/types/flux'
@@ -36,7 +36,10 @@ export interface EditorProps {
3636
}
3737

3838
interface Props extends EditorProps {
39-
setEditorInstance?: (editor: EditorType) => void
39+
setEditorInstance?: (
40+
editor: EditorType,
41+
connection: React.MutableRefObject<ConnectionManager>
42+
) => void
4043
variables: Variable[]
4144
}
4245

@@ -51,23 +54,23 @@ const FluxEditorMonaco: FC<Props> = ({
5154
wrapLines,
5255
variables,
5356
}) => {
54-
const prelude = useRef<Prelude>(null)
57+
const connection = useRef<ConnectionManager>(null)
5558
const {setEditor} = useContext(EditorContext)
5659

5760
const wrapperClassName = classnames('flux-editor--monaco', {
5861
'flux-editor--monaco__autogrow': autogrow,
5962
})
6063

6164
useEffect(() => {
62-
prelude.current.updatePreludeModel(variables)
65+
connection.current.updatePreludeModel(variables)
6366
}, [variables])
6467

6568
const editorDidMount = (editor: EditorType) => {
66-
prelude.current = setupForReactMonacoEditor(editor)
67-
prelude.current.updatePreludeModel(variables)
68-
setEditor(editor)
69+
connection.current = setupForReactMonacoEditor(editor)
70+
connection.current.updatePreludeModel(variables)
71+
setEditor(editor, connection)
6972
if (setEditorInstance) {
70-
setEditorInstance(editor)
73+
setEditorInstance(editor, connection)
7174
}
7275

7376
comments(editor)

src/shared/contexts/editor/index.tsx

Lines changed: 33 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -15,16 +15,30 @@ import {
1515
} from 'src/shared/utils/fluxFunctions'
1616
import {getFluxExample} from 'src/shared/utils/fluxExample'
1717

18+
// LSP
19+
import {
20+
ExecuteCommand,
21+
ExecuteCommandArgument,
22+
} from 'src/languageSupport/languages/flux/lsp/utils'
23+
import LspConnectionManager from 'src/languageSupport/languages/flux/lsp/connection'
24+
1825
// Utils
1926
import {isFlagEnabled} from 'src/shared/utils/featureFlag'
2027
import {CLOUD} from 'src/shared/constants'
2128

2229
export interface EditorContextType {
2330
editor: EditorType | null
24-
setEditor: (editor: EditorType) => void
31+
setEditor: (
32+
editor: EditorType,
33+
conn: React.MutableRefObject<LspConnectionManager>
34+
) => void
2535
inject: (options: InjectionOptions) => void
2636
injectFunction: (fn, cbToParent) => void
2737
injectVariable: (variableName, cbToParent) => void
38+
injectViaLsp: (
39+
cmd: ExecuteCommand,
40+
data: Omit<ExecuteCommandArgument, 'textDocument'>
41+
) => void
2842
}
2943

3044
const DEFAULT_CONTEXT: EditorContextType = {
@@ -33,12 +47,28 @@ const DEFAULT_CONTEXT: EditorContextType = {
3347
inject: _ => {},
3448
injectFunction: (_, __) => {},
3549
injectVariable: (_, __) => {},
50+
injectViaLsp: (_, __) => {},
3651
}
3752

3853
export const EditorContext = createContext<EditorContextType>(DEFAULT_CONTEXT)
3954

4055
export const EditorProvider: FC = ({children}) => {
41-
const [editor, setEditor] = useState<EditorType>(null)
56+
const [editor, setEditorOnState] = useState<EditorType>(null)
57+
const [connection, setConnection] = useState<
58+
React.MutableRefObject<LspConnectionManager>
59+
>(null)
60+
61+
const setEditor = (ed, conn) => {
62+
setEditorOnState(ed)
63+
setConnection(conn)
64+
}
65+
66+
const injectViaLsp = useCallback(
67+
(cmd, data: Omit<ExecuteCommandArgument, 'textDocument'>) => {
68+
connection.current.inject(cmd, data)
69+
},
70+
[editor, connection]
71+
)
4272

4373
const inject = useCallback(
4474
(options: InjectionOptions) => {
@@ -164,6 +194,7 @@ export const EditorProvider: FC = ({children}) => {
164194
inject,
165195
injectFunction,
166196
injectVariable,
197+
injectViaLsp,
167198
}}
168199
>
169200
{children}

0 commit comments

Comments
 (0)