-
-
Notifications
You must be signed in to change notification settings - Fork 4.2k
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
feat(explore): Add group by to explore toolbar (#76879)
This adds a basic way for users to add group bys by selecting span attributes.
- Loading branch information
Showing
11 changed files
with
224 additions
and
18 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,42 @@ | ||
import {createMemoryHistory, Route, Router, RouterContext} from 'react-router'; | ||
|
||
import {act, render} from 'sentry-test/reactTestingLibrary'; | ||
|
||
import {useGroupBys} from 'sentry/views/explore/hooks/useGroupBys'; | ||
import {RouteContext} from 'sentry/views/routeContext'; | ||
|
||
describe('useGroupBys', function () { | ||
it('allows changing group bys', function () { | ||
let groupBys, setGroupBys; | ||
|
||
function TestPage() { | ||
[groupBys, setGroupBys] = useGroupBys(); | ||
return null; | ||
} | ||
|
||
const memoryHistory = createMemoryHistory(); | ||
|
||
render( | ||
<Router | ||
history={memoryHistory} | ||
render={props => { | ||
return ( | ||
<RouteContext.Provider value={props}> | ||
<RouterContext {...props} /> | ||
</RouteContext.Provider> | ||
); | ||
}} | ||
> | ||
<Route path="/" component={TestPage} /> | ||
</Router> | ||
); | ||
|
||
expect(groupBys).toEqual(['']); // default | ||
|
||
act(() => setGroupBys(['foo', 'bar'])); | ||
expect(groupBys).toEqual(['foo', 'bar']); | ||
|
||
act(() => setGroupBys([])); | ||
expect(groupBys).toEqual(['']); // default | ||
}); | ||
}); |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,50 @@ | ||
import {useCallback, useMemo} from 'react'; | ||
import type {Location} from 'history'; | ||
|
||
import {decodeList} from 'sentry/utils/queryString'; | ||
import {useLocation} from 'sentry/utils/useLocation'; | ||
import {useNavigate} from 'sentry/utils/useNavigate'; | ||
import type {Field} from 'sentry/views/explore/hooks/useSampleFields'; | ||
|
||
interface Options { | ||
location: Location; | ||
navigate: ReturnType<typeof useNavigate>; | ||
} | ||
|
||
export function useGroupBys(): [Field[], (fields: Field[]) => void] { | ||
const location = useLocation(); | ||
const navigate = useNavigate(); | ||
const options = {location, navigate}; | ||
|
||
return useGroupBysImpl(options); | ||
} | ||
|
||
function useGroupBysImpl({ | ||
location, | ||
navigate, | ||
}: Options): [Field[], (fields: Field[]) => void] { | ||
const groupBys = useMemo(() => { | ||
const rawGroupBys = decodeList(location.query.groupBy); | ||
|
||
if (rawGroupBys.length) { | ||
return rawGroupBys; | ||
} | ||
|
||
return ['']; | ||
}, [location.query.groupBy]); | ||
|
||
const setGroupBys = useCallback( | ||
(newGroupBys: Field[]) => { | ||
navigate({ | ||
...location, | ||
query: { | ||
...location.query, | ||
groupBy: newGroupBys, | ||
}, | ||
}); | ||
}, | ||
[location, navigate] | ||
); | ||
|
||
return [groupBys, setGroupBys]; | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -1,15 +1,68 @@ | ||
import {useCallback, useMemo} from 'react'; | ||
|
||
import type {SelectOption} from 'sentry/components/compactSelect'; | ||
import {CompactSelect} from 'sentry/components/compactSelect'; | ||
import {t} from 'sentry/locale'; | ||
import {useGroupBys} from 'sentry/views/explore/hooks/useGroupBys'; | ||
import type {Field} from 'sentry/views/explore/hooks/useSampleFields'; | ||
import {useSpanFieldSupportedTags} from 'sentry/views/performance/utils/useSpanFieldSupportedTags'; | ||
|
||
import {ToolbarHeading, ToolbarSection} from './styles'; | ||
import { | ||
ToolbarHeader, | ||
ToolbarHeaderButton, | ||
ToolbarHeading, | ||
ToolbarSection, | ||
} from './styles'; | ||
|
||
interface ToolbarGroupByProps { | ||
disabled?: boolean; | ||
} | ||
export function ToolbarGroupBy() { | ||
// TODO: This should be loaded from context to avoid loading tags twice. | ||
const tags = useSpanFieldSupportedTags(); | ||
|
||
const [groupBys, setGroupBys] = useGroupBys(); | ||
|
||
const options: SelectOption<Field>[] = useMemo(() => { | ||
return [ | ||
// hard code in an empty option | ||
{label: t('(none)'), value: ''}, | ||
...Object.entries(tags).map(([tagKey, tag]) => { | ||
return { | ||
label: tag.name, | ||
value: tagKey, | ||
}; | ||
}), | ||
]; | ||
}, [tags]); | ||
|
||
const addGroupBy = useCallback(() => { | ||
setGroupBys([...groupBys, '']); | ||
}, [setGroupBys, groupBys]); | ||
|
||
const setGroupBy = useCallback( | ||
(i: number, {value}: SelectOption<Field>) => { | ||
const newGroupBys = groupBys.slice(); | ||
newGroupBys[i] = value; | ||
setGroupBys(newGroupBys); | ||
}, | ||
[setGroupBys, groupBys] | ||
); | ||
|
||
export function ToolbarGroupBy({disabled}: ToolbarGroupByProps) { | ||
return ( | ||
<ToolbarSection> | ||
<ToolbarHeading disabled={disabled}>{t('Group By')}</ToolbarHeading> | ||
<ToolbarSection data-test-id="section-group-by"> | ||
<ToolbarHeader> | ||
<ToolbarHeading>{t('Group By')}</ToolbarHeading> | ||
<ToolbarHeaderButton size="xs" onClick={addGroupBy} borderless> | ||
{t('+Add Group By')} | ||
</ToolbarHeaderButton> | ||
</ToolbarHeader> | ||
{groupBys.map((groupBy, index) => ( | ||
<CompactSelect | ||
key={index} | ||
size="md" | ||
options={options} | ||
value={groupBy} | ||
onChange={newGroupBy => setGroupBy(index, newGroupBy)} | ||
/> | ||
))} | ||
</ToolbarSection> | ||
); | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -1,13 +1,15 @@ | ||
import {t} from 'sentry/locale'; | ||
|
||
import {ToolbarHeading, ToolbarSection} from './styles'; | ||
import {ToolbarHeader, ToolbarHeading, ToolbarSection} from './styles'; | ||
|
||
interface ToolbarLimitToProps {} | ||
|
||
export function ToolbarLimitTo({}: ToolbarLimitToProps) { | ||
return ( | ||
<ToolbarSection> | ||
<ToolbarHeading>{t('Limit To')}</ToolbarHeading> | ||
<ToolbarHeader> | ||
<ToolbarHeading>{t('Limit To')}</ToolbarHeading> | ||
</ToolbarHeader> | ||
</ToolbarSection> | ||
); | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters