Select2 with JSON data serialized from Django - javascript

I have data in JSON created by Django serialization.
I use the example:
Select2 Loading remote data but still I getting information in a field that nothing found.
What should change to select2 work with data generated by Django?
JSON Data:
[{
"fields": {
"sku": "8"
},
"model": "catalog.product",
"pk": 8
},{
"fields": {
"sku": "9"
},
"model": "catalog.product",
"pk": 9
}]
Html:
<select class="js-data-example-ajax"><option value="3620194" selected="selected">select2/select2</option></select>
JavaScript:
$('.js-data-example-ajax').select2({
ajax: {
url: "{% url 'catalog.views.product_sku_json' %}",
dataType: 'json',
delay: 250,
data: function (params) {
return {
q: params.term, // search term
page: params.page
};
},
processResults: function (data, params) {
// parse the results into the format expected by Select2
// since we are using custom formatting functions we do not need to
// alter the remote JSON data, except to indicate that infinite
// scrolling can be used
params.page = params.page || 1;
return {
results: data.items,
pagination: {
more: (params.page * 30) < data.total_count
}
};
},
cache: true
},
escapeMarkup: function (markup) { return markup; }, // let our custom formatter work
minimumInputLength: 1,
});

Answer by kevin-brown on github:
You are going to need to re-map your results to have id and text keys.
https://select2.github.io/announcements-4.0.html#changed-id
And it works thanks Kevin!

Related

Populating JsTree with JSON variable

I've been trying the whole day to get this thing working but somehow JsTree doesn't want to render my JSON data.
Here is the example JSON object:
{"parent":null, "ProductOption":null, "data":"HlaHd", "text":"global", "DelegationScope":0, "children":null, "entityId":1}
I get the JSON object through an AJAX call on $(document).ready():
if ($('#ProductTree').length) {
$.ajax({
type: "Post",
url: "/blah/blah",
dataType: "json",
data: { id : blah },
success: function (json) {
createJsTree(json);
}
});
}
And here is how I'm creating the tree:
function createJsTree(json) {
$('#ProductTree').jstree({
'core': {
'themes': {
'name': 'proton',
'responsive': true
},
'check_callback': true,
'data': json
}
});
}
At first I thought maybe my JSON object is faulty, so I printed the object on the chrome's console right before creating the JsTree:
function createJsTree(json) {
console.log(json);
$('#ProductTree').jstree({
'core': {
'themes': {
'name': 'proton',
'responsive': true
},
'check_callback': true,
'data': json
}
});
}
And the JSON object is exactly as I stated above. Now the funny thing is, if I just paste the literal JSON object as the data in JsTree creation like the following:
function createJsTree(json) {
$('#ProductTree').jstree({
'core': {
'themes': {
'name': 'proton',
'responsive': true
},
'check_callback': true,
'data': { "parent": null, "ProductOption": null, "data": "HlaHd", "text": "global", "DelegationScope": 0, "children": null, "entityId": 1 }
}
});
}
Then the tree gets rendered. What on earth is going on here?
It looks like you are trying to pass a string representing a json object instead of the object itself. It should work if you write data: JSON.parse(json) replacing data: json.
You need to parse responded JSON string to json format using JSON.parse().
Hope this will help.

Unable to map array of object into jQuery autocomplete

I am adding the jQuery Autocomplete plugin to my project. I have a source value which is an array of objects (from a mySQL database). I am unable to map them into desired format of autocomplete.
This is the data want to map:
[{
"value": "730",
"label": "iPhone"
}, {
"value": "731",
"label": "Screen Protector"
}, {
"value": "732",
"label": "Maxboost"
}, {
"value": "733",
"label": "JETech"
}, {
"value": "734",
"label": "Mr Shield"
}]
$("#product_one").autocomplete({
source: $.ajax({
type: "GET",
url: "/wp-json/product/product-info/",
success: function(res) {
$.each(res, function(key, val) {
return {
"label": val.label,
"value": val.value
}
});
}
});
});
Any suggestion or modification of question would be appreciated.
The issue is because you're providing source with a jqXHR object, not an array, string or function as it expects (docs)
Given the use of AJAX, it would make the most sense for you to use provide a function which uses the request and response arguments. Also note that as the data you retrieve is already in the correct format (ie. an array of objects with label and value properties), you can provide it directly to response() without needing to loop through it. Try this:
$("#product_one").autocomplete({
source: function(request, response) {
$.ajax({
type: "GET",
url: "/wp-json/product/product-info/",
success: function(data) {
response(data);
}
});
}
});
You should first load your data and then set them as the source of the autocomplete.
$.ajax({
type:"GET",
url: "/wp-json/product/product-info/",
success:function(res){
//Based on your object creation, it looks that you can directly use the response
$( "#product_one" ).autocomplete(res);
}
});

Select2 won't load remote json response

I have an API that is called by Select2 (v4.0.5) however the debug message in the console says:
Select2: The AJAX results did not return an array in the results key of the response.
When I review the documentation at Select2's documentation site I seem to be following it correctly. This is the javascript I use on the webpage:
$('#account_id').select2({
debug: true,
minimumInputLength: 3,
dataType: 'json',
ajax: {
url: '/api/account-query',
data: function (params) {
var query = {
search: params.term,
v: "new"
}
return query;
},
}
});
This is the response from the API (sensitive bits redacted):
{
"results": [{
"id": "redacted-1",
"text": "text redacted 1"
},{
"id": "redacted-2",
"text": "text redacted 2"
},{
"id": "redacted-3",
"text": "text redacted 3"
},{
"id": "redacted-4",
"text": "text redacted 4"
},{
"id": "redacted-5",
"text": "text redacted 5"
}]
}
If I take the select2 code and supply it with the static json response (without results prepended, just the array) it works just fine.
What am I missing?
Thanks!
You have to provide the processResults callback function so Select2 able to render result in proper way.
I have created a jsfiddle (https://jsfiddle.net/shcavbng/) demo that doing the same.
$('#account_id').select2({
debug: true,
minimumInputLength: 3,
dataType: 'json',
ajax: {
url: 'https://reqres.in/api/users',
data: function (params) {
console.log('params =>' , params);
var query = {
search: params.term,
v: "new"
}
return query;
},
processResults: function (data) {
console.log('results =>' , data);
data = data.data.reduce(function(o,i){o.push({id:i.id,text:i.first_name});return o;},[]);
console.log('results =>' , data);
return {
results: data
};
}
}
});
I figured it out, and as expected I was overlooking a simple aspect:
Content-Type header needed to be application/json vs text/html

Results does not show up after search, why?

I am using the newest Select2 4.0.6-rc.1 and I am making an AJAX search, I am getting results back but for some reason they don't show up as an option on the SELECT element. Maybe I am missing some basic setup but I have been reading the docs and I can't find anything helpful. Here is what I have:
<select class="form-control" id="query"></select>
$(function() {
var $query = $("#query");
$query.select2({
width: 550,
placeholder: 'Search for a form ...',
minimumInputLength: 3,
ajax: {
url: '/ajax/forms/ajax_search_by_name',
data: function (params) {
return {
q: params.term
};
},
dataType: 'json',
delay: 250,
processResults: function (data) {
return {
results: data.items
};
}
}
});
});
The result from the backend looks like:
{
"results": [
{
"id": 1247,
"name": "amerita_infusion_services_colorado_synagis_referral_form"
},
{
"id": 3471,
"name": "medicaid_colorado_viekira"
}
]
}
Which I think is the right way to return them. I have setup a Fiddle - which BTW I couldn't make it to work with the /echo/json request - so you can play with it a little bit.
What I am missing here?

Post row datas from DataTable to an Ajax Form

I have a set of JSON data that are displayed using datatables. In one of the columns, I add a button and a text box only if the value in that column and another column meets a certain condition. this is the bit of code I used to do this:
$(document).ready(function (){
var alertTable = $('#alert-table').DataTable({
"jQueryUI": true,
"order": [ 3, 'desc' ],
"columns": [
{ "data": "source", "visible": false },
{ "data": "host" },
{ "data": "priority" },
{ "data": "ack", "render": function( data, type, row ) {
if (row.ack == "0" && row.priority > "2") {
return '<form><input class="ackname" type="text" value="Enter your name"><input class="ackbutton" type="button" value="Ack Alert" onclick="<get all items for that row and POST to a URL>"></form>';
}
return data;
}
},
],
"language": {
"emptyTable": "No Alerts Available in Table"
}
});
});
This works fine by adding a button and text in the cell. What I am looking to achieve is, when any of the button is been clicked, it should POST all the values for that row including what is typed in the text box to a URL which has another function that would extract those details and update the database and send back the refreshed data. I am new to datatables and jquery, any guide would be highly appreciated.
Have made some changes to the code, instead of form you can use div.
$(document).ready(function (){
var alertTable = $('#alert-table').DataTable({
"jQueryUI": true,
"order": [ 3, 'desc' ],
"columns": [
{ "data": "source", "visible": false },
{ "data": "host" },
{ "data": "priority" },
{ "data": "ack", "render": function( data, type, row ) {
if (row.ack == "0" && row.priority > "2") {
return '<div><input class="ackname" type="text" value="Enter your name"><input class="ackbutton" type="button" value="Ack Alert"></div>';
}
return data;
}
},
],
"language": {
"emptyTable": "No Alerts Available in Table"
}
});
$(document).on("click",".ackbutton",function() {
var currentIndex = $(this).parent().parent().index();
var rowData = alertTable.row( index ).data();
//extract the textbox value
var TextboxValue = $(this).siblings(".ackname").val();
var objToSave = {}; //Create the object as per the requirement
//Add the textbox value also to same object and send to server
objToSave["TextValue"] = TextboxValue;
$.ajax({
url: "url to another page"
data: JSON.stringify({dataForSave : objToSave}),
type: "POST",dataType: "json",
contentType: "application/json; charset=utf-8",
success: function(datas) {
//Your success Code
},
error: function(error) {
alert(error.responseText);
}
});
});
});
Since both the pages are in same project, you can also do it using single ajax, passing all the values to server at once and then calling the other page internally from server and passing in the values using query string.
This is not a running code, rather to give you a basic idea on how to proceed.
Hope this helps :)

Categories