mirror of
https://github.com/lensapp/lens.git
synced 2025-05-20 05:10:56 +00:00
add confirm to internal install extension route
Signed-off-by: Sebastian Malton <sebastian@malton.name>
This commit is contained in:
parent
dc6623ec65
commit
30f59655f0
@ -13,7 +13,7 @@ export async function installExtension(params: RouteParams): Promise<void> {
|
||||
|
||||
try {
|
||||
navigate(extensionsURL());
|
||||
await installFromNpm(name);
|
||||
await installFromNpm(name, true);
|
||||
} catch (error) {
|
||||
logger.error("[PH - Install Extension]: failed to install from NPM", error);
|
||||
}
|
||||
|
||||
@ -30,6 +30,7 @@ interface InstallRequest {
|
||||
fileName: string;
|
||||
filePath?: string;
|
||||
data?: Buffer;
|
||||
confirmInstall?: boolean;
|
||||
}
|
||||
|
||||
interface InstallRequestPreloaded extends InstallRequest {
|
||||
@ -164,6 +165,10 @@ async function requestInstall(init: InstallRequest | InstallRequest[]) {
|
||||
const folderExists = await fse.pathExists(extensionFolder);
|
||||
|
||||
if (!folderExists) {
|
||||
if (install.confirmInstall && !(await confirmInstallExtension(install.manifest))) {
|
||||
continue;
|
||||
}
|
||||
|
||||
// auto-install extension if not yet exists
|
||||
return unpackExtension(install);
|
||||
} else {
|
||||
@ -309,6 +314,20 @@ async function uninstallExtension(extension: InstalledExtension) {
|
||||
}
|
||||
}
|
||||
|
||||
function confirmInstallExtension({name, version}: LensExtensionManifest): Promise<boolean> {
|
||||
const displayName = extensionDisplayName(name, version);
|
||||
|
||||
return new Promise(resolve => {
|
||||
ConfirmDialog.open({
|
||||
message: <p>Are you sure you want to install extension <b>{displayName}</b>?</p>,
|
||||
labelOk: <Trans>Yes</Trans>,
|
||||
labelCancel: <Trans>No</Trans>,
|
||||
ok: () => resolve(true),
|
||||
cancel: () => resolve(false),
|
||||
});
|
||||
});
|
||||
}
|
||||
|
||||
function confirmUninstallExtension(extension: InstalledExtension) {
|
||||
const displayName = extensionDisplayName(extension.manifest.name, extension.manifest.version);
|
||||
|
||||
@ -357,15 +376,15 @@ async function installFromSelectFileDialog() {
|
||||
* Start extension install using a package name, which is resolved to a tarball url using the npm registry.
|
||||
* @param packageName e.g. "@publisher/extension-name"
|
||||
*/
|
||||
export async function installFromNpm(packageName: string) {
|
||||
export async function installFromNpm(packageName: string, confirm = false) {
|
||||
const tarballUrl = await extensionLoader.getNpmPackageTarballUrl(packageName, "@hackweek");
|
||||
|
||||
Notifications.info(`Installing ${packageName}`);
|
||||
|
||||
return installFromUrlOrPath(tarballUrl);
|
||||
return installFromUrlOrPath(tarballUrl, confirm);
|
||||
}
|
||||
|
||||
async function installFromUrlOrPath(installPath: string) {
|
||||
async function installFromUrlOrPath(installPath: string, confirmInstall = false) {
|
||||
ExtensionStateStore.getInstance<ExtensionStateStore>().startingInstall = true;
|
||||
const fileName = path.basename(installPath);
|
||||
|
||||
@ -376,11 +395,11 @@ async function installFromUrlOrPath(installPath: string) {
|
||||
const { promise: filePromise } = downloadFile({ url: installPath, timeout: 60000 /*1m*/ });
|
||||
const data = await filePromise;
|
||||
|
||||
await requestInstall({ fileName, data });
|
||||
await requestInstall({ fileName, data, confirmInstall });
|
||||
}
|
||||
// otherwise installing from system path
|
||||
else if (InputValidators.isPath.validate(installPath)) {
|
||||
await requestInstall({ fileName, filePath: installPath });
|
||||
await requestInstall({ fileName, filePath: installPath, confirmInstall });
|
||||
}
|
||||
} catch (error) {
|
||||
ExtensionStateStore.getInstance<ExtensionStateStore>().startingInstall = false;
|
||||
|
||||
@ -4,7 +4,7 @@ import React, { ReactNode } from "react";
|
||||
import { observable } from "mobx";
|
||||
import { observer } from "mobx-react";
|
||||
import { Trans } from "@lingui/macro";
|
||||
import { cssNames, noop, prevDefault } from "../../utils";
|
||||
import { cssNames, prevDefault } from "../../utils";
|
||||
import { Button, ButtonProps } from "../button";
|
||||
import { Dialog, DialogProps } from "../dialog";
|
||||
import { Icon } from "../icon";
|
||||
@ -13,7 +13,8 @@ export interface ConfirmDialogProps extends Partial<DialogProps> {
|
||||
}
|
||||
|
||||
export interface ConfirmDialogParams {
|
||||
ok?: () => void;
|
||||
ok?: () => void | Promise<void> | Promise<any>;
|
||||
cancel?: () => void | Promise<void> | Promise<any>;
|
||||
labelOk?: ReactNode;
|
||||
labelCancel?: ReactNode;
|
||||
message?: ReactNode;
|
||||
@ -39,7 +40,6 @@ export class ConfirmDialog extends React.Component<ConfirmDialogProps> {
|
||||
}
|
||||
|
||||
public defaultParams: ConfirmDialogParams = {
|
||||
ok: noop,
|
||||
labelOk: <Trans>Ok</Trans>,
|
||||
labelCancel: <Trans>Cancel</Trans>,
|
||||
icon: <Icon big material="warning"/>,
|
||||
@ -52,18 +52,27 @@ export class ConfirmDialog extends React.Component<ConfirmDialogProps> {
|
||||
ok = async () => {
|
||||
try {
|
||||
this.isSaving = true;
|
||||
await Promise.resolve(this.params.ok()).catch(noop);
|
||||
await this.params.ok?.();
|
||||
} catch {
|
||||
// ignore
|
||||
} finally {
|
||||
this.isSaving = false;
|
||||
}
|
||||
this.close();
|
||||
ConfirmDialog.close();
|
||||
};
|
||||
|
||||
onClose = () => {
|
||||
this.isSaving = false;
|
||||
};
|
||||
|
||||
close = () => {
|
||||
close = async () => {
|
||||
try {
|
||||
await this.params.cancel?.();
|
||||
} catch {
|
||||
// ignore
|
||||
} finally {
|
||||
this.isSaving = false;
|
||||
}
|
||||
ConfirmDialog.close();
|
||||
};
|
||||
|
||||
|
||||
Loading…
Reference in New Issue
Block a user