Skip to content
This repository was archived by the owner on Nov 6, 2018. It is now read-only.

Commit abed47a

Browse files
committed
feat(contributions): accept observable of contributions in registry
1 parent 3380e60 commit abed47a

File tree

2 files changed

+52
-8
lines changed

2 files changed

+52
-8
lines changed

src/environment/providers/contribution.test.ts

+27
Original file line numberDiff line numberDiff line change
@@ -118,6 +118,33 @@ describe('ContributionRegistry', () => {
118118
)
119119
})
120120

121+
it('supports registration of an observable', () => {
122+
const registry = new class extends ContributionRegistry {
123+
public getContributions(entries: Observable<ContributionsEntry[]>): Observable<Contributions> {
124+
return super.getContributions(entries)
125+
}
126+
}(EMPTY_OBSERVABLE_ENVIRONMENT.environment)
127+
scheduler().run(({ cold, expectObservable }) =>
128+
expectObservable(
129+
registry.getContributions(
130+
cold<ContributionsEntry[]>('-a-----|', {
131+
a: [
132+
{
133+
contributions: cold<Contributions>('--b-c-|', {
134+
b: FIXTURE_CONTRIBUTIONS_1,
135+
c: [FIXTURE_CONTRIBUTIONS_2],
136+
}),
137+
},
138+
],
139+
})
140+
)
141+
).toBe('---b-c-|', {
142+
b: FIXTURE_CONTRIBUTIONS_1,
143+
c: FIXTURE_CONTRIBUTIONS_2,
144+
})
145+
)
146+
})
147+
121148
it('emits when context changes and filters on context', () => {
122149
scheduler().run(({ cold, expectObservable }) => {
123150
const registry = new class extends ContributionRegistry {

src/environment/providers/contribution.ts

+25-8
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,5 @@
1-
import { BehaviorSubject, combineLatest, Observable, Unsubscribable } from 'rxjs'
2-
import { distinctUntilChanged, map } from 'rxjs/operators'
1+
import { BehaviorSubject, combineLatest, isObservable, Observable, of, Unsubscribable } from 'rxjs'
2+
import { distinctUntilChanged, map, switchMap } from 'rxjs/operators'
33
import {
44
ActionContribution,
55
ActionItem,
@@ -8,16 +8,22 @@ import {
88
MenuContributions,
99
MenuItemContribution,
1010
} from '../../protocol'
11-
import { isEqual } from '../../util'
11+
import { flatten, isEqual } from '../../util'
1212
import { getComputedContextProperty } from '../context/context'
1313
import { ComputedContext, evaluate, evaluateTemplate } from '../context/expr/evaluator'
1414
import { TEMPLATE_BEGIN } from '../context/expr/lexer'
1515
import { Environment } from '../environment'
1616

1717
/** A registered set of contributions from an extension in the registry. */
1818
export interface ContributionsEntry {
19-
/** The contributions. */
20-
contributions: Contributions
19+
/**
20+
* The contributions, either as a value or an observable.
21+
*
22+
* If an observable is used, it should be a cold Observable and emit (e.g., its current value) upon
23+
* subscription. The {@link ContributionRegistry#contributions} observable blocks until all observables have
24+
* emitted.
25+
*/
26+
contributions: Contributions | Observable<Contributions | Contributions[]>
2127
}
2228

2329
/**
@@ -70,10 +76,21 @@ export class ContributionRegistry {
7076
public readonly contributions: Observable<Contributions> = this.getContributions(this._entries)
7177

7278
protected getContributions(entries: Observable<ContributionsEntry[]>): Observable<Contributions> {
73-
return combineLatest(entries, this.environment).pipe(
74-
map(([entries, environment]) => {
79+
return combineLatest(
80+
entries.pipe(
81+
switchMap(entries =>
82+
combineLatest(
83+
...entries.map(
84+
entry => (isObservable(entry.contributions) ? entry.contributions : of(entry.contributions))
85+
)
86+
)
87+
)
88+
),
89+
this.environment
90+
).pipe(
91+
map(([multiContributions, environment]) => {
7592
const computedContext = { get: (key: string) => getComputedContextProperty(environment, key) }
76-
return entries.map(({ contributions }) => {
93+
return flatten(multiContributions).map(contributions => {
7794
try {
7895
return evaluateContributions(
7996
computedContext,

0 commit comments

Comments
 (0)