justiceorjustus
justiceorjustus

Reputation: 1965

Jquery autocomplete not working MVC with Entity Framework

I have two models. One of the models (my ViewModel) is tied to the textbox in the form and the other model is tied to an entity (Employees) that I'm using to autocomplete the textbox (VieModel.Name). I followed a tutorial here and cannot seem to get it working. I delved around Google, as well. It may be my newness to Entity Framework or the fact I'm using a ViewModel not tied to an entity and a Model tied to an entity.

Ultimately I am trying to autocomplete the Name in the ViewModel from the FirstName + LastName from the Employees Entity Model, but am trying FirstName for now.

Model from entity:

public partial class Employee
{
    public bool ActiveFlag { get; set; }
    public int EmpNid { get; set; }
    public string RecKey { get; set; }
    public string FirstName { get; set; }
    public string MiddleName { get; set; }
    public string LastName { get; set; }
    ... etc

My ViewModel not tied to entity but posted with this form:

public class SalesViewModel
{
    [Display(Name = "Employee Name")]
    [Required(ErrorMessage = "The employee name is required")]
    public string Name { get; set; }
    ... etc

View:

<div class="form-group">
    @Html.LabelFor(m => m.Name, new { @class = "col-md-2 control-label" })
    <div class="col-md-10">
        @Html.TextBoxFor(m => m.Name,
        new
        {
            @class = "employees-autocomplete",
            data_url = Url.Action("EmployeesAutocomplete", "Employee")
        })
        @Html.ValidationMessageFor(m => m.Name, "", new { @class = "text-danger" })
    </div>
</div>

My Jquery at the bottom of the page:

$(function () {
    $('.employees-autocomplete').autocomplete({
        minLength: 0,
        source: function (request, response) {
            var url = $(this.element).data('url');

            $.getJSON(url, { term: request.term }, function (data) {
                response(data);
            })
        }
    });
})

My JsonResult Controller:

public JsonResult EmployeesAutocomplete(string term)
{
    Employee[] matching = string.IsNullOrWhiteSpace(term) ?
         db.Employees.ToArray() :
         db.Employees.Where(p => p.FirstName.ToUpper().StartsWith(term.ToUpper())).ToArray();

    return Json(matching.Select(m => new
    {
        id = m.EmpNid,
        value = m.FirstName,
        label = m.ToString()
    }), JsonRequestBehavior.AllowGet);
}

Am I supposed to be doing anything in the post or get request? Not sure where I went wrong.

Upvotes: 0

Views: 1155

Answers (2)

Hasnain Mehmood
Hasnain Mehmood

Reputation: 417

For MVC architecture you must delete already embedded

@Scripts.Render("~/bundles/Jquery") 

and

@Scripts.Render("~/bundles/Jqueryval") 

from all .cshtml files at the end and for also views/Shared/_layout.cshtml at the end and put our jQuery suitable files on it's suitable .cshtmls files in head.

Put on head these files:

<link href="~/Content/jquery-ui-1.10.4.custom.min.css" rel="stylesheet" type="text/css" /> 

<script src="~/Scripts/jquery-1.10.2.js" type="text/javascript"></script>

<script src="~/Scripts/jquery-ui-1.10.4.custom.min.js" type="text/javascript"></script>

Upvotes: 0

Shyju
Shyju

Reputation: 218762

Your code looks fine. The only issue i see is, you are calling the ToString() on the Employee entity object/record for the label value. Since this is the value to be shown to the user, you probably want to use your FirstName or any string properties here ( Unless you overwrote the a ToString() method in your Employee class to return a string version)

Replace this

return Json(matching.Select(m => new
{
    id = m.EmpNid,
    value = m.FirstName,
    label = m.ToString()
}), JsonRequestBehavior.AllowGet);

With this

return Json(matching.Select(m => new
{
    id = m.EmpNid,
    value = m.FirstName,
    label = m.FirstName +' '+m.LastName 
}), JsonRequestBehavior.AllowGet);

As per the comment

Uncaught ReferenceError: $ is not defined(anonymous function)

This usually happens when you are trying to use jQuery before it is defined in your page. Double check the following steps

  1. Include jQuery before everything else
  2. Include jQuery UI after jQuery library
  3. Execute your page level scripts only after loading the dependeny libraries (jQuery/jQueryUI). You can do this by calling your page level scripts inside a script section.

    @section scripts
    {
      $(function(){
    
       // Your code for initializing the auto complete goes here
    
      })
    }
    

    Assuming your layout has a section called scripts which is defined after loading jQuery and jQuery UI libraries.

So in your layout file, it should be like this

@RenderBody()
<script src="https://ajax.googleapis.com/ajax/libs/jquery/3.1.0/jquery.min.js"></script>
<link rel="stylesheet" href="https://ajax.googleapis.com/ajax/libs/jqueryui/1.12.0/themes/smoothness/jquery-ui.css">
<script src="https://ajax.googleapis.com/ajax/libs/jqueryui/1.12.0/jquery-ui.min.js"></script>
@RenderSection("scripts", required: false)

Upvotes: 2

Related Questions