From 3a9f37fec1dfdcadb6519583fce1d041b89905cd Mon Sep 17 00:00:00 2001 From: davelopez <46503462+davelopez@users.noreply.github.com> Date: Sun, 24 Sep 2023 12:16:08 +0200 Subject: [PATCH 1/4] Update Git API type definitions and Provider --- client/src/@types/git.d.ts | 65 ++++++++++++++++++++++--- client/src/providers/git/gitProvider.ts | 10 +++- 2 files changed, 65 insertions(+), 10 deletions(-) diff --git a/client/src/@types/git.d.ts b/client/src/@types/git.d.ts index def05d4..5c5f357 100644 --- a/client/src/@types/git.d.ts +++ b/client/src/@types/git.d.ts @@ -3,7 +3,7 @@ * Licensed under the MIT License. See License.txt in the project root for license information. *--------------------------------------------------------------------------------------------*/ -import { Uri, Event, Disposable, ProviderResult } from "vscode"; +import { Uri, Event, Disposable, ProviderResult, Command, CancellationToken } from "vscode"; export { ProviderResult } from "vscode"; export interface Git { @@ -78,6 +78,8 @@ export const enum Status { UNTRACKED, IGNORED, INTENT_TO_ADD, + INTENT_TO_RENAME, + TYPE_CHANGED, ADDED_BY_US, ADDED_BY_THEM, @@ -126,6 +128,8 @@ export interface LogOptions { /** Max number of log entries to retrieve. If not specified, the default is 32. */ readonly maxEntries?: number; readonly path?: string; + /** A commit range, such as "0a47c67f0fb52dd11562af48658bc1dff1d75a38..0bb4bdea78e1db44d728fd6894720071e303304f" */ + readonly range?: string; } export interface CommitOptions { @@ -136,6 +140,15 @@ export interface CommitOptions { empty?: boolean; noVerify?: boolean; requireUserConfig?: boolean; + useEditor?: boolean; + verbose?: boolean; + /** + * string - execute the specified command after the commit operation + * undefined - execute the command specified in git.postCommitCommand + * after the commit operation + * null - do not execute any command after the commit operation + */ + postCommitCommand?: string | null; } export interface FetchOptions { @@ -146,11 +159,19 @@ export interface FetchOptions { depth?: number; } -export interface BranchQuery { - readonly remote?: boolean; - readonly pattern?: string; - readonly count?: number; +export interface InitOptions { + defaultBranch?: string; +} + +export interface RefQuery { readonly contains?: string; + readonly count?: number; + readonly pattern?: string; + readonly sort?: "alphabetically" | "committerdate"; +} + +export interface BranchQuery extends RefQuery { + readonly remote?: boolean; } export interface Repository { @@ -171,6 +192,7 @@ export interface Repository { getCommit(ref: string): Promise; add(paths: string[]): Promise; + revert(paths: string[]): Promise; clean(paths: string[]): Promise; apply(patch: string, reverse?: boolean): Promise; @@ -192,9 +214,11 @@ export interface Repository { createBranch(name: string, checkout: boolean, ref?: string): Promise; deleteBranch(name: string, force?: boolean): Promise; getBranch(name: string): Promise; - getBranches(query: BranchQuery): Promise; + getBranches(query: BranchQuery, cancellationToken?: CancellationToken): Promise; setBranchUpstream(name: string, upstream: string): Promise; + getRefs(query: RefQuery, cancellationToken?: CancellationToken): Promise; + getMergeBase(ref1: string, ref2: string): Promise; tag(name: string, upstream: string): Promise; @@ -248,6 +272,10 @@ export interface CredentialsProvider { getCredentials(host: Uri): ProviderResult; } +export interface PostCommitCommandsProvider { + getCommands(repository: Repository): Command[]; +} + export interface PushErrorHandler { handlePushError( repository: Repository, @@ -257,6 +285,21 @@ export interface PushErrorHandler { ): Promise; } +export interface BranchProtection { + readonly remote: string; + readonly rules: BranchProtectionRule[]; +} + +export interface BranchProtectionRule { + readonly include?: string[]; + readonly exclude?: string[]; +} + +export interface BranchProtectionProvider { + onDidChangeBranchProtection: Event; + provideBranchProtection(): BranchProtection[]; +} + export type APIState = "uninitialized" | "initialized"; export interface PublishEvent { @@ -275,13 +318,15 @@ export interface API { toGitUri(uri: Uri, ref: string): Uri; getRepository(uri: Uri): Repository | null; - init(root: Uri): Promise; + init(root: Uri, options?: InitOptions): Promise; openRepository(root: Uri): Promise; registerRemoteSourcePublisher(publisher: RemoteSourcePublisher): Disposable; registerRemoteSourceProvider(provider: RemoteSourceProvider): Disposable; registerCredentialsProvider(provider: CredentialsProvider): Disposable; + registerPostCommitCommandsProvider(provider: PostCommitCommandsProvider): Disposable; registerPushErrorHandler(handler: PushErrorHandler): Disposable; + registerBranchProtectionProvider(root: Uri, provider: BranchProtectionProvider): Disposable; } export interface GitExtension { @@ -291,7 +336,7 @@ export interface GitExtension { /** * Returns a specific API version. * - * Throws error if git extension is disabled. You can listed to the + * Throws error if git extension is disabled. You can listen to the * [GitExtension.onDidChangeEnablement](#GitExtension.onDidChangeEnablement) event * to know when the extension becomes enabled/disabled. * @@ -337,4 +382,8 @@ export const enum GitErrorCodes { PatchDoesNotApply = "PatchDoesNotApply", NoPathFound = "NoPathFound", UnknownPath = "UnknownPath", + EmptyCommitMessage = "EmptyCommitMessage", + BranchFastForwardRejected = "BranchFastForwardRejected", + BranchNotYetBorn = "BranchNotYetBorn", + TagConflict = "TagConflict", } diff --git a/client/src/providers/git/gitProvider.ts b/client/src/providers/git/gitProvider.ts index da35510..0e06f38 100644 --- a/client/src/providers/git/gitProvider.ts +++ b/client/src/providers/git/gitProvider.ts @@ -7,7 +7,7 @@ import { GitProvider } from "."; * This providers can be used only with local git repositories. */ export class BuiltinGitProvider implements GitProvider { - private gitAPI: GitAPI = undefined; + private gitAPI?: GitAPI = undefined; async initialize(): Promise { this.gitAPI = await this.getBuiltInGitApi(); @@ -18,14 +18,20 @@ export class BuiltinGitProvider implements GitProvider { } async getContents(uri: Uri, ref: string): Promise { + if (this.gitAPI === undefined) { + throw new Error("Git provider not initialized"); + } const gitUri = this.gitAPI.toGitUri(uri, ref); const repo = this.gitAPI.getRepository(gitUri); + if (repo === null) { + throw new Error(`Repository not found for uri ${uri.toString()}`); + } const contents = await repo.show(ref, uri.path); return contents; } - private async getBuiltInGitApi(): Promise { + private async getBuiltInGitApi(): Promise { try { const extension = extensions.getExtension("vscode.git") as Extension; if (extension !== undefined) { From 2b4238ac5bbc01799ce7da3e480533ddb268f753 Mon Sep 17 00:00:00 2001 From: davelopez <46503462+davelopez@users.noreply.github.com> Date: Sun, 24 Sep 2023 12:18:05 +0200 Subject: [PATCH 2/4] Fix typing issues in ComparableWorkflow --- client/src/commands/compareCleanWith.ts | 2 +- client/src/commands/index.ts | 17 +++++++++++------ 2 files changed, 12 insertions(+), 7 deletions(-) diff --git a/client/src/commands/compareCleanWith.ts b/client/src/commands/compareCleanWith.ts index 5212cb2..157125c 100644 --- a/client/src/commands/compareCleanWith.ts +++ b/client/src/commands/compareCleanWith.ts @@ -26,7 +26,7 @@ export class CompareCleanWithWorkflowsCommand extends CustomCommand { const rightComparable = ComparableWorkflow.buildFromArgs(args); if (!leftComparable || !rightComparable) { - throw new Error("You need to two workflows selected for comparison"); + throw new Error("You need to have two workflows selected for comparison"); } const leftUri = this.buildCleanWorkflowUri(leftComparable); diff --git a/client/src/commands/index.ts b/client/src/commands/index.ts index 472ec86..e903df1 100644 --- a/client/src/commands/index.ts +++ b/client/src/commands/index.ts @@ -55,16 +55,21 @@ export abstract class CustomCommand extends CommandContext { */ export class ComparableWorkflow { uri: Uri; - ref: string; + ref?: string; + // TODO: This is no longer working until a new API is available + // ref: https://github.com/microsoft/vscode/issues/177319 + // ref: https://github.com/microsoft/vscode/issues/84297 public static buildFromArgs(args: unknown[]): ComparableWorkflow | undefined { if (args.length >= 2) { - if (Object.prototype.hasOwnProperty.call(args[0], "ref")) { + const source = args[2] as string; + if (source === "git-history") { // Comes from source control timeline - return { uri: args[1] as Uri, ref: args[0]["ref"] }; - } else if (Object.prototype.hasOwnProperty.call(args[0], "scheme")) { - // Comes from file explorer - return { uri: args[0] as Uri, ref: undefined }; + return { uri: args[1] as Uri, ref: args[0] as string }; + } + if (source === "timeline.localHistory") { + // Comes from local history + return { uri: args[1] as Uri }; } } return undefined; From 1824d5f882712e322606a367291fdc7cfd8b4940 Mon Sep 17 00:00:00 2001 From: davelopez <46503462+davelopez@users.noreply.github.com> Date: Sun, 24 Sep 2023 12:19:38 +0200 Subject: [PATCH 3/4] Disable Timeline operations temporarily The Timeline does not provide useful information anymore, so we need to wait until the new VSCode Timeline API is finalized and published. --- package.json | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/package.json b/package.json index 1ed477d..722e634 100644 --- a/package.json +++ b/package.json @@ -168,12 +168,12 @@ { "command": "galaxy-workflows.compareCleanWith", "group": "3_compare@1", - "when": "config.git.enabled && !git.missing && galaxy-workflows.selectForCleanCompare" + "when": "false && config.git.enabled && !git.missing && galaxy-workflows.selectForCleanCompare" }, { "command": "galaxy-workflows.selectForCleanCompare", "group": "3_compare@2", - "when": "config.git.enabled && !git.missing && timelineItem =~ /git:file\\b/ && galaxy-workflows.gitProviderInitialized" + "when": "false && config.git.enabled && !git.missing && timelineItem =~ /git:file\\b/ && galaxy-workflows.gitProviderInitialized" } ], "explorer/context": [ From 19417bf7cc7e4cdfade75246570a22fd3ad2b752 Mon Sep 17 00:00:00 2001 From: davelopez <46503462+davelopez@users.noreply.github.com> Date: Sun, 24 Sep 2023 12:56:05 +0200 Subject: [PATCH 4/4] Update feature in readme --- README.md | 5 ++++- 1 file changed, 4 insertions(+), 1 deletion(-) diff --git a/README.md b/README.md index 31bfc47..96f6b6c 100644 --- a/README.md +++ b/README.md @@ -159,7 +159,10 @@ You can clean up the non-essential properties of a (legacy .ga) workflow with th > ⚠️ This feature is experimental and is only available using a local git repository. -Sometimes you want to compare different revisions of the same (legacy .ga) workflow and see what has changed between them. If the workflow has been through the Galaxy editor or some of the nodes have been moved around, there can be many changes that are just cosmetical and not part of the workflow logic. In those cases, you may want to get a 'simplified' diff so you can focus on the 'real' changes. You can do so in the `Timeline` or the `File Explorer` by using `Select workflow for (clean) compare` in one revision and then `Compare with this workflow (clean)` on the other revision, this will compare both revisions using the 'clean' version of the workflow (see the [Workflow Cleanup Command](#workflow-cleanup-command)), meaning the non-essential parts are removed from both documents before the comparison. +Sometimes you want to compare different revisions of the same (legacy .ga) workflow and see what has changed between them. If the workflow has been through the Galaxy editor or some of the nodes have been moved around, there can be many changes that are just cosmetical and not part of the workflow logic. In those cases, you may want to get a 'simplified' diff so you can focus on the 'real' changes. You can do so in the `Timeline` or the `File Explorer` by using `Select workflow for (clean) compare` in one revision and then `Compare with this workflow (clean)` on the other revision, this will compare both revisions using the 'clean' version of the workflow (see the [Workflow Cleanup Command](#workflow-cleanup-command)), meaning the non-essential parts are removed from both documents before the comparison. + +> ⚠️ **NOTE**: +> This feature is no longer supported in the `Timeline` until a new version of the VSCode Timeline API is finalized and published. See [this PR](https://github.com/davelopez/galaxy-workflows-vscode/pull/59) for more details. #### Legacy (ga)