mirror of
https://github.com/elastic/kibana.git
synced 2025-04-24 17:59:23 -04:00
Co-authored-by: cchaos <caroline.horn@elastic.co> Co-authored-by: Dave Snider <dave.snider@gmail.com> Co-authored-by: Kibana Machine <42973632+kibanamachine@users.noreply.github.com> Co-authored-by: Thomas Neirynck <thomas@elastic.co> Co-authored-by: Josh Dover <1813008+joshdover@users.noreply.github.com> Co-authored-by: cchaos <caroline.horn@elastic.co> Co-authored-by: Dave Snider <dave.snider@gmail.com> Co-authored-by: Thomas Neirynck <thomas@elastic.co>
This commit is contained in:
parent
660ed36354
commit
359d28d3c6
11 changed files with 360 additions and 453 deletions
|
@ -21,10 +21,28 @@ exports[`home change home route should render a link to change the default route
|
|||
/>
|
||||
<AddData
|
||||
addBasePath={[Function]}
|
||||
application={
|
||||
Object {
|
||||
"capabilities": Object {
|
||||
"navLinks": Object {
|
||||
"integrations": true,
|
||||
},
|
||||
},
|
||||
}
|
||||
}
|
||||
isDarkMode={false}
|
||||
/>
|
||||
<ManageData
|
||||
addBasePath={[Function]}
|
||||
application={
|
||||
Object {
|
||||
"capabilities": Object {
|
||||
"navLinks": Object {
|
||||
"integrations": true,
|
||||
},
|
||||
},
|
||||
}
|
||||
}
|
||||
features={Array []}
|
||||
/>
|
||||
<mockConstructor
|
||||
|
@ -57,10 +75,28 @@ exports[`home directories should not render directory entry when showOnHomePage
|
|||
/>
|
||||
<AddData
|
||||
addBasePath={[Function]}
|
||||
application={
|
||||
Object {
|
||||
"capabilities": Object {
|
||||
"navLinks": Object {
|
||||
"integrations": true,
|
||||
},
|
||||
},
|
||||
}
|
||||
}
|
||||
isDarkMode={false}
|
||||
/>
|
||||
<ManageData
|
||||
addBasePath={[Function]}
|
||||
application={
|
||||
Object {
|
||||
"capabilities": Object {
|
||||
"navLinks": Object {
|
||||
"integrations": true,
|
||||
},
|
||||
},
|
||||
}
|
||||
}
|
||||
features={Array []}
|
||||
/>
|
||||
<mockConstructor
|
||||
|
@ -93,10 +129,28 @@ exports[`home directories should render ADMIN directory entry in "Manage your da
|
|||
/>
|
||||
<AddData
|
||||
addBasePath={[Function]}
|
||||
application={
|
||||
Object {
|
||||
"capabilities": Object {
|
||||
"navLinks": Object {
|
||||
"integrations": true,
|
||||
},
|
||||
},
|
||||
}
|
||||
}
|
||||
isDarkMode={false}
|
||||
/>
|
||||
<ManageData
|
||||
addBasePath={[Function]}
|
||||
application={
|
||||
Object {
|
||||
"capabilities": Object {
|
||||
"navLinks": Object {
|
||||
"integrations": true,
|
||||
},
|
||||
},
|
||||
}
|
||||
}
|
||||
features={
|
||||
Array [
|
||||
Object {
|
||||
|
@ -176,10 +230,28 @@ exports[`home directories should render solutions in the "solution section" 1`]
|
|||
/>
|
||||
<AddData
|
||||
addBasePath={[Function]}
|
||||
application={
|
||||
Object {
|
||||
"capabilities": Object {
|
||||
"navLinks": Object {
|
||||
"integrations": true,
|
||||
},
|
||||
},
|
||||
}
|
||||
}
|
||||
isDarkMode={false}
|
||||
/>
|
||||
<ManageData
|
||||
addBasePath={[Function]}
|
||||
application={
|
||||
Object {
|
||||
"capabilities": Object {
|
||||
"navLinks": Object {
|
||||
"integrations": true,
|
||||
},
|
||||
},
|
||||
}
|
||||
}
|
||||
features={Array []}
|
||||
/>
|
||||
<mockConstructor
|
||||
|
@ -212,10 +284,28 @@ exports[`home isNewKibanaInstance should safely handle exceptions 1`] = `
|
|||
/>
|
||||
<AddData
|
||||
addBasePath={[Function]}
|
||||
application={
|
||||
Object {
|
||||
"capabilities": Object {
|
||||
"navLinks": Object {
|
||||
"integrations": true,
|
||||
},
|
||||
},
|
||||
}
|
||||
}
|
||||
isDarkMode={false}
|
||||
/>
|
||||
<ManageData
|
||||
addBasePath={[Function]}
|
||||
application={
|
||||
Object {
|
||||
"capabilities": Object {
|
||||
"navLinks": Object {
|
||||
"integrations": true,
|
||||
},
|
||||
},
|
||||
}
|
||||
}
|
||||
features={Array []}
|
||||
/>
|
||||
<mockConstructor
|
||||
|
@ -248,10 +338,28 @@ exports[`home isNewKibanaInstance should set isNewKibanaInstance to false when t
|
|||
/>
|
||||
<AddData
|
||||
addBasePath={[Function]}
|
||||
application={
|
||||
Object {
|
||||
"capabilities": Object {
|
||||
"navLinks": Object {
|
||||
"integrations": true,
|
||||
},
|
||||
},
|
||||
}
|
||||
}
|
||||
isDarkMode={false}
|
||||
/>
|
||||
<ManageData
|
||||
addBasePath={[Function]}
|
||||
application={
|
||||
Object {
|
||||
"capabilities": Object {
|
||||
"navLinks": Object {
|
||||
"integrations": true,
|
||||
},
|
||||
},
|
||||
}
|
||||
}
|
||||
features={Array []}
|
||||
/>
|
||||
<mockConstructor
|
||||
|
@ -480,314 +588,28 @@ exports[`home should render home component 1`] = `
|
|||
/>
|
||||
<AddData
|
||||
addBasePath={[Function]}
|
||||
application={
|
||||
Object {
|
||||
"capabilities": Object {
|
||||
"navLinks": Object {
|
||||
"integrations": true,
|
||||
},
|
||||
},
|
||||
}
|
||||
}
|
||||
isDarkMode={false}
|
||||
/>
|
||||
<ManageData
|
||||
addBasePath={[Function]}
|
||||
features={Array []}
|
||||
/>
|
||||
<mockConstructor
|
||||
addBasePath={[Function]}
|
||||
onChangeDefaultRoute={[Function]}
|
||||
onSetDefaultRoute={[Function]}
|
||||
path="/app/home"
|
||||
/>
|
||||
</mockConstructor>
|
||||
`;
|
||||
|
||||
exports[`home welcome should show the normal home page if loading fails 1`] = `
|
||||
<mockConstructor
|
||||
data-test-subj="homeApp"
|
||||
pageHeader={
|
||||
Object {
|
||||
"bottomBorder": false,
|
||||
"pageTitle": <FormattedMessage
|
||||
defaultMessage="Welcome home"
|
||||
id="home.header.title"
|
||||
values={Object {}}
|
||||
/>,
|
||||
}
|
||||
}
|
||||
template="empty"
|
||||
>
|
||||
<SolutionsSection
|
||||
addBasePath={[Function]}
|
||||
solutions={Array []}
|
||||
/>
|
||||
<AddData
|
||||
addBasePath={[Function]}
|
||||
isDarkMode={false}
|
||||
/>
|
||||
<ManageData
|
||||
addBasePath={[Function]}
|
||||
features={Array []}
|
||||
/>
|
||||
<mockConstructor
|
||||
addBasePath={[Function]}
|
||||
onChangeDefaultRoute={[Function]}
|
||||
onSetDefaultRoute={[Function]}
|
||||
path="/app/home"
|
||||
/>
|
||||
</mockConstructor>
|
||||
`;
|
||||
|
||||
exports[`home welcome should show the normal home page if welcome screen is disabled locally 1`] = `
|
||||
<mockConstructor
|
||||
data-test-subj="homeApp"
|
||||
pageHeader={
|
||||
Object {
|
||||
"bottomBorder": false,
|
||||
"pageTitle": <FormattedMessage
|
||||
defaultMessage="Welcome home"
|
||||
id="home.header.title"
|
||||
values={Object {}}
|
||||
/>,
|
||||
}
|
||||
}
|
||||
template="empty"
|
||||
>
|
||||
<SolutionsSection
|
||||
addBasePath={[Function]}
|
||||
solutions={Array []}
|
||||
/>
|
||||
<AddData
|
||||
addBasePath={[Function]}
|
||||
isDarkMode={false}
|
||||
/>
|
||||
<ManageData
|
||||
addBasePath={[Function]}
|
||||
features={Array []}
|
||||
/>
|
||||
<mockConstructor
|
||||
addBasePath={[Function]}
|
||||
onChangeDefaultRoute={[Function]}
|
||||
onSetDefaultRoute={[Function]}
|
||||
path="/app/home"
|
||||
/>
|
||||
</mockConstructor>
|
||||
`;
|
||||
|
||||
exports[`home welcome should show the welcome screen if enabled, and there are no index patterns defined 1`] = `
|
||||
<Welcome
|
||||
onSkip={[Function]}
|
||||
telemetry={
|
||||
Object {
|
||||
"telemetryConstants": Object {
|
||||
"getPrivacyStatementUrl": [MockFunction],
|
||||
},
|
||||
"telemetryNotifications": TelemetryNotifications {
|
||||
"http": Object {
|
||||
"addLoadingCountSource": [MockFunction],
|
||||
"anonymousPaths": Object {
|
||||
"isAnonymous": [MockFunction],
|
||||
"register": [MockFunction],
|
||||
},
|
||||
"basePath": BasePath {
|
||||
"basePath": "",
|
||||
"get": [Function],
|
||||
"prepend": [Function],
|
||||
"publicBaseUrl": undefined,
|
||||
"remove": [Function],
|
||||
"serverBasePath": "",
|
||||
},
|
||||
"delete": [MockFunction],
|
||||
"externalUrl": Object {
|
||||
"validateUrl": [MockFunction],
|
||||
},
|
||||
"fetch": [MockFunction],
|
||||
"get": [MockFunction],
|
||||
"getLoadingCount$": [MockFunction],
|
||||
"head": [MockFunction],
|
||||
"intercept": [MockFunction],
|
||||
"options": [MockFunction],
|
||||
"patch": [MockFunction],
|
||||
"post": [MockFunction],
|
||||
"put": [MockFunction],
|
||||
},
|
||||
"onSetOptInClick": [Function],
|
||||
"optInBannerId": undefined,
|
||||
"optedInNoticeBannerId": undefined,
|
||||
"overlays": Object {
|
||||
"banners": Object {
|
||||
"add": [MockFunction],
|
||||
"get$": [MockFunction],
|
||||
"getComponent": [MockFunction],
|
||||
"remove": [MockFunction],
|
||||
"replace": [MockFunction],
|
||||
},
|
||||
"openConfirm": [MockFunction],
|
||||
"openFlyout": [MockFunction],
|
||||
"openModal": [MockFunction],
|
||||
},
|
||||
"renderOptInBanner": [Function],
|
||||
"renderOptedInNoticeBanner": [Function],
|
||||
"setOptedInNoticeSeen": [Function],
|
||||
"shouldShowOptInBanner": [Function],
|
||||
"shouldShowOptedInNoticeBanner": [Function],
|
||||
"telemetryService": TelemetryService {
|
||||
"canSendTelemetry": [Function],
|
||||
"currentKibanaVersion": "mockKibanaVersion",
|
||||
"defaultConfig": Object {
|
||||
"allowChangingOptInStatus": true,
|
||||
"banner": true,
|
||||
"enabled": true,
|
||||
"optIn": true,
|
||||
"sendUsageFrom": "browser",
|
||||
"sendUsageTo": "staging",
|
||||
"telemetryNotifyUserAboutOptInDefault": true,
|
||||
"userCanChangeSettings": true,
|
||||
},
|
||||
"fetchExample": [Function],
|
||||
"fetchTelemetry": [Function],
|
||||
"getCanChangeOptInStatus": [Function],
|
||||
"getIsOptedIn": [Function],
|
||||
"getOptInStatusUrl": [Function],
|
||||
"getTelemetryUrl": [Function],
|
||||
"http": Object {
|
||||
"addLoadingCountSource": [MockFunction],
|
||||
"anonymousPaths": Object {
|
||||
"isAnonymous": [MockFunction],
|
||||
"register": [MockFunction],
|
||||
},
|
||||
"basePath": BasePath {
|
||||
"basePath": "",
|
||||
"get": [Function],
|
||||
"prepend": [Function],
|
||||
"publicBaseUrl": undefined,
|
||||
"remove": [Function],
|
||||
"serverBasePath": "",
|
||||
},
|
||||
"delete": [MockFunction],
|
||||
"externalUrl": Object {
|
||||
"validateUrl": [MockFunction],
|
||||
},
|
||||
"fetch": [MockFunction],
|
||||
"get": [MockFunction],
|
||||
"getLoadingCount$": [MockFunction],
|
||||
"head": [MockFunction],
|
||||
"intercept": [MockFunction],
|
||||
"options": [MockFunction],
|
||||
"patch": [MockFunction],
|
||||
"post": [MockFunction],
|
||||
"put": [MockFunction],
|
||||
},
|
||||
"isScreenshotMode": false,
|
||||
"notifications": Object {
|
||||
"toasts": Object {
|
||||
"add": [MockFunction],
|
||||
"addDanger": [MockFunction],
|
||||
"addError": [MockFunction],
|
||||
"addInfo": [MockFunction],
|
||||
"addSuccess": [MockFunction],
|
||||
"addWarning": [MockFunction],
|
||||
"get$": [MockFunction],
|
||||
"remove": [MockFunction],
|
||||
},
|
||||
},
|
||||
"reportOptInStatus": [MockFunction],
|
||||
"reportOptInStatusChange": true,
|
||||
"setOptIn": [Function],
|
||||
"setUserHasSeenNotice": [Function],
|
||||
"updatedConfig": undefined,
|
||||
},
|
||||
},
|
||||
"telemetryService": TelemetryService {
|
||||
"canSendTelemetry": [Function],
|
||||
"currentKibanaVersion": "mockKibanaVersion",
|
||||
"defaultConfig": Object {
|
||||
"allowChangingOptInStatus": true,
|
||||
"banner": true,
|
||||
"enabled": true,
|
||||
"optIn": true,
|
||||
"sendUsageFrom": "browser",
|
||||
"sendUsageTo": "staging",
|
||||
"telemetryNotifyUserAboutOptInDefault": true,
|
||||
"userCanChangeSettings": true,
|
||||
},
|
||||
"fetchExample": [Function],
|
||||
"fetchTelemetry": [Function],
|
||||
"getCanChangeOptInStatus": [Function],
|
||||
"getIsOptedIn": [Function],
|
||||
"getOptInStatusUrl": [Function],
|
||||
"getTelemetryUrl": [Function],
|
||||
"http": Object {
|
||||
"addLoadingCountSource": [MockFunction],
|
||||
"anonymousPaths": Object {
|
||||
"isAnonymous": [MockFunction],
|
||||
"register": [MockFunction],
|
||||
},
|
||||
"basePath": BasePath {
|
||||
"basePath": "",
|
||||
"get": [Function],
|
||||
"prepend": [Function],
|
||||
"publicBaseUrl": undefined,
|
||||
"remove": [Function],
|
||||
"serverBasePath": "",
|
||||
},
|
||||
"delete": [MockFunction],
|
||||
"externalUrl": Object {
|
||||
"validateUrl": [MockFunction],
|
||||
},
|
||||
"fetch": [MockFunction],
|
||||
"get": [MockFunction],
|
||||
"getLoadingCount$": [MockFunction],
|
||||
"head": [MockFunction],
|
||||
"intercept": [MockFunction],
|
||||
"options": [MockFunction],
|
||||
"patch": [MockFunction],
|
||||
"post": [MockFunction],
|
||||
"put": [MockFunction],
|
||||
},
|
||||
"isScreenshotMode": false,
|
||||
"notifications": Object {
|
||||
"toasts": Object {
|
||||
"add": [MockFunction],
|
||||
"addDanger": [MockFunction],
|
||||
"addError": [MockFunction],
|
||||
"addInfo": [MockFunction],
|
||||
"addSuccess": [MockFunction],
|
||||
"addWarning": [MockFunction],
|
||||
"get$": [MockFunction],
|
||||
"remove": [MockFunction],
|
||||
},
|
||||
},
|
||||
"reportOptInStatus": [MockFunction],
|
||||
"reportOptInStatusChange": true,
|
||||
"setOptIn": [Function],
|
||||
"setUserHasSeenNotice": [Function],
|
||||
"updatedConfig": undefined,
|
||||
},
|
||||
}
|
||||
}
|
||||
urlBasePath="goober"
|
||||
/>
|
||||
`;
|
||||
|
||||
exports[`home welcome stores skip welcome setting if skipped 1`] = `
|
||||
<mockConstructor
|
||||
data-test-subj="homeApp"
|
||||
pageHeader={
|
||||
Object {
|
||||
"bottomBorder": false,
|
||||
"pageTitle": <FormattedMessage
|
||||
defaultMessage="Welcome home"
|
||||
id="home.header.title"
|
||||
values={Object {}}
|
||||
/>,
|
||||
}
|
||||
}
|
||||
template="empty"
|
||||
>
|
||||
<SolutionsSection
|
||||
addBasePath={[Function]}
|
||||
solutions={Array []}
|
||||
/>
|
||||
<AddData
|
||||
addBasePath={[Function]}
|
||||
isDarkMode={false}
|
||||
/>
|
||||
<ManageData
|
||||
addBasePath={[Function]}
|
||||
application={
|
||||
Object {
|
||||
"capabilities": Object {
|
||||
"navLinks": Object {
|
||||
"integrations": true,
|
||||
},
|
||||
},
|
||||
}
|
||||
}
|
||||
features={Array []}
|
||||
/>
|
||||
<mockConstructor
|
||||
|
|
|
@ -13,7 +13,9 @@ import { Home } from './home';
|
|||
|
||||
import { FeatureCatalogueCategory } from '../../services';
|
||||
import { telemetryPluginMock } from '../../../../telemetry/public/mocks';
|
||||
import { Welcome } from './welcome';
|
||||
|
||||
let mockHasIntegrationsPermission = true;
|
||||
jest.mock('../kibana_services', () => ({
|
||||
getServices: () => ({
|
||||
getBasePath: () => 'path',
|
||||
|
@ -22,6 +24,13 @@ jest.mock('../kibana_services', () => ({
|
|||
chrome: {
|
||||
setBreadcrumbs: () => {},
|
||||
},
|
||||
application: {
|
||||
capabilities: {
|
||||
navLinks: {
|
||||
integrations: mockHasIntegrationsPermission,
|
||||
},
|
||||
},
|
||||
},
|
||||
}),
|
||||
}));
|
||||
|
||||
|
@ -35,6 +44,7 @@ describe('home', () => {
|
|||
let defaultProps: HomeProps;
|
||||
|
||||
beforeEach(() => {
|
||||
mockHasIntegrationsPermission = true;
|
||||
defaultProps = {
|
||||
directories: [],
|
||||
solutions: [],
|
||||
|
@ -182,7 +192,7 @@ describe('home', () => {
|
|||
|
||||
expect(defaultProps.localStorage.getItem).toHaveBeenCalledTimes(1);
|
||||
|
||||
expect(component).toMatchSnapshot();
|
||||
expect(component.find(Welcome).exists()).toBe(true);
|
||||
});
|
||||
|
||||
test('stores skip welcome setting if skipped', async () => {
|
||||
|
@ -196,7 +206,7 @@ describe('home', () => {
|
|||
|
||||
expect(defaultProps.localStorage.setItem).toHaveBeenCalledWith('home:welcome:show', 'false');
|
||||
|
||||
expect(component).toMatchSnapshot();
|
||||
expect(component.find(Welcome).exists()).toBe(false);
|
||||
});
|
||||
|
||||
test('should show the normal home page if loading fails', async () => {
|
||||
|
@ -205,7 +215,7 @@ describe('home', () => {
|
|||
const hasUserIndexPattern = jest.fn(() => Promise.reject('Doh!'));
|
||||
const component = await renderHome({ hasUserIndexPattern });
|
||||
|
||||
expect(component).toMatchSnapshot();
|
||||
expect(component.find(Welcome).exists()).toBe(false);
|
||||
});
|
||||
|
||||
test('should show the normal home page if welcome screen is disabled locally', async () => {
|
||||
|
@ -213,7 +223,15 @@ describe('home', () => {
|
|||
|
||||
const component = await renderHome();
|
||||
|
||||
expect(component).toMatchSnapshot();
|
||||
expect(component.find(Welcome).exists()).toBe(false);
|
||||
});
|
||||
|
||||
test("should show the normal home page if user doesn't have access to integrations", async () => {
|
||||
mockHasIntegrationsPermission = false;
|
||||
|
||||
const component = await renderHome();
|
||||
|
||||
expect(component.find(Welcome).exists()).toBe(false);
|
||||
});
|
||||
});
|
||||
|
||||
|
|
|
@ -45,10 +45,10 @@ export class Home extends Component<HomeProps, State> {
|
|||
constructor(props: HomeProps) {
|
||||
super(props);
|
||||
|
||||
const isWelcomeEnabled = !(
|
||||
getServices().homeConfig.disableWelcomeScreen ||
|
||||
props.localStorage.getItem(KEY_ENABLE_WELCOME) === 'false'
|
||||
);
|
||||
const isWelcomeEnabled =
|
||||
!getServices().homeConfig.disableWelcomeScreen &&
|
||||
getServices().application.capabilities.navLinks.integrations &&
|
||||
props.localStorage.getItem(KEY_ENABLE_WELCOME) !== 'false';
|
||||
|
||||
const body = document.querySelector('body')!;
|
||||
body.classList.add('isHomPage');
|
||||
|
|
|
@ -26,8 +26,11 @@ const RedirectToDefaultApp = () => {
|
|||
return null;
|
||||
};
|
||||
|
||||
const REDIRECT_TO_INTEGRATIONS_TAB_IDS = ['all', 'logging', 'metrics', 'security'];
|
||||
|
||||
export function HomeApp({ directories, solutions }) {
|
||||
const {
|
||||
application,
|
||||
savedObjectsClient,
|
||||
getBasePath,
|
||||
addBasePath,
|
||||
|
@ -39,10 +42,17 @@ export function HomeApp({ directories, solutions }) {
|
|||
const isCloudEnabled = environment.cloud;
|
||||
|
||||
const renderTutorialDirectory = (props) => {
|
||||
// Redirect to integrations app unless a specific tab that is still supported was specified.
|
||||
const tabId = props.match.params.tab;
|
||||
if (!tabId || REDIRECT_TO_INTEGRATIONS_TAB_IDS.includes(tabId)) {
|
||||
application.navigateToApp('integrations', { replace: true });
|
||||
return null;
|
||||
}
|
||||
|
||||
return (
|
||||
<TutorialDirectory
|
||||
addBasePath={addBasePath}
|
||||
openTab={props.match.params.tab}
|
||||
openTab={tabId}
|
||||
isCloudEnabled={isCloudEnabled}
|
||||
/>
|
||||
);
|
||||
|
|
|
@ -26,9 +26,8 @@ const INSTRUCTIONS_TYPE = {
|
|||
ON_PREM_ELASTIC_CLOUD: 'onPremElasticCloud',
|
||||
};
|
||||
|
||||
const homeTitle = i18n.translate('home.breadcrumbs.homeTitle', { defaultMessage: 'Home' });
|
||||
const addDataTitle = i18n.translate('home.breadcrumbs.addDataTitle', {
|
||||
defaultMessage: 'Add data',
|
||||
const integrationsTitle = i18n.translate('home.breadcrumbs.integrationsAppTitle', {
|
||||
defaultMessage: 'Integrations',
|
||||
});
|
||||
|
||||
class TutorialUi extends React.Component {
|
||||
|
@ -80,12 +79,8 @@ class TutorialUi extends React.Component {
|
|||
|
||||
getServices().chrome.setBreadcrumbs([
|
||||
{
|
||||
text: homeTitle,
|
||||
href: '#/',
|
||||
},
|
||||
{
|
||||
text: addDataTitle,
|
||||
href: '#/tutorial_directory',
|
||||
text: integrationsTitle,
|
||||
href: this.props.addBasePath('/app/integrations/browse'),
|
||||
},
|
||||
{
|
||||
text: tutorial ? tutorial.name : this.props.tutorialId,
|
||||
|
|
|
@ -18,12 +18,10 @@ import { getServices } from '../kibana_services';
|
|||
import { KibanaPageTemplate } from '../../../../kibana_react/public';
|
||||
import { getTutorials } from '../load_tutorials';
|
||||
|
||||
const ALL_TAB_ID = 'all';
|
||||
const SAMPLE_DATA_TAB_ID = 'sampleData';
|
||||
|
||||
const homeTitle = i18n.translate('home.breadcrumbs.homeTitle', { defaultMessage: 'Home' });
|
||||
const addDataTitle = i18n.translate('home.breadcrumbs.addDataTitle', {
|
||||
defaultMessage: 'Add data',
|
||||
const integrationsTitle = i18n.translate('home.breadcrumbs.integrationsAppTitle', {
|
||||
defaultMessage: 'Integrations',
|
||||
});
|
||||
|
||||
class TutorialDirectoryUi extends React.Component {
|
||||
|
@ -48,7 +46,7 @@ class TutorialDirectoryUi extends React.Component {
|
|||
})),
|
||||
];
|
||||
|
||||
let openTab = ALL_TAB_ID;
|
||||
let openTab = SAMPLE_DATA_TAB_ID;
|
||||
if (
|
||||
props.openTab &&
|
||||
this.tabs.some((tab) => {
|
||||
|
@ -72,10 +70,9 @@ class TutorialDirectoryUi extends React.Component {
|
|||
|
||||
getServices().chrome.setBreadcrumbs([
|
||||
{
|
||||
text: homeTitle,
|
||||
href: '#/',
|
||||
text: integrationsTitle,
|
||||
href: this.props.addBasePath(`/app/integrations/browse`),
|
||||
},
|
||||
{ text: addDataTitle },
|
||||
]);
|
||||
|
||||
const tutorialConfigs = await getTutorials();
|
||||
|
@ -155,6 +152,15 @@ class TutorialDirectoryUi extends React.Component {
|
|||
renderTabContent = () => {
|
||||
const tab = this.tabs.find(({ id }) => id === this.state.selectedTabId);
|
||||
if (tab?.content) {
|
||||
getServices().chrome.setBreadcrumbs([
|
||||
{
|
||||
text: integrationsTitle,
|
||||
href: this.props.addBasePath(`/app/integrations/browse`),
|
||||
},
|
||||
{
|
||||
text: tab.name,
|
||||
},
|
||||
]);
|
||||
return tab.content;
|
||||
}
|
||||
|
||||
|
@ -163,7 +169,7 @@ class TutorialDirectoryUi extends React.Component {
|
|||
{this.state.tutorialCards
|
||||
.filter((tutorial) => {
|
||||
return (
|
||||
this.state.selectedTabId === ALL_TAB_ID ||
|
||||
this.state.selectedTabId === SAMPLE_DATA_TAB_ID ||
|
||||
this.state.selectedTabId === tutorial.category
|
||||
);
|
||||
})
|
||||
|
|
|
@ -1,117 +1,177 @@
|
|||
// Jest Snapshot v1, https://goo.gl/fbAQLP
|
||||
|
||||
exports[`ElasticAgentCard props button 1`] = `
|
||||
<EuiCard
|
||||
description="Use Elastic Agent for a simple, unified way to collect data from your machines."
|
||||
footer={
|
||||
<EuiButton
|
||||
fill={true}
|
||||
>
|
||||
Button
|
||||
</EuiButton>
|
||||
<RedirectAppLinks
|
||||
application={
|
||||
Object {
|
||||
"capabilities": Object {
|
||||
"navLinks": Object {
|
||||
"integrations": true,
|
||||
},
|
||||
},
|
||||
}
|
||||
}
|
||||
href="/app/integrations/browse"
|
||||
image="/plugins/kibanaReact/assets/elastic_agent_card.svg"
|
||||
paddingSize="l"
|
||||
title={
|
||||
<EuiScreenReaderOnly>
|
||||
<span>
|
||||
Add Elastic Agent
|
||||
</span>
|
||||
</EuiScreenReaderOnly>
|
||||
}
|
||||
/>
|
||||
>
|
||||
<EuiCard
|
||||
description="Use Elastic Agent for a simple, unified way to collect data from your machines."
|
||||
footer={
|
||||
<EuiButton
|
||||
fill={true}
|
||||
>
|
||||
Button
|
||||
</EuiButton>
|
||||
}
|
||||
href="/app/integrations/browse"
|
||||
image="/plugins/kibanaReact/assets/elastic_agent_card.svg"
|
||||
paddingSize="l"
|
||||
title={
|
||||
<EuiScreenReaderOnly>
|
||||
<span>
|
||||
Add Elastic Agent
|
||||
</span>
|
||||
</EuiScreenReaderOnly>
|
||||
}
|
||||
/>
|
||||
</RedirectAppLinks>
|
||||
`;
|
||||
|
||||
exports[`ElasticAgentCard props category 1`] = `
|
||||
<EuiCard
|
||||
description="Use Elastic Agent for a simple, unified way to collect data from your machines."
|
||||
footer={
|
||||
<EuiButton
|
||||
fill={true}
|
||||
>
|
||||
Add Elastic Agent
|
||||
</EuiButton>
|
||||
<RedirectAppLinks
|
||||
application={
|
||||
Object {
|
||||
"capabilities": Object {
|
||||
"navLinks": Object {
|
||||
"integrations": true,
|
||||
},
|
||||
},
|
||||
}
|
||||
}
|
||||
href="/app/integrations/browse/custom"
|
||||
image="/plugins/kibanaReact/assets/elastic_agent_card.svg"
|
||||
paddingSize="l"
|
||||
title={
|
||||
<EuiScreenReaderOnly>
|
||||
<span>
|
||||
>
|
||||
<EuiCard
|
||||
description="Use Elastic Agent for a simple, unified way to collect data from your machines."
|
||||
footer={
|
||||
<EuiButton
|
||||
fill={true}
|
||||
>
|
||||
Add Elastic Agent
|
||||
</span>
|
||||
</EuiScreenReaderOnly>
|
||||
}
|
||||
/>
|
||||
</EuiButton>
|
||||
}
|
||||
href="/app/integrations/browse/custom"
|
||||
image="/plugins/kibanaReact/assets/elastic_agent_card.svg"
|
||||
paddingSize="l"
|
||||
title={
|
||||
<EuiScreenReaderOnly>
|
||||
<span>
|
||||
Add Elastic Agent
|
||||
</span>
|
||||
</EuiScreenReaderOnly>
|
||||
}
|
||||
/>
|
||||
</RedirectAppLinks>
|
||||
`;
|
||||
|
||||
exports[`ElasticAgentCard props href 1`] = `
|
||||
<EuiCard
|
||||
description="Use Elastic Agent for a simple, unified way to collect data from your machines."
|
||||
footer={
|
||||
<EuiButton
|
||||
fill={true}
|
||||
>
|
||||
Button
|
||||
</EuiButton>
|
||||
<RedirectAppLinks
|
||||
application={
|
||||
Object {
|
||||
"capabilities": Object {
|
||||
"navLinks": Object {
|
||||
"integrations": true,
|
||||
},
|
||||
},
|
||||
}
|
||||
}
|
||||
href="#"
|
||||
image="/plugins/kibanaReact/assets/elastic_agent_card.svg"
|
||||
paddingSize="l"
|
||||
title={
|
||||
<EuiScreenReaderOnly>
|
||||
<span>
|
||||
Add Elastic Agent
|
||||
</span>
|
||||
</EuiScreenReaderOnly>
|
||||
}
|
||||
/>
|
||||
>
|
||||
<EuiCard
|
||||
description="Use Elastic Agent for a simple, unified way to collect data from your machines."
|
||||
footer={
|
||||
<EuiButton
|
||||
fill={true}
|
||||
>
|
||||
Button
|
||||
</EuiButton>
|
||||
}
|
||||
href="#"
|
||||
image="/plugins/kibanaReact/assets/elastic_agent_card.svg"
|
||||
paddingSize="l"
|
||||
title={
|
||||
<EuiScreenReaderOnly>
|
||||
<span>
|
||||
Add Elastic Agent
|
||||
</span>
|
||||
</EuiScreenReaderOnly>
|
||||
}
|
||||
/>
|
||||
</RedirectAppLinks>
|
||||
`;
|
||||
|
||||
exports[`ElasticAgentCard props recommended 1`] = `
|
||||
<EuiCard
|
||||
betaBadgeLabel="Recommended"
|
||||
description="Use Elastic Agent for a simple, unified way to collect data from your machines."
|
||||
footer={
|
||||
<EuiButton
|
||||
fill={true}
|
||||
>
|
||||
Add Elastic Agent
|
||||
</EuiButton>
|
||||
<RedirectAppLinks
|
||||
application={
|
||||
Object {
|
||||
"capabilities": Object {
|
||||
"navLinks": Object {
|
||||
"integrations": true,
|
||||
},
|
||||
},
|
||||
}
|
||||
}
|
||||
href="/app/integrations/browse"
|
||||
image="/plugins/kibanaReact/assets/elastic_agent_card.svg"
|
||||
paddingSize="l"
|
||||
title={
|
||||
<EuiScreenReaderOnly>
|
||||
<span>
|
||||
>
|
||||
<EuiCard
|
||||
betaBadgeLabel="Recommended"
|
||||
description="Use Elastic Agent for a simple, unified way to collect data from your machines."
|
||||
footer={
|
||||
<EuiButton
|
||||
fill={true}
|
||||
>
|
||||
Add Elastic Agent
|
||||
</span>
|
||||
</EuiScreenReaderOnly>
|
||||
}
|
||||
/>
|
||||
</EuiButton>
|
||||
}
|
||||
href="/app/integrations/browse"
|
||||
image="/plugins/kibanaReact/assets/elastic_agent_card.svg"
|
||||
paddingSize="l"
|
||||
title={
|
||||
<EuiScreenReaderOnly>
|
||||
<span>
|
||||
Add Elastic Agent
|
||||
</span>
|
||||
</EuiScreenReaderOnly>
|
||||
}
|
||||
/>
|
||||
</RedirectAppLinks>
|
||||
`;
|
||||
|
||||
exports[`ElasticAgentCard renders 1`] = `
|
||||
<EuiCard
|
||||
description="Use Elastic Agent for a simple, unified way to collect data from your machines."
|
||||
footer={
|
||||
<EuiButton
|
||||
fill={true}
|
||||
>
|
||||
Add Elastic Agent
|
||||
</EuiButton>
|
||||
<RedirectAppLinks
|
||||
application={
|
||||
Object {
|
||||
"capabilities": Object {
|
||||
"navLinks": Object {
|
||||
"integrations": true,
|
||||
},
|
||||
},
|
||||
}
|
||||
}
|
||||
href="/app/integrations/browse"
|
||||
image="/plugins/kibanaReact/assets/elastic_agent_card.svg"
|
||||
paddingSize="l"
|
||||
title={
|
||||
<EuiScreenReaderOnly>
|
||||
<span>
|
||||
>
|
||||
<EuiCard
|
||||
description="Use Elastic Agent for a simple, unified way to collect data from your machines."
|
||||
footer={
|
||||
<EuiButton
|
||||
fill={true}
|
||||
>
|
||||
Add Elastic Agent
|
||||
</span>
|
||||
</EuiScreenReaderOnly>
|
||||
}
|
||||
/>
|
||||
</EuiButton>
|
||||
}
|
||||
href="/app/integrations/browse"
|
||||
image="/plugins/kibanaReact/assets/elastic_agent_card.svg"
|
||||
paddingSize="l"
|
||||
title={
|
||||
<EuiScreenReaderOnly>
|
||||
<span>
|
||||
Add Elastic Agent
|
||||
</span>
|
||||
</EuiScreenReaderOnly>
|
||||
}
|
||||
/>
|
||||
</RedirectAppLinks>
|
||||
`;
|
||||
|
|
|
@ -12,6 +12,7 @@ import { CoreStart } from 'kibana/public';
|
|||
import { EuiButton, EuiCard, EuiTextColor, EuiScreenReaderOnly } from '@elastic/eui';
|
||||
import { useKibana } from '../../../context';
|
||||
import { NoDataPageActions, NO_DATA_RECOMMENDED } from '../no_data_page';
|
||||
import { RedirectAppLinks } from '../../../app_links';
|
||||
|
||||
export type ElasticAgentCardProps = NoDataPageActions & {
|
||||
solution: string;
|
||||
|
@ -76,23 +77,25 @@ export const ElasticAgentCard: FunctionComponent<ElasticAgentCardProps> = ({
|
|||
);
|
||||
|
||||
return (
|
||||
<EuiCard
|
||||
paddingSize="l"
|
||||
image={image}
|
||||
href={href ?? addBasePath(`/app/integrations/browse${hasCategory}`)}
|
||||
// Bad hack to fix the need for an a11y title even though the button exists
|
||||
title={
|
||||
<EuiScreenReaderOnly>
|
||||
<span>{defaultCTAtitle}</span>
|
||||
</EuiScreenReaderOnly>
|
||||
}
|
||||
description={i18n.translate('kibana-react.noDataPage.elasticAgentCard.description', {
|
||||
defaultMessage: `Use Elastic Agent for a simple, unified way to collect data from your machines.`,
|
||||
})}
|
||||
betaBadgeLabel={recommended ? NO_DATA_RECOMMENDED : undefined}
|
||||
footer={footer}
|
||||
layout={layout as 'vertical' | undefined}
|
||||
{...cardRest}
|
||||
/>
|
||||
<RedirectAppLinks application={application}>
|
||||
<EuiCard
|
||||
paddingSize="l"
|
||||
image={image}
|
||||
href={href ?? addBasePath(`/app/integrations/browse${hasCategory}`)}
|
||||
// Bad hack to fix the need for an a11y title even though the button exists
|
||||
title={
|
||||
<EuiScreenReaderOnly>
|
||||
<span>{defaultCTAtitle}</span>
|
||||
</EuiScreenReaderOnly>
|
||||
}
|
||||
description={i18n.translate('kibana-react.noDataPage.elasticAgentCard.description', {
|
||||
defaultMessage: `Use Elastic Agent for a simple, unified way to collect data from your machines.`,
|
||||
})}
|
||||
betaBadgeLabel={recommended ? NO_DATA_RECOMMENDED : undefined}
|
||||
footer={footer}
|
||||
layout={layout as 'vertical' | undefined}
|
||||
{...cardRest}
|
||||
/>
|
||||
</RedirectAppLinks>
|
||||
);
|
||||
};
|
||||
|
|
|
@ -6,20 +6,15 @@
|
|||
* Side Public License, v 1.
|
||||
*/
|
||||
|
||||
import expect from '@kbn/expect';
|
||||
import { FtrProviderContext } from '../../ftr_provider_context';
|
||||
|
||||
export default function ({ getService, getPageObjects }) {
|
||||
const retry = getService('retry');
|
||||
export default function ({ getService, getPageObjects }: FtrProviderContext) {
|
||||
const PageObjects = getPageObjects(['common', 'header', 'home', 'dashboard']);
|
||||
|
||||
describe('add data tutorials', function describeIndexTests() {
|
||||
it('directory should display registered tutorials', async () => {
|
||||
it('directory should redirect to integrations app', async () => {
|
||||
await PageObjects.common.navigateToUrl('home', 'tutorial_directory', { useActualUrl: true });
|
||||
await PageObjects.header.waitUntilLoadingHasFinished();
|
||||
await retry.try(async () => {
|
||||
const tutorialExists = await PageObjects.home.doesSynopsisExist('netflowlogs');
|
||||
expect(tutorialExists).to.be(true);
|
||||
});
|
||||
await PageObjects.common.waitUntilUrlIncludes('/app/integrations');
|
||||
});
|
||||
});
|
||||
}
|
|
@ -2921,7 +2921,6 @@
|
|||
"home.addData.sampleDataButtonLabel": "サンプルデータを試す",
|
||||
"home.addData.sectionTitle": "データを追加して開始する",
|
||||
"home.addData.text": "データの操作を開始するには、多数の取り込みオプションのいずれかを使用します。アプリまたはサービスからデータを収集するか、ファイルをアップロードします。独自のデータを使用する準備ができていない場合は、サンプルデータセットを追加してください。",
|
||||
"home.breadcrumbs.addDataTitle": "データの追加",
|
||||
"home.breadcrumbs.homeTitle": "ホーム",
|
||||
"home.dataManagementDisableCollection": " 収集を停止するには、",
|
||||
"home.dataManagementDisableCollectionLink": "ここで使用状況データを無効にします。",
|
||||
|
|
|
@ -2950,7 +2950,6 @@
|
|||
"home.addData.sampleDataButtonLabel": "试用样例数据",
|
||||
"home.addData.sectionTitle": "首先添加您的数据",
|
||||
"home.addData.text": "要开始使用您的数据,请使用我们众多采集选项中的一个选项。从应用或服务收集数据,或上传文件。如果未准备好使用自己的数据,请添加示例数据集。",
|
||||
"home.breadcrumbs.addDataTitle": "添加数据",
|
||||
"home.breadcrumbs.homeTitle": "主页",
|
||||
"home.dataManagementDisableCollection": " 要停止收集,",
|
||||
"home.dataManagementDisableCollectionLink": "请在此禁用使用情况数据。",
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue