microsoft/vscode-react-native

Public

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

CodeCommitsIssuesPull requestsActionsInsightsSecurity
transitive-dependency-serialize-javascript

Branches

Tags

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

Clone

HTTPS

Download ZIP

src/extension/exponent/exponentPlatform.ts

212lines · modeblame

0a68f8dbArtem Egorov8 years ago1// Copyright (c) Microsoft Corporation. All rights reserved.
2// Licensed under the MIT license. See LICENSE file in the project root for details.
3
09f6024fHeniker4 years ago4import * as url from "url";
5import * as vscode from "vscode";
6import * as nls from "vscode-nls";
b23d758aEzio Li2 years ago7import * as qrcode from "qrcode-terminal";
031832ffArtem Egorov8 years ago8import { ErrorHelper } from "../../common/error/errorHelper";
9import { InternalErrorCode } from "../../common/error/internalErrorCode";
5471436aRedMickey5 years ago10import { ExpoHostType, IExponentRunOptions, PlatformType } from "../launchArgs";
4cd25962JiglioNero4 years ago11import { GeneralPlatform, MobilePlatformDeps } from "../generalPlatform";
031832ffArtem Egorov8 years ago12import { TelemetryHelper } from "../../common/telemetryHelper";
3c871141Yuri Skorokhodov7 years ago13import { QRCodeContentProvider } from "../qrCodeContentProvider";
09f6024fHeniker4 years ago14import { ExponentHelper } from "./exponentHelper";
0a68f8dbArtem Egorov8 years ago15
4787ec09Artem Egorov8 years ago16import * as XDL from "./xdlInterface";
09f6024fHeniker4 years ago17
34472878RedMickey5 years ago18nls.config({
19messageFormat: nls.MessageFormat.bundle,
20bundleFormat: nls.BundleFormat.standalone,
21})();
d7d405aeYuri Skorokhodov7 years ago22const localize = nls.loadMessageBundle();
0a68f8dbArtem Egorov8 years ago23
cea20880lexie0112 years ago24let QRCodeUrl = "";
25
4cd25962JiglioNero4 years ago26export class ExponentPlatform extends GeneralPlatform {
0a68f8dbArtem Egorov8 years ago27private exponentTunnelPath: string | null;
2e432a9eArtem Egorov8 years ago28private exponentHelper: ExponentHelper;
3c871141Yuri Skorokhodov7 years ago29private qrCodeContentProvider: QRCodeContentProvider = new QRCodeContentProvider();
62c4de22RedMickey6 years ago30constructor(runOptions: IExponentRunOptions, platformDeps: MobilePlatformDeps = {}) {
0a68f8dbArtem Egorov8 years ago31super(runOptions, platformDeps);
c036b0d3JiglioNero5 years ago32this.exponentHelper = this.packager.getExponentHelper();
0a68f8dbArtem Egorov8 years ago33this.exponentTunnelPath = null;
34}
35
0d77292aJiglioNero4 years ago36public async runApp(): Promise<void> {
ba953e9fRedMickey6 years ago37let extProps = {
031832ffArtem Egorov8 years ago38platform: {
259c018fYuri Skorokhodov5 years ago39value: PlatformType.Exponent,
031832ffArtem Egorov8 years ago40isPii: false,
4787ec09Artem Egorov8 years ago41},
031832ffArtem Egorov8 years ago42};
4787ec09Artem Egorov8 years ago43
34472878RedMickey5 years ago44extProps = TelemetryHelper.addPlatformPropertiesToTelemetryProperties(
45this.runOptions,
46this.runOptions.reactNativeVersions,
47extProps,
48);
ba953e9fRedMickey6 years ago49
0d77292aJiglioNero4 years ago50await TelemetryHelper.generate("ExponentPlatform.runApp", extProps, async () => {
51await this.loginToExponentOrSkip(this.runOptions.expoHostType);
aa7c5b92Ezio Li1 years ago52const port = this.packager.getPort();
53await XDL.setOptions(this.projectPath, { packagerPort: port });
0d77292aJiglioNero4 years ago54await XDL.startExponentServer(this.projectPath);
55
56// the purpose of this is to save the same sequence of handling 'adb reverse' command execution as in Expo
57// https://github.com/expo/expo-cli/blob/1d515d21200841e181518358fd9dc4c7b24c7cd6/packages/xdl/src/Project.ts#L2226-L2370
58// we added this to be sure that our Expo launching logic doesn't have any negative side effects
59
60if (this.runOptions.expoHostType === "tunnel") {
61await this.prepareExpoTunnels();
62} else {
63await XDL.stopAdbReverse(this.projectPath);
64}
65
66const isAdbReversed =
67this.runOptions.expoHostType !== "local"
68? false
69: // we need to execute 'adb reverse' command to bind ports used by Expo and RN of local machine to ports of a connected Android device or a running emulator
70await XDL.startAdbReverse(this.projectPath);
71let exponentUrl = "";
72switch (this.runOptions.expoHostType) {
73case "lan":
74exponentUrl = await XDL.getUrl(this.projectPath, {
75dev: true,
76minify: false,
77hostType: "lan",
78});
79break;
80case "local":
81if (isAdbReversed) {
82this.logger.info(
83localize(
84"ExpoStartAdbReverseSuccess",
85"A device or an emulator was found, 'adb reverse' command successfully executed.",
86),
87);
88} else {
89this.logger.warning(
90localize(
91"ExpoStartAdbReverseFailure",
92"Adb reverse command failed. Couldn't find connected over usb device or running emulator. Also please make sure that there is only one currently connected device or running emulator.",
93),
34472878RedMickey5 years ago94);
0d77292aJiglioNero4 years ago95}
96
97exponentUrl = await XDL.getUrl(this.projectPath, {
98dev: true,
99minify: false,
100hostType: "localhost",
ce5e88eeYuri Skorokhodov5 years ago101});
0d77292aJiglioNero4 years ago102break;
103case "tunnel":
104default:
105exponentUrl = await XDL.getUrl(this.projectPath, { dev: true, minify: false });
106}
aa7c5b92Ezio Li1 years ago107
108// Make sure expo app url port is switched to customization
109const urlString = url.parse(exponentUrl);
110urlString.port = port.toString();
111exponentUrl = `exp://${String(urlString.hostname)}:${String(urlString.port)}`;
0d77292aJiglioNero4 years ago112
113if (!exponentUrl) {
114throw ErrorHelper.getInternalError(InternalErrorCode.ExpectedExponentTunnelPath);
115}
116
cea20880lexie0112 years ago117this.exponentTunnelPath = QRCodeUrl = exponentUrl;
b29085d1Ezio Li3 years ago118const outputMessage = localize(
119"ExponentServerIsRunningOpenToSeeIt",
120"Expo server is running. Open your Expo app at {0} to see it.",
121this.exponentTunnelPath,
122);
123this.logger.info(outputMessage);
124
0d77292aJiglioNero4 years ago125if (this.runOptions.openExpoQR) {
09f6024fHeniker4 years ago126const exponentPage = vscode.window.createWebviewPanel(
0d77292aJiglioNero4 years ago127"Expo QR Code",
128"Expo QR Code",
129vscode.ViewColumn.Two,
130{},
131);
132exponentPage.webview.html = this.qrCodeContentProvider.provideTextDocumentContent(
133vscode.Uri.parse(exponentUrl),
134);
b29085d1Ezio Li3 years ago135const outputMessage = localize(
136"QRCodeOutputInstructions",
137"Scan below QR code to open your app:",
138);
139this.logger.info(outputMessage);
b23d758aEzio Li2 years ago140qrcode.generate(exponentUrl, { small: true }, (qrcode: string) =>
396110f7Ezio Li3 years ago141this.logger.info(`\n${qrcode}`),
142);
0d77292aJiglioNero4 years ago143}
144
145const copyButton = localize("CopyToClipboard", "Copy to clipboard");
146
09f6024fHeniker4 years ago147void vscode.window.showInformationMessage(outputMessage, copyButton).then(selection => {
0d77292aJiglioNero4 years ago148if (selection === copyButton) {
09f6024fHeniker4 years ago149void vscode.env.clipboard.writeText(exponentUrl);
0d77292aJiglioNero4 years ago150}
ce5e88eeYuri Skorokhodov5 years ago151});
4787ec09Artem Egorov8 years ago152});
153}
154
0d77292aJiglioNero4 years ago155public async loginToExponentOrSkip(expoHostType?: ExpoHostType): Promise<any> {
62c4de22RedMickey6 years ago156if (expoHostType !== "tunnel") {
0d77292aJiglioNero4 years ago157return;
62c4de22RedMickey6 years ago158}
0d77292aJiglioNero4 years ago159
160return await this.exponentHelper.loginToExponent(
09f6024fHeniker4 years ago161async (message, password) =>
162(await vscode.window.showInputBox({
163placeHolder: message,
164password,
165})) || "",
0d77292aJiglioNero4 years ago166async message => {
167const okButton = { title: "Ok" };
168const cancelButton = { title: "Cancel", isCloseAffordance: true };
169const answer = await vscode.window.showInformationMessage(
170message,
171{ modal: true },
172okButton,
173cancelButton,
174);
175if (answer === cancelButton) {
176throw ErrorHelper.getInternalError(InternalErrorCode.UserCancelledExpoLogin);
177}
178return "";
34472878RedMickey5 years ago179},
62c4de22RedMickey6 years ago180);
181}
182
0d77292aJiglioNero4 years ago183public async beforeStartPackager(): Promise<void> {
4787ec09Artem Egorov8 years ago184return this.exponentHelper.configureExponentEnvironment();
0a68f8dbArtem Egorov8 years ago185}
186
0d77292aJiglioNero4 years ago187public async enableJSDebuggingMode(): Promise<void> {
34472878RedMickey5 years ago188this.logger.info(
189localize(
190"ApplicationIsRunningOnExponentShakeDeviceForRemoteDebugging",
191"Application is running on Expo. Please shake device and select 'Debug JS Remotely' to enable debugging.",
192),
193);
0a68f8dbArtem Egorov8 years ago194}
db6fd42aRuslan Bikkinin7 years ago195
cbc7ac5bArtem Egorov7 years ago196public getRunArguments(): string[] {
db6fd42aRuslan Bikkinin7 years ago197return [];
198}
efb436fcRedMickey5 years ago199
0d77292aJiglioNero4 years ago200private async prepareExpoTunnels(): Promise<void> {
201try {
202await this.exponentHelper.findOrInstallNgrokGlobally();
203await XDL.startTunnels(this.projectPath);
204} finally {
205this.exponentHelper.removeNodeModulesPathFromEnvIfWasSet();
206}
efb436fcRedMickey5 years ago207}
0a68f8dbArtem Egorov8 years ago208}
cea20880lexie0112 years ago209
210export function getQRCodeUrl() {
211return QRCodeUrl;
212}