cube icon indicating copy to clipboard operation
cube copied to clipboard

Support multiple CubeProviders

Open reify-thomas-smith opened this issue 3 years ago • 5 comments

Is your feature request related to a problem? Please describe.

I have a React application that needs to query two different cube services. However, the <CubeProvider> component only supports specifying a single Cube service, and if <CubeProvider>s are nested, then only the innermost client object will be available.

Describe the solution you'd like

Add an optional name prop to <CubeProvider>, with a default value of “default”. The internal CubeContext, rather than holding a single client object, would hold an object mapping names to clients.

Hooks that presently accept an optional client argument would also accept a string value for that argument. If a string is provided, the hook would use the client with that name from the context, if it exists, or throw an error otherwise. If no value is passed, it would use the “default” client (matching current behavior).

Describe alternatives you've considered

As a workaround, I've written my own <CubeProvider> implementation that allows multiple clients. To use this with the existing hooks requires manually extracting the client instance from the context. A built-in implementation would be better.

As an alternative to the existing hooks accepting strings, we could directly expose a hook that gets a client by name, then expect the user to call this hook and pass the client object to the existing hook. This would arguably be a smaller change.

As an alternative to using the string “default” as a default name, we could treat an un-named client specially. This would arguably be cleaner in a way, but it would also be more complicated, and I don't see the need.

I am willing to work on this.

reify-thomas-smith avatar Jul 11 '22 16:07 reify-thomas-smith

Hey @reify-thomas-smith ! Could you please elaborate on your use case? Why do you need to query multiple Cube services?

paveltiunov avatar Jul 12 '22 03:07 paveltiunov

My current use case is that we have two applications written by two teams, each of which uses its own cube service. The medium-term goal is to migrate both applications to use the same cube service. However, it is impractical to rewrite one of the applications all at once, so there will be an intermediate stage in which it will need to use both services while we rewrite the application code piece-by-piece.

This is actually the second time this exact use case has come up for us. The first time, I wrote a custom provider component that worked essentially as proposed above. Since we've had the same need a second time, I thought that others might have it as well.

reify-thomas-smith avatar Jul 12 '22 13:07 reify-thomas-smith

@reify-thomas-smith That makes sense! Do you have any proposal on how API should look like in this case?

paveltiunov avatar Jul 19 '22 19:07 paveltiunov

Yeah, just add an optional name prop to CubeProvider, and have useCubeQuery and such accept a string for the client option. I have a PR I've been sitting on because I haven't had time to look at updating docs (or testing it at all), but it should clarify the proposal: #4947.

reify-thomas-smith avatar Jul 19 '22 19:07 reify-thomas-smith

If you are interested in working on this issue, please leave a comment below and we will be happy to assign the issue to you. If this is the first time you are contributing a Pull Request to Cube.js, please check our contribution guidelines. You can also post any questions while contributing in the #contributors channel in the Cube.js Slack.

github-actions[bot] avatar Jul 19 '22 19:07 github-actions[bot]