mirror of
https://github.com/harness/drone.git
synced 2025-05-17 01:20:13 +08:00
feat: [CODE-2338]: Add dry run rules param to create branch API (#2680)
* addressed review comments * Merge branch 'main' of https://git0.harness.io/l7B_kbSEQD2wjrM7PShm5w/PROD/Harness_Commons/gitness into CODE-2346 * feat: [CODE-2346]: Add an option to restore branch for merged/closed PR * feat: [CODE-2338]: Add dry run rules param to create branch API
This commit is contained in:
parent
80105035f4
commit
2f4b0036d1
@ -127,6 +127,7 @@ export interface StringsMap {
|
|||||||
'branchProtection.targetPlaceholder': string
|
'branchProtection.targetPlaceholder': string
|
||||||
'branchProtection.title': string
|
'branchProtection.title': string
|
||||||
branchProtectionRules: string
|
branchProtectionRules: string
|
||||||
|
branchRestored: string
|
||||||
branchSource: string
|
branchSource: string
|
||||||
branchSourceDesc: string
|
branchSourceDesc: string
|
||||||
branchTagCreation: string
|
branchTagCreation: string
|
||||||
@ -908,6 +909,7 @@ export interface StringsMap {
|
|||||||
resolveComments: string
|
resolveComments: string
|
||||||
resolved: string
|
resolved: string
|
||||||
resolvedComments: string
|
resolvedComments: string
|
||||||
|
restoreBranch: string
|
||||||
results: string
|
results: string
|
||||||
reviewProjectSettings: string
|
reviewProjectSettings: string
|
||||||
reviewerNotFound: string
|
reviewerNotFound: string
|
||||||
|
@ -176,6 +176,7 @@ branchCreated: Branch {branch} created.
|
|||||||
tagCreated: Tag {{tag}} created.
|
tagCreated: Tag {{tag}} created.
|
||||||
confirmation: Confirmation
|
confirmation: Confirmation
|
||||||
deleteBranch: Delete Branch
|
deleteBranch: Delete Branch
|
||||||
|
restoreBranch: Restore Branch
|
||||||
deleteTag: Delete Tag
|
deleteTag: Delete Tag
|
||||||
deleteTagConfirm: Are you sure you want to delete tag <strong>{{name}}</strong>? You can't undo this action.
|
deleteTagConfirm: Are you sure you want to delete tag <strong>{{name}}</strong>? You can't undo this action.
|
||||||
deleteBranchConfirm: Are you sure you want to delete branch <strong>{{name}}</strong>? You can't undo this action.
|
deleteBranchConfirm: Are you sure you want to delete branch <strong>{{name}}</strong>? You can't undo this action.
|
||||||
@ -187,6 +188,7 @@ compare: Compare
|
|||||||
commitString: 'Commit {commit}'
|
commitString: 'Commit {commit}'
|
||||||
repoDeleted: Repository {{repo}} deleted.
|
repoDeleted: Repository {{repo}} deleted.
|
||||||
branchDeleted: Branch {branch} deleted.
|
branchDeleted: Branch {branch} deleted.
|
||||||
|
branchRestored: Branch {branch} restored.
|
||||||
tagDeleted: Tag {tag} deleted.
|
tagDeleted: Tag {tag} deleted.
|
||||||
failedToDeleteBranch: Failed to delete Branch. Please try again.
|
failedToDeleteBranch: Failed to delete Branch. Please try again.
|
||||||
createFile: Create __path__
|
createFile: Create __path__
|
||||||
|
@ -37,6 +37,9 @@ import { Menu, PopoverPosition, Icon as BIcon } from '@blueprintjs/core'
|
|||||||
import cx from 'classnames'
|
import cx from 'classnames'
|
||||||
import ReactTimeago from 'react-timeago'
|
import ReactTimeago from 'react-timeago'
|
||||||
import type {
|
import type {
|
||||||
|
CreateBranchPathParams,
|
||||||
|
DeleteBranchQueryParams,
|
||||||
|
OpenapiCreateBranchRequest,
|
||||||
OpenapiStatePullReqRequest,
|
OpenapiStatePullReqRequest,
|
||||||
TypesListCommitResponse,
|
TypesListCommitResponse,
|
||||||
TypesPullReq,
|
TypesPullReq,
|
||||||
@ -58,6 +61,7 @@ import { OptionsMenuButton } from 'components/OptionsMenuButton/OptionsMenuButto
|
|||||||
import { UserPreference, useUserPreference } from 'hooks/useUserPreference'
|
import { UserPreference, useUserPreference } from 'hooks/useUserPreference'
|
||||||
import { useGetRepositoryMetadata } from 'hooks/useGetRepositoryMetadata'
|
import { useGetRepositoryMetadata } from 'hooks/useGetRepositoryMetadata'
|
||||||
import { PullReqSuggestionsBatch } from 'components/PullReqSuggestionsBatch/PullReqSuggestionsBatch'
|
import { PullReqSuggestionsBatch } from 'components/PullReqSuggestionsBatch/PullReqSuggestionsBatch'
|
||||||
|
import { BranchActionsButton } from '../PullRequestOverviewPanel/sections/BranchActionsSection'
|
||||||
import InlineMergeBox from './InlineMergeBox'
|
import InlineMergeBox from './InlineMergeBox'
|
||||||
import css from './PullRequestActionsBox.module.scss'
|
import css from './PullRequestActionsBox.module.scss'
|
||||||
|
|
||||||
@ -71,18 +75,13 @@ export interface PullRequestActionsBoxProps extends Pick<GitInfoProps, 'repoMeta
|
|||||||
setConflictingFiles: React.Dispatch<React.SetStateAction<string[] | undefined>>
|
setConflictingFiles: React.Dispatch<React.SetStateAction<string[] | undefined>>
|
||||||
refetchPullReq: () => void
|
refetchPullReq: () => void
|
||||||
refetchActivities: () => void
|
refetchActivities: () => void
|
||||||
deleteBranch: MutateMethod<
|
createBranch: MutateMethod<any, any, OpenapiCreateBranchRequest, CreateBranchPathParams>
|
||||||
any,
|
refetchBranch: () => Promise<void>
|
||||||
any,
|
deleteBranch: MutateMethod<any, any, DeleteBranchQueryParams, unknown>
|
||||||
{
|
showRestoreBranchButton: boolean
|
||||||
bypass_rules: boolean
|
|
||||||
dry_run_rules: boolean
|
|
||||||
commit_sha: string
|
|
||||||
},
|
|
||||||
unknown
|
|
||||||
>
|
|
||||||
showDeleteBranchButton: boolean
|
showDeleteBranchButton: boolean
|
||||||
setShowDeleteBranchButton: React.Dispatch<React.SetStateAction<boolean>>
|
setShowDeleteBranchButton: React.Dispatch<React.SetStateAction<boolean>>
|
||||||
|
setShowRestoreBranchButton: React.Dispatch<React.SetStateAction<boolean>>
|
||||||
isSourceBranchDeleted: boolean
|
isSourceBranchDeleted: boolean
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -96,13 +95,17 @@ export const PullRequestActionsBox: React.FC<PullRequestActionsBoxProps> = ({
|
|||||||
setConflictingFiles,
|
setConflictingFiles,
|
||||||
refetchPullReq,
|
refetchPullReq,
|
||||||
refetchActivities,
|
refetchActivities,
|
||||||
|
createBranch,
|
||||||
|
refetchBranch,
|
||||||
deleteBranch,
|
deleteBranch,
|
||||||
|
showRestoreBranchButton,
|
||||||
showDeleteBranchButton,
|
showDeleteBranchButton,
|
||||||
|
setShowRestoreBranchButton,
|
||||||
setShowDeleteBranchButton,
|
setShowDeleteBranchButton,
|
||||||
isSourceBranchDeleted
|
isSourceBranchDeleted
|
||||||
}) => {
|
}) => {
|
||||||
const { getString } = useStrings()
|
const { getString } = useStrings()
|
||||||
const { showSuccess, showError } = useToaster()
|
const { showError } = useToaster()
|
||||||
const inlineMergeRef = useRef<inlineMergeFormRefType>(null)
|
const inlineMergeRef = useRef<inlineMergeFormRefType>(null)
|
||||||
const { hooks, standalone } = useAppContext()
|
const { hooks, standalone } = useAppContext()
|
||||||
const space = useGetSpaceParam()
|
const space = useGetSpaceParam()
|
||||||
@ -263,11 +266,13 @@ export const PullRequestActionsBox: React.FC<PullRequestActionsBoxProps> = ({
|
|||||||
return (
|
return (
|
||||||
<MergeInfo
|
<MergeInfo
|
||||||
pullRequestMetadata={pullReqMetadata}
|
pullRequestMetadata={pullReqMetadata}
|
||||||
|
showRestoreBranchButton={showRestoreBranchButton}
|
||||||
showDeleteBranchButton={showDeleteBranchButton}
|
showDeleteBranchButton={showDeleteBranchButton}
|
||||||
setShowDeleteBranchButton={setShowDeleteBranchButton}
|
setShowDeleteBranchButton={setShowDeleteBranchButton}
|
||||||
|
setShowRestoreBranchButton={setShowRestoreBranchButton}
|
||||||
|
refetchBranch={refetchBranch}
|
||||||
|
createBranch={createBranch}
|
||||||
deleteBranch={deleteBranch}
|
deleteBranch={deleteBranch}
|
||||||
showSuccess={showSuccess}
|
|
||||||
showError={showError}
|
|
||||||
/>
|
/>
|
||||||
)
|
)
|
||||||
}
|
}
|
||||||
@ -542,28 +547,15 @@ export const PullRequestActionsBox: React.FC<PullRequestActionsBoxProps> = ({
|
|||||||
|
|
||||||
const MergeInfo: React.FC<{
|
const MergeInfo: React.FC<{
|
||||||
pullRequestMetadata: TypesPullReq
|
pullRequestMetadata: TypesPullReq
|
||||||
|
showRestoreBranchButton: boolean
|
||||||
showDeleteBranchButton: boolean
|
showDeleteBranchButton: boolean
|
||||||
setShowDeleteBranchButton: React.Dispatch<React.SetStateAction<boolean>>
|
setShowDeleteBranchButton: React.Dispatch<React.SetStateAction<boolean>>
|
||||||
deleteBranch: MutateMethod<
|
setShowRestoreBranchButton: React.Dispatch<React.SetStateAction<boolean>>
|
||||||
any,
|
refetchBranch: () => Promise<void>
|
||||||
any,
|
createBranch: MutateMethod<any, any, OpenapiCreateBranchRequest, CreateBranchPathParams>
|
||||||
{
|
deleteBranch: MutateMethod<any, any, DeleteBranchQueryParams, unknown>
|
||||||
bypass_rules: boolean
|
}> = props => {
|
||||||
dry_run_rules: boolean
|
const { pullRequestMetadata, showRestoreBranchButton, showDeleteBranchButton } = props
|
||||||
commit_sha: string
|
|
||||||
},
|
|
||||||
unknown
|
|
||||||
>
|
|
||||||
showSuccess: (message: React.ReactNode, timeout?: number, key?: string) => void
|
|
||||||
showError: (message: React.ReactNode, timeout?: number, key?: string) => void
|
|
||||||
}> = ({
|
|
||||||
pullRequestMetadata,
|
|
||||||
showDeleteBranchButton,
|
|
||||||
setShowDeleteBranchButton,
|
|
||||||
deleteBranch,
|
|
||||||
showSuccess,
|
|
||||||
showError
|
|
||||||
}) => {
|
|
||||||
const { getString } = useStrings()
|
const { getString } = useStrings()
|
||||||
|
|
||||||
return (
|
return (
|
||||||
@ -606,36 +598,11 @@ const MergeInfo: React.FC<{
|
|||||||
/>
|
/>
|
||||||
</Text>
|
</Text>
|
||||||
<FlexExpander />
|
<FlexExpander />
|
||||||
{showDeleteBranchButton && (
|
{(showDeleteBranchButton || showRestoreBranchButton) && (
|
||||||
<Button
|
<BranchActionsButton
|
||||||
margin={{ right: 'small' }}
|
{...props}
|
||||||
text={getString('deleteBranch')}
|
sourceSha={pullRequestMetadata.source_sha || ''}
|
||||||
variation={ButtonVariation.SECONDARY}
|
sourceBranch={pullRequestMetadata.source_branch || ''}
|
||||||
onClick={() => {
|
|
||||||
deleteBranch(
|
|
||||||
{},
|
|
||||||
{
|
|
||||||
queryParams: {
|
|
||||||
bypass_rules: true,
|
|
||||||
dry_run_rules: false,
|
|
||||||
commit_sha: pullRequestMetadata?.source_sha || ''
|
|
||||||
}
|
|
||||||
}
|
|
||||||
)
|
|
||||||
.then(() => {
|
|
||||||
setShowDeleteBranchButton(false)
|
|
||||||
showSuccess(
|
|
||||||
<StringSubstitute
|
|
||||||
str={getString('branchDeleted')}
|
|
||||||
vars={{
|
|
||||||
branch: pullRequestMetadata?.source_branch
|
|
||||||
}}
|
|
||||||
/>,
|
|
||||||
5000
|
|
||||||
)
|
|
||||||
})
|
|
||||||
.catch(err => showError(getErrorMessage(err)))
|
|
||||||
}}
|
|
||||||
/>
|
/>
|
||||||
)}
|
)}
|
||||||
</Layout.Horizontal>
|
</Layout.Horizontal>
|
||||||
|
@ -40,7 +40,7 @@
|
|||||||
background: var(--grey-0) !important;
|
background: var(--grey-0) !important;
|
||||||
}
|
}
|
||||||
|
|
||||||
.deleteBranchSectionContainer {
|
.branchActionsSectionContainer {
|
||||||
padding: var(--spacing-5) 2rem !important;
|
padding: var(--spacing-5) 2rem !important;
|
||||||
background: var(--grey-0) !important;
|
background: var(--grey-0) !important;
|
||||||
}
|
}
|
||||||
|
@ -21,6 +21,7 @@ export declare const blueText: string
|
|||||||
export declare const boldText: string
|
export declare const boldText: string
|
||||||
export declare const borderContainer: string
|
export declare const borderContainer: string
|
||||||
export declare const borderRadius: string
|
export declare const borderRadius: string
|
||||||
|
export declare const branchActionsSectionContainer: string
|
||||||
export declare const branchContainer: string
|
export declare const branchContainer: string
|
||||||
export declare const buttonPadding: string
|
export declare const buttonPadding: string
|
||||||
export declare const changeContainerPadding: string
|
export declare const changeContainerPadding: string
|
||||||
@ -34,7 +35,6 @@ export declare const conflictingContainer: string
|
|||||||
export declare const conflictingFileName: string
|
export declare const conflictingFileName: string
|
||||||
export declare const conflictingFilesTable: string
|
export declare const conflictingFilesTable: string
|
||||||
export declare const copyIconContainer: string
|
export declare const copyIconContainer: string
|
||||||
export declare const deleteBranchSectionContainer: string
|
|
||||||
export declare const details: string
|
export declare const details: string
|
||||||
export declare const executionIcon: string
|
export declare const executionIcon: string
|
||||||
export declare const greyContainer: string
|
export declare const greyContainer: string
|
||||||
|
@ -26,7 +26,8 @@ import type {
|
|||||||
TypesPullReqReviewer,
|
TypesPullReqReviewer,
|
||||||
RepoRepositoryOutput,
|
RepoRepositoryOutput,
|
||||||
TypesRuleViolations,
|
TypesRuleViolations,
|
||||||
TypesBranch
|
TypesBranch,
|
||||||
|
DeleteBranchQueryParams
|
||||||
} from 'services/code'
|
} from 'services/code'
|
||||||
import {
|
import {
|
||||||
PanelSectionOutletPosition,
|
PanelSectionOutletPosition,
|
||||||
@ -44,7 +45,7 @@ import ChecksSection from './sections/ChecksSection'
|
|||||||
import MergeSection from './sections/MergeSection'
|
import MergeSection from './sections/MergeSection'
|
||||||
import CommentsSection from './sections/CommentsSection'
|
import CommentsSection from './sections/CommentsSection'
|
||||||
import ChangesSection from './sections/ChangesSection'
|
import ChangesSection from './sections/ChangesSection'
|
||||||
import DeleteBranchSection from './sections/DeleteBranchSection'
|
import BranchActionsSection from './sections/BranchActionsSection'
|
||||||
import css from './PullRequestOverviewPanel.module.scss'
|
import css from './PullRequestOverviewPanel.module.scss'
|
||||||
|
|
||||||
interface PullRequestOverviewPanelProps {
|
interface PullRequestOverviewPanelProps {
|
||||||
@ -113,6 +114,7 @@ const PullRequestOverviewPanel = (props: PullRequestOverviewPanelProps) => {
|
|||||||
mergeOptions[3].method
|
mergeOptions[3].method
|
||||||
])
|
])
|
||||||
const [showDeleteBranchButton, setShowDeleteBranchButton] = useState(false)
|
const [showDeleteBranchButton, setShowDeleteBranchButton] = useState(false)
|
||||||
|
const [showRestoreBranchButton, setShowRestoreBranchButton] = useState(false)
|
||||||
const [isSourceBranchDeleted, setIsSourceBranchDeleted] = useState(false)
|
const [isSourceBranchDeleted, setIsSourceBranchDeleted] = useState(false)
|
||||||
|
|
||||||
const {
|
const {
|
||||||
@ -130,7 +132,12 @@ const PullRequestOverviewPanel = (props: PullRequestOverviewPanelProps) => {
|
|||||||
const { mutate: deleteBranch } = useMutate({
|
const { mutate: deleteBranch } = useMutate({
|
||||||
verb: 'DELETE',
|
verb: 'DELETE',
|
||||||
path: `/api/v1/repos/${repoMetadata.path}/+/branches/${pullReqMetadata.source_branch}`,
|
path: `/api/v1/repos/${repoMetadata.path}/+/branches/${pullReqMetadata.source_branch}`,
|
||||||
queryParams: { bypass_rules: true, dry_run_rules: true }
|
queryParams: { bypass_rules: true, dry_run_rules: true } as DeleteBranchQueryParams
|
||||||
|
})
|
||||||
|
const { mutate: createBranch } = useMutate({
|
||||||
|
verb: 'POST',
|
||||||
|
path: `/api/v1/repos/${repoMetadata.path}/+/branches`,
|
||||||
|
pathParams: { repo_ref: repoMetadata.path }
|
||||||
})
|
})
|
||||||
const { mutate: mergePR } = useMutate({
|
const { mutate: mergePR } = useMutate({
|
||||||
verb: 'POST',
|
verb: 'POST',
|
||||||
@ -152,6 +159,23 @@ const PullRequestOverviewPanel = (props: PullRequestOverviewPanelProps) => {
|
|||||||
useEffect(() => {
|
useEffect(() => {
|
||||||
if (error && error.status === 404) {
|
if (error && error.status === 404) {
|
||||||
setIsSourceBranchDeleted(true)
|
setIsSourceBranchDeleted(true)
|
||||||
|
createBranch({
|
||||||
|
name: pullReqMetadata.source_branch,
|
||||||
|
target: pullReqMetadata.source_sha,
|
||||||
|
bypass_rules: true,
|
||||||
|
dry_run_rules: true
|
||||||
|
}).then(res => {
|
||||||
|
if (res?.rule_violations) {
|
||||||
|
const { checkIfBypassNotAllowed } = extractInfoFromRuleViolationArr(res.rule_violations)
|
||||||
|
if (!checkIfBypassNotAllowed) {
|
||||||
|
setShowRestoreBranchButton(true)
|
||||||
|
} else {
|
||||||
|
setShowRestoreBranchButton(false)
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
setShowRestoreBranchButton(true)
|
||||||
|
}
|
||||||
|
})
|
||||||
}
|
}
|
||||||
}, [error])
|
}, [error])
|
||||||
|
|
||||||
@ -165,6 +189,8 @@ const PullRequestOverviewPanel = (props: PullRequestOverviewPanelProps) => {
|
|||||||
} else {
|
} else {
|
||||||
setShowDeleteBranchButton(false)
|
setShowDeleteBranchButton(false)
|
||||||
}
|
}
|
||||||
|
} else {
|
||||||
|
setShowDeleteBranchButton(true)
|
||||||
}
|
}
|
||||||
})
|
})
|
||||||
}
|
}
|
||||||
@ -220,9 +246,13 @@ const PullRequestOverviewPanel = (props: PullRequestOverviewPanelProps) => {
|
|||||||
PRStateLoading={PRStateLoading || loadingReviewers}
|
PRStateLoading={PRStateLoading || loadingReviewers}
|
||||||
refetchPullReq={refetchPullReq}
|
refetchPullReq={refetchPullReq}
|
||||||
refetchActivities={refetchActivities}
|
refetchActivities={refetchActivities}
|
||||||
|
createBranch={createBranch}
|
||||||
|
refetchBranch={refetchBranch}
|
||||||
deleteBranch={deleteBranch}
|
deleteBranch={deleteBranch}
|
||||||
|
showRestoreBranchButton={showRestoreBranchButton}
|
||||||
showDeleteBranchButton={showDeleteBranchButton}
|
showDeleteBranchButton={showDeleteBranchButton}
|
||||||
setShowDeleteBranchButton={setShowDeleteBranchButton}
|
setShowDeleteBranchButton={setShowDeleteBranchButton}
|
||||||
|
setShowRestoreBranchButton={setShowRestoreBranchButton}
|
||||||
isSourceBranchDeleted={isSourceBranchDeleted}
|
isSourceBranchDeleted={isSourceBranchDeleted}
|
||||||
/>
|
/>
|
||||||
{!isClosed ? (
|
{!isClosed ? (
|
||||||
@ -274,11 +304,15 @@ const PullRequestOverviewPanel = (props: PullRequestOverviewPanelProps) => {
|
|||||||
) : (
|
) : (
|
||||||
<PullRequestPanelSections
|
<PullRequestPanelSections
|
||||||
outlets={{
|
outlets={{
|
||||||
[PanelSectionOutletPosition.DELETE_BRANCH]: showDeleteBranchButton && (
|
[PanelSectionOutletPosition.BRANCH_ACTIONS]: (showDeleteBranchButton || showRestoreBranchButton) && (
|
||||||
<DeleteBranchSection
|
<BranchActionsSection
|
||||||
sourceSha={pullReqMetadata.source_sha || ''}
|
sourceSha={pullReqMetadata.source_sha || ''}
|
||||||
sourceBranch={sourceBranch}
|
sourceBranch={sourceBranch?.name || pullReqMetadata.source_branch || ''}
|
||||||
|
createBranch={createBranch}
|
||||||
|
refetchBranch={refetchBranch}
|
||||||
deleteBranch={deleteBranch}
|
deleteBranch={deleteBranch}
|
||||||
|
showDeleteBranchButton={showDeleteBranchButton}
|
||||||
|
setShowRestoreBranchButton={setShowRestoreBranchButton}
|
||||||
setShowDeleteBranchButton={setShowDeleteBranchButton}
|
setShowDeleteBranchButton={setShowDeleteBranchButton}
|
||||||
setIsSourceBranchDeleted={setIsSourceBranchDeleted}
|
setIsSourceBranchDeleted={setIsSourceBranchDeleted}
|
||||||
/>
|
/>
|
||||||
|
@ -29,7 +29,7 @@ const PullRequestPanelSections = (props: PullRequestPanelSectionsProps) => {
|
|||||||
{outlets[PanelSectionOutletPosition.COMMENTS]}
|
{outlets[PanelSectionOutletPosition.COMMENTS]}
|
||||||
{outlets[PanelSectionOutletPosition.CHECKS]}
|
{outlets[PanelSectionOutletPosition.CHECKS]}
|
||||||
{outlets[PanelSectionOutletPosition.MERGEABILITY]}
|
{outlets[PanelSectionOutletPosition.MERGEABILITY]}
|
||||||
{outlets[PanelSectionOutletPosition.DELETE_BRANCH]}
|
{outlets[PanelSectionOutletPosition.BRANCH_ACTIONS]}
|
||||||
</Layout.Vertical>
|
</Layout.Vertical>
|
||||||
)
|
)
|
||||||
}
|
}
|
||||||
|
@ -21,38 +21,26 @@ import { Icon } from '@harnessio/icons'
|
|||||||
import { useStrings } from 'framework/strings'
|
import { useStrings } from 'framework/strings'
|
||||||
import { CodeIcon } from 'utils/GitUtils'
|
import { CodeIcon } from 'utils/GitUtils'
|
||||||
import { getErrorMessage } from 'utils/Utils'
|
import { getErrorMessage } from 'utils/Utils'
|
||||||
import type { TypesBranch } from 'services/code'
|
import type { CreateBranchPathParams, DeleteBranchQueryParams, OpenapiCreateBranchRequest } from 'services/code'
|
||||||
import css from '../PullRequestOverviewPanel.module.scss'
|
import css from '../PullRequestOverviewPanel.module.scss'
|
||||||
|
|
||||||
interface DeleteBranchSectionProps {
|
interface BranchActionsSectionProps {
|
||||||
sourceSha: string
|
sourceSha: string
|
||||||
sourceBranch: TypesBranch | null
|
sourceBranch: string
|
||||||
deleteBranch: MutateMethod<
|
createBranch: MutateMethod<any, any, OpenapiCreateBranchRequest, CreateBranchPathParams>
|
||||||
any,
|
refetchBranch: () => Promise<void>
|
||||||
any,
|
deleteBranch: MutateMethod<any, any, DeleteBranchQueryParams, unknown>
|
||||||
{
|
showDeleteBranchButton: boolean
|
||||||
bypass_rules: boolean
|
|
||||||
dry_run_rules: boolean
|
|
||||||
commit_sha: string
|
|
||||||
},
|
|
||||||
unknown
|
|
||||||
>
|
|
||||||
setShowDeleteBranchButton: React.Dispatch<React.SetStateAction<boolean>>
|
setShowDeleteBranchButton: React.Dispatch<React.SetStateAction<boolean>>
|
||||||
setIsSourceBranchDeleted: React.Dispatch<React.SetStateAction<boolean>>
|
setShowRestoreBranchButton: React.Dispatch<React.SetStateAction<boolean>>
|
||||||
|
setIsSourceBranchDeleted?: React.Dispatch<React.SetStateAction<boolean>>
|
||||||
}
|
}
|
||||||
|
|
||||||
const DeleteBranchSection = ({
|
const BranchActionsSection = (props: BranchActionsSectionProps) => {
|
||||||
sourceSha,
|
|
||||||
sourceBranch,
|
|
||||||
deleteBranch,
|
|
||||||
setShowDeleteBranchButton,
|
|
||||||
setIsSourceBranchDeleted
|
|
||||||
}: DeleteBranchSectionProps) => {
|
|
||||||
const { getString } = useStrings()
|
const { getString } = useStrings()
|
||||||
const { showSuccess, showError } = useToaster()
|
|
||||||
|
|
||||||
return (
|
return (
|
||||||
<Container className={cx(css.deleteBranchSectionContainer, css.borderRadius)} padding={{ right: 'xlarge' }}>
|
<Container className={cx(css.branchActionsSectionContainer, css.borderRadius)} padding={{ right: 'xlarge' }}>
|
||||||
<Layout.Horizontal flex={{ justifyContent: 'space-between' }}>
|
<Layout.Horizontal flex={{ justifyContent: 'space-between' }}>
|
||||||
<Text flex={{ alignItems: 'center' }}>
|
<Text flex={{ alignItems: 'center' }}>
|
||||||
<StringSubstitute
|
<StringSubstitute
|
||||||
@ -63,7 +51,7 @@ const DeleteBranchSection = ({
|
|||||||
<strong className={cx(css.boldText, css.branchContainer)}>
|
<strong className={cx(css.boldText, css.branchContainer)}>
|
||||||
<Icon name={CodeIcon.Branch} size={16} />
|
<Icon name={CodeIcon.Branch} size={16} />
|
||||||
<Text className={cx(css.boldText, css.widthContainer)} lineClamp={1}>
|
<Text className={cx(css.boldText, css.widthContainer)} lineClamp={1}>
|
||||||
{sourceBranch?.name}
|
{props.sourceBranch}
|
||||||
</Text>
|
</Text>
|
||||||
</strong>
|
</strong>
|
||||||
</Container>
|
</Container>
|
||||||
@ -71,19 +59,58 @@ const DeleteBranchSection = ({
|
|||||||
}}
|
}}
|
||||||
/>
|
/>
|
||||||
</Text>
|
</Text>
|
||||||
|
<BranchActionsButton {...props} />
|
||||||
|
</Layout.Horizontal>
|
||||||
|
</Container>
|
||||||
|
)
|
||||||
|
}
|
||||||
|
|
||||||
|
export const BranchActionsButton = ({
|
||||||
|
sourceSha,
|
||||||
|
sourceBranch,
|
||||||
|
createBranch,
|
||||||
|
refetchBranch,
|
||||||
|
deleteBranch,
|
||||||
|
showDeleteBranchButton,
|
||||||
|
setShowRestoreBranchButton,
|
||||||
|
setShowDeleteBranchButton,
|
||||||
|
setIsSourceBranchDeleted
|
||||||
|
}: BranchActionsSectionProps) => {
|
||||||
|
const { getString } = useStrings()
|
||||||
|
const { showSuccess, showError } = useToaster()
|
||||||
|
|
||||||
|
return (
|
||||||
<Button
|
<Button
|
||||||
text={getString('deleteBranch')}
|
text={showDeleteBranchButton ? getString('deleteBranch') : getString('restoreBranch')}
|
||||||
variation={ButtonVariation.SECONDARY}
|
variation={ButtonVariation.SECONDARY}
|
||||||
onClick={() => {
|
onClick={() => {
|
||||||
deleteBranch({}, { queryParams: { bypass_rules: true, dry_run_rules: false, commit_sha: sourceSha } })
|
showDeleteBranchButton
|
||||||
|
? deleteBranch({}, { queryParams: { bypass_rules: true, dry_run_rules: false, commit_sha: sourceSha } })
|
||||||
.then(() => {
|
.then(() => {
|
||||||
setIsSourceBranchDeleted(true)
|
refetchBranch()
|
||||||
|
setIsSourceBranchDeleted?.(true)
|
||||||
setShowDeleteBranchButton(false)
|
setShowDeleteBranchButton(false)
|
||||||
showSuccess(
|
showSuccess(
|
||||||
<StringSubstitute
|
<StringSubstitute
|
||||||
str={getString('branchDeleted')}
|
str={getString('branchDeleted')}
|
||||||
vars={{
|
vars={{
|
||||||
branch: sourceBranch?.name
|
branch: sourceBranch
|
||||||
|
}}
|
||||||
|
/>,
|
||||||
|
5000
|
||||||
|
)
|
||||||
|
})
|
||||||
|
.catch(err => showError(getErrorMessage(err)))
|
||||||
|
: createBranch({ name: sourceBranch, target: sourceSha, bypass_rules: true })
|
||||||
|
.then(() => {
|
||||||
|
refetchBranch()
|
||||||
|
setIsSourceBranchDeleted?.(false)
|
||||||
|
setShowRestoreBranchButton(false)
|
||||||
|
showSuccess(
|
||||||
|
<StringSubstitute
|
||||||
|
str={getString('branchRestored')}
|
||||||
|
vars={{
|
||||||
|
branch: sourceBranch
|
||||||
}}
|
}}
|
||||||
/>,
|
/>,
|
||||||
5000
|
5000
|
||||||
@ -92,9 +119,7 @@ const DeleteBranchSection = ({
|
|||||||
.catch(err => showError(getErrorMessage(err)))
|
.catch(err => showError(getErrorMessage(err)))
|
||||||
}}
|
}}
|
||||||
/>
|
/>
|
||||||
</Layout.Horizontal>
|
|
||||||
</Container>
|
|
||||||
)
|
)
|
||||||
}
|
}
|
||||||
|
|
||||||
export default DeleteBranchSection
|
export default BranchActionsSection
|
@ -84,7 +84,7 @@ export enum PanelSectionOutletPosition {
|
|||||||
COMMENTS = 'comments',
|
COMMENTS = 'comments',
|
||||||
CHECKS = 'checks',
|
CHECKS = 'checks',
|
||||||
MERGEABILITY = 'mergeability',
|
MERGEABILITY = 'mergeability',
|
||||||
DELETE_BRANCH = 'deleteBranch'
|
BRANCH_ACTIONS = 'branchActions'
|
||||||
}
|
}
|
||||||
|
|
||||||
export const getMergeOptions = (getString: UseStringsReturn['getString'], mergeable: boolean): PRMergeOption[] => [
|
export const getMergeOptions = (getString: UseStringsReturn['getString'], mergeable: boolean): PRMergeOption[] => [
|
||||||
|
@ -347,6 +347,7 @@ export type OpenapiContentType = 'file' | 'dir' | 'symlink' | 'submodule'
|
|||||||
|
|
||||||
export interface OpenapiCreateBranchRequest {
|
export interface OpenapiCreateBranchRequest {
|
||||||
bypass_rules?: boolean
|
bypass_rules?: boolean
|
||||||
|
dry_run_rules?: boolean
|
||||||
name?: string
|
name?: string
|
||||||
target?: string
|
target?: string
|
||||||
}
|
}
|
||||||
@ -587,6 +588,9 @@ export interface OpenapiRule {
|
|||||||
state?: EnumRuleState
|
state?: EnumRuleState
|
||||||
type?: OpenapiRuleType
|
type?: OpenapiRuleType
|
||||||
updated?: number
|
updated?: number
|
||||||
|
user_groups?: {
|
||||||
|
[key: string]: TypesUserGroupInfo
|
||||||
|
} | null
|
||||||
users?: {
|
users?: {
|
||||||
[key: string]: TypesPrincipalInfo
|
[key: string]: TypesPrincipalInfo
|
||||||
} | null
|
} | null
|
||||||
@ -718,6 +722,7 @@ export interface ProtectionDefApprovals {
|
|||||||
|
|
||||||
export interface ProtectionDefBypass {
|
export interface ProtectionDefBypass {
|
||||||
repo_owners?: boolean
|
repo_owners?: boolean
|
||||||
|
user_group_ids?: number[]
|
||||||
user_ids?: number[]
|
user_ids?: number[]
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -1018,6 +1023,14 @@ export interface TypesConnector {
|
|||||||
updated?: number
|
updated?: number
|
||||||
}
|
}
|
||||||
|
|
||||||
|
export interface TypesCreateBranchOutput {
|
||||||
|
commit?: TypesCommit
|
||||||
|
dry_run_rules?: boolean
|
||||||
|
name?: string
|
||||||
|
rule_violations?: TypesRuleViolations[]
|
||||||
|
sha?: string
|
||||||
|
}
|
||||||
|
|
||||||
export interface TypesDeleteBranchOutput {
|
export interface TypesDeleteBranchOutput {
|
||||||
dry_run_rules?: boolean
|
dry_run_rules?: boolean
|
||||||
rule_violations?: TypesRuleViolations[]
|
rule_violations?: TypesRuleViolations[]
|
||||||
@ -1142,8 +1155,6 @@ export interface TypesInfraProviderResource {
|
|||||||
cpu?: string | null
|
cpu?: string | null
|
||||||
created?: number
|
created?: number
|
||||||
disk?: string | null
|
disk?: string | null
|
||||||
gateway_host?: string | null
|
|
||||||
gateway_port?: string | null
|
|
||||||
identifier?: string
|
identifier?: string
|
||||||
infra_provider_type?: EnumInfraProviderType
|
infra_provider_type?: EnumInfraProviderType
|
||||||
memory?: string | null
|
memory?: string | null
|
||||||
@ -1646,6 +1657,12 @@ export interface TypesUser {
|
|||||||
updated?: number
|
updated?: number
|
||||||
}
|
}
|
||||||
|
|
||||||
|
export interface TypesUserGroupInfo {
|
||||||
|
description?: string
|
||||||
|
identifier?: string
|
||||||
|
name?: string
|
||||||
|
}
|
||||||
|
|
||||||
export interface TypesUserGroupOwnerEvaluation {
|
export interface TypesUserGroupOwnerEvaluation {
|
||||||
evaluations?: TypesOwnerEvaluation[] | null
|
evaluations?: TypesOwnerEvaluation[] | null
|
||||||
id?: string
|
id?: string
|
||||||
@ -2757,7 +2774,7 @@ export interface CreateBranchPathParams {
|
|||||||
|
|
||||||
export type CreateBranchProps = Omit<
|
export type CreateBranchProps = Omit<
|
||||||
MutateProps<
|
MutateProps<
|
||||||
TypesBranch,
|
TypesCreateBranchOutput,
|
||||||
UsererrorError | TypesRulesViolations,
|
UsererrorError | TypesRulesViolations,
|
||||||
void,
|
void,
|
||||||
OpenapiCreateBranchRequest,
|
OpenapiCreateBranchRequest,
|
||||||
@ -2768,7 +2785,13 @@ export type CreateBranchProps = Omit<
|
|||||||
CreateBranchPathParams
|
CreateBranchPathParams
|
||||||
|
|
||||||
export const CreateBranch = ({ repo_ref, ...props }: CreateBranchProps) => (
|
export const CreateBranch = ({ repo_ref, ...props }: CreateBranchProps) => (
|
||||||
<Mutate<TypesBranch, UsererrorError | TypesRulesViolations, void, OpenapiCreateBranchRequest, CreateBranchPathParams>
|
<Mutate<
|
||||||
|
TypesCreateBranchOutput,
|
||||||
|
UsererrorError | TypesRulesViolations,
|
||||||
|
void,
|
||||||
|
OpenapiCreateBranchRequest,
|
||||||
|
CreateBranchPathParams
|
||||||
|
>
|
||||||
verb="POST"
|
verb="POST"
|
||||||
path={`/repos/${repo_ref}/branches`}
|
path={`/repos/${repo_ref}/branches`}
|
||||||
base={getConfig('code/api/v1')}
|
base={getConfig('code/api/v1')}
|
||||||
@ -2778,7 +2801,7 @@ export const CreateBranch = ({ repo_ref, ...props }: CreateBranchProps) => (
|
|||||||
|
|
||||||
export type UseCreateBranchProps = Omit<
|
export type UseCreateBranchProps = Omit<
|
||||||
UseMutateProps<
|
UseMutateProps<
|
||||||
TypesBranch,
|
TypesCreateBranchOutput,
|
||||||
UsererrorError | TypesRulesViolations,
|
UsererrorError | TypesRulesViolations,
|
||||||
void,
|
void,
|
||||||
OpenapiCreateBranchRequest,
|
OpenapiCreateBranchRequest,
|
||||||
@ -2790,7 +2813,7 @@ export type UseCreateBranchProps = Omit<
|
|||||||
|
|
||||||
export const useCreateBranch = ({ repo_ref, ...props }: UseCreateBranchProps) =>
|
export const useCreateBranch = ({ repo_ref, ...props }: UseCreateBranchProps) =>
|
||||||
useMutate<
|
useMutate<
|
||||||
TypesBranch,
|
TypesCreateBranchOutput,
|
||||||
UsererrorError | TypesRulesViolations,
|
UsererrorError | TypesRulesViolations,
|
||||||
void,
|
void,
|
||||||
OpenapiCreateBranchRequest,
|
OpenapiCreateBranchRequest,
|
||||||
|
@ -1550,7 +1550,7 @@ paths:
|
|||||||
content:
|
content:
|
||||||
application/json:
|
application/json:
|
||||||
schema:
|
schema:
|
||||||
$ref: '#/components/schemas/TypesBranch'
|
$ref: '#/components/schemas/TypesCreateBranchOutput'
|
||||||
description: Created
|
description: Created
|
||||||
'400':
|
'400':
|
||||||
content:
|
content:
|
||||||
@ -10674,6 +10674,8 @@ components:
|
|||||||
properties:
|
properties:
|
||||||
bypass_rules:
|
bypass_rules:
|
||||||
type: boolean
|
type: boolean
|
||||||
|
dry_run_rules:
|
||||||
|
type: boolean
|
||||||
name:
|
name:
|
||||||
type: string
|
type: string
|
||||||
target:
|
target:
|
||||||
@ -11099,6 +11101,11 @@ components:
|
|||||||
$ref: '#/components/schemas/OpenapiRuleType'
|
$ref: '#/components/schemas/OpenapiRuleType'
|
||||||
updated:
|
updated:
|
||||||
type: integer
|
type: integer
|
||||||
|
user_groups:
|
||||||
|
additionalProperties:
|
||||||
|
$ref: '#/components/schemas/TypesUserGroupInfo'
|
||||||
|
nullable: true
|
||||||
|
type: object
|
||||||
users:
|
users:
|
||||||
additionalProperties:
|
additionalProperties:
|
||||||
$ref: '#/components/schemas/TypesPrincipalInfo'
|
$ref: '#/components/schemas/TypesPrincipalInfo'
|
||||||
@ -11351,6 +11358,10 @@ components:
|
|||||||
properties:
|
properties:
|
||||||
repo_owners:
|
repo_owners:
|
||||||
type: boolean
|
type: boolean
|
||||||
|
user_group_ids:
|
||||||
|
items:
|
||||||
|
type: integer
|
||||||
|
type: array
|
||||||
user_ids:
|
user_ids:
|
||||||
items:
|
items:
|
||||||
type: integer
|
type: integer
|
||||||
@ -11858,6 +11869,21 @@ components:
|
|||||||
updated:
|
updated:
|
||||||
type: integer
|
type: integer
|
||||||
type: object
|
type: object
|
||||||
|
TypesCreateBranchOutput:
|
||||||
|
properties:
|
||||||
|
commit:
|
||||||
|
$ref: '#/components/schemas/TypesCommit'
|
||||||
|
dry_run_rules:
|
||||||
|
type: boolean
|
||||||
|
name:
|
||||||
|
type: string
|
||||||
|
rule_violations:
|
||||||
|
items:
|
||||||
|
$ref: '#/components/schemas/TypesRuleViolations'
|
||||||
|
type: array
|
||||||
|
sha:
|
||||||
|
type: string
|
||||||
|
type: object
|
||||||
TypesDeleteBranchOutput:
|
TypesDeleteBranchOutput:
|
||||||
properties:
|
properties:
|
||||||
dry_run_rules:
|
dry_run_rules:
|
||||||
@ -12101,12 +12127,6 @@ components:
|
|||||||
disk:
|
disk:
|
||||||
nullable: true
|
nullable: true
|
||||||
type: string
|
type: string
|
||||||
gateway_host:
|
|
||||||
nullable: true
|
|
||||||
type: string
|
|
||||||
gateway_port:
|
|
||||||
nullable: true
|
|
||||||
type: string
|
|
||||||
identifier:
|
identifier:
|
||||||
type: string
|
type: string
|
||||||
infra_provider_type:
|
infra_provider_type:
|
||||||
@ -13034,6 +13054,15 @@ components:
|
|||||||
updated:
|
updated:
|
||||||
type: integer
|
type: integer
|
||||||
type: object
|
type: object
|
||||||
|
TypesUserGroupInfo:
|
||||||
|
properties:
|
||||||
|
description:
|
||||||
|
type: string
|
||||||
|
identifier:
|
||||||
|
type: string
|
||||||
|
name:
|
||||||
|
type: string
|
||||||
|
type: object
|
||||||
TypesUserGroupOwnerEvaluation:
|
TypesUserGroupOwnerEvaluation:
|
||||||
properties:
|
properties:
|
||||||
evaluations:
|
evaluations:
|
||||||
|
Loading…
Reference in New Issue
Block a user