-
Notifications
You must be signed in to change notification settings - Fork 6
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Access full component metadata in ServiceBuilder.RegisterStateStore #37
Comments
@philliphoff has provided a starting point internal sealed class DeferredStateStore<T> : IStateStore
where T : IStateStore
{
private readonly Func<MetadataRequest?, T> componentFactory;
private readonly ILogger<DeferredStateStore<T>> logger;
private readonly Lazy<T> stateStore;
private MetadataRequest? metadataRequest;
public DeferredStateStore(Func<MetadataRequest?, T> componentFactory, ILogger<DeferredStateStore<T>> logger)
{
this.componentFactory = componentFactory;
this.logger = logger;
this.stateStore = new Lazy<T>(() => this.componentFactory(this.metadataRequest));
this.logger.LogInformation("DeferredStateStore created");
}
#region IStateStore Members
public Task DeleteAsync(StateStoreDeleteRequest request, CancellationToken cancellationToken = default)
{
return this.stateStore.Value.DeleteAsync(request, cancellationToken);
}
public Task<StateStoreGetResponse?> GetAsync(StateStoreGetRequest request, CancellationToken cancellationToken = default)
{
return this.stateStore.Value.GetAsync(request, cancellationToken);
}
public Task InitAsync(MetadataRequest request, CancellationToken cancellationToken = default)
{
this.logger.LogInformation("DeferredStateStore initialized");
this.metadataRequest = request;
return Task.CompletedTask;
}
public Task SetAsync(StateStoreSetRequest request, CancellationToken cancellationToken = default)
{
return this.stateStore.Value.SetAsync(request, cancellationToken);
}
#endregion
}
|
As mentioned in a related discussion on the Dapr Discord, the creation of the store/pub-sub/binding instances is deferred until the first call (i.e. typically Init()). I considered deferring further until after initialization, but was concerned that "first call is initialization" is really just a convention and may not always be true in the future (e.g. given other features/ping calls). Whether that concern is warranted is probably debateable, but I also didn't want to stray too far from the lifecycle of other SDKs and "native" component development. That's not to say that it's an unreasonable request, but it may be best to wait to see how many people require this pattern before deciding whether to fold the workaround (proxy with deferred creation) into the SDK. |
Describe the proposal
It would be really convenient if the
context
object (provided byServiceBuilder.RegisterStateStore
) actually contained all the component metadata on it, as well as just the instanceId.I ask because in my implementation, at the point of registering my state store, I need the connection string from the metadata, in order to spin up a aspnet hosted
BackgroundService
which can create some prerequisite tables, that will later be depended on by the usual state store operators (sets, gets etc)As it stands today, I have to wait until the
IPluggableComponent.InitAsync()
method is called to get access to the full metadata (MetadataRequest.Properties
) so I can access the connection string and then pass it back via aTaskCompletionSource<string>
to theBackgroundService
. It works, but leads to a messy abstraction.If you’re with me so far, and agree that making the component metadata available at the point of
ServiceBuilder.RegisterStateStore
makes sense, then I could suggest we go a step further…. which would make theIPluggableComponent.InitAsync()
method completely redundant and could be removed from the API surface.This is my current implementation :
But I would like to see something like this :
The text was updated successfully, but these errors were encountered: