Show custom messages for no SDKs in Launch Emulator dialog
Summary: Our launch emulator button isn't very helpful when you don't have any SDKs set up as it shows you exactly the same message as if it was loading for a bit longer. We've seen a low, but constant flow of support requests and it's often not easy to debug remotely unless you dig into the state export. This sets up a new actionable message when you have neither Android nor iOS support enabled and sends you straight to the settings. Changelog: Show alert in Launch Emulator dialogue if no SDKs are enabled Reviewed By: mweststrate Differential Revision: D36596972 fbshipit-source-id: ba72e9aaeb136c1a7e2f360ef9fbbeec6bc76f4d
This commit is contained in:
committed by
Facebook GitHub Bot
parent
015be5ad83
commit
fe29183014
@@ -21,6 +21,7 @@ import {Layout, renderReactRoot, withTrackingScope} from 'flipper-plugin';
|
|||||||
import {Provider} from 'react-redux';
|
import {Provider} from 'react-redux';
|
||||||
import {IOSDeviceParams} from 'flipper-common';
|
import {IOSDeviceParams} from 'flipper-common';
|
||||||
import {getRenderHostInstance} from '../../RenderHost';
|
import {getRenderHostInstance} from '../../RenderHost';
|
||||||
|
import SettingsSheet from '../../chrome/SettingsSheet';
|
||||||
|
|
||||||
const COLD_BOOT = 'cold-boot';
|
const COLD_BOOT = 'cold-boot';
|
||||||
|
|
||||||
@@ -36,12 +37,47 @@ function LaunchEmulatorContainer({onClose}: {onClose: () => void}) {
|
|||||||
return <LaunchEmulatorDialog onClose={onClose} />;
|
return <LaunchEmulatorDialog onClose={onClose} />;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
function NoSDKsEnabledAlert({onClose}: {onClose: () => void}) {
|
||||||
|
const [showSettings, setShowSettings] = useState(false);
|
||||||
|
const footer = (
|
||||||
|
<>
|
||||||
|
<Button onClick={onClose}>Close</Button>
|
||||||
|
<Button type="primary" onClick={() => setShowSettings(true)}>
|
||||||
|
Open Settings
|
||||||
|
</Button>
|
||||||
|
</>
|
||||||
|
);
|
||||||
|
return (
|
||||||
|
<>
|
||||||
|
<Modal
|
||||||
|
visible
|
||||||
|
centered
|
||||||
|
onCancel={onClose}
|
||||||
|
title="No Mobile SDKs Enabled"
|
||||||
|
footer={footer}>
|
||||||
|
<Layout.Container gap>
|
||||||
|
<Alert message="You currently have neither Android nor iOS Development support enabled. To use emulators or simulators, you need to enable at least one in the settings." />
|
||||||
|
</Layout.Container>
|
||||||
|
</Modal>
|
||||||
|
{showSettings && (
|
||||||
|
<SettingsSheet
|
||||||
|
platform={
|
||||||
|
getRenderHostInstance().serverConfig.environmentInfo.os.platform
|
||||||
|
}
|
||||||
|
onHide={() => setShowSettings(false)}
|
||||||
|
/>
|
||||||
|
)}
|
||||||
|
</>
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
export const LaunchEmulatorDialog = withTrackingScope(
|
export const LaunchEmulatorDialog = withTrackingScope(
|
||||||
function LaunchEmulatorDialog({onClose}: {onClose: () => void}) {
|
function LaunchEmulatorDialog({onClose}: {onClose: () => void}) {
|
||||||
const iosEnabled = useStore((state) => state.settingsState.enableIOS);
|
const iosEnabled = useStore((state) => state.settingsState.enableIOS);
|
||||||
const androidEnabled = useStore(
|
const androidEnabled = useStore(
|
||||||
(state) => state.settingsState.enableAndroid,
|
(state) => state.settingsState.enableAndroid,
|
||||||
);
|
);
|
||||||
|
|
||||||
const [iosEmulators, setIosEmulators] = useState<IOSDeviceParams[]>([]);
|
const [iosEmulators, setIosEmulators] = useState<IOSDeviceParams[]>([]);
|
||||||
const [androidEmulators, setAndroidEmulators] = useState<string[]>([]);
|
const [androidEmulators, setAndroidEmulators] = useState<string[]>([]);
|
||||||
|
|
||||||
@@ -79,6 +115,10 @@ export const LaunchEmulatorDialog = withTrackingScope(
|
|||||||
});
|
});
|
||||||
}, [androidEnabled]);
|
}, [androidEnabled]);
|
||||||
|
|
||||||
|
if (!iosEnabled && !androidEnabled) {
|
||||||
|
return <NoSDKsEnabledAlert onClose={onClose} />;
|
||||||
|
}
|
||||||
|
|
||||||
const items = [
|
const items = [
|
||||||
...(androidEmulators.length > 0
|
...(androidEmulators.length > 0
|
||||||
? [<AndroidOutlined key="android logo" />]
|
? [<AndroidOutlined key="android logo" />]
|
||||||
|
|||||||
@@ -17,8 +17,16 @@ import {createRootReducer} from '../../../reducers';
|
|||||||
import {sleep} from 'flipper-plugin';
|
import {sleep} from 'flipper-plugin';
|
||||||
import {getRenderHostInstance} from '../../../RenderHost';
|
import {getRenderHostInstance} from '../../../RenderHost';
|
||||||
|
|
||||||
test('Can render and launch android apps - empty', async () => {
|
test('Can render and launch android apps - no emulators', async () => {
|
||||||
const store = createStore(createRootReducer());
|
const store = createStore(createRootReducer());
|
||||||
|
store.dispatch({
|
||||||
|
type: 'UPDATE_SETTINGS',
|
||||||
|
payload: {
|
||||||
|
...store.getState().settingsState,
|
||||||
|
enableAndroid: true,
|
||||||
|
enableIOS: true,
|
||||||
|
},
|
||||||
|
});
|
||||||
|
|
||||||
const responses: any = {
|
const responses: any = {
|
||||||
'ios-get-simulators': [],
|
'ios-get-simulators': [],
|
||||||
@@ -44,6 +52,43 @@ test('Can render and launch android apps - empty', async () => {
|
|||||||
`);
|
`);
|
||||||
});
|
});
|
||||||
|
|
||||||
|
test('Can render and launch android apps - no SDKs', async () => {
|
||||||
|
const store = createStore(createRootReducer());
|
||||||
|
store.dispatch({
|
||||||
|
type: 'UPDATE_SETTINGS',
|
||||||
|
payload: {
|
||||||
|
...store.getState().settingsState,
|
||||||
|
enableAndroid: false,
|
||||||
|
enableIOS: false,
|
||||||
|
},
|
||||||
|
});
|
||||||
|
|
||||||
|
const responses: any = {
|
||||||
|
'ios-get-simulators': [],
|
||||||
|
'android-get-emulators': [],
|
||||||
|
};
|
||||||
|
getRenderHostInstance().flipperServer.exec = async function (cmd: any) {
|
||||||
|
return responses[cmd];
|
||||||
|
} as any;
|
||||||
|
const onClose = jest.fn();
|
||||||
|
|
||||||
|
const renderer = render(
|
||||||
|
<Provider store={store}>
|
||||||
|
<LaunchEmulatorDialog onClose={onClose} />
|
||||||
|
</Provider>,
|
||||||
|
);
|
||||||
|
|
||||||
|
expect(await renderer.findByText(/No Mobile SDKs Enabled/))
|
||||||
|
.toMatchInlineSnapshot(`
|
||||||
|
<div
|
||||||
|
class="ant-modal-title"
|
||||||
|
id="rcDialogTitle1"
|
||||||
|
>
|
||||||
|
No Mobile SDKs Enabled
|
||||||
|
</div>
|
||||||
|
`);
|
||||||
|
});
|
||||||
|
|
||||||
test('Can render and launch android apps', async () => {
|
test('Can render and launch android apps', async () => {
|
||||||
const store = createStore(createRootReducer());
|
const store = createStore(createRootReducer());
|
||||||
|
|
||||||
|
|||||||
Reference in New Issue
Block a user