1

When a user clicks a save button, a JavaScript function uses AJAX to call the Controller and send over JSON data about the objects.

JavaScript Function

$.ajax({
        url: "/Data/sendFridgeItems?items=" + JSON.stringify($scope.items.data),
        type: "POST",
        data: JSON.stringify($scope.items.data),
        dataType: "json",
        contentType: "application/json; charset=utf-8",
        success: function () {
            console.log("good!");
        },
        error: function () {
            console.log("error");
        }
    });

Controller

[HttpPost]
    public ActionResult SendFridgeItems(string items)
    {
        fridge[] fridgeItems = JsonConvert.DeserializeObject<fridge[]>(items);
        foreach (fridge item in fridgeItems)
        {
            bool exists = cookDB.fridges.AsEnumerable()
                .Any(x => x.Name == item.Name && x.Purchased == item.Purchased && x.Count == item.Count);
            if (!exists)
            {
                cookDB.fridges.Add(item);
                cookDB.SaveChangesAsync();
            }
        }
        return null;
    }

It works, but I don't think the way of sending my data through the url parameter is correct in my situation, because the data will be big enough. I wanted to know if there is a better way to send my data to the controller?

I tried to send it this way, but the controller receives null value.

$.ajax({
        url: "/Data/sendFridgeItems",
        type: "POST",
        data: JSON.stringify($scope.items.data),
        dataType: "json",
        contentType: "application/json; charset=utf-8",
        success: function () {
            console.log("good!");
        },
        error: function () {
            console.log("error");
        }
    });

JSON of $scope.items.data

[{"id":2,"name":"Item1","count":2,"type":"pcs.","purchased":"12/09/2017","wasted":"15/10/2017","cam":"Freezer","comment":"no comment","$$hashKey":"object:38"},{"id":3,"name":"Item2","count":30,"type":"g.","purchased":"15/01/1880","wasted":"21/03/1882","cam":"Cooler","comment":"commented","$$hashKey":"object:39"}]

$scope.items

$scope.items = {
    "count": 2,
    "data": [
      {
          "name": "Item1",
          "count": 2,
          "type": "pcs.",
          "purchased": "12/09/2017",
          "wasted": "15/10/2017",
          "cam": "Freezer",
          "comment": "no comment"
      },
  {
          "name": "Item2",
          "count": 30,
          "type": "g.",
          "purchased": "15/01/1880",
          "wasted": "21/03/1882",
          "cam": "Cooler",
          "comment": "Commented"
      }
    ]
};

Fixed Controller For N.Ivanov's solution (this controller+ N.Ivanov's ajax = solution)

public ActionResult SendFridgeItems(fridge[] items)
    {
        fridge[] fridgeItems = JsonConvert.DeserializeObject<fridge[]>(items.ToString());
        foreach (fridge item in items)
        {
            bool exists = cookDB.fridges.AsEnumerable()
                .Any(x => x.Name == item.Name && x.Purchased == item.Purchased && x.Count == item.Count);
            if (!exists)
            {
                cookDB.fridges.Add(item);
                cookDB.SaveChangesAsync();
            }
        }
        return null;
    }
1
  • Make it like this and let me know data: {"items":JSON.stringify($scope.items.data)}, Commented Jul 6, 2017 at 10:23

2 Answers 2

1

The data field in ajax takes in an Object, you are giving it a string. Try and supply only your object, assuming that $scope.items.data is an object. If you give a bit more information on what $scope variable is, then I can give you a better answer.

Code:

$.ajax({ url: "/Data/sendFridgeItems", type: "POST", d̶a̶t̶a̶:̶ ̶$̶s̶c̶o̶p̶e̶.̶i̶t̶e̶m̶s̶.̶d̶a̶t̶a̶,̶ dataType: "json", contentType: "application/json; charset=utf-8", success: function () { console.log("good!"); }, error: function () { console.log("error"); } });

Hope this helps!


EDIT:

Further inspection after you have provided the contents of $scope.items.data led me to notice that $scope.items.data is an array of objects. So in order for the ajax to work and actually supply valid JSON, try the following code: $.ajax({ url: "/Data/sendFridgeItems", type: "POST", data: { "items": $scope.items.data }, dataType: "json", contentType: "application/json; charset=utf-8", success: function () { console.log("good!"); }, error: function () { console.log("error"); } });

I have verified that { "item": $scope.items.data } is a valid JSON through JSONLint

Hope this solves your problem!

Sign up to request clarification or add additional context in comments.

7 Comments

You could also try it like this: data: { item: JSON.stringify($scope.items.data)}, Hope this helps!
"data: $scope.items.data " fires "Invalid JSON primitive: Item1". And data: { item: JSON.stringify($scope.items.data)} fires "Invalid JSON primitive: item". Quoting like data: { "item": JSON.stringify($scope.items.data) } fires same error. Variable is in the same scope with function. Added data of my $scope.items.data in JSON format to question
@Ryu I have updated my answer, check the EDIT, hope it works out!
I appreciate your help. Sorry I forgot to mention what $scope.items.data is an array. I have updated question, added $scope.items value. I checked JSON too, it is correct, but even with your new solution I catch xhr.responseText on error, and response text show me "Invalid JSON primitive: items".
Finally I fixed it, the problem was in Controller. I used data: {items: $scope.desserts.data}, but controller needed fix too, instead of string I used "fridge[] items", fridge is a c# class with same fields as JS array, and also I removed line fridge[] fridgeItems = JsonConvert.DeserializeObject<fridge[]>(items.ToString()), because now I don't need deserialize array.
|
0

Try JSON Parse to parse data as Object and send it to controller

$.ajax({
    url: "/Data/sendFridgeItems",
    type: "POST",
    data: JSON.parse($scope.items.data),
    dataType: "json",
    contentType: "application/json; charset=utf-8",
    success: function () {
        console.log("good!");
    },
    error: function () {
        console.log("error");
    }
});

Comments

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.