Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

feat(issue-views): Update banner and tooltip copy, make banner dismissable, feedback -> read docs #77878

Draft
wants to merge 2 commits into
base: master
Choose a base branch
from
Draft
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
2 changes: 2 additions & 0 deletions static/app/utils/analytics/issueAnalyticsEvents.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -221,6 +221,7 @@ export type IssueEventParameters = {
search_source: string;
search_type: string;
};
'issue_views.add_view.banner_dismissed': {};
'issue_views.add_view.clicked': {};
'issue_views.add_view.custom_query_saved': {
query: string;
Expand Down Expand Up @@ -386,6 +387,7 @@ export const issueEventMap: Record<IssueEventKey, string | null> = {
'Issue Views: Custom Query Saved From Add View',
'issue_views.add_view.saved_search_saved': 'Issue Views: Saved Search Saved',
'issue_views.add_view.recommended_view_saved': 'Issue Views: Recommended View Saved',
'issue_views.add_view.banner_dismissed': 'Issue Views: Add View Banner Dismissed',
'issue_views.shared_view_opened': 'Issue Views: Shared View Opened',
'issue_views.temp_view_discarded': 'Issue Views: Temporary View Discarded',
'issue_views.temp_view_saved': 'Issue Views: Temporary View Saved',
Expand Down
152 changes: 121 additions & 31 deletions static/app/views/issueList/addViewPage.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -3,11 +3,13 @@ import styled from '@emotion/styled';

import bannerStar from 'sentry-images/spot/banner-star.svg';

import {Button} from 'sentry/components/button';
import {usePrompt} from 'sentry/actionCreators/prompts';
import {Button, LinkButton} from 'sentry/components/button';
import InteractionStateLayer from 'sentry/components/interactionStateLayer';
import ExternalLink from 'sentry/components/links/externalLink';
import QuestionTooltip from 'sentry/components/questionTooltip';
import {FormattedQuery} from 'sentry/components/searchQueryBuilder/formattedQuery';
import {IconMegaphone} from 'sentry/icons';
import {IconClose, IconMegaphone} from 'sentry/icons';
import {t} from 'sentry/locale';
import {space} from 'sentry/styles/space';
import type {SavedSearch} from 'sentry/types/group';
Expand Down Expand Up @@ -42,35 +44,34 @@ const RECOMMENDED_SEARCHES: SearchSuggestion[] = [
];

function AddViewPage({savedSearches}: {savedSearches: SavedSearch[]}) {
const toolTipContents = (
<Container>
{t(
'Saved searches will be deprecated soon. For any you wish to return to, please save them as views.'
)}
<ExternalLink href={'https://docs.sentry.io/product/issues/issue-views'}>
{t('Learn More')}
</ExternalLink>
</Container>
);

const savedSearchTitle = (
<SavedSearchesTitle>
{t('Saved Searches (will be deprecated)')}
<QuestionTooltip
icon="info"
title={t(
'Saved searches will be deprecated soon. For any you wish to return to, please save them as views.'
)}
title={toolTipContents}
size="sm"
position="top"
skipWrapper
isHoverable
/>
</SavedSearchesTitle>
);

return (
<AddViewWrapper>
<Banner>
<BannerStar1 src={bannerStar} />
<BannerStar2 src={bannerStar} />
<BannerStar3 src={bannerStar} />
<Title>{t('Find what you need, faster')}</Title>
<SubTitle>
{t(
"Save your issue searches for quick access. Views are for your eyes only – no need to worry about messing up other team members' views."
)}
</SubTitle>
<FeedbackButton />
</Banner>
<AddViewBanner hasSavedSearches={savedSearches && savedSearches.length !== 0} />
<SearchSuggestionList
title={'Recommended Searches'}
searchSuggestions={RECOMMENDED_SEARCHES}
Expand All @@ -92,6 +93,67 @@ function AddViewPage({savedSearches}: {savedSearches: SavedSearch[]}) {
);
}

function AddViewBanner({hasSavedSearches}: {hasSavedSearches: boolean}) {
const organization = useOrganization();

const {isPromptDismissed, dismissPrompt} = usePrompt({
feature: 'issue_views_add_view_banner',
organization,
});

return !isPromptDismissed ? (
<Banner>
<BannerStar1 src={bannerStar} />
<BannerStar2 src={bannerStar} />
<BannerStar3 src={bannerStar} />
<Title>
{t('Welcome to the new Issue Views experience (Early Adopter only)')}
<DismissButton
analyticsEventKey="issue_views.add_view.banner_dismissed"
analyticsEventName="'Issue Views: Add View Banner Dismissed"
size="zero"
borderless
icon={<IconClose size="xs" />}
aria-label={t('Dismiss')}
onClick={() => dismissPrompt()}
/>
</Title>
<SubTitle>
<div>
{t(
'Issues just got a lot more personalized! Save your frequent issue searches for quick access.'
)}
</div>
<div>{t('A few notes before you get started:')}</div>
<AFewNotesList>
<li>
<b>Views are for your eyes only.</b> No need to worry about messing up other
team members' views
</li>
<li>
<b>Drag your views to reorder.</b> The leftmost view is your “default”
experience
</li>
{hasSavedSearches && (
<li>
<b>Custom searches will be deprecated in the future. </b> You can save them
as views from the list below (only appears if you have custom searches)
</li>
)}
</AFewNotesList>
</SubTitle>
<FittedLinkButton
size="sm"
href="https://docs.sentry.io/product/issues/issue-views"
external
>
{t('Read Docs')}
</FittedLinkButton>
<FeedbackButton />
</Banner>
) : null;
}

function SearchSuggestionList({
title,
searchSuggestions,
Expand All @@ -100,6 +162,15 @@ function SearchSuggestionList({
const {onNewViewSaved} = useContext(NewTabContext);
const organization = useOrganization();

const analyticsKey =
type === 'recommended'
? 'issue_views.add_view.recommended_view_saved'
: 'issue_views.add_view.saved_search_saved';
const analyticsEventName =
type === 'recommended'
? 'Issue Views: Recommended View Saved'
: 'Issue Views: Saved Search Saved';

return (
<Suggestions>
<TitleWrapper>{title}</TitleWrapper>
Expand All @@ -109,10 +180,6 @@ function SearchSuggestionList({
key={index}
onClick={() => {
onNewViewSaved?.(suggestion.label, suggestion.query, false);
const analyticsKey =
type === 'recommended'
? 'issue_views.add_view.recommended_view_saved'
: 'issue_views.add_view.saved_search_saved';
trackAnalytics(analyticsKey, {
organization,
persisted: false,
Expand All @@ -136,16 +203,13 @@ function SearchSuggestionList({
onClick={e => {
e.stopPropagation();
onNewViewSaved?.(suggestion.label, suggestion.query, true);
const analyticsKey =
type === 'recommended'
? 'issue_views.add_view.recommended_view_saved'
: 'issue_views.add_view.saved_search_saved';
trackAnalytics(analyticsKey, {
organization,
persisted: true,
label: suggestion.label,
query: suggestion.query,
});
}}
analyticsEventKey={analyticsKey}
analyticsEventName={analyticsEventName}
analyticsParams={{
persisted: true,
label: suggestion.label,
query: suggestion.query,
}}
borderless
>
Expand Down Expand Up @@ -289,8 +353,11 @@ const Title = styled('div')`
`;

const SubTitle = styled('div')`
display: flex;
flex-direction: column;
font-weight: ${p => p.theme.fontWeightNormal};
font-size: ${p => p.theme.fontSizeMedium};
gap: ${space(0.5)};
`;

const AddViewWrapper = styled('div')`
Expand Down Expand Up @@ -334,3 +401,26 @@ const BannerStar3 = styled('img')`
display: none;
}
`;

const Container = styled('div')`
display: inline-flex;
flex-direction: column;
align-items: flex-start;
text-align: left;
gap: ${space(1)};
`;

const AFewNotesList = styled('ul')`
margin-bottom: ${space(0.5)};
`;

const FittedLinkButton = styled(LinkButton)`
width: fit-content;
`;

const DismissButton = styled(Button)`
position: absolute;
top: ${space(1)};
right: ${space(1)};
color: ${p => p.theme.subText};
`;
Loading