我的网站中有帖子类别。我创建了一个下拉过滤器,可以根据所选类别过滤我的帖子。
过滤器是作为控制器操作方法创建的,但我想将其设为全局。
这是过滤器代码 -
FilterController.cs
:
public IActionResult Index(string postCategory)
{
var filteredPost = from p in _context.Posts select p;
if (postCategory != "All")
{
if (!string.IsNullOrEmpty(postCategory))
{
ViewBag.PostCategory = postCategory;
filteredPost = filteredPost.Where(p => p.PostCategory == postCategory);
}
}
else if (!string.IsNullOrEmpty("All"))
{
filteredPost = _context.Posts;
}
return View(await filteredPost.ToListAsync());
}
目前所有控制器都依靠
_context.Posts
来显示数据。该代码根据用户选择的类别过滤 _context.Posts
内的 filteredPost
。我想在其余控制器中使用 filteredPost
而不是 _context.Posts
。我怎样才能实现这个目标?
我想使用
filteredPost
而不是 _context.Posts
的控制器示例:
[HttpGet]
public async Task<IActionResult> Index()
{
return View(await _context.Posts.ToListAsync());
}
感谢所有建议。谢谢你。
不要将其视为“全局过滤器”——这不是 Web 应用程序框架(好吧)工作的方式。
我不建议使用共享/通用
Controller
子类:从长远来看,这只会导致问题;幸运的是,您所需要的只是一些扩展方法:
public static class MyHttpContextExtensions
{
/// <summary>Postfix version of <see cref="String.IsNullOrWhiteSpace" />.</summary>
public static Boolean IsSet( [NotNullWhen(true)] this String? s ) => !String.IsNullOrWhiteSpace( s );
/// <summary>Case-insensitive ordinal string equality.</summary>
public static Boolean EqualsIns( this String? left, String? right ) => StringComparer.OrdinalIgnoreCase.Equals( left, right );
public static async IQueryable<Post> GetFilteredPosts( this HttpContext httpContext )
{
if( httpContext is null ) throw new ArgumentNullException(nameof(httpContext));
MyDbContext dbContext = httpContext.RequestServices.GetRequiredService<MyDbContext>();
String? postCatFilter = httpContext.Request.Query["postCategory"];
if( postCatFilter.IsSet() && !"all".EqualsIns( postCatFilter ) )
{
return dbContext.Posts.Where( p => p.PostCategory == postCatFilter );
}
else
{
return dbContext.Posts;
}
}
public static async IQueryable<Post> GetFilteredPosts( this ControllerBase controller )
{
return GetFilteredPosts( httpContext: controller.HttpContext );
}
}
那么在你的any
Controller
中,你需要做的就是(例如):
public class ExampleController
{
private readonly MyDbContext dbContext;
public ExampleController( MyDbContext dbContext )
{
this.dbContext = dbContext ?? throw new ArgumentNullException(nameof(dbContext));
}
[Route( "/foo" )]
public async Task<IActionResult> GetFoo()
{
List<Post> postsList = await this.GetFilteredPosts().ToListAsync();
return this.View( "Foo", postsList );
}
}
请注意,
MyDbContext
的作用域为每个请求,因此从 MyDbContext
返回的 HttpContext.RequestServices
与 ExampleController.dbContext
是同一实例。