Clientside MVVM binding from MVC JsonResult

5 posts, 0 answers
  1. Erik Stell
    Erik Stell avatar
    11 posts
    Member since:
    Dec 2013

    Posted 25 Mar 2015 Link to this post

    I have a view that is using a kendo.observable with a datasource wired to call a .NET MVC ActionResult that returns Json data (both the view and the ActionResult are in the same domain.  I tried using jsonp to see if anything shook out differently, but no dice.)

    $(document).ready(function () {
         var viewModel = kendo.observable({
            data: new kendo.data.DataSource({
                transport: {
                    read: {
                        url: "GetCardOrder?shipSuffix=123123123",
                        dataType: "json"
                    }
                },
                batch: true
            }),
        });
        kendo.bind($("#order_details"), viewModel);
        viewModel.data.read();
    });

    further up in the html  view I am binding an html element to a value that is going to return from that GetCardOrder call:
    <div class="col-sm-6 col-md-5">
         <label>Group:</label>
         <span data-bind="text: data.Group"></span>
    </div>

    I have verified using fiddler that the ActionResult is being called and it is returning a valid block of Json data (specifically the Group value shown above).  However, when I debug the javascript after the .read is called, the datasource has 0 data, and thus nothing is being updated in the view.

    It's entirely possible I am missing something basic here.  







  2. Erik Stell
    Erik Stell avatar
    11 posts
    Member since:
    Dec 2013

    Posted 25 Mar 2015 in reply to Erik Stell Link to this post

    I think I may have solved my own issue, but I would like to know if it's hacky or not:

    <script>
        $(document).ready(function () {
            var dataSource = new kendo.data.DataSource({
                transport: {
                    read: "GetCardOrder?shipSuffix=123123123",
                    dataType: "json"
                },
                schema: {
                    data: function (response) {
                        return response;
                    }
                },
                requestEnd: function(e) {
                    alert("done" + e);
                    var viewModel = kendo.observable({
                        inst: e.response
                    });
     
                    kendo.bind($("#order_details"), viewModel.inst);
                }
            });
            dataSource.read();
     
        });
    </script>

    This handles the comm between the DataSource and the ActionResult, and the MVVM bindings are now populating.  Is this the ideal, or did I over engineer my solution?  ;) 
  3. Kendo UI is VS 2017 Ready
  4. Alexander Popov
    Admin
    Alexander Popov avatar
    1416 posts

    Posted 27 Mar 2015 Link to this post

    Hello Erik,

    Both approaches could be used, depending on your goals. Would you please elaborate a bit? Also, can you share an example of what the read request's response looks like?

    Regards,
    Alexander Popov
    Telerik
     
    Join us on our journey to create the world's most complete HTML 5 UI Framework - download Kendo UI now!
     
  5. Erik Stell
    Erik Stell avatar
    11 posts
    Member since:
    Dec 2013

    Posted 27 Mar 2015 in reply to Alexander Popov Link to this post

    Ultimately, the page is a simple order details screen.  There are two linked dropdown lists at the top where a user selects a company name and a order number, respectively.  The order number dropdown has a change event registered to it to take that order number, call an MNC ActionResult to get the data and return it to the view as JSON.  The goal was to be able to change the displayed order without having to reload the page using a standard form submit/response cycle.

    Ultimately I was able to get it all working with the code below.  However, there was also a challenge of getting the DataSource to refire its read action when a user changed the order number, and then have the results update the data on the screen.  After managing to get the read action to refire, I wound up having to unbind and rebind the view model for the updated data to refresh on the screen.  That latter part feels wrong to me, based on what I understand about MVVM and the observable object.

    var dataSource;
    var viewModel;       
         
    function ShipOrderSelected(evt) {
        dataSource.transport.read();
    }
     
    $(document).ready(function () {
        dataSource = new kendo.data.DataSource({
            serverFiltering: true,
            transport: {
                read: function(options) {
                    $.ajax({
                        url: "GetCardOrder?shipSuffix=" + $("#shiporder").val(),
                        dataType: "json",
                        success: function(result) {
                            viewModel.selectedProduct = result; //returned JSON
                            kendo.unbind($("#order_details"));
                            kendo.bind($("#order_details"), viewModel.selectedProduct);
                        },
                        error: function(result) {
                        }
                    });                   
                }               
            },
            schema: {
                data: function(response) {
                    return response;
                }
            },
            requestEnd: function(e) {
                viewModel.selectedProduct = e.response; //returned JSON
                kendo.unbind($("#order_details"));
                kendo.bind($("#order_details"), viewModel.selectedProduct);
            }
        });
        viewModel = kendo.observable({
            productsSource: dataSource,
            selectedProduct: null,
            hasChanges: false,
        });
        viewModel.productsSource.read();
    });

    The read request's JSON is pretty straightforward:

    {
        "CloseCode": "0",
        "CloseDate": "12/30/1899 12:00:00 AM",
        "Group": "661",
        "Location": "",
        "Notes": "",
        "OrderNumber": "792481",
        "Received": "3/25/2015 12:00:00 AM",
        "QCComplete": null
    }

     

  6. Alexander Popov
    Admin
    Alexander Popov avatar
    1416 posts

    Posted 27 Mar 2015 Link to this post

    Hello again Erik,

    If my understanding is correct, then using a DataSource in this case seems unnecessary, since the server sends a single object instead of an array. You can get the same behavior using a function that makes the Ajax request. Once the request's success event is triggered you can use the set method to apply the incoming value to a certain ViewModel field. Here is a proof of concept example.

    Regards,
    Alexander Popov
    Telerik
     
    Join us on our journey to create the world's most complete HTML 5 UI Framework - download Kendo UI now!
     
Back to Top
Kendo UI is VS 2017 Ready