Skip to content

Commit

Permalink
Merge branch 'development' into update-before-closing
Browse files Browse the repository at this point in the history
  • Loading branch information
sergiou87 committed Oct 26, 2022
2 parents fe93c29 + 064af16 commit 9ca90af
Show file tree
Hide file tree
Showing 36 changed files with 741 additions and 146 deletions.
2 changes: 1 addition & 1 deletion .github/workflows/release-pr.yml
Original file line number Diff line number Diff line change
Expand Up @@ -37,7 +37,7 @@ jobs:
private_key: ${{ secrets.DESKTOP_RELEASES_APP_PRIVATE_KEY }}

- name: Create Release Pull Request
uses: peter-evans/create-pull-request@v4.1.3
uses: peter-evans/create-pull-request@v4.2.0
if: |
startsWith(github.ref, 'refs/heads/releases/') && !contains(github.ref, 'test')
with:
Expand Down
4 changes: 4 additions & 0 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -84,6 +84,10 @@ resources relevant to the project.

If you're looking for something to work on, check out the [help wanted](https://github.com/desktop/desktop/issues?q=is%3Aissue+is%3Aopen+label%3A%22help%20wanted%22) label.

## Building Desktop

To get your development environment set up for building Desktop, see [setup.md](./docs/contributing/setup.md).

## More Resources

See [desktop.github.com](https://desktop.github.com) for more product-oriented
Expand Down
4 changes: 2 additions & 2 deletions app/package.json
Original file line number Diff line number Diff line change
Expand Up @@ -3,7 +3,7 @@
"productName": "GitHub Desktop",
"bundleID": "com.github.GitHubClient",
"companyName": "GitHub, Inc.",
"version": "3.1.2-beta1",
"version": "3.1.3-beta1",
"main": "./main.js",
"repository": {
"type": "git",
Expand All @@ -30,7 +30,7 @@
"desktop-trampoline": "desktop/desktop-trampoline#v0.9.8",
"dexie": "^3.2.2",
"dompurify": "^2.3.3",
"dugite": "^2.0.0",
"dugite": "^2.1.0",
"electron-window-state": "^5.0.3",
"event-kit": "^2.0.0",
"focus-trap-react": "^8.1.0",
Expand Down
2 changes: 1 addition & 1 deletion app/src/lib/app-state.ts
Original file line number Diff line number Diff line change
Expand Up @@ -22,7 +22,6 @@ import {
ICloneProgress,
IMultiCommitOperationProgress,
} from '../models/progress'
import { Popup } from '../models/popup'

import { SignInState } from './stores/sign-in-store'

Expand All @@ -47,6 +46,7 @@ import {
MultiCommitOperationStep,
} from '../models/multi-commit-operation'
import { IChangesetData } from './git'
import { Popup } from '../models/popup'

export enum SelectionType {
Repository,
Expand Down
2 changes: 1 addition & 1 deletion app/src/lib/editors/darwin.ts
Original file line number Diff line number Diff line change
Expand Up @@ -45,7 +45,7 @@ const editors: IDarwinExternalEditor[] = [
},
{
name: 'VSCodium',
bundleIdentifiers: ['com.visualstudio.code.oss'],
bundleIdentifiers: ['com.visualstudio.code.oss', 'com.vscodium'],
},
{
name: 'Sublime Text',
Expand Down
5 changes: 5 additions & 0 deletions app/src/lib/feature-flag.ts
Original file line number Diff line number Diff line change
Expand Up @@ -113,6 +113,11 @@ export function enableStartingPullRequests(): boolean {
return enableBetaFeatures()
}

/** Should we enable starting pull requests? */
export function enableStackedPopups(): boolean {
return enableDevelopmentFeatures()
}

/** Should we enable mechanism to prevent closing while the app is updating? */
export function enablePreventClosingWhileUpdating(): boolean {
return enableBetaFeatures()
Expand Down
6 changes: 2 additions & 4 deletions app/src/lib/multi-commit-operation.ts
Original file line number Diff line number Diff line change
Expand Up @@ -4,7 +4,6 @@ import {
conflictSteps,
MultiCommitOperationStepKind,
} from '../models/multi-commit-operation'
import { Popup, PopupType } from '../models/popup'
import { TipState } from '../models/tip'
import { IMultiCommitOperationState, IRepositoryState } from './app-state'

Expand Down Expand Up @@ -39,12 +38,11 @@ export function getMultiCommitOperationChooseBranchStep(
}

export function isConflictsFlow(
currentPopup: Popup | null,
isMultiCommitOperationPopupOpen: boolean,
multiCommitOperationState: IMultiCommitOperationState | null
): boolean {
return (
currentPopup !== null &&
currentPopup.type === PopupType.MultiCommitOperation &&
isMultiCommitOperationPopupOpen &&
multiCommitOperationState !== null &&
conflictSteps.includes(multiCommitOperationState.step.kind)
)
Expand Down
126 changes: 126 additions & 0 deletions app/src/lib/popup-manager.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,126 @@
import { Popup, PopupType } from '../models/popup'
import { enableStackedPopups } from './feature-flag'
import { sendNonFatalException } from './helpers/non-fatal-exception'
import { uuid } from './uuid'

/**
* The limit of how many popups allowed in the stack. Working under the
* assumption that a user should only be dealing with a couple of popups at a
* time, if a user hits the limit this would indicate a problem.
*/
const defaultPopupStackLimit = 50

/**
* The popup manager is to manage the stack of currently open popups.
*/
export class PopupManager {
private popupStack = new Array<Popup>()

public constructor(private readonly popupLimit = defaultPopupStackLimit) {}

/**
* Returns the last popup added to the stack.
*/
public get currentPopup(): Popup | null {
return this.popupStack.at(-1) ?? null
}

/**
* Returns whether there are any popups in the stack.
*/
public get isAPopupOpen(): boolean {
return this.currentPopup !== null
}

/**
* Returns an array of all popups in the stack of the provided type.
**/
public getPopupsOfType(popupType: PopupType): ReadonlyArray<Popup> {
return this.popupStack.filter(p => p.type === popupType)
}

/**
* Returns whether there are any popups of a given type in the stack.
*/
public areTherePopupsOfType(popupType: PopupType): boolean {
return this.popupStack.some(p => p.type === popupType)
}

/**
* Adds a popup to the stack.
* - The popup will be given a unique id and returned.
* - It will not add multiple popups of the same type to the stack
**/
public addPopup(popupToAdd: Popup): Popup {
const existingPopup = this.getPopupsOfType(popupToAdd.type)

if (!enableStackedPopups()) {
this.popupStack = [popupToAdd]
return popupToAdd
}

if (existingPopup.length > 0) {
log.warn(
`Attempted to add a popup of already existing type - ${popupToAdd.type}.`
)
return popupToAdd
}

const popup = { id: uuid(), ...popupToAdd }
this.popupStack.push(popup)

if (this.popupStack.length > this.popupLimit) {
// Remove the oldest
const oldest = this.popupStack[0]
sendNonFatalException(
'TooManyPopups',
new Error(
`Max number of ${this.popupLimit} popups reached while adding popup of type ${popup.type}. Removing last popup from the stack -> type ${oldest.type} `
)
)
this.popupStack = this.popupStack.slice(1)
}
return popup
}

/**
* Updates a popup in the stack and returns it.
* - It uses the popup id to find and update the popup.
*/
public updatePopup(popupToUpdate: Popup) {
if (popupToUpdate.id === undefined) {
log.warn(`Attempted to update a popup without an id.`)
return
}

const index = this.popupStack.findIndex(p => p.id === popupToUpdate.id)
if (index < 0) {
log.warn(`Attempted to update a popup not in the stack.`)
return
}

this.popupStack = [
...this.popupStack.slice(0, index),
popupToUpdate,
...this.popupStack.slice(index + 1),
]
}

/**
* Removes a popup based on it's id.
*/
public removePopup(popup: Popup) {
if (popup.id === undefined) {
log.warn(`Attempted to remove a popup without an id.`)
return
}
this.popupStack = this.popupStack.filter(p => p.id !== popup.id)
}

/**
* Removes any popup of the given type from the stack
*/
public removePopupByType(popupType: PopupType) {
this.popupStack = this.popupStack.filter(p => p.type !== popupType)
}
}
38 changes: 33 additions & 5 deletions app/src/lib/rebase.ts
Original file line number Diff line number Diff line change
Expand Up @@ -3,6 +3,26 @@ import { IAheadBehind } from '../models/branch'
import { TipState } from '../models/tip'
import { clamp } from './clamp'

/** Represents the force-push availability state of a branch. */
export enum ForcePushBranchState {
/** The branch cannot be force-pushed (it hasn't diverged from its upstream) */
NotAvailable,

/**
* The branch can be force-pushed, but the user didn't do any operation that
* we consider should be followed by a force-push, like rebasing or amending a
* pushed commit.
*/
Available,

/**
* The branch can be force-pushed, and the user did some operation that we
* consider should be followed by a force-push, like rebasing or amending a
* pushed commit.
*/
Recommended,
}

/**
* Format rebase percentage to ensure it's a value between 0 and 1, but to also
* constrain it to two significant figures, avoiding the remainder that comes
Expand All @@ -16,18 +36,24 @@ export function formatRebaseValue(value: number) {
* Check application state to see whether the action applied to the current
* branch should be a force push
*/
export function isCurrentBranchForcePush(
export function getCurrentBranchForcePushState(
branchesState: IBranchesState,
aheadBehind: IAheadBehind | null
) {
): ForcePushBranchState {
if (aheadBehind === null) {
// no tracking branch found
return false
return ForcePushBranchState.NotAvailable
}

const { tip, forcePushBranches } = branchesState
const { ahead, behind } = aheadBehind

if (behind === 0 || ahead === 0) {
// no a diverged branch to force push
return ForcePushBranchState.NotAvailable
}

const { tip, forcePushBranches } = branchesState

let canForcePushBranch = false
if (tip.kind === TipState.Valid) {
const localBranchName = tip.branch.nameWithoutRemote
Expand All @@ -36,5 +62,7 @@ export function isCurrentBranchForcePush(
canForcePushBranch = foundEntry === sha
}

return canForcePushBranch && behind > 0 && ahead > 0
return canForcePushBranch
? ForcePushBranchState.Recommended
: ForcePushBranchState.Available
}
Loading

0 comments on commit 9ca90af

Please sign in to comment.