diff --git a/client/web/src/enterprise/insights/pages/getting-started/CodeInsightsExamples.module.scss b/client/web/src/enterprise/insights/pages/getting-started/CodeInsightsExamples.module.scss new file mode 100644 index 00000000000..f564b39443a --- /dev/null +++ b/client/web/src/enterprise/insights/pages/getting-started/CodeInsightsExamples.module.scss @@ -0,0 +1,50 @@ +.section { + display: flex; + flex-wrap: wrap; + gap: 1rem; +} + +.card { + flex: 1; + flex-basis: 25rem; +} + +.chart { + min-height: 15rem; + flex-grow: 1; + width: 100%; + position: relative; + flex-basis: 18rem; +} + +.chart-content { + position: absolute; + width: 100%; + height: 100%; + top: 0; + left: 0; +} + +.legend { + display: flex; + flex-direction: column; + gap: 0.5rem; + margin-top: 1rem; + + &--horizontal { + flex-direction: column; + } +} + +.code { + background-color: var(--gray-01); + padding: 0.25rem 0.5rem; + width: 100%; + display: inline-block; + border-radius: var(--border-radius); +} + +.capture-group { + display: flex; + height: 100%; +} diff --git a/client/web/src/enterprise/insights/pages/getting-started/CodeInsightsExamples.story.tsx b/client/web/src/enterprise/insights/pages/getting-started/CodeInsightsExamples.story.tsx new file mode 100644 index 00000000000..c02e46d8c33 --- /dev/null +++ b/client/web/src/enterprise/insights/pages/getting-started/CodeInsightsExamples.story.tsx @@ -0,0 +1,13 @@ +import { Meta } from '@storybook/react' +import React from 'react' + +import { WebStory } from '../../../../components/WebStory' + +import { CodeInsightsExamples } from './CodeInsightsExamples' + +export default { + title: 'web/insights/getting-started/CodeInsightExamples', + decorators: [story => {() => story()}], +} as Meta + +export const StandardExample = () => diff --git a/client/web/src/enterprise/insights/pages/getting-started/CodeInsightsExamples.tsx b/client/web/src/enterprise/insights/pages/getting-started/CodeInsightsExamples.tsx new file mode 100644 index 00000000000..875cfb0a5ba --- /dev/null +++ b/client/web/src/enterprise/insights/pages/getting-started/CodeInsightsExamples.tsx @@ -0,0 +1,155 @@ +import { ParentSize } from '@visx/responsive' +import classNames from 'classnames' +import React from 'react' +import { LineChartContent, LineChartContent as LineChartContentType, LineChartSeries } from 'sourcegraph' + +import * as View from '../../../../views' +import { LegendBlock, LegendItem } from '../../../../views' +import { + getLineStroke, + LineChart, +} from '../../../../views/components/view/content/chart-view-content/charts/line/components/LineChartContent' + +import styles from './CodeInsightsExamples.module.scss' + +export const CodeInsightsExamples: React.FunctionComponent = () => ( +
+ + +
+) + +interface ExampleCardProps { + className?: string +} + +interface SeriesWithQuery extends LineChartSeries { + query: string +} + +type Content = Omit, 'chart' | 'series'> & { series: SeriesWithQuery[] } + +const SEARCH_INSIGHT_EXAMPLES_DATA: Content = { + data: [ + { x: 1588965700286 - 4 * 24 * 60 * 60 * 1000, a: null, b: null }, + { x: 1588965700286 - 3 * 24 * 60 * 60 * 1000, a: null, b: null }, + { x: 1588965700286 - 2 * 24 * 60 * 60 * 1000, a: 94, b: 200 }, + { x: 1588965700286 - 1.5 * 24 * 60 * 60 * 1000, a: 134, b: null }, + { x: 1588965700286 - 1.3 * 24 * 60 * 60 * 1000, a: null, b: 150 }, + { x: 1588965700286 - 1 * 24 * 60 * 60 * 1000, a: 134, b: 190 }, + { x: 1588965700286, a: 123, b: 170 }, + ], + series: [ + { + dataKey: 'a', + name: 'A metric', + stroke: 'var(--blue)', + query: 'file:README archived:no fork:no', + }, + { + dataKey: 'b', + name: 'B metric', + stroke: 'var(--warning)', + query: '-file:README archived:no fork:no', + }, + ], + xAxis: { + dataKey: 'x', + scale: 'time', + type: 'number', + }, +} + +export const CodeInsightSearchExample: React.FunctionComponent = props => { + const { className } = props + + return ( + All repositories} + className={classNames(className)} + > +
+ + {({ width, height }) => ( + + )} + +
+ + + {SEARCH_INSIGHT_EXAMPLES_DATA.series.map(line => ( + (line)}> + {line.name} + {line.query} + + ))} + +
+ ) +} + +const CAPTURE_INSIGHT_EXAMPLES_DATA: LineChartContent = { + chart: 'line' as const, + data: [ + { x: 1588965700286 - 6 * 24 * 60 * 60 * 1000, a: 20, b: 200 }, + { x: 1588965700286 - 5 * 24 * 60 * 60 * 1000, a: 40, b: 177 }, + { x: 1588965700286 - 4 * 24 * 60 * 60 * 1000, a: 110, b: 150 }, + { x: 1588965700286 - 3 * 24 * 60 * 60 * 1000, a: 105, b: 165 }, + { x: 1588965700286 - 2 * 24 * 60 * 60 * 1000, a: 160, b: 100 }, + { x: 1588965700286 - 1 * 24 * 60 * 60 * 1000, a: 184, b: 85 }, + { x: 1588965700286, a: 200, b: 50 }, + ], + series: [ + { + dataKey: 'a', + name: 'Go 1.11', + stroke: 'var(--oc-indigo-7)', + }, + { + dataKey: 'b', + name: 'Go 1.12', + stroke: 'var(--oc-orange-7)', + }, + ], + xAxis: { + dataKey: 'x', + scale: 'time' as const, + type: 'number', + }, +} + +export const CodeInsightCaptureExample: React.FunctionComponent = props => { + const { className } = props + + return ( + repo:github.com/awesomeOrg/examplerepo} + className={classNames(className)} + > +
+
+ + {({ width, height }) => ( + + )} + +
+ + + {CAPTURE_INSIGHT_EXAMPLES_DATA.series.map(line => ( + (line)}> + {line.name} + + ))} + +
+ nvm install ([0-9]+\.[0-9]+) archived:no fork:no +
+ ) +} + +const InlineCodeBlock: React.FunctionComponent> = props => ( + {props.children} +) diff --git a/client/web/src/views/components/view/View.tsx b/client/web/src/views/components/view/View.tsx index 98e28f5dcc8..4d932774eb9 100644 --- a/client/web/src/views/components/view/View.tsx +++ b/client/web/src/views/components/view/View.tsx @@ -14,7 +14,7 @@ type ViewCardElementProps = React.DetailedHTMLProps /** @@ -35,7 +35,6 @@ export const View: React.FunctionComponent> = p (props: LineChartProps): R hasViewManySeries && hasEnoughXSpace return ( - -
- {/* - In case if we have a legend to render we have to have responsive container for chart - just to calculate right sizes for chart content = rootContainerSizes - legendSizes - */} - - {({ width, height }) => } - +
+ {/* + In case if we have a legend to render we have to have responsive container for chart + just to calculate right sizes for chart content = rootContainerSizes - legendSizes + */} + + {({ width, height }) => } + - -
    - {props.series.map(line => ( -
  • -
    - {line.name} -
  • - ))} -
-
-
- + + + {props.series.map(line => ( + + {line.name} + + ))} + + +
) } + +export const LegendBlock: React.FunctionComponent> = props => ( +
    {props.children}
+) + +interface LegendItem { + color: string +} + +export const LegendItem: React.FunctionComponent = props => ( +
  • +
    + {props.children} +
  • +) diff --git a/client/web/src/views/components/view/content/chart-view-content/charts/line/components/LineChartContent.module.scss b/client/web/src/views/components/view/content/chart-view-content/charts/line/components/LineChartContent.module.scss index b63d465c70d..1be6d274200 100644 --- a/client/web/src/views/components/view/content/chart-view-content/charts/line/components/LineChartContent.module.scss +++ b/client/web/src/views/components/view/content/chart-view-content/charts/line/components/LineChartContent.module.scss @@ -1,10 +1,4 @@ .content { - position: absolute; - width: 100%; - height: 100%; - top: 0; - left: 0; - &--with-cursor { cursor: pointer; } diff --git a/client/web/src/views/components/view/content/chart-view-content/charts/line/components/LineChartContent.tsx b/client/web/src/views/components/view/content/chart-view-content/charts/line/components/LineChartContent.tsx index 446ab62ce3d..a6149c4d27a 100644 --- a/client/web/src/views/components/view/content/chart-view-content/charts/line/components/LineChartContent.tsx +++ b/client/web/src/views/components/view/content/chart-view-content/charts/line/components/LineChartContent.tsx @@ -1,7 +1,16 @@ import { curveLinear } from '@visx/curve' import { GridRows } from '@visx/grid' import { Group } from '@visx/group' -import { Axis, DataProvider, GlyphSeries, LineSeries, Tooltip, TooltipProvider, XYChart } from '@visx/xychart' +import { + Axis, + DataProvider, + GlyphSeries, + LineSeries, + Tooltip, + TooltipProvider, + XYChart, + EventEmitterProvider, +} from '@visx/xychart' import { RenderTooltipParams } from '@visx/xychart/lib/components/Tooltip' import { XYCHART_EVENT_SOURCE } from '@visx/xychart/lib/constants' import isValidNumber from '@visx/xychart/lib/typeguards/isValidNumber' @@ -9,7 +18,7 @@ import { EventHandlerParams } from '@visx/xychart/lib/types' import classNames from 'classnames' import React, { ReactElement, useCallback, useMemo, useState, MouseEvent, useRef } from 'react' import { noop } from 'rxjs' -import { LineChartContent as LineChartContentType } from 'sourcegraph' +import { LineChartContent as LineChartContentType, LineChartSeries } from 'sourcegraph' import { DEFAULT_LINE_STROKE } from '../constants' import { generateAccessors } from '../helpers/generate-accessors' @@ -43,9 +52,8 @@ const SCALES_CONFIG = { } // Line color accessor -export const getLineStroke = ( - line: LineChartContentType['series'][number] -): string => line?.stroke ?? DEFAULT_LINE_STROKE +export const getLineStroke = (line: LineChartSeries): string => + line?.stroke ?? DEFAULT_LINE_STROKE const stopPropagation = (event: React.MouseEvent): void => event.stopPropagation() @@ -70,6 +78,14 @@ export interface LineChartContentProps onDatumLinkClick?: (event: React.MouseEvent) => void } +export function LineChart(props: LineChartContentProps): ReactElement { + return ( + + + + ) +} + /** * Displays line chart content - line chart, tooltip, active point */ @@ -220,7 +236,7 @@ export function LineChartContent(props: LineChartContentPr const hoveredDatumLink = hoveredDatum ? hoveredDatumLinks[+hoveredDatum.datum.x] ?? hoveredDatumLinks[hoveredDatum.index] : null - const rootClasses = classNames(styles.content, { [styles.contentWithCursor]: !!hoveredDatumLink }) + const rootClasses = classNames({ [styles.contentWithCursor]: !!hoveredDatumLink }) return (
    diff --git a/client/web/src/views/components/view/content/chart-view-content/charts/line/index.ts b/client/web/src/views/components/view/content/chart-view-content/charts/line/index.ts index e0bf4f45776..882fed8174f 100644 --- a/client/web/src/views/components/view/content/chart-view-content/charts/line/index.ts +++ b/client/web/src/views/components/view/content/chart-view-content/charts/line/index.ts @@ -1,3 +1,4 @@ -export { LineChart } from './LineChart' +export { LineChart, LegendBlock, LegendItem } from './LineChart' export { LineChartSettingsContext, LineChartLayoutOrientation } from './line-chart-settings-provider' export { EMPTY_DATA_POINT_VALUE, DEFAULT_LINE_STROKE } from './constants' +export { getLineStroke } from './components/LineChartContent' diff --git a/sg.config.yaml b/sg.config.yaml index 799216ba9e2..b125f1ef688 100644 --- a/sg.config.yaml +++ b/sg.config.yaml @@ -317,7 +317,7 @@ commands: install: yarn --no-progress env: WEBPACK_SERVE_INDEX: true - SOURCEGRAPH_API_URL: https://sourcegraph.com + SOURCEGRAPH_API_URL: https://k8s.sgdev.org web-standalone-http-prod: cmd: yarn workspace @sourcegraph/web serve:prod