46

I am trying to pass my model to a controller using JQuery/Ajax, I'm not sure how to do this correctly. So far I have tried using Url.Action but the model is blank.

Note: none of the duplicate threads on stackoverflow seem to address using ASP.NET 5 MVC 6.

View:

$("#inpDateCompleted").change(function () {
        var url = '@(Url.Action("IndexPartial", "DashBoard", Model, null))';
        $("#DailyInvoiceItems").load(url);
});

Controller:

 [HttpGet]
 public PartialViewResult IndexPartial(DashBoardViewModel m)
 {
      // Do stuff with my model
      return PartialView("_IndexPartial");
 }
11
  • Its a bit unclear what your trying to do. The 3rd parameter of your Url.Action() would be the original model when you first generated the view, and if your model contained any properties which are complex objects or collection it would all fail anyway. Commented Nov 26, 2015 at 22:36
  • 1
    That would only pass the original model (Url.Action() is razor code that is parsed on the server before its sent to the view). If your only wanting to send the selected date to the method, use $("#DailyInvoiceItems").load('@(Url.Action("IndexPartial", "DashBoard")', { date: $(yourdatecontrol).val()); }); and change the method to have a DateTime date parameter. Commented Nov 26, 2015 at 22:46
  • 2
    You can use $('form').serialize() to serialize all the controls in your form. e.g. $.post('@(Url.Action("IndexPartial", "DashBoard"), $('form').serialize()`, function(data) { $("#DailyInvoiceItems").html(data); }); Commented Nov 26, 2015 at 22:51
  • 1
    Thats what $('form').serialize() will do. Your DashBoardViewModel m parameter will be correctly bound (assuming you have generated you form controls correctly) Commented Nov 26, 2015 at 22:59
  • 1
    Well that means you really should be using a view model (i.e containing only those properties you need in the view), but no, any properties you exclude will just be their default value in the method. Commented Nov 26, 2015 at 23:05

4 Answers 4

90

Looks like your IndexPartial action method has an argument which is a complex object. If you are passing a a lot of data (complex object), It might be a good idea to convert your action method to a HttpPost action method and use jQuery post to post data to that. GET has limitation on the query string value.

[HttpPost]
public PartialViewResult IndexPartial(DashboardViewModel m)
{
   //May be you want to pass the posted model to the parial view?
   return PartialView("_IndexPartial");
}

Your script should be

var url = "@Url.Action("IndexPartial","YourControllerName")";

var model = { Name :"Shyju", Location:"Detroit"};

$.post(url, model, function(res){
   //res contains the markup returned by the partial view
   //You probably want to set that to some Div.
   $("#SomeDivToShowTheResult").html(res);
});

Assuming Name and Location are properties of your DashboardViewModel class and SomeDivToShowTheResult is the id of a div in your page where you want to load the content coming from the partialview.

Sending complex objects?

You can build more complex object in js if you want. Model binding will work as long as your structure matches with the viewmodel class

var model = { Name :"Shyju", 
              Location:"Detroit", 
              Interests : ["Code","Coffee","Stackoverflow"]
            };

$.ajax({
    type: "POST",
    data: JSON.stringify(model),
    url: url,
    contentType: "application/json"
}).done(function (res) {
    $("#SomeDivToShowTheResult").html(res);
});

For the above js model to be transformed to your method parameter, Your View Model should be like this.

public class DashboardViewModel
{
  public string Name {set;get;}
  public string Location {set;get;}
  public List<string> Interests {set;get;}
}

And in your action method, specify [FromBody]

[HttpPost]
public PartialViewResult IndexPartial([FromBody] DashboardViewModel m)
{
    return PartialView("_IndexPartial",m);
}
Sign up to request clarification or add additional context in comments.

4 Comments

Thanks, I understand regarding the Post/Get, but it appears in your code you are just posting one parameter of the model, is it not possible just to pass the entire model? The entire DashboardVIewModel.
@ Reafidy See full implementation below
@Reafidy Cool. Check out stackoverflow.com/a/20226220/40521 for a more detailed explanation on posting models to controllers.
Is it possible for jquery to read the model parameters back from the PartialView once it returns? For example, I want to create a new element and read the new Model Id passed back from the controller to add an additional dom element? I know I could include this in the partial view, but what if I want the Id for another section unrelated to the partial view, but with that element id?
15

Use the following JS:

$(document).ready(function () {
    $("#btnsubmit").click(function () {

             $.ajax({
                 type: "POST",
                 url: '/Plan/PlanManage',     //your action
                 data: $('#PlanForm').serialize(),   //your form name.it takes all the values of model               
                 dataType: 'json',
                 success: function (result) {
                     console.log(result);
                 }
             })
        return false;
    });
});

and the following code on your controller:

[HttpPost]
public string PlanManage(Plan objplan)  //model plan
{
}

2 Comments

Add some explanation to your code so that the answer is more reusable for others.
This technique was amazingly simple and effective for me. I placed the ajax call on an actionlink with javascript, rather than on a submit button.
8

As suggested in other answers it's probably easiest to "POST" the form data to the controller. If you need to pass an entire Model/Form you can easily do this with serialize() e.g.

$('#myform').on('submit', function(e){
    e.preventDefault();

    var formData = $(this).serialize();

    $.post('/student/update', formData, function(response){
         //Do something with response
    });
});

So your controller could have a view model as the param e.g.

 [HttpPost]
 public JsonResult Update(StudentViewModel studentViewModel)
 {}

Alternatively if you just want to post some specific values you can do:

$('#myform').on('submit', function(e){
    e.preventDefault();

    var studentId = $(this).find('#Student_StudentId');
    var isActive = $(this).find('#Student_IsActive');

    $.post('/my/url', {studentId : studentId, isActive : isActive}, function(response){
         //Do something with response
    });
});

With a controller like:

     [HttpPost]
     public JsonResult Update(int studentId, bool isActive)
     {}

Comments

7
//C# class

public class DashBoardViewModel 
{
    public int Id { get; set;} 
    public decimal TotalSales { get; set;} 
    public string Url { get; set;} 
     public string MyDate{ get; set;} 
}

//JavaScript file
//Create dashboard.js file
$(document).ready(function () {

    // See the html on the View below
    $('.dashboardUrl').on('click', function(){
        var url = $(this).attr("href"); 
    });

    $("#inpDateCompleted").change(function () {   

        // Construct your view model to send to the controller
        // Pass viewModel to ajax function 

        // Date
        var myDate = $('.myDate').val();

        // IF YOU USE @Html.EditorFor(), the myDate is as below
        var myDate = $('#MyDate').val();
        var viewModel = { Id : 1, TotalSales: 50, Url: url, MyDate: myDate };


        $.ajax({
            type: 'GET',
            dataType: 'json',
            cache: false,
            url: '/Dashboard/IndexPartial',
            data: viewModel ,
            success: function (data, textStatus, jqXHR) {
                //Do Stuff 
                $("#DailyInvoiceItems").html(data.Id);
            },
            error: function (jqXHR, textStatus, errorThrown) {
                //Do Stuff or Nothing
            }
        });

    });
});

//ASP.NET 5 MVC 6 Controller
public class DashboardController {

    [HttpGet]
    public IActionResult IndexPartial(DashBoardViewModel viewModel )
    {
        // Do stuff with my model
        var model = new DashBoardViewModel {  Id = 23 /* Some more results here*/ };
        return Json(model);
    }
}

// MVC View 
// Include jQuerylibrary
// Include dashboard.js 
<script src="~/Scripts/jquery-2.1.3.js"></script>
<script src="~/Scripts/dashboard.js"></script>
// If you want to capture your URL dynamically 

<div>
    <a class="dashboardUrl" href ="@Url.Action("IndexPartial","Dashboard")"> LinkText </a>
</div>
<div>
    <input class="myDate" type="text"/>
//OR
   @Html.EditorFor(model => model.MyDate) 
</div>

16 Comments

@NEDian Thanks for Indentation
Thanks, using 'var viewModel = { Id : 1, MyDate:};' how do I get a value from a textbox on the page into the mydate parameter?
Sorry I was meaning how do I get a date from a textbox into the viewModel parameter?
Great, and sorry - once last question, how do I get the results of the ajax query to load in the "#DailyInvoiceItems" DIV?
Hope you can see the code changes and how you handle the result on success of ajax call
|

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.