mirror of
https://github.com/elastic/kibana.git
synced 2025-04-23 17:28:26 -04:00
[Logs onboarding] Add select logs step (#156182)
Closes #154941 <img width="1434" alt="image" src="https://user-images.githubusercontent.com/1313018/236182563-e3c037ec-9ffb-49bb-9c05-a42882e3e66d.png"> --------- Co-authored-by: Oliver Gupte <oliver.gupte@elastic.co>
This commit is contained in:
parent
5207e52895
commit
52b2e38da4
10 changed files with 422 additions and 64 deletions
|
@ -5,10 +5,11 @@
|
|||
* 2.0.
|
||||
*/
|
||||
|
||||
import { EuiFlexGroup, EuiFlexItem, EuiSpacer } from '@elastic/eui';
|
||||
import { EuiFlexGroup, EuiFlexItem, EuiSpacer, EuiTitle } from '@elastic/eui';
|
||||
import { i18n } from '@kbn/i18n';
|
||||
import { useBreadcrumbs } from '@kbn/observability-plugin/public';
|
||||
import React, { ComponentType, useRef, useState } from 'react';
|
||||
import { breadcrumbsApp } from '../../../application/app';
|
||||
import {
|
||||
FilmstripFrame,
|
||||
FilmstripTransition,
|
||||
|
@ -16,8 +17,6 @@ import {
|
|||
} from '../../shared/filmstrip_transition';
|
||||
import { Provider as WizardProvider, Step as WizardStep } from './wizard';
|
||||
import { HorizontalSteps } from './wizard/horizontal_steps';
|
||||
import { PageTitle } from './wizard/page_title';
|
||||
import { breadcrumbsApp } from '../../../application/app';
|
||||
|
||||
export function CustomLogs() {
|
||||
useBreadcrumbs(
|
||||
|
@ -62,7 +61,16 @@ function AnimatedTransitionsWizard() {
|
|||
<EuiFlexGroup direction="column" alignItems="center">
|
||||
<EuiFlexItem grow={false}>
|
||||
<EuiSpacer size="l" />
|
||||
<PageTitle />
|
||||
<EuiTitle size="l">
|
||||
<h1>
|
||||
{i18n.translate(
|
||||
'xpack.observability_onboarding.title.collectCustomLogs',
|
||||
{
|
||||
defaultMessage: 'Collect custom logs',
|
||||
}
|
||||
)}
|
||||
</h1>
|
||||
</EuiTitle>
|
||||
</EuiFlexItem>
|
||||
<EuiFlexItem grow={false} style={{ width: '50%' }}>
|
||||
<HorizontalSteps />
|
||||
|
|
|
@ -0,0 +1,105 @@
|
|||
/*
|
||||
* Copyright Elasticsearch B.V. and/or licensed to Elasticsearch B.V. under one
|
||||
* or more contributor license agreements. Licensed under the Elastic License
|
||||
* 2.0; you may not use this file except in compliance with the Elastic License
|
||||
* 2.0.
|
||||
*/
|
||||
|
||||
import {
|
||||
EuiButton,
|
||||
EuiButtonEmpty,
|
||||
EuiCallOut,
|
||||
EuiFlexGroup,
|
||||
EuiFlexItem,
|
||||
EuiHorizontalRule,
|
||||
EuiLoadingSpinner,
|
||||
EuiSpacer,
|
||||
EuiSteps,
|
||||
EuiText,
|
||||
} from '@elastic/eui';
|
||||
import React from 'react';
|
||||
import { useWizard } from '.';
|
||||
import { useFetcher } from '../../../../hooks/use_fetcher';
|
||||
import {
|
||||
StepPanel,
|
||||
StepPanelContent,
|
||||
StepPanelFooter,
|
||||
} from '../../../shared/step_panel';
|
||||
|
||||
export function CollectLogs() {
|
||||
const { goToStep, goBack } = useWizard();
|
||||
|
||||
const { data } = useFetcher((callApi) => {
|
||||
return callApi('GET /internal/observability_onboarding/get_status');
|
||||
}, []);
|
||||
|
||||
function onContinue() {
|
||||
goToStep('inspect');
|
||||
}
|
||||
|
||||
function onBack() {
|
||||
goBack();
|
||||
}
|
||||
|
||||
return (
|
||||
<StepPanel title="">
|
||||
<StepPanelContent>
|
||||
<EuiText color="subdued">
|
||||
<p>
|
||||
It might take a few minutes for the data to get to Elasticsearch. If
|
||||
you're not seeing any, try generating some to verify. If
|
||||
you're having trouble connecting, check out the troubleshooting
|
||||
guide.
|
||||
</p>
|
||||
</EuiText>
|
||||
<EuiSpacer size="m" />
|
||||
<EuiCallOut>
|
||||
<EuiFlexGroup justifyContent="flexStart" alignItems="center">
|
||||
<EuiFlexItem grow={false}>
|
||||
<EuiLoadingSpinner size="m" />
|
||||
</EuiFlexItem>
|
||||
<EuiFlexItem grow={false}>
|
||||
<EuiText color="subdued">
|
||||
<p>Listening for incoming logs</p>
|
||||
</EuiText>
|
||||
</EuiFlexItem>
|
||||
</EuiFlexGroup>
|
||||
</EuiCallOut>
|
||||
<EuiSpacer size="m" />
|
||||
<EuiSteps
|
||||
titleSize="xs"
|
||||
steps={[
|
||||
{ title: 'Ping received', status: data?.status, children: null },
|
||||
{ title: 'File found', status: 'complete', children: null },
|
||||
{
|
||||
title: 'Downloading Elastic Agent',
|
||||
status: 'loading',
|
||||
children: null,
|
||||
},
|
||||
{
|
||||
title: 'Starting Elastic Agent',
|
||||
status: 'incomplete',
|
||||
children: null,
|
||||
},
|
||||
]}
|
||||
/>
|
||||
<EuiHorizontalRule margin="l" />
|
||||
<EuiFlexGroup justifyContent="center" alignItems="center">
|
||||
<EuiFlexItem grow={false}>
|
||||
<EuiButtonEmpty iconType="help">Need some help?</EuiButtonEmpty>
|
||||
</EuiFlexItem>
|
||||
</EuiFlexGroup>
|
||||
</StepPanelContent>
|
||||
<StepPanelFooter
|
||||
items={[
|
||||
<EuiButton color="ghost" fill onClick={onBack}>
|
||||
Back
|
||||
</EuiButton>,
|
||||
<EuiButton color="primary" fill onClick={onContinue}>
|
||||
Continue
|
||||
</EuiButton>,
|
||||
]}
|
||||
/>
|
||||
</StepPanel>
|
||||
);
|
||||
}
|
|
@ -5,12 +5,13 @@
|
|||
* 2.0.
|
||||
*/
|
||||
|
||||
import React from 'react';
|
||||
import { EuiStepsHorizontal } from '@elastic/eui';
|
||||
import { i18n } from '@kbn/i18n';
|
||||
import React from 'react';
|
||||
import { useWizard } from '.';
|
||||
|
||||
export function HorizontalSteps() {
|
||||
const { getPath } = useWizard();
|
||||
const { getPath, goToStep } = useWizard();
|
||||
const [currentStep, ...previousSteps] = getPath().reverse();
|
||||
|
||||
function getStatus(stepKey: ReturnType<typeof getPath>[0]) {
|
||||
|
@ -23,28 +24,63 @@ export function HorizontalSteps() {
|
|||
return 'incomplete';
|
||||
}
|
||||
|
||||
function isDisabled(stepKey: ReturnType<typeof getPath>[0]) {
|
||||
return getStatus(stepKey) === 'incomplete';
|
||||
}
|
||||
|
||||
return (
|
||||
<EuiStepsHorizontal
|
||||
steps={[
|
||||
{
|
||||
title: 'Name logs',
|
||||
status: getStatus('nameLogs'),
|
||||
onClick: () => {},
|
||||
title: i18n.translate(
|
||||
'xpack.observability_onboarding.steps.selectLogs',
|
||||
{
|
||||
defaultMessage: 'Select logs',
|
||||
}
|
||||
),
|
||||
status: getStatus('selectLogs'),
|
||||
onClick: () => {
|
||||
goToStep('selectLogs');
|
||||
},
|
||||
},
|
||||
{
|
||||
title: 'Configure logs',
|
||||
title: i18n.translate(
|
||||
'xpack.observability_onboarding.steps.configureLogs',
|
||||
{
|
||||
defaultMessage: 'Configure logs',
|
||||
}
|
||||
),
|
||||
status: getStatus('configureLogs'),
|
||||
onClick: () => {},
|
||||
disabled: isDisabled('configureLogs'),
|
||||
onClick: () => {
|
||||
goToStep('configureLogs');
|
||||
},
|
||||
},
|
||||
{
|
||||
title: 'Install shipper',
|
||||
title: i18n.translate(
|
||||
'xpack.observability_onboarding.steps.installShipper',
|
||||
{
|
||||
defaultMessage: 'Install shipper',
|
||||
}
|
||||
),
|
||||
status: getStatus('installElasticAgent'),
|
||||
onClick: () => {},
|
||||
disabled: isDisabled('installElasticAgent'),
|
||||
onClick: () => {
|
||||
goToStep('installElasticAgent');
|
||||
},
|
||||
},
|
||||
{
|
||||
title: 'Import data',
|
||||
status: getStatus('importData'),
|
||||
onClick: () => {},
|
||||
title: i18n.translate(
|
||||
'xpack.observability_onboarding.steps.collectLogs',
|
||||
{
|
||||
defaultMessage: 'Collect logs',
|
||||
}
|
||||
),
|
||||
status: getStatus('collectLogs'),
|
||||
disabled: isDisabled('collectLogs'),
|
||||
onClick: () => {
|
||||
goToStep('collectLogs');
|
||||
},
|
||||
},
|
||||
]}
|
||||
/>
|
||||
|
|
|
@ -26,7 +26,7 @@ import {
|
|||
StepPanelFooter,
|
||||
} from '../../../shared/step_panel';
|
||||
|
||||
export function ImportData() {
|
||||
export function CollectLogs() {
|
||||
const { goToStep, goBack } = useWizard();
|
||||
|
||||
const { data } = useFetcher((callApi) => {
|
||||
|
|
|
@ -5,11 +5,11 @@
|
|||
* 2.0.
|
||||
*/
|
||||
|
||||
import { NameLogs } from './name_logs';
|
||||
import { ConfigureLogs } from './configure_logs';
|
||||
import { SelectLogs } from './select_logs';
|
||||
import { InstallElasticAgent } from './install_elastic_agent';
|
||||
import { createWizardContext } from '../../../../context/create_wizard_context';
|
||||
import { ImportData } from './import_data';
|
||||
import { CollectLogs } from './collect_logs';
|
||||
import { Inspect } from './inspect';
|
||||
|
||||
interface WizardState {
|
||||
|
@ -45,12 +45,12 @@ const initialState: WizardState = {
|
|||
|
||||
const { Provider, Step, useWizard } = createWizardContext({
|
||||
initialState,
|
||||
initialStep: 'nameLogs',
|
||||
initialStep: 'selectLogs',
|
||||
steps: {
|
||||
nameLogs: NameLogs,
|
||||
selectLogs: SelectLogs,
|
||||
configureLogs: ConfigureLogs,
|
||||
installElasticAgent: InstallElasticAgent,
|
||||
importData: ImportData,
|
||||
collectLogs: CollectLogs,
|
||||
inspect: Inspect,
|
||||
},
|
||||
});
|
||||
|
|
|
@ -39,7 +39,7 @@ export function InstallElasticAgent() {
|
|||
|
||||
function onContinue() {
|
||||
setState({ ...getState(), elasticAgentPlatform, alternativeShippers });
|
||||
goToStep('importData');
|
||||
goToStep('collectLogs');
|
||||
}
|
||||
|
||||
function createAlternativeShipperToggle(
|
||||
|
|
|
@ -1,37 +0,0 @@
|
|||
/*
|
||||
* Copyright Elasticsearch B.V. and/or licensed to Elasticsearch B.V. under one
|
||||
* or more contributor license agreements. Licensed under the Elastic License
|
||||
* 2.0; you may not use this file except in compliance with the Elastic License
|
||||
* 2.0.
|
||||
*/
|
||||
|
||||
import React from 'react';
|
||||
import { EuiTitle } from '@elastic/eui';
|
||||
import { useWizard } from '.';
|
||||
|
||||
export function PageTitle() {
|
||||
const { getPath } = useWizard();
|
||||
const [currentStep] = getPath().reverse();
|
||||
|
||||
if (currentStep === 'installElasticAgent') {
|
||||
return (
|
||||
<EuiTitle size="l">
|
||||
<h1>Select your shipper</h1>
|
||||
</EuiTitle>
|
||||
);
|
||||
}
|
||||
|
||||
if (currentStep === 'importData') {
|
||||
return (
|
||||
<EuiTitle size="l">
|
||||
<h1>Incoming logs</h1>
|
||||
</EuiTitle>
|
||||
);
|
||||
}
|
||||
|
||||
return (
|
||||
<EuiTitle size="l">
|
||||
<h1>Collect and analyze my logs</h1>
|
||||
</EuiTitle>
|
||||
);
|
||||
}
|
|
@ -0,0 +1,242 @@
|
|||
/*
|
||||
* Copyright Elasticsearch B.V. and/or licensed to Elasticsearch B.V. under one
|
||||
* or more contributor license agreements. Licensed under the Elastic License
|
||||
* 2.0; you may not use this file except in compliance with the Elastic License
|
||||
* 2.0.
|
||||
*/
|
||||
|
||||
/* eslint-disable @elastic/eui/href-or-on-click */
|
||||
|
||||
import React, { PropsWithChildren, MouseEvent } from 'react';
|
||||
import {
|
||||
EuiTitle,
|
||||
EuiLink,
|
||||
EuiButton,
|
||||
EuiFlexGroup,
|
||||
EuiFlexItem,
|
||||
EuiHorizontalRule,
|
||||
EuiSpacer,
|
||||
EuiCard,
|
||||
EuiIcon,
|
||||
EuiIconProps,
|
||||
} from '@elastic/eui';
|
||||
import { i18n } from '@kbn/i18n';
|
||||
import {
|
||||
StepPanel,
|
||||
StepPanelContent,
|
||||
StepPanelFooter,
|
||||
} from '../../../shared/step_panel';
|
||||
import { useWizard } from '.';
|
||||
import { useKibanaNavigation } from '../../../../hooks/use_kibana_navigation';
|
||||
|
||||
export function SelectLogs() {
|
||||
const { navigateToKibanaUrl, navigateToAppUrl } = useKibanaNavigation();
|
||||
const { goToStep, getState, setState } = useWizard();
|
||||
|
||||
function onBack() {
|
||||
navigateToKibanaUrl('/app/observabilityOnboarding');
|
||||
}
|
||||
|
||||
return (
|
||||
<StepPanel
|
||||
title={i18n.translate(
|
||||
'xpack.observability_onboarding.selectLogs.chooseType',
|
||||
{
|
||||
defaultMessage: 'What logs do you want to collect?',
|
||||
}
|
||||
)}
|
||||
>
|
||||
<StepPanelContent>
|
||||
<EuiFlexGroup>
|
||||
<EuiFlexItem grow={false} style={{ width: '50%' }}>
|
||||
<OptionCard
|
||||
title={i18n.translate(
|
||||
'xpack.observability_onboarding.selectLogs.streamLogFiles',
|
||||
{
|
||||
defaultMessage: 'Stream log files',
|
||||
}
|
||||
)}
|
||||
iconType="desktop"
|
||||
onClick={() => {
|
||||
setState({ ...getState(), logsType: 'log-file' });
|
||||
goToStep('configureLogs');
|
||||
}}
|
||||
description={i18n.translate(
|
||||
'xpack.observability_onboarding.selectLogs.streamLogFiles.description',
|
||||
{
|
||||
defaultMessage: 'Stream your log file or directory.',
|
||||
}
|
||||
)}
|
||||
/>
|
||||
</EuiFlexItem>
|
||||
</EuiFlexGroup>
|
||||
<EuiHorizontalRule margin="l" />
|
||||
<LogsTypeSection
|
||||
title={i18n.translate(
|
||||
'xpack.observability_onboarding.selectLogs.networkStreamingLogs',
|
||||
{
|
||||
defaultMessage: 'Network streaming logs',
|
||||
}
|
||||
)}
|
||||
>
|
||||
<EuiFlexGroup>
|
||||
<EuiFlexItem>
|
||||
<OptionCard
|
||||
title={i18n.translate(
|
||||
'xpack.observability_onboarding.selectLogs.sysLog',
|
||||
{
|
||||
defaultMessage: 'TCP/UDP/Syslog',
|
||||
}
|
||||
)}
|
||||
iconType="documents"
|
||||
onClick={() => {}}
|
||||
description={i18n.translate(
|
||||
'xpack.observability_onboarding.selectLogs.sysLog.description',
|
||||
{
|
||||
defaultMessage:
|
||||
'Stream logs over TCP or UDP ports or from your syslog server.',
|
||||
}
|
||||
)}
|
||||
/>
|
||||
</EuiFlexItem>
|
||||
<EuiFlexItem>
|
||||
<OptionCard
|
||||
title={i18n.translate(
|
||||
'xpack.observability_onboarding.selectLogs.httpEndpointLogs',
|
||||
{
|
||||
defaultMessage: 'HTTP Endpoint',
|
||||
}
|
||||
)}
|
||||
iconType="documents"
|
||||
onClick={() => {}}
|
||||
description={i18n.translate(
|
||||
'xpack.observability_onboarding.selectLogs.httpEndpointLogs.description',
|
||||
{
|
||||
defaultMessage:
|
||||
'Collect JSON data from listening HTTP port.',
|
||||
}
|
||||
)}
|
||||
/>
|
||||
</EuiFlexItem>
|
||||
</EuiFlexGroup>
|
||||
</LogsTypeSection>
|
||||
<EuiHorizontalRule margin="l" />
|
||||
<LogsTypeSection
|
||||
title={i18n.translate(
|
||||
'xpack.observability_onboarding.selectLogs.other',
|
||||
{
|
||||
defaultMessage: 'Other',
|
||||
}
|
||||
)}
|
||||
>
|
||||
<EuiFlexGroup>
|
||||
<EuiFlexItem>
|
||||
<OptionCard
|
||||
title={i18n.translate(
|
||||
'xpack.observability_onboarding.selectLogs.uploadLogFiles',
|
||||
{
|
||||
defaultMessage: 'Upload log files',
|
||||
}
|
||||
)}
|
||||
iconType="exportAction"
|
||||
onClick={() => {}}
|
||||
description={i18n.translate(
|
||||
'xpack.observability_onboarding.selectLogs.uploadLogFiles.description',
|
||||
{
|
||||
defaultMessage:
|
||||
'Upload data from a CSV, TSV, JSON or other log file type for analysis.',
|
||||
}
|
||||
)}
|
||||
/>
|
||||
</EuiFlexItem>
|
||||
<EuiFlexItem>
|
||||
<OptionCard
|
||||
title={i18n.translate(
|
||||
'xpack.observability_onboarding.selectLogs.useOwnShipper',
|
||||
{
|
||||
defaultMessage: 'Get an API key',
|
||||
}
|
||||
)}
|
||||
iconType="package"
|
||||
onClick={() => {}}
|
||||
description={i18n.translate(
|
||||
'xpack.observability_onboarding.selectLogs.useOwnShipper.description',
|
||||
{
|
||||
defaultMessage:
|
||||
'Use your own shipper to collect logs data by generating an API key.',
|
||||
}
|
||||
)}
|
||||
/>
|
||||
</EuiFlexItem>
|
||||
</EuiFlexGroup>
|
||||
<EuiSpacer size="m" />
|
||||
<EuiLink
|
||||
href="#"
|
||||
target="_blank"
|
||||
onClick={(event: MouseEvent) => {
|
||||
event.preventDefault();
|
||||
navigateToAppUrl('/integrations/browse/observability');
|
||||
}}
|
||||
>
|
||||
{i18n.translate(
|
||||
'xpack.observability_onboarding.exploreOtherIntegrations',
|
||||
{
|
||||
defaultMessage: 'Explore other integrations',
|
||||
}
|
||||
)}
|
||||
</EuiLink>
|
||||
</LogsTypeSection>
|
||||
</StepPanelContent>
|
||||
<StepPanelFooter
|
||||
items={[
|
||||
<EuiButton color="ghost" fill onClick={onBack}>
|
||||
{i18n.translate('xpack.observability_onboarding.steps.back', {
|
||||
defaultMessage: 'Back',
|
||||
})}
|
||||
</EuiButton>,
|
||||
<></>,
|
||||
]}
|
||||
/>
|
||||
</StepPanel>
|
||||
);
|
||||
}
|
||||
|
||||
function LogsTypeSection({
|
||||
title,
|
||||
children,
|
||||
}: PropsWithChildren<{ title: string }>) {
|
||||
return (
|
||||
<>
|
||||
<EuiTitle size="s">
|
||||
<h3>{title}</h3>
|
||||
</EuiTitle>
|
||||
<EuiSpacer size="m" />
|
||||
{children}
|
||||
</>
|
||||
);
|
||||
}
|
||||
|
||||
function OptionCard({
|
||||
title,
|
||||
iconType,
|
||||
onClick,
|
||||
description,
|
||||
}: {
|
||||
title: string;
|
||||
iconType: EuiIconProps['type'];
|
||||
onClick: () => void;
|
||||
description: string;
|
||||
}) {
|
||||
return (
|
||||
<EuiCard
|
||||
layout="horizontal"
|
||||
icon={<EuiIcon type={iconType} size="l" />}
|
||||
title={title}
|
||||
titleSize="xs"
|
||||
paddingSize="m"
|
||||
onClick={onClick}
|
||||
hasBorder={true}
|
||||
description={description}
|
||||
/>
|
||||
);
|
||||
}
|
|
@ -25,7 +25,7 @@ import { breadcrumbsApp } from '../../../application/app';
|
|||
export function Home() {
|
||||
useBreadcrumbs([], breadcrumbsApp);
|
||||
|
||||
const navigateToKibanaUrl = useKibanaNavigation();
|
||||
const { navigateToKibanaUrl } = useKibanaNavigation();
|
||||
|
||||
const handleClickSystemLogs = () => {};
|
||||
const handleClickCustomLogs = () => {
|
||||
|
|
|
@ -15,13 +15,17 @@ interface ObservabilityOnboardingAppServices {
|
|||
|
||||
export function useKibanaNavigation() {
|
||||
const {
|
||||
application: { navigateToUrl },
|
||||
application: { navigateToUrl, navigateToApp },
|
||||
http: { basePath },
|
||||
} = useKibana<ObservabilityOnboardingAppServices>().services;
|
||||
|
||||
const navigateToKibanaUrl = (kibanaPath: string) => {
|
||||
navigateToUrl(basePath.prepend(kibanaPath));
|
||||
navigateToUrl(basePath.prepend(kibanaPath), {});
|
||||
};
|
||||
|
||||
return navigateToKibanaUrl;
|
||||
const navigateToAppUrl = (path: string) => {
|
||||
navigateToApp('', { path, openInNewTab: true });
|
||||
};
|
||||
|
||||
return { navigateToKibanaUrl, navigateToAppUrl };
|
||||
}
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue