[英]Architecture for Restricting DbContext Access
我目前正在編寫一個rest框架,我想創建一種方法來不僅限制通過讀取而且還可以通過寫入來限制對某些實體的訪問。 當前,我已經創建了一個基本的DbContext,它可以像這樣處理授權(我省略了一些代碼(例如,選項分配),因為它們與問題無關):
public abstract class AuthorizedDbContext : DbContext
{
//...
protected override void OnModelCreating(ModelBuilder modelBuilder)
{
var constraintOptions = this._authorizationOptions.ConstraintOptions;
constraintOptions.ApplyStaticConstraint(modelBuilder, this);
base.OnModelCreating(modelBuilder);
}
public async override Task<int> SaveChangesAsync(bool acceptAllChangesOnSuccess, CancellationToken cancellationToken = default(CancellationToken))
{
this.VerifyResourceAccess();
return await base.SaveChangesAsync(acceptAllChangesOnSuccess, cancellationToken);
}
protected void VerifyResourceAccess()
{
if (false == ChangeTracker.HasChanges())
{
return;
}
//WARNING: if you don't set the change tracking behavior to no tracking, you could reload entities by accident
var previousTrackingBehavior = this.ChangeTracker.QueryTrackingBehavior;
this.ChangeTracker.QueryTrackingBehavior = QueryTrackingBehavior.NoTracking;
this._authorizationOptions.ContextValidator.ValidateAndThrow(this);
this.ChangeTracker.QueryTrackingBehavior = previousTrackingBehavior;
}
}
目前,我注入了一個dbcontext驗證程序,該驗證程序用於處理限制更新和保存更改時的其他驗證。
用戶放心,知道使用此授權上下文時,如果不通過用戶在其代碼中定義的所有驗證,就無法更新實體。
但是,這種體系結構很爛,並且嚴重限制了用戶代碼的靈活性,例如,如果用戶要使用IdentityDbContext,除非我創建從IdentityDbContext<AppUser>
繼承的AuthorizedDbContext,否則將無法實現。
相反,我更喜歡在它們的上下文周圍使用包裝器。 例如
//Pseudo-Code
AuthorizedDbContextScope<T>: IDisposable
where T: DbContext
{
public void ApplyConstraints()
{
this._options.DynamicConstraints.Foreach(EntityFrameWorkZ.ApplyDynamicFilterFromAction)
}
}
此包裝的唯一問題是1.我無法公開DbContext功能,無法覆蓋范圍內的保存更改,我必須強制用戶在包裝上調用保存更改。
我可以在啟動時使用DynamicProxy從其DbContext繼承,但是這似乎有些矯,過正,這會嚴重減慢項目的啟動速度。
如果有人對我可以如何更好地普遍限制我的更新提出建議,請告訴我。
如何在不限制用戶代碼繼承靈活性的情況下完全限制數據庫更改?
這是主觀的,但我會試一試。
所有這些想法都可能受解決方案的體系結構以及一個或多個應用程序使用該功能的限制。
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.