import {initializeOrg} from 'sentry-test/initializeOrg';
import {act, render, screen, userEvent, waitFor} from 'sentry-test/reactTestingLibrary';
import {textWithMarkupMatcher} from 'sentry-test/utils';
import {generateOnboardingDocKeys} from 'sentry/components/performanceOnboarding/usePerformanceOnboardingDocs';
import SidebarContainer from 'sentry/components/sidebar';
import {SidebarPanelKey} from 'sentry/components/sidebar/types';
import PageFiltersStore from 'sentry/stores/pageFiltersStore';
import {PersistedStoreProvider} from 'sentry/stores/persistedStore';
import ProjectsStore from 'sentry/stores/projectsStore';
import SidebarPanelStore from 'sentry/stores/sidebarPanelStore';
import {OrganizationContext} from 'sentry/views/organizationContext';
import {RouteContext} from 'sentry/views/routeContext';
jest.mock('sentry/actionCreators/serviceIncidents');
describe('Sidebar > Performance Onboarding Checklist', function () {
const {organization, router} = initializeOrg({
router: {
location: {query: {}, search: ''},
push: jest.fn(),
},
} as any);
const broadcast = TestStubs.Broadcast();
const apiMocks: any = {};
const location = {...router.location, ...{pathname: '/test/'}};
const getElement = props => {
return (
);
};
const renderSidebar = props => render(getElement(props));
beforeEach(function () {
jest.resetAllMocks();
PageFiltersStore.init();
PageFiltersStore.onInitializeUrlState(
{
projects: [],
environments: [],
datetime: {start: null, end: null, period: '24h', utc: null},
},
new Set()
);
apiMocks.broadcasts = MockApiClient.addMockResponse({
url: `/organizations/${organization.slug}/broadcasts/`,
body: [broadcast],
});
});
afterEach(() => {
MockApiClient.clearMockResponses();
PageFiltersStore.teardown();
});
it('displays boost performance card', async function () {
const {container} = renderSidebar({
organization: {
...organization,
features: ['onboarding'],
},
});
await waitFor(() => container);
const quickStart = screen.getByText('Quick Start');
expect(quickStart).toBeInTheDocument();
userEvent.click(quickStart);
const sidebar = await screen.findByRole('dialog');
expect(sidebar).toBeInTheDocument();
expect(screen.getByText('Capture your first error')).toBeInTheDocument();
expect(screen.getByText('Level Up')).toBeInTheDocument();
expect(screen.getByText('Boost performance')).toBeInTheDocument();
userEvent.click(quickStart);
expect(screen.queryByText('Boost performance')).not.toBeInTheDocument();
});
it('checklist feature disabled', async function () {
const {container} = renderSidebar({
organization: {
...organization,
features: ['onboarding'],
},
});
await waitFor(() => container);
window.open = jest.fn().mockImplementation(() => true);
const quickStart = screen.getByText('Quick Start');
expect(quickStart).toBeInTheDocument();
userEvent.click(quickStart);
const sidebar = await screen.findByRole('dialog');
expect(sidebar).toBeInTheDocument();
expect(screen.getByText('Capture your first error')).toBeInTheDocument();
expect(screen.getByText('Level Up')).toBeInTheDocument();
expect(screen.getByText('Boost performance')).toBeInTheDocument();
const performanceCard = screen.getByTestId('setup_transactions');
userEvent.click(performanceCard);
expect(window.open).toHaveBeenCalledWith(
'https://docs.sentry.io/product/performance/getting-started/',
'_blank'
);
});
it('checklist feature enabled > navigate to performance page > project with onboarding support', async function () {
ProjectsStore.loadInitialData([
TestStubs.Project({platform: 'javascript-react', firstTransactionEvent: false}),
]);
const {container} = renderSidebar({
organization: {
...organization,
features: ['onboarding', 'performance-onboarding-checklist'],
},
});
await waitFor(() => container);
window.open = jest.fn().mockImplementation(() => true);
const quickStart = screen.getByText('Quick Start');
expect(quickStart).toBeInTheDocument();
userEvent.click(quickStart);
const sidebar = await screen.findByRole('dialog');
expect(sidebar).toBeInTheDocument();
expect(screen.getByText('Capture your first error')).toBeInTheDocument();
expect(screen.getByText('Level Up')).toBeInTheDocument();
expect(screen.getByText('Boost performance')).toBeInTheDocument();
const performanceCard = screen.getByTestId('setup_transactions');
userEvent.click(performanceCard);
expect(window.open).not.toHaveBeenCalled();
expect(router.push).toHaveBeenCalledWith(
'/organizations/org-slug/performance/?project=2#performance-sidequest'
);
});
it('checklist feature enabled > navigate to performance page > project without onboarding support', async function () {
ProjectsStore.loadInitialData([
TestStubs.Project({platform: 'javascript-angular', firstTransactionEvent: false}),
]);
const {container} = renderSidebar({
organization: {
...organization,
features: ['onboarding', 'performance-onboarding-checklist'],
},
});
await waitFor(() => container);
window.open = jest.fn().mockImplementation(() => true);
const quickStart = screen.getByText('Quick Start');
expect(quickStart).toBeInTheDocument();
userEvent.click(quickStart);
const sidebar = await screen.findByRole('dialog');
expect(sidebar).toBeInTheDocument();
expect(screen.getByText('Capture your first error')).toBeInTheDocument();
expect(screen.getByText('Level Up')).toBeInTheDocument();
expect(screen.getByText('Boost performance')).toBeInTheDocument();
const performanceCard = screen.getByTestId('setup_transactions');
userEvent.click(performanceCard);
expect(window.open).not.toHaveBeenCalled();
expect(router.push).toHaveBeenCalledWith(
'/organizations/org-slug/performance/?project=2#performance-sidequest'
);
});
it('checklist feature enabled > navigate to performance page > project without performance support', async function () {
ProjectsStore.loadInitialData([
TestStubs.Project({platform: 'elixir', firstTransactionEvent: false}),
]);
const {container} = renderSidebar({
organization: {
...organization,
features: ['onboarding', 'performance-onboarding-checklist'],
},
});
await waitFor(() => container);
window.open = jest.fn().mockImplementation(() => true);
const quickStart = screen.getByText('Quick Start');
expect(quickStart).toBeInTheDocument();
userEvent.click(quickStart);
const sidebar = await screen.findByRole('dialog');
expect(sidebar).toBeInTheDocument();
expect(screen.getByText('Capture your first error')).toBeInTheDocument();
expect(screen.getByText('Level Up')).toBeInTheDocument();
expect(screen.getByText('Boost performance')).toBeInTheDocument();
const performanceCard = screen.getByTestId('setup_transactions');
userEvent.click(performanceCard);
expect(window.open).not.toHaveBeenCalled();
expect(router.push).toHaveBeenCalledWith('/organizations/org-slug/performance/');
});
it('displays checklist', async function () {
const project = TestStubs.Project({
platform: 'javascript-react',
firstTransactionEvent: false,
});
ProjectsStore.loadInitialData([project]);
const docApiMocks: any = {};
const docKeys = generateOnboardingDocKeys(project.platform);
docKeys.forEach(docKey => {
docApiMocks[docKey] = MockApiClient.addMockResponse({
url: `/projects/${organization.slug}/${project.slug}/docs/${docKey}/`,
method: 'GET',
body: {html: `
${docKey}
content`},
});
});
MockApiClient.addMockResponse({
url: `/projects/${organization.slug}/${project.slug}/`,
method: 'GET',
body: {},
});
renderSidebar({
organization: {
...organization,
features: ['onboarding', 'performance-onboarding-checklist'],
},
});
act(() => {
SidebarPanelStore.activatePanel(SidebarPanelKey.PerformanceOnboarding);
});
expect(
await screen.findByText(
textWithMarkupMatcher('Adding Performance to your React project is simple.')
)
).toBeInTheDocument();
for (const docKey of docKeys) {
expect(
await screen.findByText(textWithMarkupMatcher(`${docKey} content`))
).toBeInTheDocument();
}
});
});