Browse Source

fix(release): Escape releases with quotes (#40746)

Scott Cooper 2 years ago
parent
commit
5f7a7c0a56

+ 5 - 2
static/app/views/releases/detail/index.tsx

@@ -37,7 +37,7 @@ import withOrganization from 'sentry/utils/withOrganization';
 import withPageFilters from 'sentry/utils/withPageFilters';
 import withPageFilters from 'sentry/utils/withPageFilters';
 import AsyncView from 'sentry/views/asyncView';
 import AsyncView from 'sentry/views/asyncView';
 
 
-import {getReleaseBounds, ReleaseBounds} from '../utils';
+import {getReleaseBounds, ReleaseBounds, searchReleaseVersion} from '../utils';
 
 
 import ReleaseHeader from './header/releaseHeader';
 import ReleaseHeader from './header/releaseHeader';
 
 
@@ -143,12 +143,15 @@ class ReleasesDetail extends AsyncView<Props, State> {
         query: {
         query: {
           project: location.query.project,
           project: location.query.project,
           environment: location.query.environment ?? [],
           environment: location.query.environment ?? [],
-          query: `release:"${params.release}"`,
+          query: searchReleaseVersion(params.release),
           field: 'sum(session)',
           field: 'sum(session)',
           statsPeriod: '90d',
           statsPeriod: '90d',
           interval: '1d',
           interval: '1d',
         },
         },
       },
       },
+      {
+        allowError: error => error.status === 400,
+      },
     ]);
     ]);
 
 
     return endpoints;
     return endpoints;

+ 11 - 3
static/app/views/releases/detail/overview/index.tsx

@@ -48,7 +48,12 @@ import {
   PROJECT_PERFORMANCE_TYPE,
   PROJECT_PERFORMANCE_TYPE,
 } from 'sentry/views/performance/utils';
 } from 'sentry/views/performance/utils';
 
 
-import {getReleaseParams, isReleaseArchived, ReleaseBounds} from '../../utils';
+import {
+  getReleaseParams,
+  isReleaseArchived,
+  ReleaseBounds,
+  searchReleaseVersion,
+} from '../../utils';
 import {ReleaseContext} from '..';
 import {ReleaseContext} from '..';
 
 
 import CommitAuthorBreakdown from './sidebar/commitAuthorBreakdown';
 import CommitAuthorBreakdown from './sidebar/commitAuthorBreakdown';
@@ -127,7 +132,7 @@ class ReleaseOverview extends AsyncView<Props> {
       id: undefined,
       id: undefined,
       version: 2,
       version: 2,
       name: `Release ${formatVersion(version)}`,
       name: `Release ${formatVersion(version)}`,
-      query: `event.type:transaction release:${version}`,
+      query: `event.type:transaction ${searchReleaseVersion(version)}`,
       fields: ['transaction', 'failure_count()', 'epm()', 'p50()'],
       fields: ['transaction', 'failure_count()', 'epm()', 'p50()'],
       orderby: '-failure_count',
       orderby: '-failure_count',
       range: statsPeriod || undefined,
       range: statsPeriod || undefined,
@@ -438,7 +443,10 @@ class ReleaseOverview extends AsyncView<Props> {
                 errored: allReleasesErrored,
                 errored: allReleasesErrored,
                 response: allReleases,
                 response: allReleases,
               }) => (
               }) => (
-                <SessionsRequest {...sessionsRequestProps} query={`release:"${version}"`}>
+                <SessionsRequest
+                  {...sessionsRequestProps}
+                  query={searchReleaseVersion(version)}
+                >
                   {({
                   {({
                     loading: thisReleaseLoading,
                     loading: thisReleaseLoading,
                     reloading: thisReleaseReloading,
                     reloading: thisReleaseReloading,

+ 9 - 1
static/app/views/releases/utils/index.spec.tsx

@@ -1,6 +1,6 @@
 import {initializeOrg} from 'sentry-test/initializeOrg';
 import {initializeOrg} from 'sentry-test/initializeOrg';
 
 
-import {getReleaseBounds, getReleaseParams} from 'sentry/views/releases/utils';
+import {getReleaseBounds, getReleaseParams, searchReleaseVersion} from './index';
 
 
 describe('releases/utils', () => {
 describe('releases/utils', () => {
   describe('getReleaseBounds', () => {
   describe('getReleaseBounds', () => {
@@ -150,3 +150,11 @@ describe('releases/utils', () => {
     });
     });
   });
   });
 });
 });
+
+describe('searchReleaseVersion()', function () {
+  it('should escape quotes', function () {
+    expect(searchReleaseVersion('com.sentry.go_app@"1.0.0-chore"')).toBe(
+      'release:"com.sentry.go_app@\\"1.0.0-chore\\""'
+    );
+  });
+});

+ 9 - 0
static/app/views/releases/utils/index.tsx

@@ -235,3 +235,12 @@ export const ADOPTION_STAGE_LABELS: Record<
 
 
 export const isMobileRelease = (releaseProjectPlatform: PlatformKey) =>
 export const isMobileRelease = (releaseProjectPlatform: PlatformKey) =>
   ([...mobile, ...desktop] as string[]).includes(releaseProjectPlatform);
   ([...mobile, ...desktop] as string[]).includes(releaseProjectPlatform);
+
+/**
+ * Helper that escapes quotes and formats release version into release search
+ * ex - com.sentry.go_app@"1.0.0-chore"
+ */
+export function searchReleaseVersion(version: string): string {
+  // Wrap with quotes and escape any quotes inside
+  return `release:"${version.replace(/"/g, '\\"')}"`;
+}