Implementing an AJAX Request in .NET Core 6 MVC
One of the problems with implementing a search feature that returns a table in a partial view is the Entity Framework model declarations must be strongly-typed. This means we run into difficulties declarating a model in the containing view and an IEnumerable instance of it for the partial view. One way around this is to instead discard the model for the mainview, and use jQuery and AJAX to read values from specific input elements in the main view, and pass those values to the controller action that returns the partial view with the IEnumerable model. One of the advantages of this method is the codebase might be cleaner and the application wouldn't need to reload entire sections to update parts of the main view - we can choose to update only the content within specific div tags.
jQuery and AJAX Setup
Install Microsoft.jQuery.Unobtrusive.Ajax using NuGet. This will be loaded into the /Dependencies/Packages folder of the project. For some reason this was missing in the template project.
All the AJAX handlers should be in a dedicated JavaScript file. The .NET Core 6 MVC template provides a site.js file for this, but here I've placed the custom JS in ~/js/home.js. This should be referenced in ~\Views\Shared_Layout.cshtml as follows:
<script src="~/js/site.js" asp-append-version="true"></script>
<script src="~/js/home.js"></script>
Note: This should be placed after the line referencing jquery.min.js, as this needs to load first. Alternatively, setting RenderSectionAsync() to true might solve any loading issues related to this.
An example:
// AJAX handler for user search
$(".btn-submit-user-query").click(function (e) {
var searchTerm = $(".user-search-term").val();
$.ajax({
url: '/Home/AdminUsersSearch',
type: 'GET',
contentType: 'application/json; charset=utf-8',
data: { searchTerm },
success: function (data) {
//var message = data.Message;
$('#user-search-results').html(data);
}
})
});
On success, the above function will replace whatever's within the #user-search-results div with whatever is returned by the IAction controller method. In this case it will be a partial view with a model populated by the search results.
The controller action will require an [HttpAction] attribute to respond to AJAX calls:
[HttpGet]
public IActionResult AdminUsersSearch(string searchTerm)
{
var model = _context.Users.Where(m => m.UserName.Contains(searchTerm)).ToList();
return PartialView("_UsersSearchResults", model);
}