Skip to content

Commit 3a936cd

Browse files
feat(Designer): Add Custom Editor for Vs-Code To Display DM Editor (#4592)
* addeddraft using http connector * added logic for displaytext * removed console logs * cleaned up * moved displayText to editorOptions * added flag to only display for vscode * changed structure and passed workflowService * added vscode extension commands * fixed typo * removed unused code * changed based on suggestions * removed unused markdown * changed back unwanted change * nit * connected services * removed previous non custom editor logic * removed manifest sample change from http * fixed nit --------- Co-authored-by: Travis Harris <[email protected]>
1 parent 88df97d commit 3a936cd

File tree

6 files changed

+84
-7
lines changed

6 files changed

+84
-7
lines changed

apps/vs-code-designer/src/app/commands/workflows/openDesigner/openDesignerForLocalProject.ts

+8
Original file line numberDiff line numberDiff line change
@@ -22,6 +22,7 @@ import {
2222
import { saveWorkflowParameter } from '../../../utils/codeless/parameter';
2323
import { startDesignTimeApi } from '../../../utils/codeless/startDesignTimeApi';
2424
import { sendRequest } from '../../../utils/requestUtils';
25+
import { createNewDataMapCmd } from '../../dataMapper/dataMapper';
2526
import { OpenDesignerBase } from './openDesignerBase';
2627
import { HTTP_METHODS } from '@microsoft/logic-apps-shared';
2728
import type { IActionContext } from '@microsoft/vscode-azext-utils';
@@ -212,6 +213,13 @@ export default class OpenDesignerForLocalProject extends OpenDesignerBase {
212213
break;
213214
}
214215

216+
case ExtensionCommand.openRelativeLink: {
217+
if (msg.content === '/dataMapper') {
218+
createNewDataMapCmd(this.context);
219+
}
220+
break;
221+
}
222+
215223
default:
216224
break;
217225
}
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,52 @@
1+
import type { IEditorParameterInfo, IEditorProps, IEditorService } from '@microsoft/logic-apps-shared';
2+
import { Link } from '@fluentui/react';
3+
4+
export interface CustomEditorServiceOptions {
5+
areCustomEditorsEnabled?: boolean;
6+
openRelativeLink?: (relativeLink: string) => void;
7+
}
8+
9+
export class CustomEditorService implements IEditorService {
10+
_areCustomEditorsEnabled = true;
11+
12+
constructor(public readonly options: CustomEditorServiceOptions) {
13+
const { areCustomEditorsEnabled } = options;
14+
this._areCustomEditorsEnabled = areCustomEditorsEnabled ?? true;
15+
}
16+
17+
public getEditor = (props: IEditorParameterInfo) => {
18+
if (!this._areCustomEditorsEnabled) {
19+
return undefined;
20+
}
21+
22+
const { operationInfo, parameter } = props;
23+
const { connectorId, operationId } = operationInfo ?? {};
24+
const { parameterName, editor, editorOptions } = parameter ?? {};
25+
26+
if (connectorId === 'connectionProviders/dataMapperOperations' && operationId === 'xsltTransform' && parameterName === 'text') {
27+
return {
28+
EditorComponent: this.DisplayTextEditor,
29+
hideLabel: true,
30+
editor,
31+
editorOptions,
32+
};
33+
}
34+
35+
return undefined;
36+
};
37+
38+
DisplayTextEditor = ({ editorOptions }: IEditorProps) => {
39+
return (
40+
<>
41+
{editorOptions?.displayText?.text}
42+
<Link
43+
onClick={() => {
44+
this.options?.openRelativeLink?.(editorOptions?.displayText?.relativeLink ?? '');
45+
}}
46+
>
47+
{editorOptions?.displayText?.relativeLinkText}
48+
</Link>
49+
</>
50+
);
51+
};
52+
}

apps/vs-code-react/src/app/designer/servicesHelper.ts

+13
Original file line numberDiff line numberDiff line change
@@ -27,6 +27,7 @@ import type { ConnectionAndAppSetting, ConnectionsData, IDesignerPanelMetadata }
2727
import { ExtensionCommand, HttpClient } from '@microsoft/vscode-extension-logic-apps';
2828
import type { QueryClient } from 'react-query';
2929
import type { WebviewApi } from 'vscode-webview';
30+
import { CustomEditorService } from './customEditorService';
3031

3132
export const getDesignerServices = (
3233
baseUrl: string,
@@ -50,6 +51,7 @@ export const getDesignerServices = (
5051
workflowService: IWorkflowService;
5152
hostService: IHostService;
5253
runService: StandardRunService;
54+
editorService: CustomEditorService;
5355
apimService: BaseApiManagementService;
5456
functionService: BaseFunctionService;
5557
} => {
@@ -283,6 +285,16 @@ export const getDesignerServices = (
283285
httpClient,
284286
});
285287

288+
const editorService = new CustomEditorService({
289+
areCustomEditorsEnabled: true,
290+
openRelativeLink: (relativeLink: string) => {
291+
return vscode.postMessage({
292+
command: ExtensionCommand.openRelativeLink,
293+
content: relativeLink,
294+
});
295+
},
296+
});
297+
286298
return {
287299
connectionService,
288300
connectorService,
@@ -293,6 +305,7 @@ export const getDesignerServices = (
293305
workflowService,
294306
hostService,
295307
runService,
308+
editorService,
296309
apimService,
297310
functionService,
298311
};

libs/designer-ui/src/lib/settings/settingsection/customTokenField.tsx

+9-7
Original file line numberDiff line numberDiff line change
@@ -8,7 +8,7 @@ import type {
88
IEditorProps,
99
IRenderDefaultEditorParams,
1010
} from '@microsoft/logic-apps-shared';
11-
import { equals } from '@microsoft/logic-apps-shared';
11+
import { equals, isObject } from '@microsoft/logic-apps-shared';
1212
import { useCallback } from 'react';
1313

1414
export type CustomTokenFieldProps = Omit<TokenFieldProps, 'editor' | 'editorOptions'> & ICustomEditorAndOptions;
@@ -26,7 +26,7 @@ export const CustomTokenField = (props: CustomTokenFieldProps) => {
2626
renderDefaultEditor,
2727
disabled: props.readOnly,
2828
};
29-
return <EditorComponent {...customEditorProps} />;
29+
return EditorComponent ? <EditorComponent {...customEditorProps} /> : <></>;
3030
};
3131

3232
function useRenderDefaultEditor(tokenFieldProps: Omit<TokenFieldProps, 'editor' | 'editorOptions' | 'value' | 'onValueChange'>) {
@@ -51,13 +51,15 @@ const customEditorName = 'internal-custom-editor';
5151

5252
export type ICustomEditorAndOptions = { editor: typeof customEditorName; editorOptions: ICustomEditorOptions };
5353

54-
export const isCustomEditor = (props: { editor?: string | undefined; editorOptions?: unknown }): props is ICustomEditorAndOptions => {
54+
export const isCustomEditor = (props: { editor?: string | undefined; editorOptions?: any }): props is ICustomEditorAndOptions => {
5555
const { editor, editorOptions } = props;
56+
5657
return (
57-
equals(editor, customEditorName) &&
58-
typeof editorOptions === 'object' &&
59-
!!editorOptions &&
60-
typeof (editorOptions as { EditorComponent: unknown }).EditorComponent === 'function'
58+
editorOptions?.visibility === 'custom' ||
59+
(equals(editor, customEditorName) &&
60+
isObject(editorOptions) &&
61+
!!editorOptions &&
62+
typeof (editorOptions as { EditorComponent: unknown }).EditorComponent === 'function')
6163
);
6264
};
6365

libs/designer-ui/src/lib/settings/settingsection/settingTokenField.tsx

+1
Original file line numberDiff line numberDiff line change
@@ -65,6 +65,7 @@ export const SettingTokenField = ({ ...props }: SettingTokenFieldProps) => {
6565
const labelId = useId('msla-editor-label');
6666
const hideLabel =
6767
(isCustomEditor(props) && props.editorOptions?.hideLabel === true) || equals(props.editor?.toLowerCase(), 'floatingactionmenu');
68+
6869
return (
6970
<>
7071
{!hideLabel && (

libs/vscode-extension/src/lib/models/extensioncommand.ts

+1
Original file line numberDiff line numberDiff line change
@@ -39,6 +39,7 @@ export const ExtensionCommand = {
3939
completeOauthLogin: 'CompleteOauthLogin',
4040
webviewLoaded: 'webviewLoaded',
4141
webviewRscLoadError: 'webviewRscLoadError',
42+
openRelativeLink: 'openRelativeLink',
4243
} as const;
4344
export type ExtensionCommand = (typeof ExtensionCommand)[keyof typeof ExtensionCommand];
4445

0 commit comments

Comments
 (0)