microsoft/vscode-react-native

Public

mirrored from https://github.com/microsoft/vscode-react-nativeAvailable

CodeCommitsIssuesPull requestsActionsInsightsSecurity
1.3.0

Branches

Tags

  • No tags available.
0Branches0Tags
Go to file
Add file
Code

Clone

HTTPS

Download ZIP

src/extension/debuggingConfiguration/reactNativeDebugConfigProvider.ts

333lines · modecode

1// Copyright (c) Microsoft Corporation. All rights reserved.
2// Licensed under the MIT license. See LICENSE file in the project root for details.
3
4import * as vscode from "vscode";
5import { TelemetryHelper } from "../../common/telemetryHelper";
6import { Telemetry } from "../../common/telemetry";
7import { PlatformType } from "../launchArgs";
8import { IWDPHelper } from "../../debugger/direct/IWDPHelper";
9import { DebugScenarioNameGenerator } from "./debugScenarioNameGenerator";
10import { ILaunchRequestArgs } from "../../debugger/debugSessionBase";
11import {
12 DEBUG_TYPES,
13 DebugScenarioType,
14 DebugConfigurationQuickPickItem,
15 DebugConfigurationState,
16} from "./debugConfigTypesAndConstants";
17import { MultiStepInput, IMultiStepInput, InputStep, IQuickPickParameters } from "./multiStepInput";
18import { ConfigProviderFactory } from "./configurationProviders/configProviderFactory";
19import * as nls from "vscode-nls";
20nls.config({
21 messageFormat: nls.MessageFormat.bundle,
22 bundleFormat: nls.BundleFormat.standalone,
23})();
24const localize = nls.loadMessageBundle();
25
26export class ReactNativeDebugConfigProvider implements vscode.DebugConfigurationProvider {
27 private debugConfigurations = {
28 "Debug Android": {
29 name: "Debug Android",
30 cwd: "${workspaceFolder}",
31 type: DEBUG_TYPES.REACT_NATIVE,
32 request: "launch",
33 platform: PlatformType.Android,
34 },
35 "Run Android": {
36 name: "Run Android",
37 cwd: "${workspaceFolder}",
38 type: DEBUG_TYPES.REACT_NATIVE,
39 request: "launch",
40 platform: PlatformType.Android,
41 enableDebug: false,
42 },
43 "Debug iOS": {
44 name: "Debug iOS",
45 cwd: "${workspaceFolder}",
46 type: DEBUG_TYPES.REACT_NATIVE,
47 request: "launch",
48 platform: PlatformType.iOS,
49 },
50 "Run iOS": {
51 name: "Run iOS",
52 cwd: "${workspaceFolder}",
53 type: DEBUG_TYPES.REACT_NATIVE,
54 request: "launch",
55 platform: PlatformType.iOS,
56 enableDebug: false,
57 },
58 "Debug Windows": {
59 name: "Debug Windows",
60 cwd: "${workspaceFolder}",
61 type: DEBUG_TYPES.REACT_NATIVE,
62 request: "launch",
63 platform: PlatformType.Windows,
64 },
65 "Debug macOS": {
66 name: "Debug macOS",
67 cwd: "${workspaceFolder}",
68 type: DEBUG_TYPES.REACT_NATIVE,
69 request: "launch",
70 platform: PlatformType.macOS,
71 },
72 "Attach to packager": {
73 name: "Attach to packager",
74 cwd: "${workspaceFolder}",
75 type: DEBUG_TYPES.REACT_NATIVE,
76 request: "attach",
77 },
78 "Debug in Exponent": {
79 name: "Debug in Exponent",
80 cwd: "${workspaceFolder}",
81 type: DEBUG_TYPES.REACT_NATIVE,
82 request: "launch",
83 platform: PlatformType.Exponent,
84 },
85 "Debug Android Hermes - Experimental": {
86 name: "Debug Android Hermes - Experimental",
87 cwd: "${workspaceFolder}",
88 type: DEBUG_TYPES.REACT_NATIVE_DIRECT,
89 request: "launch",
90 platform: PlatformType.Android,
91 },
92 "Run Android Hermes - Experimental": {
93 name: "Run Android Hermes - Experimental",
94 cwd: "${workspaceFolder}",
95 type: DEBUG_TYPES.REACT_NATIVE_DIRECT,
96 request: "launch",
97 platform: PlatformType.Android,
98 enableDebug: false,
99 },
100 "Attach to the React Native Hermes - Experimental": {
101 name: "Attach to the React Native Hermes - Experimental",
102 cwd: "${workspaceFolder}",
103 type: DEBUG_TYPES.REACT_NATIVE_DIRECT,
104 request: "attach",
105 },
106 "Attach to the React Native iOS - Experimental": {
107 name: "Attach to the React Native iOS - Experimental",
108 cwd: "${workspaceFolder}",
109 type: DEBUG_TYPES.REACT_NATIVE_DIRECT,
110 request: "attach",
111 platform: PlatformType.iOS,
112 port: IWDPHelper.iOS_WEBKIT_DEBUG_PROXY_DEFAULT_PORT, // 9221
113 },
114 "Debug Direct iOS - Experimental": {
115 name: "Debug Direct iOS - Experimental",
116 cwd: "${workspaceFolder}",
117 type: DEBUG_TYPES.REACT_NATIVE_DIRECT,
118 request: "launch",
119 platform: PlatformType.iOS,
120 port: IWDPHelper.iOS_WEBKIT_DEBUG_PROXY_DEFAULT_PORT, // 9221
121 },
122 "Run Direct iOS - Experimental": {
123 name: "Run Direct iOS - Experimental",
124 cwd: "${workspaceFolder}",
125 type: DEBUG_TYPES.REACT_NATIVE_DIRECT,
126 request: "launch",
127 platform: PlatformType.iOS,
128 enableDebug: false,
129 },
130 };
131
132 private initialPickConfig: ReadonlyArray<vscode.QuickPickItem> = [
133 {
134 label: "Debug Android",
135 description: localize("DebugAndroidConfigDesc", "Run and debug Android application"),
136 },
137 {
138 label: "Run Android",
139 description: localize("RunAndroidConfigDesc", "Run Android application"),
140 },
141 {
142 label: "Debug iOS",
143 description: localize("DebugiOSConfigDesc", "Run and debug iOS application"),
144 },
145 {
146 label: "Run iOS",
147 description: localize("RuniOSConfigDesc", "Run iOS application"),
148 },
149 {
150 label: "Debug Windows",
151 description: localize("DebugWindowsConfigDesc", "Run and debug Windows application"),
152 },
153 {
154 label: "Debug macOS",
155 description: localize("DebugmacOSConfigDesc", "Run and debug macOS application"),
156 },
157 {
158 label: "Attach to packager",
159 description: localize(
160 "AttachToPackagerConfigDesc",
161 "Attach to already working application packager",
162 ),
163 },
164 {
165 label: "Debug in Exponent",
166 description: localize(
167 "DebugExpoConfigDesc",
168 "Debug Expo application or React Native application in Expo",
169 ),
170 },
171 {
172 label: "Debug Android Hermes - Experimental",
173 description: localize(
174 "DebugAndroidHermesConfigDesc",
175 "Run and debug Android Hermes application",
176 ),
177 },
178 {
179 label: "Attach to the React Native Hermes - Experimental",
180 description: localize(
181 "AttachToPackagerHermesConfigDesc",
182 "Attach to already working React Native Hermes application on Android directly",
183 ),
184 },
185 {
186 label: "Attach to the React Native iOS - Experimental",
187 description: localize(
188 "AttachToPackageriOSConfigDesc",
189 "Attach to already working React Native iOS application directly",
190 ),
191 },
192 {
193 label: "Debug Direct iOS - Experimental",
194 description: localize(
195 "DebugDirectiOSConfigDesc",
196 "Run and debug iOS application directly",
197 ),
198 },
199 {
200 label: "Run Direct iOS - Experimental",
201 description: localize(
202 "RunDirectiOSConfigDesc",
203 "Run iOS application with direct debugging support",
204 ),
205 },
206 ];
207
208 private sequentialPickConfig: ReadonlyArray<DebugConfigurationQuickPickItem> = [
209 {
210 label: "Run application",
211 description: localize(
212 "RunApplicationScenario",
213 "Run React Native application without debugging",
214 ),
215 type: DebugScenarioType.RunApp,
216 },
217 {
218 label: "Debug application",
219 description: localize("DebugApplicationScenario", "Debug React Native application"),
220 type: DebugScenarioType.DebugApp,
221 },
222 {
223 label: "Attach to application",
224 description: localize(
225 "AttachApplicationScenario",
226 "Attach to running React Native application",
227 ),
228 type: DebugScenarioType.AttachApp,
229 },
230 ];
231
232 public async provideDebugConfigurations(
233 folder: vscode.WorkspaceFolder | undefined, // eslint-disable-line @typescript-eslint/no-unused-vars
234 token?: vscode.CancellationToken, // eslint-disable-line @typescript-eslint/no-unused-vars
235 ): Promise<vscode.DebugConfiguration[]> {
236 return new Promise<vscode.DebugConfiguration[]>(resolve => {
237 const configPicker = this.prepareDebugConfigPicker();
238 const disposables: vscode.Disposable[] = [];
239 const pickHandler = () => {
240 let chosenConfigsEvent = TelemetryHelper.createTelemetryEvent(
241 "chosenDebugConfigurations",
242 );
243 let selected: string[] = configPicker.selectedItems.map(element => element.label);
244 chosenConfigsEvent.properties["selectedItems"] = selected;
245 Telemetry.send(chosenConfigsEvent);
246 const launchConfig = this.gatherDebugScenarios(selected);
247 disposables.forEach(d => d.dispose());
248 resolve(launchConfig);
249 };
250
251 disposables.push(
252 configPicker.onDidAccept(pickHandler),
253 configPicker.onDidHide(pickHandler),
254 configPicker,
255 );
256
257 configPicker.show();
258 });
259 }
260
261 public async provideDebugConfigurationSequentially(
262 folder: vscode.WorkspaceFolder | undefined,
263 token?: vscode.CancellationToken,
264 ): Promise<vscode.DebugConfiguration | undefined> {
265 const config: Partial<ILaunchRequestArgs> = {};
266 const state = { config, scenarioType: DebugScenarioType.DebugApp, folder, token };
267
268 const multiStep = new MultiStepInput<DebugConfigurationState>();
269 await multiStep.run((input, s) => this.pickDebugConfiguration(input, s), state);
270
271 if (Object.keys(state.config).length === 0) {
272 return;
273 } else {
274 if (state.config.type === DEBUG_TYPES.REACT_NATIVE_DIRECT) {
275 state.config.name = DebugScenarioNameGenerator.createScenarioName(
276 state.scenarioType,
277 state.config.type,
278 state.config.platform,
279 true,
280 );
281 } else {
282 state.config.name = DebugScenarioNameGenerator.createScenarioName(
283 state.scenarioType,
284 state.config.type || DEBUG_TYPES.REACT_NATIVE,
285 state.config.platform,
286 );
287 }
288 return state.config as vscode.DebugConfiguration;
289 }
290 }
291
292 private async pickDebugConfiguration(
293 input: IMultiStepInput<DebugConfigurationState>,
294 state: DebugConfigurationState,
295 ): Promise<InputStep<DebugConfigurationState> | void> {
296 state.config = {};
297 const pick = await input.showQuickPick<
298 DebugConfigurationQuickPickItem,
299 IQuickPickParameters<DebugConfigurationQuickPickItem>
300 >({
301 title: localize("DebugConfigQuickPickSequentialLabel", "Select a debug configuration"),
302 placeholder: "Debug Configuration",
303 activeItem: this.sequentialPickConfig[0],
304 items: this.sequentialPickConfig,
305 });
306 if (pick) {
307 const provider = ConfigProviderFactory.create(pick.type);
308 return provider.buildConfiguration.bind(provider);
309 }
310 }
311
312 private gatherDebugScenarios(selectedItems: string[]): vscode.DebugConfiguration[] {
313 let launchConfig: vscode.DebugConfiguration[] = selectedItems.map(
314 element => this.debugConfigurations[element],
315 );
316 return launchConfig;
317 }
318
319 private prepareDebugConfigPicker(): vscode.QuickPick<vscode.QuickPickItem> {
320 const debugConfigPicker = vscode.window.createQuickPick();
321 debugConfigPicker.canSelectMany = true;
322 debugConfigPicker.ignoreFocusOut = true;
323 debugConfigPicker.title = localize(
324 "DebugConfigQuickPickLabel",
325 "Pick debug configurations",
326 );
327 debugConfigPicker.items = this.initialPickConfig;
328 // QuickPickItem property `picked` doesn't work, so this line will check first item in the list
329 // which is supposed to be Debug Android
330 debugConfigPicker.selectedItems = [this.initialPickConfig[0]];
331 return debugConfigPicker;
332 }
333}
334