@gitkraken/core-gitlens 0.21.0 → 0.22.1
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/CHANGELOG.md +17 -1
- package/dist/git/utils/autolink.utils.d.ts +4 -1
- package/dist/git/utils/autolink.utils.js +12 -3
- package/dist/git/utils/autolink.utils.js.map +1 -1
- package/dist/plus/integrations/authentication/configuredIntegrationService.d.ts +7 -0
- package/dist/plus/integrations/authentication/configuredIntegrationService.js +12 -0
- package/dist/plus/integrations/authentication/configuredIntegrationService.js.map +1 -1
- package/dist/plus/integrations/authentication/integrationAuthenticationService.js +5 -3
- package/dist/plus/integrations/authentication/integrationAuthenticationService.js.map +1 -1
- package/dist/plus/integrations/authentication/models.d.ts +9 -0
- package/dist/plus/integrations/authentication/models.js +13 -1
- package/dist/plus/integrations/authentication/models.js.map +1 -1
- package/dist/plus/integrations/authentication/observedAuthenticationProvider.d.ts +34 -0
- package/dist/plus/integrations/authentication/observedAuthenticationProvider.js +227 -0
- package/dist/plus/integrations/authentication/observedAuthenticationProvider.js.map +1 -0
- package/dist/plus/integrations/index.d.ts +4 -2
- package/dist/plus/integrations/index.js.map +1 -1
- package/dist/plus/integrations/integrationService.d.ts +9 -4
- package/dist/plus/integrations/integrationService.js +30 -7
- package/dist/plus/integrations/integrationService.js.map +1 -1
- package/dist/plus/integrations/manager.d.ts +18 -1
- package/dist/plus/integrations/models/integration.d.ts +8 -1
- package/dist/plus/integrations/models/integration.js +79 -10
- package/dist/plus/integrations/models/integration.js.map +1 -1
- package/dist/plus/integrations/models/issuesIntegration.d.ts +20 -1
- package/dist/plus/integrations/models/issuesIntegration.js +106 -2
- package/dist/plus/integrations/models/issuesIntegration.js.map +1 -1
- package/dist/plus/integrations/providers/issueSorts.d.ts +0 -1
- package/dist/plus/integrations/providers/jira-server.d.ts +10 -2
- package/dist/plus/integrations/providers/jira-server.js +74 -7
- package/dist/plus/integrations/providers/jira-server.js.map +1 -1
- package/dist/plus/integrations/providers/jira.d.ts +3 -3
- package/dist/plus/integrations/providers/jira.js +5 -27
- package/dist/plus/integrations/providers/jira.js.map +1 -1
- package/dist/plus/integrations/providers/linear.d.ts +1 -1
- package/dist/plus/integrations/providers/linear.js +3 -27
- package/dist/plus/integrations/providers/linear.js.map +1 -1
- package/dist/plus/integrations/providers/providerApiClient.js +4 -1
- package/dist/plus/integrations/providers/providerApiClient.js.map +1 -1
- package/dist/plus/integrations/providers/providerErrors.d.ts +4 -1
- package/dist/plus/integrations/providers/providerErrors.js +13 -4
- package/dist/plus/integrations/providers/providerErrors.js.map +1 -1
- package/dist/plus/integrations/providers/providersApi.js +1 -1
- package/dist/plus/integrations/providers/providersApi.js.map +1 -1
- package/dist/plus/integrations/providers/trello.d.ts +1 -1
- package/dist/plus/integrations/providers/trello.js +1 -1
- package/dist/plus/integrations/providers/trello.js.map +1 -1
- package/dist/plus/integrations/providers/utils/issueAutolinks.d.ts +8 -0
- package/dist/plus/integrations/providers/utils/issueAutolinks.js +20 -0
- package/dist/plus/integrations/providers/utils/issueAutolinks.js.map +1 -0
- package/dist/plus/integrations/reads/autolinks.d.ts +7 -0
- package/dist/plus/integrations/reads/autolinks.js +40 -0
- package/dist/plus/integrations/reads/autolinks.js.map +1 -0
- package/dist/plus/integrations/reads/context.d.ts +4 -2
- package/dist/plus/integrations/reads/drains.d.ts +0 -1
- package/dist/plus/integrations/reads/hierarchy.js +1 -1
- package/dist/plus/integrations/reads/issueBatch.js +1 -1
- package/dist/plus/integrations/reads/issueTracker.js +1 -1
- package/dist/plus/integrations/reads/resolveRepository.js +1 -1
- package/docs/integrations.md +22 -1
- package/package.json +1 -1
|
@@ -1,8 +1,9 @@
|
|
|
1
1
|
import { Event } from "../../utils/event.js";
|
|
2
|
+
import { RefSet } from "../../git/models/autolink.js";
|
|
2
3
|
import { IssueSearchCriteria, IssueShape, IssueSorting, IssueStateFilter } from "../../git/models/issue.js";
|
|
3
4
|
import { PullRequestFilter, PullRequestSearchCriteria, PullRequestShape, PullRequestStateFilter } from "../../git/models/pullRequest.js";
|
|
4
5
|
import { ConfiguredIntegrationDescriptor } from "./authentication/models.js";
|
|
5
|
-
import { IntegrationIds } from "./constants.js";
|
|
6
|
+
import { IntegrationIds, IssuesCloudHostIntegrationId, IssuesSelfManagedHostIntegrationId } from "./constants.js";
|
|
6
7
|
import { ConfiguredIntegrationsChangeEvent } from "./authentication/configuredIntegrationService.js";
|
|
7
8
|
import { ConnectionStateChangeEvent, ProviderBroadenResult, ProviderOrganization, ProviderPagedResult, ProviderRepositoryShape, ProviderResult, ProviderSweepResult, ResolveRepositoryResult } from "./results.js";
|
|
8
9
|
import { IssueFilter } from "./providerFilters.js";
|
|
@@ -214,6 +215,14 @@ export type ListProjectsOptions = {
|
|
|
214
215
|
connectionId?: never;
|
|
215
216
|
domain?: never;
|
|
216
217
|
};
|
|
218
|
+
export type GetAutolinkReferencesOptions = {
|
|
219
|
+
providerId: IssuesCloudHostIntegrationId.Jira | IssuesSelfManagedHostIntegrationId.JiraServer;
|
|
220
|
+
connectionId?: string;
|
|
221
|
+
/** Trusted self-managed domain fallback, as on the other provider reads. */
|
|
222
|
+
domain?: string;
|
|
223
|
+
/** Drops discovery and awaits a fresh build; retires builds started before the refresh. */
|
|
224
|
+
forceSync?: boolean;
|
|
225
|
+
};
|
|
217
226
|
/**
|
|
218
227
|
* Public, provider-neutral integration facade. Provider clients and integration model instances remain private
|
|
219
228
|
* implementation details so SDK changes don't expand this contract.
|
|
@@ -281,6 +290,14 @@ export interface IntegrationManager {
|
|
|
281
290
|
deleteConnection(id: IntegrationIds, connectionId: string): Promise<void>;
|
|
282
291
|
listOrgs(options?: ListOrgsOptions): Promise<ProviderResult<ProviderOrganization>>;
|
|
283
292
|
listProjects(options?: ListProjectsOptions): Promise<ProviderResult<ProviderOrganization>>;
|
|
293
|
+
/**
|
|
294
|
+
* Jira project references for one connection. Cold discovery is awaited. Returns `undefined` for an
|
|
295
|
+
* unresolved target or failed/incomplete discovery; an empty set means complete discovery found no links.
|
|
296
|
+
* Each call reads the provider; callers own coalescing and caching.
|
|
297
|
+
* Match with `getAutolinks` or `getBranchAutolinks` from `git/utils/autolink.utils.js` in the host process;
|
|
298
|
+
* references can contain compiled regular expressions and are not a wire format.
|
|
299
|
+
*/
|
|
300
|
+
getAutolinkReferences(options: GetAutolinkReferencesOptions): Promise<RefSet | undefined>;
|
|
284
301
|
listRepos(options: {
|
|
285
302
|
providerId: IntegrationIds;
|
|
286
303
|
org?: string;
|
|
@@ -7,7 +7,7 @@ import { Issue as Issue$1, IssueShape, IssueSyncedWith } from "../../../git/mode
|
|
|
7
7
|
import { PullRequest, PullRequestMergeableState, PullRequestReviewDecision, PullRequestReviewState, PullRequestStatusCheckRollupState } from "../../../git/models/pullRequest.js";
|
|
8
8
|
import { ScopedLogger } from "../../../utils/logger.scoped.js";
|
|
9
9
|
import { Account as Account$1 } from "../../../git/models/author.js";
|
|
10
|
-
import { ConnectionResource, ProviderAuthenticationSession } from "../authentication/models.js";
|
|
10
|
+
import { ConnectionResource, ProviderAuthenticationSession, SessionPublication } from "../authentication/models.js";
|
|
11
11
|
import { GitCloudHostIntegrationId, IntegrationIds, IssuesCloudHostIntegrationId, IssuesHostIntegrationIds } from "../constants.js";
|
|
12
12
|
import { Sources } from "../telemetry.js";
|
|
13
13
|
import { ProviderWarningCause, ProviderWarningScope } from "../results.js";
|
|
@@ -300,8 +300,15 @@ export declare abstract class IntegrationBase<ID extends IntegrationIds = Integr
|
|
|
300
300
|
* otherwise stay invisible, or keep being searched, for the rest of the session (#5907).
|
|
301
301
|
*/
|
|
302
302
|
invalidateDiscoveryCaches(): void;
|
|
303
|
+
invalidateDiscoveryForConnection(_connectionId?: string): void;
|
|
304
|
+
getSessionDiscoveryGeneration(_sessionId?: string, _connectionId?: string, _cloud?: boolean): number;
|
|
305
|
+
get discoveryGeneration(): number;
|
|
306
|
+
protected isResolvedSessionCurrent(_session: ProviderAuthenticationSession | undefined, _generation: number): boolean;
|
|
307
|
+
onSessionPublishing(publication: SessionPublication): void;
|
|
308
|
+
protected invalidatePublishedSession(_publication: SessionPublication, _affectsPrimary: boolean): void;
|
|
303
309
|
private static readonly requestExceptionLimit;
|
|
304
310
|
private requestExceptionCount;
|
|
311
|
+
private resetRecoveryAccounting;
|
|
305
312
|
resetRequestExceptionCount(syncReqUsecase: SyncReqUsecase | 'all'): void;
|
|
306
313
|
/**
|
|
307
314
|
* Resets request exceptions without resetting the amount of syncs
|
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
import { isCancellationError } from "../../../utils/cancellation.js";
|
|
1
|
+
import { CancellationError, isCancellationError } from "../../../utils/cancellation.js";
|
|
2
2
|
import { Logger as _logger } from "../../../utils/logger.js";
|
|
3
3
|
import { getScopedLogger } from "../../../utils/logger.scoped.js";
|
|
4
4
|
import { debug, trace } from "../../../utils/decorators/log.js";
|
|
@@ -12,6 +12,7 @@ import { isProviderUnreachableError, toError } from "../errors.js";
|
|
|
12
12
|
import "../constants.js";
|
|
13
13
|
import { isAzureProviderId } from "../providers/providerErrors.js";
|
|
14
14
|
import { attributeScopedAuthFailures, hasOnlyScopedAuthFailures, markCredentialRefusals, toCollectionScopeFailure } from "../collectionMetadata.js";
|
|
15
|
+
import { getSessionIdentity } from "../authentication/models.js";
|
|
15
16
|
import { areDomainsOnSameHost } from "../utils/domain.utils.js";
|
|
16
17
|
import { isSelfManagedHostIntegrationId } from "../utils/integration.utils.js";
|
|
17
18
|
import { throwIfAllSettledFailed } from "../providers/utils/providerPaging.js";
|
|
@@ -118,6 +119,7 @@ var IntegrationBase = class IntegrationBase {
|
|
|
118
119
|
this.didChangeConnection = didChangeConnection;
|
|
119
120
|
}
|
|
120
121
|
dispose() {
|
|
122
|
+
this.invalidateDiscoveryCaches();
|
|
121
123
|
this._onDidChange.dispose();
|
|
122
124
|
}
|
|
123
125
|
get authProviderDescriptor() {
|
|
@@ -365,13 +367,41 @@ var IntegrationBase = class IntegrationBase {
|
|
|
365
367
|
* otherwise stay invisible, or keep being searched, for the rest of the session (#5907).
|
|
366
368
|
*/
|
|
367
369
|
invalidateDiscoveryCaches() {}
|
|
370
|
+
invalidateDiscoveryForConnection(_connectionId) {
|
|
371
|
+
this.invalidateDiscoveryCaches();
|
|
372
|
+
}
|
|
373
|
+
getSessionDiscoveryGeneration(_sessionId, _connectionId, _cloud) {
|
|
374
|
+
return this.discoveryGeneration;
|
|
375
|
+
}
|
|
376
|
+
get discoveryGeneration() {
|
|
377
|
+
return 0;
|
|
378
|
+
}
|
|
379
|
+
isResolvedSessionCurrent(_session, _generation) {
|
|
380
|
+
return true;
|
|
381
|
+
}
|
|
382
|
+
onSessionPublishing(publication) {
|
|
383
|
+
const { session, previousSessionId, replacePrimary } = publication;
|
|
384
|
+
const cloud = session != null ? session.cloud : publication.cloud;
|
|
385
|
+
const sameVariant = cloud == null || this._session?.cloud == null || cloud === this._session.cloud;
|
|
386
|
+
const affectsPrimary = replacePrimary === true && (session != null || cloud == null || this._session != null && sameVariant) || this._session === null && session != null || this._session != null && sameVariant && (session?.id === this._session.id || previousSessionId === this._session.id);
|
|
387
|
+
if (affectsPrimary && getSessionIdentity(this._session) !== getSessionIdentity(session)) this._session = void 0;
|
|
388
|
+
this.invalidatePublishedSession(publication, affectsPrimary);
|
|
389
|
+
}
|
|
390
|
+
invalidatePublishedSession(_publication, _affectsPrimary) {
|
|
391
|
+
this.invalidateDiscoveryCaches();
|
|
392
|
+
}
|
|
368
393
|
static requestExceptionLimit = 5;
|
|
369
394
|
requestExceptionCount = 0;
|
|
395
|
+
resetRecoveryAccounting() {
|
|
396
|
+
this.requestExceptionCount = 0;
|
|
397
|
+
this._syncRequestsPerFailedUsecase.clear();
|
|
398
|
+
this._rejectedTokens.clear();
|
|
399
|
+
}
|
|
370
400
|
resetRequestExceptionCount(syncReqUsecase) {
|
|
371
401
|
this.requestExceptionCount = 0;
|
|
372
402
|
if (syncReqUsecase === "all") {
|
|
373
|
-
this.
|
|
374
|
-
this.
|
|
403
|
+
this.resetRecoveryAccounting();
|
|
404
|
+
this.invalidateDiscoveryCaches();
|
|
375
405
|
} else this._syncRequestsPerFailedUsecase.delete(syncReqUsecase);
|
|
376
406
|
}
|
|
377
407
|
/**
|
|
@@ -416,7 +446,7 @@ var IntegrationBase = class IntegrationBase {
|
|
|
416
446
|
syncCloudConnection(state, forceSync) {
|
|
417
447
|
return this.runSessionTransition(() => this.syncCloudConnectionLocked(state, forceSync));
|
|
418
448
|
}
|
|
419
|
-
async syncCloudConnectionLocked(state, forceSync) {
|
|
449
|
+
async syncCloudConnectionLocked(state, forceSync, reason = "explicit") {
|
|
420
450
|
const scope = getScopedLogger();
|
|
421
451
|
if (this._session?.cloud === false && state !== "connected") {
|
|
422
452
|
if (this.id !== "github" && !this.skippedNonCloudReported) {
|
|
@@ -435,7 +465,10 @@ var IntegrationBase = class IntegrationBase {
|
|
|
435
465
|
const oldSession = this._session;
|
|
436
466
|
let resyncing = false;
|
|
437
467
|
if (forceSync) {
|
|
438
|
-
|
|
468
|
+
if (reason === "explicit") {
|
|
469
|
+
this._rejectedTokens.clear();
|
|
470
|
+
this.invalidateDiscoveryForConnection();
|
|
471
|
+
}
|
|
439
472
|
await this.ctx.storage.deleteWorkspace(this.connectedKey);
|
|
440
473
|
resyncing = true;
|
|
441
474
|
} else {
|
|
@@ -454,7 +487,7 @@ var IntegrationBase = class IntegrationBase {
|
|
|
454
487
|
if (!isCancellationError(ex)) scope?.error(ex);
|
|
455
488
|
failure = toError(ex);
|
|
456
489
|
}
|
|
457
|
-
if (oldSession && newSession && newSession.accessToken !== oldSession.accessToken) this.
|
|
490
|
+
if (oldSession && newSession && newSession === this._session && newSession.accessToken !== oldSession.accessToken) this.resetRecoveryAccounting();
|
|
458
491
|
if (resyncing && newSession == null && !refetchFailed) await (await this.authenticationService.get(this.authProvider.id)).deleteSession(this.authProviderDescriptor, { preserveConfigured: false });
|
|
459
492
|
break;
|
|
460
493
|
}
|
|
@@ -660,7 +693,7 @@ var IntegrationBase = class IntegrationBase {
|
|
|
660
693
|
let failure;
|
|
661
694
|
if (this._resyncs !== resyncs) failure = this._lastResyncFailure;
|
|
662
695
|
else if (this._session != null && this.connectionExpired === true) try {
|
|
663
|
-
failure = await this.syncCloudConnectionLocked("connected", true);
|
|
696
|
+
failure = await this.syncCloudConnectionLocked("connected", true, "expired");
|
|
664
697
|
} catch (ex) {
|
|
665
698
|
failure = toError(ex);
|
|
666
699
|
}
|
|
@@ -719,8 +752,14 @@ var IntegrationBase = class IntegrationBase {
|
|
|
719
752
|
this._session = null;
|
|
720
753
|
}
|
|
721
754
|
if (this.ctx.config.isIntegrationsEnabled?.() === false) return void 0;
|
|
722
|
-
|
|
723
|
-
|
|
755
|
+
const generation = this.discoveryGeneration;
|
|
756
|
+
if (createIfNeeded || sync) {
|
|
757
|
+
await this.ctx.storage.deleteWorkspace(this.connectedKey);
|
|
758
|
+
if (this.getSessionDiscoveryGeneration(this._session?.id, void 0, this._session?.cloud) > generation) {
|
|
759
|
+
if (sync) throw new CancellationError();
|
|
760
|
+
return;
|
|
761
|
+
}
|
|
762
|
+
} else if (this.ctx.storage.getWorkspace(this.connectedKey) === false) return;
|
|
724
763
|
let session;
|
|
725
764
|
try {
|
|
726
765
|
session = await (await this.authenticationService.get(this.authProvider.id)).getSession(this.authProviderDescriptor, sync ? {
|
|
@@ -734,7 +773,15 @@ var IntegrationBase = class IntegrationBase {
|
|
|
734
773
|
if (session?.expiresAt != null && session.expiresAt < /* @__PURE__ */ new Date()) session = null;
|
|
735
774
|
if (session != null && !this.isSessionForIntegrationHost(session)) session = void 0;
|
|
736
775
|
} catch (ex) {
|
|
776
|
+
if (isCancellationError(ex) || !this.isResolvedSessionCurrent(void 0, generation)) {
|
|
777
|
+
if (sync) throw new CancellationError();
|
|
778
|
+
return;
|
|
779
|
+
}
|
|
737
780
|
await this.ctx.storage.deleteWorkspace(this.connectedKey);
|
|
781
|
+
if (!this.isResolvedSessionCurrent(void 0, generation)) {
|
|
782
|
+
if (sync) throw new CancellationError();
|
|
783
|
+
return;
|
|
784
|
+
}
|
|
738
785
|
if (!sync && ex instanceof Error && ex.message.includes("User did not consent")) return;
|
|
739
786
|
if (sync) {
|
|
740
787
|
this.smoothifyRequestExceptionCount();
|
|
@@ -742,18 +789,40 @@ var IntegrationBase = class IntegrationBase {
|
|
|
742
789
|
}
|
|
743
790
|
session = null;
|
|
744
791
|
}
|
|
745
|
-
if (session
|
|
792
|
+
if (!this.isResolvedSessionCurrent(session ?? void 0, generation)) {
|
|
793
|
+
if (sync) throw new CancellationError();
|
|
794
|
+
return;
|
|
795
|
+
}
|
|
796
|
+
if (session === void 0 && !createIfNeeded && !sync) {
|
|
797
|
+
await this.ctx.storage.deleteWorkspace(this.connectedKey);
|
|
798
|
+
if (!this.isResolvedSessionCurrent(void 0, generation)) return void 0;
|
|
799
|
+
}
|
|
800
|
+
if (getSessionIdentity(this._session) !== getSessionIdentity(session)) this.onSessionPublishing({
|
|
801
|
+
session: session ?? void 0,
|
|
802
|
+
replacePrimary: true
|
|
803
|
+
});
|
|
804
|
+
else if (refetch && session != null) this.onSessionPublishing({
|
|
805
|
+
session,
|
|
806
|
+
replacePrimary: true
|
|
807
|
+
});
|
|
746
808
|
this._session = session ?? null;
|
|
747
809
|
this.smoothifyRequestExceptionCount();
|
|
748
810
|
if (session != null) {
|
|
811
|
+
const publishedGeneration = this.getSessionDiscoveryGeneration(session.id, void 0, session.cloud);
|
|
749
812
|
await this.ctx.storage.storeWorkspace(this.connectedKey, true);
|
|
813
|
+
if (this._session !== session || publishedGeneration !== this.getSessionDiscoveryGeneration(session.id, void 0, session.cloud)) {
|
|
814
|
+
if (sync) throw new CancellationError();
|
|
815
|
+
return;
|
|
816
|
+
}
|
|
750
817
|
queueMicrotask(() => {
|
|
818
|
+
if (this._session !== session || publishedGeneration !== this.getSessionDiscoveryGeneration(session.id, void 0, session.cloud)) return;
|
|
751
819
|
this._onDidChange.fire();
|
|
752
820
|
this.didChangeConnection?.fire({
|
|
753
821
|
integration: this,
|
|
754
822
|
key: this.key,
|
|
755
823
|
reason: "connected"
|
|
756
824
|
});
|
|
825
|
+
if (this._session !== session || publishedGeneration !== this.getSessionDiscoveryGeneration(session.id, void 0, session.cloud)) return;
|
|
757
826
|
(async () => {
|
|
758
827
|
try {
|
|
759
828
|
await this.providerOnConnect?.();
|