Просмотр исходного кода

feat(ui): Release Details Sidebar component update (#29842)

* feat(ui): Release Details Sidebar component update

Update design of release details sidebar and add new component to keep the sidebar headers/content/etc consistent.

FIXES WOR-1313

* rename releasesidebarsection to sidebarsection

* add margin to sidebarsection component, remove wrapper style from release detail sidebar sections

* remove unused styles file
Kelly Carino 3 лет назад
Родитель
Сommit
57faeacccb

+ 47 - 0
static/app/components/sidebarSection.tsx

@@ -0,0 +1,47 @@
+import * as React from 'react';
+import styled from '@emotion/styled';
+
+import space from 'app/styles/space';
+
+type Props = {
+  title: React.ReactNode;
+  children?: React.ReactNode;
+  icon?: React.ReactNode;
+};
+
+/**
+ * Used to add the new sidebar section on a page.
+ */
+function SidebarSection({title, children, icon, ...props}: Props) {
+  return (
+    <Wrapper>
+      <Heading {...props}>
+        {title}
+        {icon && <IconWrapper>{icon}</IconWrapper>}
+      </Heading>
+      <SectionContent>{children}</SectionContent>
+    </Wrapper>
+  );
+}
+
+const Wrapper = styled('div')`
+  margin-bottom: ${space(3)};
+`;
+
+const Heading = styled('h6')`
+  color: ${p => p.theme.textColor};
+  display: flex;
+  font-size: ${p => p.theme.fontSizeMedium};
+  margin: ${space(1)} 0;
+`;
+
+const IconWrapper = styled('div')`
+  color: ${p => p.theme.subText};
+  margin-left: ${space(0.5)};
+`;
+
+const SectionContent = styled('div')`
+  color: ${p => p.theme.subText};
+`;
+
+export default SidebarSection;

+ 0 - 35
static/app/components/sidebarSectionTitle.tsx

@@ -1,35 +0,0 @@
-import * as React from 'react';
-import styled from '@emotion/styled';
-
-import space from 'app/styles/space';
-
-type Props = {
-  title: React.ReactNode;
-  icon?: React.ReactNode;
-};
-
-/**
- * Used to add a new subheading in a sidebar section.
- */
-function SidebarSectionTitle({title, icon, ...props}: Props) {
-  return (
-    <Heading {...props}>
-      {title}
-      {icon && <IconWrapper>{icon}</IconWrapper>}
-    </Heading>
-  );
-}
-
-const Heading = styled('h6')`
-  color: ${p => p.theme.gray400};
-  display: flex;
-  font-size: ${p => p.theme.fontSizeMedium};
-  margin-bottom: ${space(1)};
-`;
-
-const IconWrapper = styled('div')`
-  color: ${p => p.theme.gray200};
-  margin-left: ${space(0.5)};
-`;
-
-export default SidebarSectionTitle;

+ 3 - 5
static/app/views/releases/detail/overview/sidebar/commitAuthorBreakdown.tsx

@@ -4,6 +4,7 @@ import AsyncComponent from 'app/components/asyncComponent';
 import UserAvatar from 'app/components/avatar/userAvatar';
 import Button from 'app/components/button';
 import Collapsible from 'app/components/collapsible';
+import SidebarSection from 'app/components/sidebarSection';
 import {t, tn} from 'app/locale';
 import overflowEllipsis from 'app/styles/overflowEllipsis';
 import space from 'app/styles/space';
@@ -11,8 +12,6 @@ import {Commit, User} from 'app/types';
 import {percent} from 'app/utils';
 import {userDisplayName} from 'app/utils/formatters';
 
-import {SectionHeading, Wrapper} from '../styles';
-
 type GroupedAuthorCommits = {
   [key: string]: {author: User | undefined; commitCount: number};
 };
@@ -84,8 +83,7 @@ class CommitAuthorBreakdown extends AsyncComponent<Props, State> {
     }
 
     return (
-      <Wrapper>
-        <SectionHeading>{t('Commit Author Breakdown')}</SectionHeading>
+      <SidebarSection title={t('Commit Author Breakdown')}>
         <Collapsible
           expandButton={({onExpand, numberOfHiddenItems}) => (
             <Button priority="link" onClick={onExpand}>
@@ -106,7 +104,7 @@ class CommitAuthorBreakdown extends AsyncComponent<Props, State> {
             </AuthorLine>
           ))}
         </Collapsible>
-      </Wrapper>
+      </SidebarSection>
     );
   }
 }

+ 3 - 6
static/app/views/releases/detail/overview/sidebar/deploys.tsx

@@ -1,14 +1,13 @@
 import styled from '@emotion/styled';
 
 import DeployBadge from 'app/components/deployBadge';
+import SidebarSection from 'app/components/sidebarSection';
 import TextOverflow from 'app/components/textOverflow';
 import TimeSince from 'app/components/timeSince';
 import {t} from 'app/locale';
 import space from 'app/styles/space';
 import {Deploy} from 'app/types';
 
-import {SectionHeading, Wrapper} from '../styles';
-
 type Props = {
   version: string;
   orgSlug: string;
@@ -18,9 +17,7 @@ type Props = {
 
 const Deploys = ({version, orgSlug, projectId, deploys}: Props) => {
   return (
-    <Wrapper>
-      <SectionHeading>{t('Deploys')}</SectionHeading>
-
+    <SidebarSection title={t('Deploys')}>
       {deploys.map(deploy => (
         <Row key={deploy.id}>
           <StyledDeployBadge
@@ -34,7 +31,7 @@ const Deploys = ({version, orgSlug, projectId, deploys}: Props) => {
           </TextOverflow>
         </Row>
       ))}
-    </Wrapper>
+    </SidebarSection>
   );
 };
 

+ 9 - 12
static/app/views/releases/detail/overview/sidebar/otherProjects.tsx

@@ -5,12 +5,11 @@ import Button from 'app/components/button';
 import Collapsible from 'app/components/collapsible';
 import IdBadge from 'app/components/idBadge';
 import {extractSelectionParameters} from 'app/components/organizations/globalSelectionHeader/utils';
+import SidebarSection from 'app/components/sidebarSection';
 import {t, tn} from 'app/locale';
 import space from 'app/styles/space';
 import {Organization, ReleaseProject} from 'app/types';
 
-import {SectionHeading, Wrapper} from '../styles';
-
 type Props = {
   projects: ReleaseProject[];
   location: Location;
@@ -20,15 +19,13 @@ type Props = {
 
 function OtherProjects({projects, location, version, organization}: Props) {
   return (
-    <Wrapper>
-      <SectionHeading>
-        {tn(
-          'Other Project for This Release',
-          'Other Projects for This Release',
-          projects.length
-        )}
-      </SectionHeading>
-
+    <SidebarSection
+      title={tn(
+        'Other Project for This Release',
+        'Other Projects for This Release',
+        projects.length
+      )}
+    >
       <Collapsible
         expandButton={({onExpand, numberOfHiddenItems}) => (
           <Button priority="link" onClick={onExpand}>
@@ -61,7 +58,7 @@ function OtherProjects({projects, location, version, organization}: Props) {
           </Row>
         ))}
       </Collapsible>
-    </Wrapper>
+    </SidebarSection>
   );
 }
 

+ 3 - 5
static/app/views/releases/detail/overview/sidebar/projectReleaseDetails.tsx

@@ -4,14 +4,13 @@ import Count from 'app/components/count';
 import DateTime from 'app/components/dateTime';
 import {KeyValueTable, KeyValueTableRow} from 'app/components/keyValueTable';
 import Link from 'app/components/links/link';
+import SidebarSection from 'app/components/sidebarSection';
 import TextOverflow from 'app/components/textOverflow';
 import TimeSince from 'app/components/timeSince';
 import Version from 'app/components/version';
 import {t, tn} from 'app/locale';
 import {ReleaseMeta, ReleaseWithHealth} from 'app/types';
 
-import {SectionHeading, Wrapper} from '../styles';
-
 type Props = {
   release: ReleaseWithHealth;
   releaseMeta: ReleaseMeta;
@@ -23,8 +22,7 @@ const ProjectReleaseDetails = ({release, releaseMeta, orgSlug, projectSlug}: Pro
   const {version, versionInfo, dateCreated, firstEvent, lastEvent} = release;
 
   return (
-    <Wrapper>
-      <SectionHeading>{t('Project Release Details')}</SectionHeading>
+    <SidebarSection title={t('Project Release Details')}>
       <KeyValueTable>
         <KeyValueTableRow
           keyName={t('Created')}
@@ -64,7 +62,7 @@ const ProjectReleaseDetails = ({release, releaseMeta, orgSlug, projectSlug}: Pro
           }
         />
       </KeyValueTable>
-    </Wrapper>
+    </SidebarSection>
   );
 };
 

+ 22 - 26
static/app/views/releases/detail/overview/sidebar/releaseAdoption.tsx

@@ -11,7 +11,7 @@ import TransitionChart from 'app/components/charts/transitionChart';
 import TransparentLoadingMask from 'app/components/charts/transparentLoadingMask';
 import NotAvailable from 'app/components/notAvailable';
 import QuestionTooltip from 'app/components/questionTooltip';
-import SidebarSectionTitle from 'app/components/sidebarSectionTitle';
+import SidebarSection from 'app/components/sidebarSection';
 import Tag from 'app/components/tag';
 import Tooltip from 'app/components/tooltip';
 import {IconWarning} from 'app/icons';
@@ -33,7 +33,6 @@ import {
   isMobileRelease,
 } from '../../../utils';
 import {generateReleaseMarkLines, releaseMarkLinesLabels} from '../../utils';
-import {Wrapper} from '../styles';
 
 const sessionsAxisIndex = 0;
 const usersAxisIndex = 1;
@@ -235,10 +234,10 @@ function ReleaseAdoption({
   const multipleEnvironments = environment.length === 0 || environment.length > 1;
 
   return (
-    <Wrapper>
+    <div>
       {isMobileRelease(project.platform) && (
         <Feature features={['release-adoption-stage']}>
-          <SidebarSectionTitle
+          <SidebarSection
             title={t('Adoption Stage')}
             icon={
               multipleEnvironments && (
@@ -251,21 +250,22 @@ function ReleaseAdoption({
                 />
               )
             }
-          />
-          {adoptionStageLabel && !multipleEnvironments ? (
-            <div>
-              <StyledTooltip title={adoptionStageLabel.tooltipTitle} isHoverable>
-                <Tag type={adoptionStageLabel.type}>{adoptionStageLabel.name}</Tag>
-              </StyledTooltip>
-              <AdoptionEnvironment>
-                {tct(`in [environment]`, {environment})}
-              </AdoptionEnvironment>
-            </div>
-          ) : (
-            <NotAvailableWrapper>
-              <NotAvailable />
-            </NotAvailableWrapper>
-          )}
+          >
+            {adoptionStageLabel && !multipleEnvironments ? (
+              <div>
+                <Tooltip title={adoptionStageLabel.tooltipTitle} isHoverable>
+                  <Tag type={adoptionStageLabel.type}>{adoptionStageLabel.name}</Tag>
+                </Tooltip>
+                <AdoptionEnvironment>
+                  {tct(`in [environment]`, {environment})}
+                </AdoptionEnvironment>
+              </div>
+            ) : (
+              <NotAvailableWrapper>
+                <NotAvailable />
+              </NotAvailableWrapper>
+            )}
+          </SidebarSection>
         </Feature>
       )}
       <RelativeBox>
@@ -324,21 +324,17 @@ function ReleaseAdoption({
           </TransitionChart>
         )}
       </RelativeBox>
-    </Wrapper>
+    </div>
   );
 }
 
-const StyledTooltip = styled(Tooltip)`
-  margin-bottom: ${space(3)};
-`;
-
 const NotAvailableWrapper = styled('div')`
   display: flex;
   align-items: center;
-  margin-bottom: ${space(3)};
 `;
 
 const AdoptionEnvironment = styled('span')`
+  color: ${p => p.theme.textColor};
   margin-left: ${space(0.5)};
   font-size: ${p => p.theme.fontSizeSmall};
 `;
@@ -347,7 +343,7 @@ const RelativeBox = styled('div')`
   position: relative;
 `;
 
-const ChartTitle = styled(SidebarSectionTitle)`
+const ChartTitle = styled(SidebarSection)`
   margin: 0;
 `;
 

+ 18 - 25
static/app/views/releases/detail/overview/sidebar/releaseStats.tsx

@@ -1,8 +1,8 @@
 import styled from '@emotion/styled';
 
-import {SectionHeading} from 'app/components/charts/styles';
 import DeployBadge from 'app/components/deployBadge';
 import NotAvailable from 'app/components/notAvailable';
+import SidebarSection from 'app/components/sidebarSection';
 import TimeSince from 'app/components/timeSince';
 import {t} from 'app/locale';
 import space from 'app/styles/space';
@@ -19,30 +19,24 @@ function ReleaseStats({organization, release, project}: Props) {
 
   return (
     <Container>
-      <div>
-        <SectionHeading>
-          {lastDeploy?.dateFinished ? t('Date Deployed') : t('Date Created')}
-        </SectionHeading>
-        <div>
-          <TimeSince date={lastDeploy?.dateFinished ?? dateCreated} />
-        </div>
-      </div>
+      <SidebarSection
+        title={lastDeploy?.dateFinished ? t('Date Deployed') : t('Date Created')}
+      >
+        <TimeSince date={lastDeploy?.dateFinished ?? dateCreated} />
+      </SidebarSection>
 
-      <div>
-        <SectionHeading>{t('Last Deploy')}</SectionHeading>
-        <div>
-          {lastDeploy?.dateFinished ? (
-            <DeployBadge
-              deploy={lastDeploy}
-              orgSlug={organization.slug}
-              version={version}
-              projectId={project.id}
-            />
-          ) : (
-            <NotAvailable />
-          )}
-        </div>
-      </div>
+      <SidebarSection title={t('Last Deploy')}>
+        {lastDeploy?.dateFinished ? (
+          <DeployBadge
+            deploy={lastDeploy}
+            orgSlug={organization.slug}
+            version={version}
+            projectId={project.id}
+          />
+        ) : (
+          <NotAvailable />
+        )}
+      </SidebarSection>
     </Container>
   );
 }
@@ -51,7 +45,6 @@ const Container = styled('div')`
   display: grid;
   grid-template-columns: 50% 50%;
   grid-row-gap: ${space(2)};
-  margin-bottom: ${space(3)};
 `;
 
 export default ReleaseStats;

+ 3 - 4
static/app/views/releases/detail/overview/sidebar/totalCrashFreeUsers.tsx

@@ -6,6 +6,7 @@ import moment from 'moment';
 import AsyncComponent from 'app/components/asyncComponent';
 import Count from 'app/components/count';
 import {getParams} from 'app/components/organizations/globalSelectionHeader/getParams';
+import SidebarSection from 'app/components/sidebarSection';
 import {URL_PARAM} from 'app/constants/globalSelectionHeader';
 import {t, tn} from 'app/locale';
 import overflowEllipsis from 'app/styles/overflowEllipsis';
@@ -14,7 +15,6 @@ import {CrashFreeTimeBreakdown, Organization} from 'app/types';
 import {defined} from 'app/utils';
 
 import {displayCrashFreePercent} from '../../../utils';
-import {SectionHeading, Wrapper} from '../styles';
 
 type Props = AsyncComponent['props'] & {
   location: Location;
@@ -88,8 +88,7 @@ class TotalCrashFreeUsers extends AsyncComponent<Props, State> {
     }
 
     return (
-      <Wrapper>
-        <SectionHeading>{t('Total Crash Free Users')}</SectionHeading>
+      <SidebarSection title={t('Total Crash Free Users')}>
         <Timeline>
           {timeline.map(row => (
             <Row key={row.date.toString()}>
@@ -111,7 +110,7 @@ class TotalCrashFreeUsers extends AsyncComponent<Props, State> {
             </Row>
           ))}
         </Timeline>
-      </Wrapper>
+      </SidebarSection>
     );
   }
 }

+ 0 - 12
static/app/views/releases/detail/overview/styles.tsx

@@ -1,12 +0,0 @@
-import styled from '@emotion/styled';
-
-import {SectionHeading as BaseSectionHeading} from 'app/components/charts/styles';
-import space from 'app/styles/space';
-
-export const Wrapper = styled('div')`
-  margin-bottom: ${space(3)};
-`;
-
-export const SectionHeading = styled(BaseSectionHeading)`
-  margin: 0 0 ${space(1.5)} 0;
-`;