internal P_StrictedStorageOpCtx(P_StorageOpCtx baseCtx, PersistenceEntityReferenceKeyTypeDescriptor referenceKeyTypeDescriptor) : base(baseCtx: baseCtx) { // _baseCtx = baseCtx; _referenceKeyTypeDescriptor = referenceKeyTypeDescriptor; }
P_StorageOpCtxBase P_GetStrictedCtx(PersistenceEntityReferenceKeyTypeDescriptor key) => ReadDA(ref _strictedCtxs) .GetOrAdd( key: key, factory: P_CreateStrictedCtx, unclaimedValue: (locKey, locValue) => locValue?.Dispose(), dictionaryOwner: this, spinLock: ReadDA(ref _strictedCtxsSpinLock, considerDisposeRequest: true));
// TODO: Put strings into the resources. // public virtual async Task <IReferenceKeyProvider <TKey> > RequireReferenceKeyProviderAsync <TKey>(PersistenceEntityReferenceKeyTypeDescriptor keyTypeDescriptor, IContext ctx = default) where TKey : struct { await Task.CompletedTask; var provider = InitDA(location: ref _referenceKeyProvider, factory: create, cleanup: cleanup); if (provider is IReferenceKeyProvider <TKey> requiredProvider) { return(requiredProvider); } else { throw new EonException(message: $"Type of existing provider is not compatible with the required type.{Environment.NewLine}Type of existing provider:{provider.GetType().FmtStr().GNLI2()}{Environment.NewLine}Required type of provider:{typeof(IReferenceKeyProvider<TKey>).FmtStr().GNLI2()}"); } // IReferenceKeyProvider create() { var locSettings = ReferenceKeyProviderSettings; if (locSettings is null) { throw new EonException(message: $"There is no the reference key provider settings.{Environment.NewLine}\tComponent:{this.FmtStr().GNLI2()}"); } else if (locSettings.IsDisabled) { throw new EonException(message: $"Usage of the reference key provider not enabled by the settings.{Environment.NewLine}\tComponent:{this.FmtStr().GNLI2()}"); } else { var locFactory = ServiceProvider.GetRequiredService <IReferenceKeyProviderFactory>(); if (locFactory.CanCreate(arg: locSettings)) { using (var locCtx = new GenericContext(outerCtx: ctx)) { locCtx.Set(prop: DependencyContextProps.DependenciesProp, value: this.ToValueHolder(ownsValue: false)); return(locFactory.CreateAsync(arg: ReferenceKeyProviderSettings, ctx: locCtx).Unwrap().WaitResultWithTimeout()); } } else { throw new EonException(message: $"The factory cannot create an instance of the reference key provider using the specified settings.{Environment.NewLine}\tFactory:{locFactory.FmtStr().GNLI2()}{Environment.NewLine}\tSettings:{locSettings.FmtStr().GNLI2()}{Environment.NewLine}\tComponent:{this.FmtStr().GNLI2()}"); } } } void cleanup(IReferenceKeyProvider locProvider) => locProvider?.Dispose(); }
P_StorageOpCtxBase P_CreateStrictedCtx(PersistenceEntityReferenceKeyTypeDescriptor key) => ActivationUtilities .RequireConstructor <P_StorageOpCtx, PersistenceEntityReferenceKeyTypeDescriptor, P_StorageOpCtxBase>( concreteType: typeof(P_StrictedStorageOpCtx <,>).MakeGenericType(typeArguments: new Type[] { typeof(TEfDbContext), key.EntityType, key.ReferenceKeyType })) (arg1 : this, arg2 : key);